'''
-Medium-

'order' and 'str' are strings composed of lowercase letters. In order, no letter occurs more than once.

order was sorted in some custom order previously. We want to permute the characters of str so that
they match the order that order was sorted. More specifically, if x occurs before y in order, then x
should occur before y in the returned string.

Return any permutation of str (as a string) that satisfies this property.

Example:
Input:
order = "cba"
str = "abcd"
Output: "cbad"
Explanation:
"a", "b", "c" appear in order, so the order of "a", "b", "c" should be "c", "b", and "a".
Since "d" does not appear in order, it can be at any position in the returned string.
"dcba", "cdba", "cbda" are also valid outputs.

Note:

order has length at most 26, and no character is repeated in order.
str has length at most 200.
order and str consist of lowercase letters only.

'''

from collections import Counter

class Solution(object):
    def customSortString(self, order, str):
        """
        :type order: str
        :type str: str
        :rtype: str
        """
        cnt = Counter(str)
        oset = set(order)
        res = ''
        for c in order:
            if c in cnt:
                res += c*cnt[c]
        for k in cnt:
            if k not in oset:
                res += k*cnt[k]
        return res

if __name__ == "__main__":
    print(Solution().customSortString(order = "cba", str = "abcd"))


##basic text input quiz
from ipywidgets import widgets, Layout, Box, GridspecLayout

def create_textinputquiz_widget(description, text_description, correct_answer, a2, hint):  ##grid for option table

    correct_answer = correct_answer  ##float ##str
    alternativ = widgets.Text(value='',
                              placeholder='',
                              description='',
                              disabled=False, layout=(Layout(width='auto'))
                              )
    ##question description
    description_out = widgets.Output(layout=Layout(width='auto'))
    with description_out:
        print(description)
    ##description before text widget
    text_description_out = widgets.Output(layout=Layout(width='auto'))
    with text_description_out:
        print(text_description)
    ##description after text widget e.g. units
    a2_out = widgets.Output(layout=Layout(width='auto'))
    with a2_out:
        print(a2)
    ##
    feedback_out = widgets.Output()

    def check_selection(b):
        a = alternativ.value

        if a == correct_answer:
            s = "Correct!"

        else:
            s = "Wrong answer unfortunately"
        with feedback_out:
            feedback_out.clear_output()
            print(s)

        return

    check = widgets.Button(description="check")
    check.on_click(check_selection)
    ##
    hint_out = widgets.Output()

    def hint_selection(b):
        with hint_out:
            print(hint)
        with feedback_out:
            feedback_out.clear_output()
            print(hint)

    hintbutton = widgets.Button(description="hint")
    hintbutton.on_click(hint_selection)

    return widgets.VBox([description_out,
                         widgets.HBox([text_description_out, alternativ, a2_out]),
                         widgets.HBox([hintbutton, check]), feedback_out],
                        layout=Layout(display='flex',
                                      flex_flow='column',
                                      align_items='stretch',
                                      width='auto'))

def quiz():
    questions1 = create_textinputquiz_widget('What is the value of dt if you have 5 minutes timestep data?', "answer:", '1/12', "hour",
                                            '[hint]: Read part 1.1')
    questions2 = create_textinputquiz_widget('Is the timeunit same for all energy units?', "answer:", 'yes', "!",
                                             '[hint]: Read part 1.6')
    questions3 = create_textinputquiz_widget('How many production units we have in this model with energy flow always out?', "answer:", '2', "unit(s)",
                                             '[hint]: Read part 1.3')
    questions4 = create_textinputquiz_widget('How many consumption units we have in this model with energy flow always in?', "answer:", '3',
                                             "unit(s)", '[hint]: Read part 1.3')
    questions5 = create_textinputquiz_widget('Is energy flow of storage always in?', "answer:",
                                             'no', "!",'[hint]: Read part 1.3.1')
    questions6 = create_textinputquiz_widget('How much electricity was exported?', "answer:",
                                             '0', "kWh", '[hint]: Read part 1.5')
    questions7 = create_textinputquiz_widget('At what hour the storage was discharged?', "answer:",
                                             '20', "hour", '[hint]: Read part 1.8')
    questions8 = create_textinputquiz_widget('How much electricity was imported this time? (one decimal)', "answer:",
                                             '4.7', "kWh", '[hint]: Read part 1.8')
    display(questions1)
    display(questions2)
    display(questions3)
    display(questions4)
    display(questions5)
    display(questions6)
    display(questions7)
    display(questions8)

quiz()


import os
from nltk.corpus import stopwords
import timeit
import time
import json
import nltk
from nltk.tokenize import word_tokenize
import xlrd

_path = os.path.dirname(__file__)

_error_message = '''
Please provide a text as an input.
You can either provide the text as an argument: python -m subjectivity.classify this is my opinion.
Or pipe the text from the command line: python -m subjectivity.classify < data/random_text.txt
'''

def _aggregate_sentence(args):
    return_str = ''
    for argument in args:
        return_str += argument + ' '
    return return_str

def _get_subj_or_obj_sentences_from_text(text):
    from subjectivity.subjectivity_classifier import SubjectivityClassifier
    classifier = SubjectivityClassifier(model_filename=os.path.join(_path, '../data/save/subj-29.tf'),
                                        word_filename=os.path.join(_path, '../data/word_embeddings/glove.6B.50d.txt'))
    return classifier.classify_sentences_in_text(text)

def print_sentences(sentences_dict):
    print('\nOBJECTIVE SENTENCES:')

    f.write('\nOBJECTIVE SENTENCES:')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    [print(item) for item in sentences_dict['objective']]
    for item in sentences_dict['objective']:
    	res.append(item)
    	f.write(item + '\n')
    print("RESULT:",res)

    print('\nSUBJECTIVE SENTENCES:')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\nSUBJECTIVE SENTENCES:')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    f.write('\n')
    [print(item) for item in sentences_dict['subjective']]
    for item in sentences_dict['subjective']:
    	f.write(item + '\n')
    f.close()

def remove_stop_words(sentence):
    stop_words = set(stopwords.words('english'))
    words = sentence.split()
    filtered_words = [r for r in words if not r in stop_words]
    return " ".join(filtered_words)

def remove_punctuations(r_sentence):
    punctuations = '''!()-[]{};:'"\,<>/@#$%^&*_~'''
    '''stop_words = set(stopwords.words('english'))
    words = sentence.split()
    filtered_words = [r for r in words if not r in stop_words]'''
    no_punct = ""
    for char in r_sentence:
       if char not in punctuations:
           no_punct = no_punct + char
    return no_punct

def posTagger(tokenized_sentences) :
    tagged = []
    for sentence in tokenized_sentences :
        tag = nltk.pos_tag(sentence)
        tagged.append(tag)
    return tagged

start_time = time.time()
if __name__ == '__main__':
    import os
    import sys
    f= open("result.txt","w+")
    f1= open("time_result.txt","w+")
    f1.write('\nEXECUTION TIME FOR NEURAL NETWORK:')
    f1.write('\n')
    f1.write('\n')
    res = []
    if len(sys.argv) > 1:
        sentence = _aggregate_sentence(sys.argv[1:])
        print_sentences(_get_subj_or_obj_sentences_from_text(sentence))
    else:
        if os.isatty(0):
            print(_error_message)
            exit(0)
        sentence = sys.stdin.read().strip()
        print("SENTENCES:",sentence)
        r_sentence = remove_stop_words(sentence)
        print("PRINT REMOVED STOP WORDS SENTENCE:",r_sentence)
        rr_sentence = remove_punctuations(r_sentence)
        print("PRINT REMOVED PUNCTUATIONS IN SENTENCE:",rr_sentence)
        tokens = word_tokenize(rr_sentence)
        print("TOKENIZED SENTENCES :",tokens)
        tagged = posTagger(tokens)
        print("P  O  S  : IN SENTENCE:",tagged)
        start_time1 = time.time()
        if sentence:
        	content = _get_subj_or_obj_sentences_from_text(rr_sentence)
        	time.time()
        	print("EXECUTION TIME FOR NEURAL NETWORK-------------------------1")
	        print("--- %s seconds ---" % (time.time() - start_time1))
	        t = time.time() - start_time1
	        f1.write(str(t))
	        print_sentences(_get_subj_or_obj_sentences_from_text(rr_sentence))
	        print(" ")
	        print("EXECUTION TIME FOR NEURAL NETWORK")
	        print("--- %s seconds ---" % (time.time() - start_time1))

print(" ")
print("EXECUTION TIME")
print("--- %s seconds ---" % (time.time() - start_time))
tt = time.time() - start_time
f1.write('\n')
f1.write('\n')
f1.write('\n')
f1.write('\nEXECUTION TIME FOR CODE:')
f1.write('\n')
f1.write('\n')
f1.write(str(tt))
f1.close()


# -*- coding: utf-8 -*-
"""Retrieve/Build input datasets.

Created on Sat Mar  5 10:33:33 2022

@author: travis
"""
import datetime as dt
import os

from importlib import resources
from pathlib import Path

import drip

from drip.exceptions import ParameterError
from drip.loggers import init_logger, set_handler
from drip.app.options.indices import INDEX_NAMES

logger = init_logger(__name__)

class Paths:
    """Methods for handling paths to package data."""

    @classmethod
    @property
    def paths(cls):
        """Return posix path objects for package data items."""
        contents = resources.files(drip.__name__)
        data = [file for file in contents.iterdir() if file.name == "data"][0]
        data.joinpath("indices").mkdir(exist_ok=True)
        paths = {}
        for folder in data.iterdir():
            name = os.path.splitext(folder.name)[0].lower()
            paths[name] = folder
        return paths

    @classmethod
    @property
    def home(cls):
        """Return application home directory."""
        return resources.files(drip.__name__).parent

    @classmethod
    @property
    def indices(cls):
        """Return list of paths to index netcdfs."""
        paths = list(cls.paths["indices"].glob("*/*.nc"))
        paths = [path for path in paths if "_" not in path.name]
        paths.sort()
        indices = {}
        for path in paths:
            name = path.name.replace(".nc", "")
            indices[name] = path
        return indices

    @classmethod
    @property
    def log_directory(cls):
        """Return path to log directory."""
        log_dir = Path("~/.drip/logs").expanduser()
        log_dir.mkdir(parents=True, exist_ok=True)
        return log_dir


from flask import render_template, current_app, request, \
    flash, redirect, url_for, jsonify
from flask_security import roles_accepted, current_user
from sqlalchemy import func

import uuid

from . import agroup
from .forms import AssociateGroupForm

from pgscm import sqla
from pgscm.db import models
from pgscm.utils import __, DeleteForm, check_role, is_region_role, soft_delete
from pgscm import const as c

crud_role = c.ADMIN_MOD_ROLE

@agroup.route('/vi/lien-nhom', endpoint='index_vi', methods=['GET', 'POST'])
@agroup.route('/en/associate-group', endpoint='index_en',
              methods=['GET', 'POST'])
@roles_accepted(*c.ALL_ROLES)
def index():
    form = AssociateGroupForm()
    dform = DeleteForm()

    if current_app.config['AJAX_CALL_ENABLED']:
        form.province_id.choices = []
        return render_template('agroup/index.html', form=form, dform=dform)
    else:
        province_id = current_user.province_id
        if province_id and is_region_role():
            ags = models.AssociateGroup.query.filter_by(
                province_id=province_id, _deleted_at=None).order_by(
                                models.AssociateGroup.name.asc()).all()
            form.province_id.choices = [
                (p.province_id, p.type + " " + p.name) for p in
                models.Province.query.filter_by(province_id=province_id).all()]
        else:
            ags = models.AssociateGroup.query.filter_by(_deleted_at=None)\
                .order_by(models.AssociateGroup.name.asc()).all()
            form.province_id.choices = []

        # form create or edit submit
        if request.method == 'POST' and form.data['submit']:
            if not check_role(crud_role):
                return redirect(url_for(request.endpoint))

            form.province_id.choices = [(form.province_id.data,
                                         form.province_id.label.text)]
            # edit associate group
            if form.id.data:
                if form.validate_on_submit():
                    edit_agroup = sqla.session.query(models.AssociateGroup) \
                        .filter_by(id=form.id.data).one()
                    edit_agroup.email = form.email.data
                    edit_agroup.associate_group_code = form \
                        .associate_group_code.data
                    edit_agroup.name = form.name.data
                    if edit_agroup.province_id != form.province_id.data:
                        edit_agroup.province = models.Province.query \
                            .filter_by(province_id=form.province_id.data) \
                            .one()
                    flash(str(__('Update associate group success!')),
                          'success')
                    return redirect(url_for(request.endpoint))
                else:
                    flash(str(__('The form is not validated!')), 'error')

            # add associate group
            else:
                form.id.data = str(uuid.uuid4())
                if form.validate_on_submit():
                    province = sqla.session.query(models.Province) \
                        .filter_by(province_id=form.province_id.data).one()
                    as_group = form.associate_group_code.data
                    new_agroup = models.AssociateGroup(
                        id=form.id.data,
                        associate_group_code=as_group,
                        name=form.name.data, province=province,
                        email=form.email.data,
                    )
                    sqla.session.add(new_agroup)
                    sqla.session.commit()
                    flash(str(__('Add associate group success!')), 'success')
                    return redirect(url_for(request.endpoint))

                else:
                    flash(str(__('The form is not validated!')), 'error')

                    # form delete submit
        if request.method == 'POST' and dform.data['submit_del']:
            if not check_role(crud_role):
                return redirect(url_for(request.endpoint))
            elif dform.validate_on_submit():
                del_agroup = sqla.session.query(models.AssociateGroup) \
                    .filter_by(id=dform.id.data).one()
                del_agroup._deleted_at = func.now()
                if dform.modify_info.data:
                    del_agroup._modify_info = dform.modify_info.data
                sqla.session.commit()
                flash(str(__('Delete associate group success!')), 'success')
                return redirect(url_for(request.endpoint))

        return render_template('agroup/index.html', ags=ags,
                               form=form, dform=dform)

@agroup.route('/vi/them-lien-nhom', endpoint='add_agroup_vi', methods=['POST'])
@agroup.route('/en/add-agroup', endpoint='add_agroup_en', methods=['POST'])
@roles_accepted(*c.ADMIN_MOD_ROLE)
def add_agroup():
    form = AssociateGroupForm()
    form.province_id.choices = [(form.province_id.data,
                                 form.province_id.label.text)]
    form.id.data = str(uuid.uuid4())
    if form.validate_on_submit():
        province = sqla.session.query(models.Province) \
            .filter_by(province_id=form.province_id.data).one()
        as_group = form.associate_group_code.data
        new_agroup = models.AssociateGroup(
            id=form.id.data,
            associate_group_code=as_group,
            name=form.name.data, province=province,
            email=form.email.data,
            created_at=form.created_at.data
        )
        sqla.session.add(new_agroup)
        sqla.session.commit()
        return jsonify(is_success=True,
                       message=str(__('Add associate group success!')))
    else:
        return jsonify(is_success=False,
                       message=str(__('The form is not validate!')))

@agroup.route('/vi/sua-lien-nhom', endpoint='edit_agroup_vi', methods=['PUT'])
@agroup.route('/en/edit-agroup', endpoint='edit_agroup_en', methods=['PUT'])
@roles_accepted(*c.ADMIN_MOD_ROLE)
def edit_agroup():
    form = AssociateGroupForm()
    form.province_id.choices = [(form.province_id.data,
                                form.province_id.label.text)]
    if form.validate_on_submit():
        edit_agroup = sqla.session.query(models.AssociateGroup) \
            .filter_by(id=form.id.data).one()
        edit_agroup.email = form.email.data
        edit_agroup.associate_group_code = form \
            .associate_group_code.data
        edit_agroup.name = form.name.data
        edit_agroup.created_at = form.created_at.data
        if edit_agroup.province_id != form.province_id.data:
            edit_agroup.province = models.Province.query \
                .filter_by(province_id=form.province_id.data) \
                .one()
        sqla.session.commit()
        return jsonify(is_success=True,
                       message=str(__('Edit associate group success!')))
    else:
        return jsonify(is_success=False,
                       message=str(__('The form is not validate!')))

@agroup.route('/vi/xoa-lien-nhom', endpoint='delete_agroup_vi',
              methods=['DELETE'])
@agroup.route('/en/delete-agroup', endpoint='delete_agroup_en',
              methods=['DELETE'])
@roles_accepted(*c.ADMIN_MOD_ROLE)
def delete_agroup():
    return soft_delete(sqla, "agroup", models)


"""Support for the Wyze lock."""
import logging
from typing import Any, List, Optional, Union

from zigpy.profiles import zha
from zigpy.quirks import CustomCluster, CustomDevice
import zigpy.types as t
from zigpy.zcl import foundation
from zigpy.zcl.clusters.closures import DoorLock
from zigpy.zcl.clusters.general import (
    Basic,
    Identify,
    Ota,
    PollControl,
    PowerConfiguration,
    Time,
)
from zigpy.zcl.clusters.homeautomation import Diagnostic
from zigpy.zcl.clusters.security import IasZone

from . import YUNDING
from zhaquirks import Bus, LocalDataCluster
from zhaquirks.const import (
    CLUSTER_COMMAND,
    DEVICE_TYPE,
    ENDPOINTS,
    INPUT_CLUSTERS,
    MODELS_INFO,
    OFF,
    ON,
    OUTPUT_CLUSTERS,
    PROFILE_ID,
    ZONE_STATE,
)

WYZE_CLUSTER_ID = 0xFC00
ZONE_TYPE = 0x0001

_LOGGER = logging.getLogger(__name__)

class DoorLockCluster(CustomCluster, DoorLock):
    """DoorLockCluster cluster."""

    cluster_id = DoorLock.cluster_id

    def __init__(self, *args, **kwargs):
        """Init."""
        super().__init__(*args, **kwargs)
        self.endpoint.device.lock_bus.add_listener(self)

    def lock_event(self, locked):
        """Motion event."""
        self._update_attribute(0x0000, locked)

class MotionCluster(LocalDataCluster, IasZone):
    """Motion cluster."""

    cluster_id = IasZone.cluster_id

    def __init__(self, *args, **kwargs):
        """Init."""
        super().__init__(*args, **kwargs)
        self.endpoint.device.motion_bus.add_listener(self)
        super()._update_attribute(ZONE_TYPE, IasZone.ZoneType.Contact_Switch)

    def motion_event(self, zone_state):
        """Motion event."""
        super().listener_event(CLUSTER_COMMAND, None, ZONE_STATE, [zone_state])
        _LOGGER.debug("%s - Received motion event message", self.endpoint.device.ieee)

class WyzeCluster(CustomCluster, Basic):
    """Wyze manufacturer specific cluster implementation."""

    cluster_id = WYZE_CLUSTER_ID
    ep_attribute = "wyze_lock_cluster"
    attributes = {}
    server_commands = {}
    client_commands = {}

    def handle_message(
        self,
        hdr: foundation.ZCLHeader,
        args: List[Any],
        *,
        dst_addressing: Optional[
            Union[t.Addressing.Group, t.Addressing.IEEE, t.Addressing.NWK]
        ] = None,
    ):
        """Handle a message on this cluster."""
        self.debug("ZCL request 0x%04x: %s", hdr.command_id, args)
        i = 0
        for arg in args:
            self.info("index: %s value: %s", i, arg)
            i += 1
        self.warning("argument length: %s", len(args))
        self.warning("argument: %s", ",".join(map(str, args)))
        if len(args) < 70 or len(args) > 100:
            self.warning("argument list bad length: %s", len(args))
            return
        self.info(
            "Interesting attributes - 52: %s, 41: %s, 56: %s, 57: %s",
            args[52],
            args[41],
            args[56],
            args[57],
        )

        """
        Manual Lock: 52: 216, 41: 99, 56: 227, 57: 84
        Manual Unlock: 52: 216, 41: 100, 56: 227, 57: 84
        """
        if args[52] == 180 and args[41] == 165:
            self.warning("the lock is unlocked via the app")
            self.endpoint.device.lock_bus.listener_event("lock_event", 2)
        elif args[52] == 180 and args[41] == 162:
            self.warning("the lock is locked via the app")
            self.endpoint.device.lock_bus.listener_event("lock_event", 1)
        elif args[52] == 216 and args[41] == 100:
            self.warning("the lock is unlocked manually")
            self.endpoint.device.lock_bus.listener_event("lock_event", 2)
        elif args[52] == 216 and args[41] == 99:
            self.warning("the lock is locked manually")
            self.endpoint.device.lock_bus.listener_event("lock_event", 1)
        elif args[52] == 189 and args[41] == 162:
            self.warning("the lock is locked via auto lock")
            self.endpoint.device.lock_bus.listener_event("lock_event", 1)
        if args[52] == 74 and args[41] == 177:
            self.warning("the door is open")
            self.endpoint.device.motion_bus.listener_event("motion_event", ON)
        elif args[52] == 74 and args[41] == 178:
            self.warning("the door is closed")
            self.endpoint.device.motion_bus.listener_event("motion_event", OFF)

class WyzeLock(CustomDevice):
    """Wyze lock device."""

    def __init__(self, *args, **kwargs):
        """Init."""
        self.lock_bus = Bus()
        self.motion_bus = Bus()
        super().__init__(*args, **kwargs)

    signature = {
        #  <SimpleDescriptor endpoint=1 profile=260 device_type=10
        # device_version=1
        # input_clusters=[0, 1, 3, 32, 257, 2821, 64512]
        # output_clusters=[10, 25, 64512]>
        MODELS_INFO: [(YUNDING, "Ford")],
        ENDPOINTS: {
            1: {
                PROFILE_ID: zha.PROFILE_ID,
                DEVICE_TYPE: zha.DeviceType.DOOR_LOCK,
                INPUT_CLUSTERS: [
                    Basic.cluster_id,
                    PowerConfiguration.cluster_id,
                    Identify.cluster_id,
                    PollControl.cluster_id,
                    DoorLock.cluster_id,
                    Diagnostic.cluster_id,
                    WYZE_CLUSTER_ID,
                ],
                OUTPUT_CLUSTERS: [Ota.cluster_id, Time.cluster_id, WYZE_CLUSTER_ID],
            }
        },
    }
    replacement = {
        ENDPOINTS: {
            1: {
                PROFILE_ID: zha.PROFILE_ID,
                DEVICE_TYPE: zha.DeviceType.DOOR_LOCK,
                INPUT_CLUSTERS: [
                    Basic.cluster_id,
                    PowerConfiguration.cluster_id,
                    Identify.cluster_id,
                    PollControl.cluster_id,
                    DoorLockCluster,
                    Diagnostic.cluster_id,
                    WyzeCluster,
                    MotionCluster,
                ],
                OUTPUT_CLUSTERS: [Ota.cluster_id, Time.cluster_id, WyzeCluster],
            }
        }
    }


from typing import List, Dict
import json

from geonoderest.geonodetypes import GeonodeCmdOutObjectKey, GeonodeCmdOutListKey
from geonoderest.rest import GeonodeRest
from geonoderest.cmdprint import print_list_on_cmd, print_json

class GeonodeObjectHandler(GeonodeRest):
    LIST_CMDOUT_HEADER: List[GeonodeCmdOutObjectKey] = [
        GeonodeCmdOutListKey(type=list, key="pk")
    ]
    GET_CMDOUT_PROPERTIES: List[GeonodeCmdOutObjectKey] = [
        GeonodeCmdOutListKey(type=list, key="pk")
    ]
    DEFAULT_UPLOAD_KEYS: List[str] = ["key", "value"]
    JSON_OBJECT_NAME: str = ""
    ENDPOINT_NAME: str = ""
    SINGULAR_RESOURCE_NAME: str = ""

    def cmd_list(self, **kwargs):
        """show list of geonode obj on the cmdline"""
        obj = self.list(**kwargs)
        if kwargs["json"]:
            print_json(obj)
        else:
            print_list_on_cmd(obj, self.LIST_CMDOUT_HEADER)

    def list(self, **kwargs) -> Dict:
        """returns dict of datasets from geonode

        Returns:
            Dict: request response
        """
        r = self.http_get(
            endpoint=f"{self.ENDPOINT_NAME}/?page_size={kwargs['page_size']}"
        )
        return r[self.JSON_OBJECT_NAME]

    def cmd_delete(self, pk: int, **kwargs):
        self.delete(pk=pk, **kwargs)
        print(f"{self.JSON_OBJECT_NAME}: {pk} deleted ...")

    def delete(self, pk: int, **kwargs):
        """delete geonode resource object"""
        self.http_get(endpoint=f"{self.ENDPOINT_NAME}/{pk}")
        self.http_delete(endpoint=f"resources/{pk}/delete")

    def cmd_patch(self, pk: int, fields: str, **kwargs):
        obj = self.patch(pk, fields, **kwargs)
        print_json(obj)

    def patch(self, pk: int, fields: str, **kwargs) -> Dict:
        """tries to generate  object from incoming json string

        Args:
            pk (int): pk of the object
            fields (str): string of potential json object

        Returns:
            Dict: obj details

        Raises:
             ValueError: catches json.decoder.JSONDecodeError and raises ValueError as decoding is not working
        """
        try:
            json_data = json.loads(fields)
        except ValueError:
            raise (
                ValueError(
                    f"unable to decode argument: | {fields} | to json object ..."
                )
            )

        return self.http_patch(endpoint=f"{self.ENDPOINT_NAME}/{pk}/", params=json_data)

    def cmd_describe(self, pk: int, **kwargs):
        obj = self.get(pk=pk, **kwargs)
        print_json(obj)

    def get(self, pk: int, **kwargs) -> Dict:
        """get details for a given pk

        Args:
            pk (int): pk of the object

        Returns:
            Dict: obj details
        """
        r = self.http_get(
            endpoint=f"{self.ENDPOINT_NAME}/{pk}?page_size={kwargs['page_size']}"
        )
        return r[self.SINGULAR_RESOURCE_NAME]


#!/usr/bin/env python
# coding: utf-8

# In[1]:

import pandas as pd
import tensorflow as tf
# from tensorflow.keras.utils import get_file

try:
    path = tf.keras.utils.get_file('kddcup.data_10_percent.gz', origin=
    'http://kdd.ics.uci.edu/databases/kddcup99/kddcup.data_10_percent.gz')
except:
    print('Error downloading')
    raise

print(path)

# This file is a CSV, just no CSV extension or headers
# Download from: http://kdd.ics.uci.edu/databases/kddcup99/kddcup99.html
df = pd.read_csv(path, header=None)

print("Read {} rows.".format(len(df)))
# df = df.sample(frac=0.1, replace=False) # Uncomment this line to
# sample only 10% of the dataset
df.dropna(inplace=True,axis=1) # For now, just drop NA's
# (rows with missing values)

# The CSV file has no column heads, so add them
df.columns = [
    'duration',
    'protocol_type',
    'service',
    'flag',
    'src_bytes',
    'dst_bytes',
    'land',
    'wrong_fragment',
    'urgent',
    'hot',
    'num_failed_logins',
    'logged_in',
    'num_compromised',
    'root_shell',
    'su_attempted',
    'num_root',
    'num_file_creations',
    'num_shells',
    'num_access_files',
    'num_outbound_cmds',
    'is_host_login',
    'is_guest_login',
    'count',
    'srv_count',
    'serror_rate',
    'srv_serror_rate',
    'rerror_rate',
    'srv_rerror_rate',
    'same_srv_rate',
    'diff_srv_rate',
    'srv_diff_host_rate',
    'dst_host_count',
    'dst_host_srv_count',
    'dst_host_same_srv_rate',
    'dst_host_diff_srv_rate',
    'dst_host_same_src_port_rate',
    'dst_host_srv_diff_host_rate',
    'dst_host_serror_rate',
    'dst_host_srv_serror_rate',
    'dst_host_rerror_rate',
    'dst_host_srv_rerror_rate',
    'outcome'
]

pd.set_option('display.max_columns', 5)
pd.set_option('display.max_rows', 5)
# display 5 rows
display(df[0:5])

# ## Analyzing a Dataset
# Before we preprocess the KDD99 dataset let's have a look at the individual columns and distributions. You can use the following script to give a high-level overview of how a dataset appears.

# In[2]:

import pandas as pd
import os
import numpy as np
from sklearn import metrics
from scipy.stats import zscore

def expand_categories(values):
    result = []
    s = values.value_counts()
    t = float(len(values))
    for v in s.index:
        result.append("{}:{}%".format(v,round(100*(s[v]/t),2)))
    return "[{}]".format(",".join(result))

def analyze(df):
    print()
    cols = df.columns.values
    total = float(len(df))

    print("{} rows".format(int(total)))
    for col in cols:
        uniques = df[col].unique()
        unique_count = len(uniques)
        if unique_count>100:
            print("** {}:{} ({}%)".format(col,unique_count,int(((unique_count)/total)*100)))
        else:
            print("** {}:{}".format(col,expand_categories(df[col])))
            expand_categories(df[col])

# In[3]:

# Analyze KDD-99
analyze(df)

# ## Encode the feature vector
# We use the same two functions provided earlier to preprocess the data. The first encodes Z-Scores, and the second creates dummy variables from categorical columns.

# In[4]:

# Encode a numeric column as zscores
def encode_numeric_zscore(df, name, mean=None, sd=None):
    if mean is None:
        mean = df[name].mean()

    if sd is None:
        sd = df[name].std()

    df[name] = (df[name] - mean) / sd

# Encode text values to dummy variables(i.e. [1,0,0],
# [0,1,0],[0,0,1] for red,green,blue)
def encode_text_dummy(df, name):
    dummies = pd.get_dummies(df[name])
    for x in dummies.columns:
        dummy_name = f"{name}-{x}"
        df[dummy_name] = dummies[x]
    df.drop(name, axis=1, inplace=True)

# In[5]:

# Now encode the feature vector

encode_numeric_zscore(df, 'duration')
encode_text_dummy(df, 'protocol_type')
encode_text_dummy(df, 'service')
encode_text_dummy(df, 'flag')
encode_numeric_zscore(df, 'src_bytes')
encode_numeric_zscore(df, 'dst_bytes')
encode_text_dummy(df, 'land')
encode_numeric_zscore(df, 'wrong_fragment')
encode_numeric_zscore(df, 'urgent')
encode_numeric_zscore(df, 'hot')
encode_numeric_zscore(df, 'num_failed_logins')
encode_text_dummy(df, 'logged_in')
encode_numeric_zscore(df, 'num_compromised')
encode_numeric_zscore(df, 'root_shell')
encode_numeric_zscore(df, 'su_attempted')
encode_numeric_zscore(df, 'num_root')
encode_numeric_zscore(df, 'num_file_creations')
encode_numeric_zscore(df, 'num_shells')
encode_numeric_zscore(df, 'num_access_files')
encode_numeric_zscore(df, 'num_outbound_cmds')
encode_text_dummy(df, 'is_host_login')
encode_text_dummy(df, 'is_guest_login')
encode_numeric_zscore(df, 'count')
encode_numeric_zscore(df, 'srv_count')
encode_numeric_zscore(df, 'serror_rate')
encode_numeric_zscore(df, 'srv_serror_rate')
encode_numeric_zscore(df, 'rerror_rate')
encode_numeric_zscore(df, 'srv_rerror_rate')
encode_numeric_zscore(df, 'same_srv_rate')
encode_numeric_zscore(df, 'diff_srv_rate')
encode_numeric_zscore(df, 'srv_diff_host_rate')
encode_numeric_zscore(df, 'dst_host_count')
encode_numeric_zscore(df, 'dst_host_srv_count')
encode_numeric_zscore(df, 'dst_host_same_srv_rate')
encode_numeric_zscore(df, 'dst_host_diff_srv_rate')
encode_numeric_zscore(df, 'dst_host_same_src_port_rate')
encode_numeric_zscore(df, 'dst_host_srv_diff_host_rate')
encode_numeric_zscore(df, 'dst_host_serror_rate')
encode_numeric_zscore(df, 'dst_host_srv_serror_rate')
encode_numeric_zscore(df, 'dst_host_rerror_rate')
encode_numeric_zscore(df, 'dst_host_srv_rerror_rate')

# display 5 rows

df.dropna(inplace=True,axis=1)
df[0:5]
# This is the numeric feature vector, as it goes to the neural net

# Convert to numpy - Classification
x_columns = df.columns.drop('outcome')
x = df[x_columns].values
dummies = pd.get_dummies(df['outcome']) # Classification
outcomes = dummies.columns
num_classes = len(outcomes)
y = dummies.values

# In[6]:

df.groupby('outcome')['outcome'].count()

# ## Train the Neural Network

# In[7]:

import pandas as pd
import io
import requests
import numpy as np
import os
from sklearn.model_selection import train_test_split
from sklearn import metrics
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense, Activation
from tensorflow.keras.callbacks import EarlyStopping

# Create a test/train split.  25% test
# Split into train/test
x_train, x_test, y_train, y_test = train_test_split(
    x, y, test_size=0.25, random_state=42)

# Create neural net
model = Sequential()
model.add(Dense(10, input_dim=x.shape[1], activation='relu'))
model.add(Dense(50, input_dim=x.shape[1], activation='relu'))
model.add(Dense(10, input_dim=x.shape[1], activation='relu'))
model.add(Dense(1, kernel_initializer='normal'))
model.add(Dense(y.shape[1],activation='softmax'))
model.compile(loss='categorical_crossentropy', optimizer='adam')
monitor = EarlyStopping(monitor='val_loss', min_delta=1e-3, patience=5, verbose=1, mode='auto',restore_best_weights=True)
model.fit(x_train,y_train,validation_data=(x_test,y_test), callbacks=[monitor],verbose=2,epochs=1000)

# In[56]:

# Measure accuracy
y_pred = model.predict(x_test)
y_pred = np.argmax(y_pred,axis=1)
y_test = np.argmax(y_test,axis=1)
score = metrics.accuracy_score(y_test, y_pred)
print("Validation score: {}".format(score))

# In[58]:

from sklearn.metrics import classification_report, confusion_matrix, roc_curve, roc_auc_score
# matrix = metrics.confusion_matrix(y_test.argmax(axis=1), y_pred.argmax(axis=1))

# Estimation: Confusion Matrix & classification-report
# _confusion_matrix = confusion_matrix(y_test, y_pred)
arr_outcomes = list(outcomes)
arr_outcomes2 = (arr_outcomes[:19] + arr_outcomes[21:23])
_classification_report = classification_report(y_test, y_pred, target_names=arr_outcomes2, output_dict=False)
_classification_report_dict = classification_report(y_test, y_pred, target_names=arr_outcomes2, output_dict=True)

# print(_confusion_matrix)
print(_classification_report)

# In[59]:

def roc_auc_score_multiclass(y_test, y_pred, average = "macro"):
    """roc_auc_score_multiclass function evaluate the multiclass output as a ROC AUC score.

    :param y_test: test label
    :param y_pred: test label
    :param average: "macro" or Label encoder
    :return: _confusion_matrix, _classification_report, _auc_dict, _classification_report_dict
    """

    #creating a set of all the unique classes using the actual class list
    unique_class = set(y_test)
    roc_auc_dict = {}
    for per_class in unique_class:
        #creating a list of all the classes except the current class
        other_class = [x for x in unique_class if x != per_class]

        #marking the current class as 1 and all other classes as 0
        new_y_test = [0 if x in other_class else 1 for x in y_test]
        new_y_pred = [0 if x in other_class else 1 for x in y_pred]

        #using the sklearn metrics method to calculate the roc_auc_score
        roc_auc = roc_auc_score(new_y_test, new_y_pred, average = average)
        roc_auc_dict[per_class] = roc_auc

    return roc_auc_dict

# In[64]:

from matplotlib import pyplot
# For Multiclass AUC
_auc_dict = roc_auc_score_multiclass(y_test, y_pred)
_auc_dict = dict((arr_outcomes[key], value) for (key, value) in _auc_dict.items())

print('\n-----Confusion Matrix-----\n')
print(_confusion_matrix)
print('\n-----Classification Report-----\n')
print(_classification_report)
print('\n-----AUC Dictionary-----\n')
print(str(_auc_dict))

metrix = ['precision', 'recall', 'f1-score']
#     metrix = ['precision', 'recall', 'f1-score', 'support']
xKeys = arr_outcomes2
for met in metrix:
    xValues = []
    for target_name in arr_outcomes2:
        xValues += [_classification_report_dict[target_name][met]]

    pyplot.title(met)
    pyplot.bar(range(len(xValues)), list(xValues), align='center')
    pyplot.xticks(range(len(xKeys)), list(xKeys))
    pyplot.show()

pyplot.title('AUC')
pyplot.bar(range(len(_auc_dict)), list(_auc_dict.values()), align='center')
pyplot.xticks(range(len(_auc_dict)), list(_auc_dict.keys()))
pyplot.show()

# In[ ]:


# External imports
from uuid import uuid4
from sqlalchemy.orm import Session
from sqlalchemy import func
from datetime import timedelta, datetime
# Helper imports
from core_layer.connection_handler import get_db_session
from core_layer import helper
# Model imports
from core_layer.model.submission_model import Submission

def create_submission_db(submission, is_test, session):
    """Inserts a new submission into the database

    Parameters
    ----------
    submission: Submission, required
        The submission to be inserted

    Returns
    ------
    submission: Submission
        The inserted submission
    """
    session = get_db_session(is_test, session)

    submission.id = str(uuid4())
    submission.submission_date = helper.get_date_time_now(is_test)

    session.add(submission)
    session.commit()

    return submission

def get_submissions_by_item_id(item_id, is_test, session):

    session = get_db_session(is_test, session)
    submissions = session.query(Submission).filter(
        Submission.item_id == item_id).all()
    return submissions

def confirm_submission(submission_id, is_test, session):

    session = get_db_session(is_test, session)
    submission = session.query(Submission).filter(
        Submission.id == submission_id).one()
    submission.status = 'confirmed'
    session.merge(submission)
    session.commit()
    return submission

def anonymize_unconfirmed_submissions(is_test, session):

    session = get_db_session(is_test, session)
    two_days_ago = helper.get_date_time(
        datetime.now() - timedelta(days=2), is_test)
    submissions = session.query(Submission).filter(
        Submission.status == 'unconfirmed', Submission.submission_date < two_days_ago).all()
    counter = 0
    for submission in submissions:
        submission.mail = None
        session.merge(submission)
        counter += 1

    session.commit()
    return counter


from collections import deque

from tree.Invert_Binary_Tree import TreeNode

"""approach:
1. traverse binary tree until we find the split of two given nodes. t => O(log n)
1.1 when ever the split occur that's our least common ancestor

edge case:
1. what if node node itself one of the given two nodes
    => then node node must be LCA
"""

class Solution:
    def lowestCommonAncestor(self, root: TreeNode, p: TreeNode, q: TreeNode) -> TreeNode:
        while root:
            if p.val < root.val and q.val < root.val:
                root = root.left
            elif p.val > root.val and q.val > root.val:
                root = root.right
            else:
                return root.val

    def bfs(self, root):
        if not root:
            return []
        node_values = []
        total_sum = 0
        queue = deque()
        queue.append(root)
        while queue:
            node = queue.popleft()
            node_values.append(node.val)
            total_sum += node.val

            if node.left:
                queue.append(node.left)
            if node.right:
                queue.append(node.right)
        return node_values

def create_tree():
    tree = TreeNode(6)
    tree.left = TreeNode(2)
    tree.right = TreeNode(10)
    tree.left.left = TreeNode(0)
    tree.left.right = TreeNode(4)
    tree.left.right.left = TreeNode(3)
    tree.left.right.right = TreeNode(5)
    tree.right.left = TreeNode(7)
    tree.right.right = TreeNode(11)
    tree.right.left.right = TreeNode(8)
    return tree

if __name__ == '__main__':
    # Tree:
    #       6
    #    /     \
    #   2       10
    #  / \     /  \
    # 0   4   7    11
    #    / \   \
    #   3   5    8
    _tree = create_tree()

    solution = Solution()
    print(solution.lowestCommonAncestor(_tree, _tree.right.left, _tree.right.right))


'''
-Medium-
*BFS*

You are given an integer n, the number of nodes in a directed graph where the nodes are labeled from 0 to n - 1. Each edge is red or blue in this graph, and there could be self-edges and parallel edges.

You are given two arrays redEdges and blueEdges where:

redEdges[i] = [ai, bi] indicates that there is a directed red edge from node ai to node bi in the graph, and
blueEdges[j] = [uj, vj] indicates that there is a directed blue edge from node uj to node vj in the graph.
Return an array answer of length n, where each answer[x] is the length of the shortest path from node 0 to node x such that the edge colors alternate along the path, or -1 if such a path does not exist.

Example 1:

Input: n = 3, redEdges = [[0,1],[1,2]], blueEdges = []
Output: [0,1,-1]
Example 2:

Input: n = 3, redEdges = [[0,1]], blueEdges = [[2,1]]
Output: [0,1,-1]

Constraints:

1 <= n <= 100
0 <= redEdges.length, blueEdges.length <= 400
redEdges[i].length == blueEdges[j].length == 2
0 <= ai, bi, uj, vj < n

'''

from typing import List
from collections import defaultdict, deque

class Solution:
    def shortestAlternatingPaths(self, n: int, redEdges: List[List[int]], blueEdges: List[List[int]]) -> List[int]:
        graph = defaultdict(list)
        for u,v in redEdges:
            graph[u].append((v, 1))
        for u,v in blueEdges:
            graph[u].append((v, -1))
        res = [-1]*n
        que = deque([(0, 0, 0)])
        visited = {(0,-1), (0, 1)}
        while que:
            u, col, d = que.popleft()
            if res[u] == -1:
                res[u] = d
            for v,c in graph[u]:
                if col > -1 and c == -1 and (v, -1) not in visited:
                    visited.add((v, -1))
                    que.append((v, -1, d+1))
                if col < 1 and c == 1 and (v, 1) not in visited:
                    visited.add((v, 1))
                    que.append((v, 1, d+1))
        return res

if __name__ == "__main__":
    n = 5
    red = [[0,1],[1,2],[2,3],[3,4]]
    blue = [[1,2],[2,3],[3,1]]
    print(Solution().shortestAlternatingPaths(n, red, blue))


#!/usr/bin/env python
import django
import logging
import os
import sys

from django.conf import settings
from django.test.runner import DiscoverRunner
from edc_test_utils import DefaultTestSettings
from os.path import abspath, dirname, join

app_name = 'ambition_permissions'
base_dir = dirname(abspath(__file__))

DEFAULT_SETTINGS = DefaultTestSettings(
    calling_file=__file__,
    BASE_DIR=base_dir,
    LOAD_NAVBARS=False,
    APP_NAME=app_name,
    ETC_DIR=os.path.join(base_dir, app_name, "tests", "etc"),
    SUBJECT_CONSENT_MODEL="ambition_subject.subjectconsent",
    SUBJECT_VISIT_MODEL="ambition_subject.subjectvisit",
    SUBJECT_REQUISITION_MODEL="ambition_subject.subjectrequisition",
    ADVERSE_EVENT_ADMIN_SITE="ambition_ae_admin",
    ADVERSE_EVENT_APP_LABEL="ambition_ae",
    EDC_BOOTSTRAP=3,
    EMAIL_BACKEND="django.core.mail.backends.locmem.EmailBackend",
    EMAIL_CONTACTS={
        "data_request": "someone@example.com",
        "data_manager": "someone@example.com",
        "tmg": "someone@example.com",
    },
    EMAIL_ENABLED=True,
    HOLIDAY_FILE=join(base_dir, app_name, "tests", "holidays.csv"),
    LIVE_SYSTEM=False,
    RANDOMIZATION_LIST_PATH=join(
        base_dir, app_name, "tests", "test_randomization_list.csv"),
    INSTALLED_APPS=[
        "django.contrib.admin",
        "django.contrib.auth",
        "django.contrib.contenttypes",
        "django.contrib.sessions",
        "django.contrib.messages",
        "django.contrib.staticfiles",
        "django.contrib.sites",
        "django_crypto_fields.apps.AppConfig",
        "edc_action_item.apps.AppConfig",
        "edc_adverse_event.apps.AppConfig",
        "edc_appointment.apps.AppConfig",
        "edc_auth.apps.AppConfig",
        "edc_dashboard.apps.AppConfig",
        "edc_export.apps.AppConfig",
        "edc_identifier.apps.AppConfig",
        "edc_data_manager.apps.AppConfig",
        "edc_lab.apps.AppConfig",
        "edc_lab_dashboard.apps.AppConfig",
        "edc_locator.apps.AppConfig",
        "edc_metadata.apps.AppConfig",
        "edc_metadata_rules.apps.AppConfig",
        "edc_navbar.apps.AppConfig",
        "edc_notification.apps.AppConfig",
        "edc_offstudy.apps.AppConfig",
        "edc_pharmacy.apps.AppConfig",
        "edc_registration.apps.AppConfig",
        "edc_reference.apps.AppConfig",
        "edc_permissions.apps.AppConfig",
        "edc_sites.apps.AppConfig",
        "edc_visit_schedule.apps.AppConfig",
        'ambition_ae.apps.AppConfig',
        'ambition_labs.apps.AppConfig',
        'ambition_lists.apps.AppConfig',
        'ambition_prn.apps.AppConfig',
        'ambition_rando.apps.AppConfig',
        'ambition_screening.apps.AppConfig',
        'ambition_visit_schedule.apps.AppConfig',
        'ambition_subject.apps.AppConfig',
        'ambition_permissions.apps.AppConfig',
    ],
    add_dashboard_middleware=True,
    add_lab_dashboard_middleware=True,
    use_test_urls=True,
).settings

def main():
    if not settings.configured:
        settings.configure(**DEFAULT_SETTINGS)
    django.setup()
    tags = [t.split('=')[1] for t in sys.argv if t.startswith('--tag')]
    failures = DiscoverRunner(failfast=True, tags=tags).run_tests(
        [f'{app_name}.tests'])
    sys.exit(failures)

if __name__ == "__main__":
    logging.basicConfig()
    main()


from functools import partial
import gym
from typing import Dict, List, Type

from asrel.core.utils import get_class_from_module_path
from asrel.environments.base import BaseEnvironment

class GymEnvironment(gym.Wrapper, BaseEnvironment):
  def __init__(
    self,
    id: str,
    wrappers: List[Dict],
    **kwargs
  ):
    env = gym.make(id)
    for wrapper_config in wrappers:
      wrapper = self.get_wrapper_from_config(wrapper_config)
      env = wrapper(env)

    super().__init__(env)

    self.env = env

  def get_wrapper_from_config(self, config: Dict) -> Type[gym.Wrapper]:
    wrapper_path = config["path"]
    wrapper_class_name = config.get("class")
    wrapper_class = get_class_from_module_path(wrapper_path, class_name=wrapper_class_name, class_suffix="GymWrapper")

    return partial(wrapper_class, **config.get("conf", {}))


import re
from tabulate import tabulate

def main(args):
    path = vars(args)['path']
    windows_audit(path)

def windows_audit(path: str):
    parameter = ['Без аудита', 'Успех и сбой', 'Успех', 'Сбой']
    master_map = {}

    with open(path, 'r') as filez:

        current_table = ''
        for s in filez:
            if "Категория или подкатегория" in s:
                break

        for s in filez:
            if s[0] != ' ':
                current_table = s.replace('\n', '')
                master_map[current_table] = {}
            else:
                for p in parameter:
                    if re.search(p + '$', s):
                        value = p
                        key = s.split(p)[0].strip()
                        master_map[current_table][key] = value

    for k in master_map:
        print(k)
        print(tabulate(master_map[k].items(), headers=['Параметр', 'Значение'], tablefmt="grid"))
        print()


from nltk.tokenize import word_tokenize
from sacrebleu.metrics import BLEU, CHRF, TER
from bert_score import score
import os
from models import config
import csv
from rouge import Rouge
import numpy as np

def calc_distinct_n(n, candidates, print_score: bool = True):
    dict = {}
    total = 0
    candidates = [word_tokenize(candidate) for candidate in candidates]
    for sentence in candidates:
        for i in range(len(sentence) - n + 1):
            ney = tuple(sentence[i : i + n])
            dict[ney] = 1
            total += 1
    score = len(dict) / (total + 1e-16)

    if print_score:
        print(f"***** Distinct-{n}: {score*100} *****")

    return score

def calc_distinct(candidates, print_score: bool = True):
    scores = []
    for i in range(2):
        score = calc_distinct_n(i + 1, candidates, print_score)
        scores.append(score)

    return scores

def read_file(file_name, dec_type="Greedy"):
    f = open(f"./results/{file_name}.txt", "r", encoding="utf-8")

    refs = []
    cands = []
    dec_str = f"{dec_type}:"

    for i, line in enumerate(f.readlines()):
        if i == 1:
            _, ppl, _, acc = line.strip("EVAL	Loss	PPL	Accuracy").split()
            print(f"PPL: {ppl}\tAccuracy: {float(acc)*100}%")
        if line.startswith(dec_str):
            exp = line.strip(dec_str).strip("\n")
            cands.append(exp)
        if line.startswith("Ref:"):
            ref = line.strip("Ref:").strip("\n")
            refs.append(ref)

    return refs, cands, float(ppl), float(acc)

if __name__ == "__main__":
    if not os.path.exists(config.report_path):
        os.makedirs(config.report_path)
    files = [
        'emotion_flow',
        'more_emotion',
    ]

    with open(config.report_path + "/Report_Greedy1.csv", "w", newline='') as reportFile:
        fp_write = csv.writer(reportFile)
        fp_write.writerow(
            ['Model', 'PPL', 'Distinct-1', 'Distinct-2', 'Accuracy', 'Bleu', 'Rouge-l', 'P-Bert', 'R-Bert', 'F-Bert', 'CHRF'])
        for f in files:
            print(f"Evaluating {f}")
            refs, cands, p, a = read_file(f, dec_type="Greedy")

            dist_1, dist_2 = calc_distinct(cands)

            bleu = BLEU().corpus_score(cands, [refs])
            print(f"***** BLEU: {bleu.score} *****")

            scores = Rouge().get_scores(cands, refs)
            print(f"***** Rouge-f : {np.mean([score['rouge-l']['f'] for score in scores]) * 100} *****")

            P_Bert, R_Bert, F_Bert = score(cands, refs, lang="en", rescale_with_baseline=True)
            print(f"***** Bert_P: {P_Bert.mean() * 100} *****")
            print(f"***** Bert_R: {R_Bert.mean() * 100} *****")
            print(f"***** Bert_F: {F_Bert.mean() * 100} *****")

            chrf = CHRF().corpus_score(cands, [refs])
            print(f"***** CHRF: {chrf.score} *****")

            result = ['#' + str(f),
                      round(p, 4),
                      round(dist_1 * 100, 4) , round(dist_2 * 100, 4),
                      round(a, 4),
                      round(bleu.score, 4),
                      round(np.mean([score['rouge-l']['f'] for score in scores]) * 100, 4),
                      round(float(P_Bert.mean())* 100, 4), round(float(R_Bert.mean()) * 100, 4), round(float(F_Bert.mean()) * 100, 4),
                      round(chrf.score, 4)]
            fp_write.writerow(result)

    # with open(config.report_path + "/Report_Beam.csv", "w", newline='') as reportFile:
    #     fp_write = csv.writer(reportFile)
    #     fp_write.writerow(
    #         ['Model', 'PPL', 'Distinct-1', 'Distinct-2', 'Accuracy', 'Bleu', 'P-Bert', 'R-Bert', 'F-Bert', 'CHRF', 'TER'])
    #     for f in files:
    #         print(f"Evaluating {f}")
    #         refs, cands, p, a = read_file(f, dec_type="Beam")
    #
    #         dist_1, dist_2 = calc_distinct(cands)
    #
    #         bleu = BLEU().corpus_score(cands, [refs])
    #
    #         print(f"***** BLEU: {bleu.score} *****")
    #
    #         P_Bert, R_Bert, F_Bert = score(cands, refs, lang="en", rescale_with_baseline=True)
    #         print(f"***** Bert_P: {P_Bert.mean() * 100} *****")
    #         print(f"***** Bert_R: {R_Bert.mean() * 100} *****")
    #         print(f"***** Bert_F: {F_Bert.mean() * 100} *****")
    #
    #         chrf = CHRF().corpus_score(cands, [refs])
    #         print(f"***** CHRF: {chrf.score} *****")
    #
    #         ter = TER().corpus_score(cands, [refs])
    #         print(f"***** TER: {ter.score} *****")
    #
    #         result = [f,
    #                   round(p, 4),
    #                   round(dist_1 * 100, 4), round(dist_2 * 100, 4),
    #                   round(a, 4),
    #                   round(bleu.score, 4),
    #                   round(float(P_Bert.mean()) * 100, 4), round(float(R_Bert.mean()) * 100, 4),
    #                   round(float(F_Bert.mean()) * 100, 4),
    #                   round(chrf.score, 4),
    #                   round(ter.score, 4)]
    #         fp_write.writerow(result)


from flask import  request, jsonify
from flask.views import MethodView
from app.endereco.model import Enderecos
from app.extensions import db
from app.endereco.auxiliar import testar_entradas_endereco

class EnderecoDetails(MethodView):      # /enderecos
    def get(self):
        enderecos = Enderecos.query.all()
        return jsonify([endereco.json() for endereco in enderecos]),200

    def post(self):
        dados = request.json
        cep = dados.get('cep')
        logadouro = dados.get('logadouro')
        numero = dados.get('numero')
        complemento = dados.get('complemento')
        bairro = dados.get('bairro')
        cidade = dados.get('cidade')
        estado = dados.get('estado')
        usuario_id = dados.get("usuario_id")

        error = testar_entradas_endereco(cep,logadouro,numero,complemento,bairro,cidade,estado,usuario_id)
        if (error != False):
            return error

        endereco = Enderecos(cep = cep, logadouro = logadouro, numero = numero, complemento = complemento,
                             bairro = bairro, cidade = cidade, estado = estado, usuario_id = usuario_id)

        db.session.add(endereco)
        db.session.commit()

        return endereco.json() , 200

class PaginaEnderecos(MethodView):      # /enderecos/<int:id>
    def get(self,id):
        endereco = Enderecos.query.get_or_404(id)
        return endereco.json(),200

    def put(self,id):
        endereco = Enderecos.query.get_or_404(id)
        dados = request.json
        cep = dados.get('cep')
        logadouro = dados.get('logadouro')
        numero = dados.get('numero')
        complemento = dados.get('complemento')
        bairro = dados.get('bairro')
        cidade = dados.get('cidade')
        estado = dados.get('estado')
        usuario_id = dados.get("usuario_id")

        error = testar_entradas_endereco(cep,logadouro,numero,complemento,bairro,cidade,estado,usuario_id)
        if (error != False):
            return error

        endereco.cep = cep
        endereco.logadouro = logadouro
        endereco.numero = numero
        endereco.complemento = complemento
        endereco.bairro = bairro
        endereco.cidade = cidade
        endereco.estado = estado
        endereco.usuario_id = usuario_id

        db.session.commit()
        return endereco.json() , 200

    def patch(self,id):
        endereco = Enderecos.query.get_or_404(id)
        dados = request.json
        cep = dados.get('cep', endereco.cep)
        logadouro = dados.get('logadouro', endereco.logadouro)
        numero = dados.get('numero',endereco.numero)
        complemento = dados.get('complemento',endereco.complemento)
        bairro = dados.get('bairro',endereco.bairro)
        cidade = dados.get('cidade',endereco.cidade)
        estado = dados.get('estado',endereco.estado)
        usuario_id = dados.get("usuario_id",endereco.usuario_id)

        error = testar_entradas_endereco(cep,logadouro,numero,complemento,bairro,cidade,estado,usuario_id)
        if (error != False):
            return error

        endereco.cep = cep
        endereco.logadouro = logadouro
        endereco.numero = numero
        endereco.complemento = complemento
        endereco.bairro = bairro
        endereco.cidade = cidade
        endereco.estado = estado
        endereco.usuario_id = usuario_id

        db.session.commit()
        return endereco.json() , 200

    def delete(self,id):
        endereco = Enderecos.query.get_or_404(id)
        db.session.delete(endereco)
        db.session.commit()
        return endereco.json(), 200


import json
import logging
import os
import random
import time
from concurrent.futures.thread import ThreadPoolExecutor
from enum import Enum
from typing import List
from urllib.parse import urlencode

import requests

from src.utils import *

class Mode(Enum):
    MODE_MONTH = "monthly"
    MODE_WEEK = "weekly"
    MODE_DAY = "daily"
    MODE_ROOKIE = "rookie"
    MODE_ORIGINAL = "original"
    MODE_MALE = "male"
    MODE_FEMALE = "female"
    MODE_R18 = "_r18"

ONLY_ILLUST = True
ONLY_COVER = True
TIMEOUT = 60
MODE: Mode = Mode.MODE_WEEK
SAVE_PATH = "../images/"
DELAY_SECONDS = 3
r18 = False

HEADER = {
    "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) "
                  "Chrome/90.0.4430.212 Safari/537.36 "

}
PROXY = {"http": "socks5://127.0.0.1:19527", "https": "socks5://127.0.0.1:19527"}

def create_rank_url(index: int) -> str:
    qurey = {
        "mode": MODE.value,
        "p": index,
        "format": "json"
    }
    if r18:
        qurey["mode"] += MODE.MODE_R18.value
    if ONLY_ILLUST:
        qurey["content"] = "illust"
    return f"https://www.pixiv.net/ranking.php?{urlencode(qurey)}"

def task_generator():
    item_count = 0
    index = 1
    while True:
        url = create_rank_url(index)
        resp = session.get(url)
        data = json.loads(resp.text)
        contents: List = data["contents"]
        for content in contents:
            yield int(content["illust_id"])

        item_count += len(contents)
        if item_count >= data["rank_total"]:
            break
        index += 1

def task_pages(illust_id: int):
    pages_url = f"https://www.pixiv.net/ajax/illust/{illust_id}/pages?lang=zh"
    data = json.loads(session.get(pages_url).text)
    for item in data["body"]:
        yield item["urls"]["original"]

def task_img_download(img_url: str, name: str, delay: float = 0) -> bool:
    path = get_img_save_path(name)
    try:
        if len(name) == 0:
            return False

        if delay >= 0:
            logging.info(f"休眠{delay}秒")
            time.sleep(delay)

        resp = session.get(url=img_url, stream=True, timeout=TIMEOUT, headers={"referer": "https://www.pixiv.net"})
        total_size = int(resp.headers["content-length"])
        logging.info(f"{img_url}({format_file_size(total_size)})开始下载")
        size = 0

        with open(path, "wb") as f:
            for chunk in resp.iter_content(chunk_size=4 * 1024):
                f.write(chunk)
                size += len(chunk)
                # logging.info(f'{img_url}已下载:{percentage(size / total_size)}')
            f.close()
        logging.info(f"{img_url}：下载成功")
        return True
    except Exception as e:
        logging.error(img_url + "：下载失败")
        logging.exception(e)
        if os.path.exists(path):
            os.remove(path)
        return False

def get_img_save_path(name):
    return SAVE_PATH + "/" + name

def main():
    tasks = []
    if not os.path.exists(SAVE_PATH):
        os.makedirs(SAVE_PATH)
    thread_pool = ThreadPoolExecutor(max_workers=5)
    img_count = 0
    exist_count = 0
    for illust_id in task_generator():
        for img_url in task_pages(illust_id):
            img_count += 1
            name = get_name_from_url(img_url)
            path = get_img_save_path(name)
            if os.path.exists(path):
                exist_count += 1
                logging.info(f"{img_url}：已存在")
                if ONLY_COVER:
                    break
                else:
                    continue

            delay = DELAY_SECONDS + random.randint(0, 5)
            tasks.append(thread_pool.submit(task_img_download, img_url, name, delay))

            if ONLY_COVER:
                break
        # if img_count >= 10:
        #     break

    success = 0
    for task in tasks:
        if task.result():
            success += 1

    logging.info(f"图片数：{img_count},成功下载数：{success},已下载数：{exist_count},失败下载数：{img_count - success - exist_count}")

if __name__ == '__main__':
    logging.basicConfig(level=logging.INFO)

    session = requests.session()
    session.proxies = PROXY
    session.headers = HEADER
    main()


from __future__ import absolute_import, print_function

import docopt
import io
import math
import os
import string
import sys

from resultformat import result_file

try:
    from StringIO import StringIO
except ImportError:
    from io import StringIO

def resultprint(document, limit=None):
    output = StringIO()
    doc = result_file.parse(document)
    output.write("\n")
    output.write("\n".join(map(str, doc[:limit])))
    output.write("\n")
    return output.getvalue()

def round_decimals(n, decimals=0):
    factor = 10 ** decimals
    return math.floor(n*factor + 0.5) / factor

def resultcsv(document, limit=None):
    output = StringIO()
    doc = result_file.parse(document)
    output.write("Elapsed Time (s);Distance (km);Phys. kJoule;Slope (%);NM;RPM;Speed (km/h);Watt;Gear;Device Active;Pulse;Pulse Type;Training Type;Training Value;Pulse Time 1;2;3;4;5;6\n")
    for record in doc[:limit]:
        output.write('{0};'.format(record.elapsed_time))
        output.write('{0:.3f};'.format(round_decimals(record.distance / 1000, 3)))
        output.write('{0:.1f};'.format(round_decimals(record.energy,1)))
        output.write('{0:.1f};'.format(round_decimals(record.slope * 0.1, 1)))
        output.write('{0:.1f};'.format(round_decimals(record.torque * 0.1, 1)))
        output.write('{0:.1f};'.format(round_decimals(record.rpm * 0.1, 1)))
        output.write('{0:.1f};'.format(round_decimals(record.speed * 0.1, 1)))
        output.write('{0};'.format(record.power))
        output.write('{0};'.format(record.gear))
        output.write('{0};'.format(record.device_active))
        output.write('{0};'.format(record.pulse))
        output.write('{0};'.format(record.pulse_type))
        output.write('{0};'.format(record.training_type))
        output.write('{0:.1f};'.format(round_decimals(record.training_value,1)))
        output.write('{0};'.format(record.pulse_time_1))
        output.write('{0};'.format(record.pulse_time_2))
        output.write('{0};'.format(record.pulse_time_3))
        output.write('{0};'.format(record.pulse_time_4))
        output.write('{0};'.format(record.pulse_time_5))
        output.write('{0}'.format(record.pulse_time_6))
        output.write("\n")
    return output.getvalue()

def main(argv=None):
    if (sys.version_info < (3,0)):
        reload(sys)
        sys.setdefaultencoding('utf-8')

    if (argv == None):
        argv = sys.argv[1:]

    try:
        args = docopt.docopt(__doc__, argv=argv, version='resultread ' + '1.0')

        limit = None
        if args['--limit']:
            limit = int(args['--limit'])

        if args['--input']:
            with io.open(args['--input'], 'rb') as f:
                if args['--raw']:
                    text = resultprint(f.read(), limit)
                else:
                    text = resultcsv(f.read(), limit)
        else:
            with sys.stdin as f:
                if args['--raw']:
                    text = resultprint(f.read(), limit)
                else:
                    text = resultcsv(f.read(), limit)

        if args['--output']:
            with io.open(args['--output'], 'wb') as outfile:
                outfile.write(text.encode('utf-8'))
        else:
            sys.stdout.write(text)

        return 0

    except KeyboardInterrupt:
        print(" Interrupted.", file=sys.stderr)

    except IOError as error:
        print("error: IOError {0}".format(error, file=sys.stderr))

    return 1

if __name__ == "__main__":
    sys.exit(main())


'''
By: ind3x
This script is something of a sustitude cypher but for this part i had to change the index to start at 1
'''

import fidx
from sympy import mod_inverse
#create custom type `list1b` from `list`
fidx.add(list, name='list1')

#add a map int indexes (i -> i-1)
fidx.list1.set_index_map(int, lambda _,i: i-1, override=True)

#create your lists

#numbers that form strings
numbers= fidx.list1([268,413,110,190,426,419,108,229,310,379,323,373,385,236,92,96,169,321,284,185,154,137,186])

#Array of charrecters sustituted by numbers
letters_and_numbers= fidx.list1(['A','B','C','D','E','F','J','H','I','J','K','L','M','N','O','P','Q','R','S',
'T','U','V','W','X','Y','Z','0','1','2','3','4','5','6','7','8','9','_'])

print("\nLetters and numbers are:",len(letters_and_numbers))
print("Flag is:", len(numbers), " long\n")

i=1
while i <= len(numbers):
    mod = numbers[i] % 41
    print(letters_and_numbers[mod_inverse(mod,41)], end='')
    i +=1
print("\n")


import sys
import os
import requests
import json
from argparse import ArgumentParser

def main(argv):
    parser = ArgumentParser()
    parser.add_argument("--token", dest="token", help="GitHub API personal access token ")
    parser.add_argument("--action", dest="action", default="build", help="The trigger action")
    parser.add_argument("--branch", dest="branch", help="The branch to build")
    parser.add_argument("--skip-engine", dest="skip_engine", action='store_true', default=False, help="Skip building the engine")
    parser.add_argument("--skip-sdk", dest="skip_sdk", action='store_true', default=False, help="Skip building the Defold SDK")
    parser.add_argument("--skip-bob", dest="skip_bob", action='store_true', default=False, help="Skip building bob")
    parser.add_argument("--skip-editor", dest="skip_editor", action='store_true', default=False, help="Skip building the editor")
    parser.add_argument("--skip-sign", dest="skip_sign", action='store_true', default=False, help="Skip signing the artefacts")

    args = parser.parse_args()

    if not args.token:
        args.token = os.environ.get("GITHUB_TOKEN")
    if not args.token:
        print("You must provide a GitHub token")
        exit(1)

    post_data = {
        "event_type": args.action,
        "client_payload": {
            "skip_engine": args.skip_engine,
            "skip_sdk": args.skip_sdk,
            "skip_bob": args.skip_bob,
            "skip_editor": args.skip_editor,
            "skip_sign": args.skip_sign,
            "branch": args.branch
        }
    }

    headers = {
        "Accept": "application/vnd.github.everest-preview+json",
        "Authorization": "token %s" % args.token
    }

    r = requests.post('https://api.github.com/repos/defold/defold/dispatches', json=post_data, headers=headers)
    print(r)

if __name__ == "__main__":
    main(sys.argv[1:])


import os
from pathlib import Path

def mergeFiles(src, dest):
    srcfile = open(src, 'r')
    srclines = srcfile.readlines()
    forappend = ''.join(srclines)
    dstfile = open(dest, 'a')
    dstfile.write(forappend)
    dstfile.close()

def processContentFromFile(path):
    if '.lproj' not in path:
        return
    array = path.split('/')
    code = array[2].split('.')[0]
    print('code ' + path)
    destpath = '../Electrum/texts/' + code + '.lproj/Localizable.strings'
    if Path(destpath).is_file():
        mergeFiles(path, destpath)
    else:
        print(': ' + code)
        exit(1)
for root, dirs, files in os.walk("../temp"):
    for file in files:
        path = root + '/' + file
        processContentFromFile(path)


import itertools
import operator
import string

from pathlib import Path
from collections import deque, namedtuple

from . import data
from . import diff

def init ():
    data.init ()
    # init() should happen once
    if (data.GIT_DIR /'refs/heads/master').is_file():
        return
    data.update_ref ('HEAD', data.RefValue (symbolic=True, value='refs/heads/master'))

def write_tree ():
    # Get Index as a tree of dicts
    index_as_tree = {}
    with data.get_index () as index:
        for path, oid in index.items ():
            path = path.split ('/')
            dirpath, filename = path[:-1], path[-1]

            current = index_as_tree
            # Find the dict for the directory of this file
            for dirname in dirpath:
                current = current.setdefault (dirname, {})
            current[filename] = oid

    def write_tree_recursive (tree_dict):
        entries = []
        for name, value in tree_dict.items ():
            if type (value) is dict:
                type_ = 'tree'
                oid = write_tree_recursive (value)
            else:
                type_ = 'blob'
                oid = value
            entries.append ((name, oid, type_))

        tree = ''.join (f'{type_} {oid} {name}\n'
                        for name, oid, type_
                        in sorted (entries))
        return data.hash_object (tree.encode (), 'tree')

    return write_tree_recursive (index_as_tree)

# def _iter_tree_entries (oid):
#     if not oid:
#         return
#     tree = data.get_object (oid, 'tree')
#     for entry in tree.decode ().splitlines ():
#         type_, oid, name = entry.split (' ', 2)
#         yield type_, oid, name

def _iter_tree_entries (oid):
    if not oid:
        return ''
    return (entry.split (' ', 2)
            for entry in data.get_object (oid, 'tree').decode ().splitlines ())

def get_tree (oid, base_path=''):
    result = {}
    for type_, oid, name in _iter_tree_entries (oid):
        assert '/' not in name
        # assert name not in ('..', '.')
        path = base_path + name
        if type_ == 'blob':
            result[path] = oid
        elif type_ == 'tree':
            result.update (get_tree (oid, f'{path}/'))
        else:
            assert False, f'Unknown tree entry {type_}'
    return result

# def get_working_tree ():
#     result = {}
#     for root, _, filenames in os.walk ('.'):
#         for filename in filenames:
#             path = os.path.relpath (f'{root}/{filename}')
#             if is_ignored (path) or not os.path.isfile (path):
#                 continue
#             with open (path, 'rb') as f:
#                 result[path] = data.hash_object (f.read ())
#     return result

def get_working_tree ():
    file_path = Path('.')
    result = {}
    for fp in (fp for fp in file_path.rglob('*')
               if not is_ignored(fp) and fp.is_file()):
        result [str(fp)] = data.hash_object(fp.read_bytes())
    return result

def get_index_tree ():
    with data.get_index () as index:
        return index

# def _empty_current_directory ():
#     for root, dirnames, filenames in os.walk ('.', topdown=False):
#         for filename in filenames:
#             path = os.path.relpath (f'{root}/{filename}')
#             if is_ignored (path) or not os.path.isfile (path):
#                 continue
#             os.remove (path)
#         for dirname in dirnames:
#             path = os.path.relpath (f'{root}/{dirname}')
#             if is_ignored (path):
#                 continue
#             try:
#                 os.rmdir (path)
#             except (FileNotFoundError, OSError):
#                 # Deletion might fail if the directory contains ignored files,
#                 # so it's OK
#                 pass

def _empty_current_directory ():
    """ Remove all files/directories of the current tree (unless is_ignored)"""
    paths = []

    # First removing all files...
    for path in (fp for fp in Path('.').rglob ('*')
               if not is_ignored (fp)):
        if path.is_file ():
            path.unlink ()
        else:
            paths.append(path)

    # then removing all directories...
    paths.sort (reverse=True)
    for path in paths:
        path.rmdir()

def read_tree (tree_oid, update_working=False):
    with data.get_index () as index:
        index.clear ()
        index.update (get_tree (tree_oid))

        if update_working:
            _checkout_index (index)

def read_tree_merged (t_base, t_HEAD, t_other, update_working=False):
    with data.get_index () as index:
        index.clear ()
        index.update (diff.merge_trees (
            get_tree (t_base),
            get_tree (t_HEAD),
            get_tree (t_other)
        ))

        if update_working:
            _checkout_index (index)

def _checkout_index (index):
    """For every entry in the index, the respected object is copied to the given
    file path. Any missing directory structure is created during the process.
    """
    _empty_current_directory ()
    for path, oid in index.items ():
        fp = Path(path)
        if not fp.parent.is_dir():
            fp.parent.mkdir(parents=True, exist_ok=True)
        fp.write_bytes(data.get_object (oid, 'blob'))

def commit (message):
    commit = f'tree {write_tree ()}\n'

    HEAD = data.get_ref ('HEAD').value
    if HEAD:
        commit += f'parent {HEAD}\n'
    MERGE_HEAD = data.get_ref ('MERGE_HEAD').value
    if MERGE_HEAD:
        commit += f'parent {MERGE_HEAD}\n'
        data.delete_ref ('MERGE_HEAD', deref=False)

    commit += '\n'
    commit += f'{message}\n'

    oid = data.hash_object (commit.encode (), 'commit')

    data.update_ref ('HEAD', data.RefValue (symbolic=False, value=oid))

    return oid

def checkout (name):
    oid = get_oid (name)
    commit = get_commit (oid)
    read_tree (commit.tree, update_working=True)

    if is_branch (name):
        HEAD = data.RefValue (symbolic=True, value=f'refs/heads/{name}')
    else:
        HEAD = data.RefValue (symbolic=False, value=oid)

    data.update_ref ('HEAD', HEAD, deref=False)

def reset (oid):
    data.update_ref ('HEAD', data.RefValue (symbolic=False, value=oid))

def merge (other):
    HEAD = data.get_ref ('HEAD').value
    assert HEAD
    merge_base = get_merge_base (other, HEAD)
    c_other = get_commit (other)

    # Handle fast-forward merge
    if merge_base == HEAD:
        read_tree (c_other.tree, update_working=True)
        data.update_ref ('HEAD',
                         data.RefValue (symbolic=False, value=other))
        print ('Fast-forward merge, no need to commit')
        return

    data.update_ref ('MERGE_HEAD', data.RefValue (symbolic=False, value=other))

    c_base = get_commit (merge_base)
    c_HEAD = get_commit (HEAD)
    read_tree_merged (c_base.tree, c_HEAD.tree, c_other.tree, update_working=True)
    print ('Merged in working tree\nPlease commit')

def get_merge_base (oid1, oid2):
    parents1 = set (iter_commits_and_parents ({oid1}))

    for oid in iter_commits_and_parents ({oid2}):
        if oid in parents1:
            return oid

def is_ancestor_of (commit, maybe_ancestor):
    return maybe_ancestor in iter_commits_and_parents ({commit})

def create_tag (name, oid):
    data.update_ref (f'refs/tags/{name}', data.RefValue (symbolic=False, value=oid))

def create_branch (name, oid):
    data.update_ref (f'refs/heads/{name}', data.RefValue (symbolic=False, value=oid))

def iter_branch_names ():
    """ Return a generator yielding all branch names """
    return (ref[0].split('/')[-1] for ref in data.iter_refs ('refs/heads/'))

def is_branch (branch):
    return data.get_ref (f'refs/heads/{branch}').value is not None

def get_branch_name ():
    HEAD = data.get_ref ('HEAD', deref=False)
    if not HEAD.symbolic:
        return None
    HEAD = HEAD.value
    assert HEAD.startswith ('refs/heads/')
    return HEAD.split('/')[-1]

Commit = namedtuple ('Commit', ['tree', 'parents', 'message'])

def get_commit (oid):
    parents = []

    commit = data.get_object (oid, 'commit').decode ()
    lines = iter (commit.splitlines ())
    for line in itertools.takewhile (operator.truth, lines):
        key, value = line.split (' ', 1)
        if key == 'tree':
            tree = value
        elif key == 'parent':
            parents.append (value)
        else:
            assert False, f'Unknown field {key}'

    message = '\n'.join (lines)
    return Commit (tree=tree, parents=parents, message=message)

def iter_commits_and_parents (oids):
    # N.B. Must yield the oid before acccessing it (to allow caller to fetch it
    # if needed)
    oids = deque (oids)
    visited = set ()

    while oids:
        oid = oids.popleft ()
        if not oid or oid in visited:
            continue
        visited.add (oid)
        yield oid

        commit = get_commit (oid)
        # Return first parent next
        oids.extendleft (commit.parents[:1])
        # Return other parents later
        oids.extend (commit.parents[1:])

def iter_objects_in_commits (oids):
    # N.B. Must yield the oid before acccessing it (to allow caller to fetch it
    # if needed)

    visited = set ()
    def iter_objects_in_tree (oid):
        visited.add (oid)
        yield oid
        for type_, oid, _ in _iter_tree_entries (oid):
            if oid not in visited:
                if type_ == 'tree':
                    yield from iter_objects_in_tree (oid)
                else:
                    visited.add (oid)
                    yield oid

    for oid in iter_commits_and_parents (oids):
        yield oid
        commit = get_commit (oid)
        if commit.tree not in visited:
            yield from iter_objects_in_tree (commit.tree)

def get_oid (name):
    if name == '@': name = 'HEAD'

    # Name is ref
    refs_to_try = [
        f'{name}',
        f'refs/{name}',
        f'refs/tags/{name}',
        f'refs/heads/{name}',
    ]
    for ref in refs_to_try:
        if data.get_ref (ref, deref=False).value:
            return data.get_ref (ref).value

    # Name is SHA1
    is_hex = all (c in string.hexdigits for c in name)
    if len (name) == 40 and is_hex:
        return name

    assert False, f'Unknown name {name}'

# def add (filenames):

#     def add_file (filename):
#         # Normalize path
#         filename = os.path.relpath (filename)
#         with open (filename, 'rb') as f:
#             oid = data.hash_object (f.read ())
#         index[filename] = oid

#     def add_directory (dirname):
#         for root, _, filenames in os.walk (dirname):
#             for filename in filenames:
#                 # Normalize path
#                 path = os.path.relpath (f'{root}/{filename}')
#                 if is_ignored (path) or not os.path.isfile (path):
#                     continue
#                 add_file (path)

#     with data.get_index () as index:
#         for name in filenames:
#             if os.path.isfile (name):
#                 add_file (name)
#             elif os.path.isdir (name):
#                 add_directory (name)

def add (filenames):
    """
    Add one or more files/directories to the Index file
    Expects a list of file paths
    """
    with data.get_index () as index:
        for file_path in filenames:
            if is_ignored(file_path):
                continue
            elif file_path.is_file():
                # add file/hash for specified file
                index[str(file_path)] = data.hash_object(file_path.read_bytes())
            elif file_path.is_dir():
                # Add dictionary of files/hashes within specified path
                result = {}
                for fp in (fp for fp in file_path.rglob('*')
                        if not is_ignored(fp) and fp.is_file()):
                    result [str(fp)] = data.hash_object(fp.read_bytes())
                index.update(**result)

# def is_ignored (path):
#     return '.gitcl' in path.split ('/')

def is_ignored (path):
    """ Filter criteria of files/dirs to be ignored """
    # exlude Python cache files
    if '__pycache__' in path.parts:
        return False

    # dirs to exclude
    for s in [ '.gitignore', '.gitcl', 'gitcl.egg-info']:
        if s in path.parts:
            return True

    return False


import cv2
from typing import Callable

# Function to preprocess an image
def preprocess_image(image):
    # img = cv2.resize(image, (0, 0), fx=2, fy=2)
    img = image.copy()
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    image = cv2.threshold(gray, 0, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)[1]
    return image

# Function to extract and reformat text from an image using the given OCR library
def extract_and_reformat_text(image_path, ocr_function: Callable):
    image = cv2.imread(image_path)
    preprocessed_image = preprocess_image(image)
    extracted_text = ocr_function(preprocessed_image)
    return extracted_text