# -*- coding:UTF-8 -*-

import tensorflow as tf
from tensorflow import keras
import tushare as ts
import numpy as np
import pandas as pd
import os
import time
import sys
from absl import app
from absl import flags
import random
sys.path.append("..")
from common import base_common
from common import np_common
from common.const_def import *
import tushare_data
import feature
import dl_model
import trade_base

reload(sys)
sys.setdefaultencoding('utf-8')
os.environ['TF_CPP_MIN_LOG_LEVEL'] = '2'

FLAGS = flags.FLAGS

# min_wave_width_left = 2
# min_wave_width_right = 2
# trade_off_threshold = 0
# up_100avg_condition = True
# up_200avg_condition = False
# wave_index = 'close'
# save_original_dataset = False

EXTREME_NONE = 0
EXTREME_PEAK = 1
EXTREME_VALLEY = 2
EXTREME_STR = ['NONE', 'PEAK', 'VALLEY']

STATUS_NONE = 0
STATUS_UP = 1
STATUS_DOWN = 2
WAVE_STATUS_STR = ['NONE', 'UP', 'DOWN']

# wave_test_dataset_sample_num = 5

class ExtremeWave(trade_base.TradeBase):
    def __init__(self,
                 o_data_source,
                 o_feature,
                 min_wave_width_left = 2,
                 min_wave_width_right = 2,
                 up_100avg_condition = True,
                 trade_off_threshold = 0,
                 cut_loss_ratio = 0.1,
                 dataset_sample_num = 5):
        class_name = 'extreme_wave'
        # inherit class setting
        self.min_wave_width_left = min_wave_width_left
        self.min_wave_width_right = min_wave_width_right
        self.up_100avg_condition = up_100avg_condition
        self.trade_off_threshold = trade_off_threshold
        app_setting_name = '%u_%u_%u_%u_%u' % (min_wave_width_left,
                                         min_wave_width_right,
                                         int(up_100avg_condition),
                                         trade_off_threshold,
                                         dataset_sample_num)
        super(ExtremeWave, self).__init__(o_data_source,
                                      o_feature,
                                      class_name,
                                      app_setting_name,
                                      0.0,
                                      dataset_sample_num,
                                      cut_loss_ratio)

    # 返回 extreme_flag, extreme_value
    def FitExtreme(self, pp_data, data_len, day_index):
        if (data_len - day_index) < (self.min_wave_width_left + self.min_wave_width_right + 1):
            return EXTREME_NONE, 0.0
        middle_index = day_index + self.min_wave_width_right
        middle_value = pp_data[middle_index][PPI_close]
        is_peak = True
        is_valley = True
        for iloop in range(1, self.min_wave_width_left + 1):
            temp_value = pp_data[middle_index + iloop][PPI_close]
            if middle_value > temp_value:
                is_valley = False
            elif middle_value < temp_value:
                is_peak = False
        for iloop in range(1, self.min_wave_width_right + 1):
            temp_value = pp_data[middle_index - iloop][PPI_close]
            if middle_value >= temp_value:
                is_valley = False
            elif middle_value <= temp_value:
                is_peak = False
        # 计算 extreme_flag 当天峰谷标志
        if is_peak:
            extreme_flag = EXTREME_PEAK
        elif is_valley:
            extreme_flag = EXTREME_VALLEY
        else:
            extreme_flag = EXTREME_NONE
        return extreme_flag, middle_value

    def TradePP(self, pp_data):
        data_len = len(pp_data)
        if data_len == 0:
            return
        self.wave_data = np.zeros((data_len), dtype=np.int)
        self.trade_flag = np.zeros((data_len), dtype=np.int)
        last_peak = []
        last_valley = []
        trade_off_count = 0
        last_extreme = EXTREME_NONE
        current_status = STATUS_NONE
        last_flag = TS_NONE

        for day_loop in reversed(range(0, data_len)):
            day_index_reversed = data_len - day_loop - 1  # day_loop 倒数的 index
            close = pp_data[day_loop][PPI_close]
            close_10_avg = pp_data[day_loop][PPI_close_10_avg]
            close_100_avg = pp_data[day_loop][PPI_close_100_avg]
            fit_flag, e_value = self.FitExtreme(pp_data, data_len, day_loop)

            # set self.trade_flag
            if fit_flag == EXTREME_PEAK:
                if len(last_peak) > 0 and e_value <= last_peak[0]:
                    self.trade_flag[day_loop] = TS_OFF
            elif fit_flag == EXTREME_VALLEY:
                if len(last_valley) > 0 and e_value <= last_valley[0]:
                    self.trade_flag[day_loop] = TS_OFF

            if len(last_valley) > 0 and close < last_valley[0]:
                self.trade_flag[day_loop] = TS_OFF
            if (len(last_peak) > 0 and close > last_peak[0]) and \
               ((not self.up_100avg_condition) or (close_10_avg > close_100_avg)) and \
               (trade_off_count >= self.trade_off_threshold):
                self.trade_flag[day_loop] = TS_ON

            # set last_peak,last_valley,last_extreme,self.wave_data
            if fit_flag == EXTREME_PEAK:
                last_peak.insert(0, e_value)
                last_extreme = EXTREME_PEAK
                current_status = WS_DOWN
            elif fit_flag == EXTREME_VALLEY:
                last_valley.insert(0, e_value)
                last_extreme = EXTREME_VALLEY
                current_status = WS_UP
            self.wave_data[day_loop] = current_status

            # set trade_off_count
            if last_flag == TS_ON:
                trade_off_count = 0
            else:
                trade_off_count += 1
            if self.trade_flag[day_loop] != TS_NONE:
                last_flag = self.trade_flag[day_loop]

    def TradeNextStatus(self, pp_data, day_index):
        trade_flag = self.trade_flag[day_index]
        return trade_flag

def main(argv):
    del argv

    o_data_source = tushare_data.DataSource(20000101, '', '', 1, 20120101, 20200106, False, False, True)
    o_feature = feature.Feature(30, feature.FUT_D5_NORM, 1, False, False)
    # o_feature = feature.Feature(30, feature.FUT_D5_NORM, 1, False, False)
    # o_feature = feature.Feature(30, feature.FUT_5REGION5_NORM, 5, False, False)
    # o_feature = feature.Feature(30, feature.FUT_2AVG5_NORM, 5, False, False)
    o_wave = ExtremeWave(o_data_source, o_feature, 2, 2, False, 0, 0.1, 5)
    split_date = 20180101
    o_dl_model = dl_model.DLModel('%s_%u' % (o_wave.setting_name, split_date),
                                  o_feature.feature_unit_num,
                                  o_feature.feature_unit_size,
                                  32, 10240, 0.004, 'mean_absolute_tp0_max_ratio_error')
    if FLAGS.mode == 'data':
        o_data_source.DownloadData()
        o_data_source.UpdatePPData()
    elif FLAGS.mode == 'testall':
        o_wave.TradeTestAll()
    elif FLAGS.mode == 'test':
        o_wave.TradeTestStock(FLAGS.c, FLAGS.show)
    elif FLAGS.mode == 'show':
        o_wave.ShowTradePP(FLAGS.c)
    elif FLAGS.mode == 'train':
        tf, tl, vf, vl, td = o_wave.GetDataset(split_date)
        tl = tl * 100.0
        vl  = vl * 100.0
        o_dl_model.Train(tf, tl, vf, vl, FLAGS.epoch)
    elif FLAGS.mode == 'rtest':
        tf, tl, tf, tl, ta = o_wave.GetDataset(split_date)
        o_dl_model.LoadModel(FLAGS.epoch)
        o_wave.RTest(o_dl_model, tf, ta, False)

    exit()

if __name__ == "__main__":
    flags.DEFINE_string('mode', 'test', 'test | testall | train')
    flags.DEFINE_string('c', '000001.SZ', 'ts code')
    flags.DEFINE_integer('epoch', 100, 'train or rtest epoch')
    flags.DEFINE_boolean('show', False, 'show trade record')
    app.run(main)


#! /usr/bin/env python

import numpy as np
import json

from tqdm import tqdm
from typing import List, Dict, Tuple
from pathlib import Path

class InvalidEvaluationTypeError(Exception):

    def __init__(self, eval_type, message="Evaluation type is not in list [scale, goals]"):
        self.eval_type = eval_type
        self.message = message
        super().__init__(self.message)

    def __str__(self):
        return f'{self.eval_type} -> {self.message}'

class InvalidEvaluationMetricError(Exception):

    def __init__(self, metric, message="Chosen evaluation metric is not among the possibilities: miura, policy or time"):
        self.metric = metric
        self.message = message
        super().__init__(self.message)

    def __str__(self):
        return f'{self.metric} -> {self.message}'

class InvalidFrameworkError(Exception):

    def __init__(self, metric, message="Chosen framework choice is not available. Available options are: policy or miura"):
        self.metric = metric
        self.message = message
        super().__init__(self.message)

    def __str__(self):
        return f'{self.metric} -> {self.message}'

class TimeoutException(Exception):

    def __init__(self, max_time, message="Could not finish evaluation in under 2 hours."):
        self.max_time = max_time
        self.message = message
        super().__init__(self.message)

    def __str__(self):
        return f'{self.max_time} -> {self.message}'

def signal_handler(signum, frame):
    raise TimeoutException(7200)

def store_savepoint(file_path: Path, results: Dict, iteration: int) -> None:
    # Create JSON with save data
    save_data = dict()
    save_data['results'] = results
    save_data['iteration'] = iteration

    # Save data to file
    with open(file_path, 'w') as json_file:
        json.dump(save_data, json_file)

def load_savepoint(file_path: Path) -> Tuple[Dict, int]:
    json_file = open(file_path, 'r')
    data = json.load(json_file)

    return data['results'], data['iteration']

def value_iteration(mdp: Tuple[np.ndarray, List[str], Dict[str, np.ndarray], np.ndarray, float]) -> np.ndarray:
    X = mdp[0]
    A = mdp[1]
    P = mdp[2]
    c = mdp[3]
    gamma = mdp[4]

    nS = len(X)
    nA = len(A)

    J = np.zeros(nS)
    err = 1
    i = 0

    while err > 1e-8:

        Q = []
        for act in range(nA):
            Q += [c[:, act] + gamma * P[A[act]].dot(J)]

        Jnew = np.min(Q, axis=0)
        err = np.linalg.norm(J - Jnew)
        J = Jnew

        i += 1

    return J[:, None]

def policy_iteration(mdp: Tuple[np.ndarray, List[str], Dict[str, np.ndarray], np.ndarray, float]) -> (np.ndarray, np.ndarray):
    X = mdp[0]
    A = mdp[1]
    P = mdp[2]
    c = mdp[3]
    gamma = mdp[4]
    nX = len(X)
    nA = len(A)

    # Initialize pol
    pol = np.ones((nX, nA)) / nA

    # Initialize Q
    Q = np.zeros((nX, nA))

    quit = False
    i = 0

    while not quit:

        print('Iteration %d' % (i + 1), end='\r')

        J = mdp.evaluate_pol(pol)

        for act in range(nA):
            Q[:, act, None] = c[:, act, None] + gamma * P[A[act]].dot(J)

        Qmin = Q.max(axis=1, keepdims=True)
        polnew = np.isclose(Q, Qmin, atol=1e-10, rtol=1e-10).astype(int)
        polnew = polnew / polnew.sum(axis=1, keepdims=True)

        quit = (pol == polnew).all()
        pol = polnew
        i += 1

    print('N. iterations: ', i)

    return pol, Q

def trajectory(mdp: Tuple[np.ndarray, List[str], Dict[str, np.ndarray], np.ndarray, float], x0: str,
               pol: np.ndarray, goal_states: List[int]) -> (np.ndarray, np.ndarray):
    X = mdp[0]
    A = mdp[1]
    P = mdp[2]

    nX = len(X)
    nA = len(A)

    traj = [x0]
    actions = []
    x = list(X).index(x0)
    stop = False

    while not stop:
        a = np.random.choice(nA, p=pol[x, :])
        x = np.random.choice(nX, p=P[A[a]][x, :])

        traj += [X[x]]
        actions += [A[a]]

        stop = (x in goal_states)
        if stop:
            actions += [A[np.random.choice(nA, p=pol[x, :])]]

    return np.array(traj), np.array(actions)

def trajectory_reward(mdp: Tuple[np.ndarray, List[str], Dict[str, np.ndarray], np.ndarray, float], trajs: np.ndarray) -> float:
    r_avg = 0
    X = list(mdp[0])
    A = list(mdp[1])
    c = mdp[3]
    gamma = mdp[4]

    n_trajs = len(trajs)

    with tqdm(total=len(trajs)) as progress_bar:
        for traj in trajs:

            states = traj[0]
            actions = traj[1]
            r_traj = 0
            g = 1

            for j in range(len(actions)):
                x = states[j]
                a = actions[j]
                r_traj += g * c[X.index(x), A.index(a)]
                g *= gamma

            r_avg += r_traj / n_trajs
            progress_bar.update(1)

    return r_avg


#!/usr/bin/env python2.7
from __future__ import print_function
from icalendar import Calendar, Event
from datetime import datetime, timedelta
from time import strptime, strftime, mktime

""" See https://secure.wideworld-sports.me/wws_membership/PrintSchedule.asp?ID=1439
and https://secure.wideworld-sports.me/wws_membership/DivisionReport.asp?ID=1439

This could be improved to go read the schedule from the web page based
on season, team name, etc.  Or just copying-and-pasting the schedule
to a text file and using grep and stuff like this one does """

def writeICS(file, sched):

    location = "Wide World Sports, 2140 Oak Valley Dr, Ann Arbor, MI 48103"
    ical = Calendar()

    for m in sorted(sched):
        event=Event()
        event.add('summary', "Fairies Soccer on "+sched[m]['desc'])
        event.add('dtstart', sched[m]['starttime'])
        event.add('dtend', sched[m]['endtime'])
        event.add('location', location)

        ical.add_component(event)

    # write out our calendar to a nicely formatted .ics file
    f = open(file,"wb")
    f.write(ical.to_ical(ical))
    f.close

if __name__ == '__main__':
    FILE="./ff"  # hopefully there is a file called 'ff' formated like:
    # 1/14/2017	Sat 	1:30 PM	Big Georges Field	Fairies	 	WWSC 8-9 Portugal
    # with tabs separating the items

    with open (FILE, "rb") as f:
        a=f.readlines()

    a = [b.strip('\n') for b in a]

    game = dict()
    for evt in a:
        # break up the line on tabs
        line = evt.split('\t')
        # cope with the date and time
        ds = strftime('%Y-%m-%dT%H:%M',
                      strptime(line[0]+" "+line[2],
                                        "%m/%d/%Y %I:%M %p"))
        # make a datetime object so icalendar.event.add works
        dss = datetime.fromtimestamp(
            mktime(strptime(line[0]+" "+line[2],
                            "%m/%d/%Y %I:%M %p")))
        # make the duration for the end time
        dse = dss + timedelta(hours=1)
        # make the game details (start, end, description)
        game[ds] = dict()
        game[ds]['desc'] = "{}: {} vs {}".format(
            line[3],
            line[4],
            line[6])
        game[ds]['starttime'] = dss
        game[ds]['endtime'] = dse

    # print a nice schedule to the screen
    for d in sorted(game):
        print ("{} -  {}".format(d, game[d]['desc']))

    # write the ICS file for importing into a calendar program
    writeICS("FairiesWinter2017Schedule.ics", game)


from copy import deepcopy
import logging
import os

from flamingo.core.errors import MultipleObjectsReturned, ObjectDoesNotExist
from flamingo.core.data_model import Content, Q
from flamingo.core.utils.string import slugify

logger = logging.getLogger('flamingo.plugins.Menu')

def is_active(section, menu, content):
    def _contains(menu, content):
        for i in menu:
            if i is content:
                return True

            if isinstance(i, (list, tuple, )):
                if _contains(i, content):
                    return True

        return False

    if isinstance(section, Section) and section.content is content:
        return True

    if (isinstance(section, Section) and
       isinstance(content['menu_path'], list) and
       section in content['menu_path']):

        return True

    if isinstance(menu, Content):
        return menu is content

    return _contains(menu, content)

def is_dict(v):
    return isinstance(v, dict)

def is_list(v):
    return isinstance(v, list)

class Section:
    def __init__(self, name, url=''):
        self.name = name
        self.url = url or slugify(self.name)
        self.content = None

    def __str__(self):
        return self.name

    def __repr__(self):
        return "<Section('{}', url='{}')>".format(self.name, self.url)

class Menu:
    THEME_PATHS = [
        os.path.join(os.path.dirname(__file__), 'theme'),
    ]

    def templating_engine_setup(self, context, templating_engine):
        templating_engine.env.globals['is_active'] = is_active
        templating_engine.env.globals['is_dict'] = is_dict
        templating_engine.env.globals['is_list'] = is_list

    def contents_parsed(self, context):
        create_indices = context.settings.get('MENU_CREATE_INDICES', False)

        index_template = context.settings.get(
            'MENU_INDEX_TEMPLATE', 'menu/index.html')

        if not hasattr(context.settings, 'MENU'):
            context.settings.MENU = {
                'main': [],
            }

        self.menu = deepcopy(context.settings.MENU)

        def resolve_links(menu):
            for item in menu:
                section_args, url = item

                if isinstance(url, list):
                    # setup section
                    if not isinstance(section_args, (list, tuple)):
                        section_args = [section_args]

                    if not isinstance(item[0], Section):
                        item[0] = Section(*section_args)

                    resolve_links(url)

                else:
                    logger.debug('resolving %s', item[1])

                    try:
                        if isinstance(item[1], (Content, Section, )):
                            logger.debug('resolving skipped')

                            return

                        if isinstance(item[1], str):
                            lookup = Q(path=item[1])

                        elif not isinstance(item[1], Q):
                            lookup = Q(item[1])

                        else:
                            lookup = item[1]

                        item[1] = context.contents.get(lookup)

                        logger.debug('%s -> %s', lookup, item[1])

                    except ObjectDoesNotExist:
                        logger.error(
                            "no content with %s %s found",
                            'path' if isinstance(lookup, str) else 'lookup',
                            lookup or repr(lookup),
                        )

                    except MultipleObjectsReturned:
                        logger.error(
                            "multiple contents found with %s %s found",
                            'path' if isinstance(lookup, str) else 'lookup',
                            lookup or repr(lookup),
                        )

        # setup menus
        if isinstance(self.menu, list):
            self.menu = {
                'main': self.menu,
            }

        elif 'main' not in self.menu:
            self.menu['main'] = []

        # resolve links
        for menu_name, menu in self.menu.items():
            resolve_links(menu)

        # create section indices
        def create_section_indices(menu, path):
            current_section = None

            def gen_content(menu, path):
                url = '/'

                for section in path + [current_section]:
                    url = os.path.join(url, section.url)

                url = os.path.join(url, 'index.html')

                content = Content(
                    type='menu/index',
                    title=current_section.name,
                    url=url,
                    output=url[1:],
                    menu=menu,
                    template=index_template,
                    menu_path=path,
                )

                context.contents.add(content)
                current_section.content = content

            for item in menu:
                if isinstance(item, Section):
                    current_section = item

                    gen_content(menu[1:], path)

                elif isinstance(item, Content):
                    item['menu_path'] = path

                elif isinstance(item, (list, tuple)):
                    if current_section:
                        create_section_indices(item, path+[current_section])

                    else:
                        create_section_indices(item, path)

        if create_indices:
            for menu_name, menu in self.menu.items():
                create_section_indices(menu, path=[])


"""Обновлении таблицы успешных заказов

Revision ID: 1d213c402d10
Revises: de9fdb3b95c9
Create Date: 2021-03-24 22:51:53.974240

"""
from alembic import op
import sqlalchemy as sa

# revision identifiers, used by Alembic.
revision = '1d213c402d10'
down_revision = 'de9fdb3b95c9'
branch_labels = None
depends_on = None

def upgrade():
    # ### commands auto generated by Alembic - please adjust! ###
    op.add_column('completed_orders', sa.Column('general_complete_time', sa.DateTime(), nullable=True))
    op.add_column('completed_orders', sa.Column('region', sa.Integer(), nullable=True))
    # ### end Alembic commands ###

def downgrade():
    # ### commands auto generated by Alembic - please adjust! ###
    op.drop_column('completed_orders', 'region')
    op.drop_column('completed_orders', 'general_complete_time')
    # ### end Alembic commands ###

migrations/versions/1d213c402d10_обновлении_таблицы_успешных_заказов.py


# -*- coding: utf-8 -*-
""" Installer for the energy.content package.
"""
from os.path import join
from setuptools import find_packages
from setuptools import setup

NAME = 'energy.content'
PATH = ['src'] + NAME.split('.') + ['version.txt']
VERSION = open(join(*PATH)).read().strip()

long_description = '\n\n'.join([
    open('README.rst').read(),
    open('CONTRIBUTORS.rst').read(),
    open(join("docs", "HISTORY.txt")).read(),
])

setup(
    name=NAME,
    version=VERSION,
    description="EnergyUnion extensions for Plone",
    long_description_content_type="text/x-rst",
    long_description=long_description,
    # Get more from https://pypi.org/classifiers/
    classifiers=[
        "Environment :: Web Environment",
        "Framework :: Plone",
        "Framework :: Plone :: Addon",
        "Framework :: Plone :: 5.1",
        "Programming Language :: Python",
        "Programming Language :: Python :: 2.7",
        "Operating System :: OS Independent",
        "License :: OSI Approved :: GNU General Public License v2 (GPLv2)",
    ],
    keywords='Python Plone',
    author='Tiberiu Ichim',
    author_email='tiberiu.ichim@eaudeweb.ro',
    url='https://github.com/collective/energy.content',
    project_urls={
        'PyPI': 'https://pypi.python.org/pypi/energy.content',
        'Source': 'https://github.com/collective/energy.content',
        'Tracker': 'https://github.com/collective/energy.content/issues',
        # 'Documentation': 'https://energy.content.readthedocs.io/en/latest/',
    },
    license='GPL version 2',
    packages=find_packages('src', exclude=['ez_setup']),
    namespace_packages=['energy'],
    package_dir={'': 'src'},
    include_package_data=True,
    zip_safe=False,
    install_requires=[
        'setuptools',
        # -*- Extra requirements: -*-
        'z3c.jbot',
        'plone.api>=1.8.4',
        'plone.restapi',
        'plone.app.dexterity',
        'collective.monkeypatcher',
    ],
    extras_require={
        'test': [
            'plone.app.testing',
            'plone.testing',
            'plone.app.contenttypes',
            'plone.app.robotframework[debug]',
        ],
    },
    entry_points="""
    [z3c.autoinclude.plugin]
    target = plone
    [console_scripts]
    update_locale = energy.content.locales.update:update_locale
    """,
)


from django import forms
from .models import ReflectIssues, ReflectContents, ReflectProblem

# class ReflectIssues...で使う

class ReflectIssuesForm(forms.ModelForm):
    class Meta:
        model = ReflectIssues
        fields = ('issues',)
        labels = {'issues': '論点'}

class ReflectContentsForm(forms.ModelForm):
    class Meta:
        model = ReflectContents
        fields = ('ref_issues', 'comment_type', 'comment_content')
        labels = {'ref_issues': '参照論点', 'comment_type': 'コメントタイプ', 'comment_content': 'コメント内容'}

class ReflectProblemForm(forms.ModelForm):
    class Meta:
        model = ReflectProblem
        fields = ('problem',)
        labels = {'problem': '問題点'}


import pytest

from src.entities import Room, Map, UndirectedGraph

@pytest.mark.parametrize("room, expected", [
    ({"id": 1, "name": "Hallway", "north": 2, "east": 7, "objects": []}, {2, 7}),
    ({"id": 7, "name": "Living room", "west": 1, "north": 4, "objects": []}, {1, 4}),
    ({"id": 5, "name": "Bedroom", "south": 2, "east": 6, "objects": [{"name": "Pillow"}]}, {2, 6})
])
def test_room_returns_linked_rooms(room, expected):
    r = Room(**room)
    assert r.get_linked_rooms() == expected

@pytest.mark.parametrize("map, id, expected", [
    (
        {
            "rooms": [
                {"id": 1, "name": "Hallway", "north": 2, "east": 7, "objects": []},
                {"id": 2, "name": "Dining Room", "north": 5, "south": 1, "west": 3, "east": 4, "objects": []},
                {"id": 3, "name": "Kitchen", "east": 2, "objects": [{"name": "Knife"}]},
                {"id": 4, "name": "Sun Room", "west": 2, "north": 6, "south": 7, "objects": []},
                {"id": 5, "name": "Bedroom", "south": 2, "east": 6, "objects": [{"name": "Pillow"}]},
                {"id": 6, "name": "Bathroom", "west": 5, "south": 4, "objects": []},
                {"id": 7, "name": "Living room", "west": 1, "north": 4, "objects": [{"name": "Potted Plant"}]}
            ]
        },
        6,
        {"id": 6, "name": "Bathroom", "west": 5, "south": 4, "objects": []}
    ),
    (
        {
            "rooms": [
                {"id": 1, "name": "Hallway", "north": 2, "east": 7, "objects": []},
                {"id": 2, "name": "Dining Room", "north": 5, "south": 1, "west": 3, "east": 4, "objects": []},
                {"id": 3, "name": "Kitchen", "east": 2, "objects": [{"name": "Knife"}]},
            ]
        },
        2,
        {"id": 2, "name": "Dining Room", "north": 5, "south": 1, "west": 3, "east": 4, "objects": []}
    ),
])
def test_map_returns_room_by_id(map, id, expected):
    m = Map(**map)
    assert m.get_room(id) == Room(**expected)

@pytest.mark.parametrize("v, neighbours", [
    (1, (2, 5, 7)),
    (0, (1,)),
])
def test_graph_set_neighbours(v, neighbours):
    graph = UndirectedGraph()
    graph.add_neighbours(v, neighbours)
    assert graph.schema_.get(v) == neighbours

@pytest.mark.parametrize("v, neighbours", [
    (1, (2, 5, 7)),
    (0, (1,)),
])
def test_graph_get_neighbours(v, neighbours):
    graph = UndirectedGraph()
    graph.schema_.update({v: neighbours})
    assert graph.get_neighbours(v) == neighbours


import tkinter as tk
import consulta as c
import push
import slack_mensage
import time
from datetime import datetime

root = tk.Tk()

root.geometry('600x200')
root.title("Monitor Maestro")
root.iconbitmap('equiplano-logo-vertical.ico')

sec = None
consulta = c.Consulta()
def tick():
    global sec
    global respostas

    hora = datetime.now().strftime('%H:%M:%S')

    if sec == None or sec == 0:

        sec = int(inicio.get())*60

    if hora in ['07:00:00', '12:00:00', '17:00:00']:
        print(hora)
        slack_mensage.mensage_slack('Olá ... fiquem tranquilos ... estou monitorando o Maestro de Toledo ... :white_check_mark:')

    if sec == 1:
        time['text'] = 'Consultando...'
        root.update()
        sec = 0
        if sec == 0:
            msg = consulta.login()
            print(msg)

            if msg == 'Maestro pode estar parado.':
                erro['text'] = msg
                push.push()
                root.update()
            else:
                resposta['text'] = msg
                root.update()

            time['text'] = int(inicio.get())
            root.update()
            tick()
    else:
        sec = sec - 1
        relogio = int(sec/60)
        if sec%2:
            t = '. . .'
        else: t = ' . . '
        if relogio > 1:
            time['text'] = 'A próxima consulta será realizada em menos de '+ str(relogio+1) + ' minutos ' + t
        elif relogio == 1:
            time['text'] = 'A próxima consulta será realizada em menos de ' + str(relogio+1) + ' minuto ' + t
        else:
            time['text'] = 'Restam ' + str(sec) + ' segundos para próxima consulta.'
        time.after(1000, tick)

    return sec

label = tk.Label(root, text="Tempo de verificação no Maestro")
label.pack()
inicio = tk.Entry(root, textvariable=0)
inicio.pack()
time = tk.Label(root, fg='green')
time.pack()
resposta = tk.Label(root, fg='blue')
resposta.pack()
erro = tk.Label(root, fg='red')
erro.pack()
tk.Button(root, fg='blue', text='Start', command=tick, state='normal').pack()

root.update()
root.mainloop()

tick()

#pyinstaller --onefile -n MaestroMonitoring --noconsole --icon=equiplano-logo-vertical.ico main.py


# -*- coding: utf-8 -*-

import pytest
import ZConfig
import transaction

from collections import OrderedDict

from ZODB import DB
from ZODB.DemoStorage import DemoStorage
from cromlech.zodb.utils import eval_loader, init_db
from cromlech.zodb.utils import initialize_applications

from ..testing import DummySite, MyApp, SimpleApp

def test_eval_loader():
    assert eval_loader('cromlech.zodb.utils:eval_loader') is eval_loader
    assert (eval_loader('cromlech.zodb.tests.fixture:Foo').__doc__ ==
            "class to test eval_loader")
    with pytest.raises(RuntimeError):
        eval_loader(':foo')
    with pytest.raises(ImportError):
        # module does not exists
        eval_loader('cromlech.zodb.doesnotexiste:id')
    with pytest.raises(ImportError):
        # object inside module does not exists
        eval_loader('cromlech.zodb.tests.fixture:Bar')

foo = object()

def add_foo(db):
    tm = transaction.TransactionManager()
    conn = db.open(tm)
    conn.root()['foo'] = foo
    tm.get().commit()
    conn.close()

def test_init_db():
    configuration = """
        <zodb>
        <demostorage>
        </demostorage>
        </zodb>"""
    db = init_db(configuration, add_foo)
    conn = db.open()
    assert conn.root()['foo'] is foo

def test_init_db_bad_conf():
    configuration = """
        <zodb>
            <UNKNOWN_storage>
            </UNKNOWN_storage>
        </zodb>"""
    with pytest.raises(ZConfig.ConfigurationSyntaxError):
        init_db(configuration, add_foo)

def test_initialize_applications():

    def apps():
        return {'mine':MyApp, 'app': SimpleApp, 'app2': SimpleApp,
                'obj':tuple}

    def failing_apps():
        return OrderedDict((('foo', SimpleApp), ('spam', lambda: 1/0)))

    db = DB(DemoStorage())
    initialize_applications(db, apps)
    conn = db.open()
    root = conn.root()
    assert root['mine']() == b"running !"
    assert root['app']() == b"simply running !"
    assert root['app2']() == b"simply running !"
    assert isinstance(root['obj'], tuple)
    transaction.abort()
    conn.close()

    # verify it's all or nothing
    try:
        initialize_applications(db, failing_apps)
    except ZeroDivisionError:
        pass
    conn = db.open()
    root = conn.root()
    assert 'foo' not in root
    conn.close()


import logging
import textwrap
from abc import abstractmethod
from copy import copy
from typing import Any, Iterable, List, Optional

import numpy as np
from scipy.stats import truncnorm

import popart
from pingpong.scope_manager import Scope

def normal_init_data(dtype, shape, mean, std_dev):
    # Truncated random normal between 2 standard devations
    data = truncnorm.rvs(-2, 2, loc=mean, scale=std_dev, size=np.prod(shape))
    data = data.reshape(shape).astype(dtype)
    return data

logger = logging.getLogger(__name__)

class Parameter:
    def __init__(self,
                 name: str,
                 shape: tuple,
                 value: Optional[np.ndarray] = None,
                 popart_tensor: Optional[str] = None):
        self.name = name
        self.shape = shape
        self.value = value
        self.popart_tensor = popart_tensor
        self.vgid = None

def flatten(l):
    for el in l:
        if isinstance(el, Iterable) and not isinstance(el, (str, bytes)):
            yield from flatten(el)
        else:
            yield el

class Block:
    """Base class for popart layers."""

    def __init__(self,
                 scope: Scope,
                 params: List[Parameter] = [],
                 dtype: np.dtype = np.float16,
                 builder=None,
                 initializers=None,
                 scope_provider=None):

        self.scope = scope
        self._params = params
        self._dtype = dtype
        self.num_params = 0
        self.total_params = None
        self.line_length = 98
        self.sub_blocks = []
        if builder is None:
            raise ValueError('Builder must be passed in as kwarg.')
        if scope_provider is None:
            raise ValueError('ScopeProvider must be passed in as kwarg.')
        self._builder = builder
        self.scope_provider = scope_provider
        self.initializers = {} if initializers is None else initializers

    def __setattr__(self, name: str, value: Any) -> None:
        if isinstance(value, Block):
            self.sub_blocks.append(value)

        elif isinstance(value, Iterable):
            for el in flatten(value):
                if isinstance(el, Block):
                    self.sub_blocks.append(el)

        super(Block, self).__setattr__(name, value)

    @property
    def builder(self):
        return self._builder

    @builder.setter
    def builder(self, _):
        raise ValueError('Cannot set builder property outside of Block class.')

    def format_row(self, fields, indent=False):
        positions = [int(self.line_length * p) for p in [.45, .7, .8, 1.]]
        line = ''
        if indent:
            fields[0] = '    ' + fields[0]
        for i in range(len(fields)):
            if i > 0:
                line = line[:-1] + ' '
            line += str(fields[i])
            line = line[:positions[i]]
            line += ' ' * (positions[i] - len(line))
        return line

    def __repr__(self):
        name = self.scope.name
        cls_name = self.__class__.__name__
        pp_phase = self.scope.execution_phase if hasattr(
            self.scope, 'execution_phase') else None
        fields = [
            name + ' (' + cls_name + ')', pp_phase, self.scope.vgid,
            f'{self.count_params():,}'.rjust(10)
        ]
        s = self.format_row(fields)

        if len(self.sub_blocks) > 1:
            modstr = "\n".join([
                "{block}".format(block=block.__repr__())
                for block in self.sub_blocks
            ])
            s = "\n".join([s, modstr])
        return s

    def summary(self):
        header = ['Layer (type)', 'Pingpong Phase', 'VGID', 'Param #']
        print(self.format_row(header))
        print('_' * self.line_length)
        total_params = 0
        for blks in self.sub_blocks:
            print(blks)
            total_params += blks.count_params()

        print('Total params: {:,}'.format(total_params))

    def count_params(self):
        if self.total_params is not None:
            return self.total_params
        child_params = 0
        for item in self.sub_blocks:
            child_params += item.count_params()
        self.total_params = child_params + self.num_params
        return self.total_params

    def __create_params__(self):
        # Create params only for a single block - not recursive
        for param in self._params:
            if param.popart_tensor is None:
                data = self.initializers.get(param.name, None)
                if isinstance(data, np.ndarray):
                    if data.dtype != self._dtype:
                        raise ValueError(
                            f"Type of {param.name} does not match value provided. \n"
                            f"Provided {data.dtype}. Required {self._dtype}")
                    if np.any(data.shape != np.array(param.shape)):
                        if np.all(data.T.shape == np.array(param.shape)):
                            data = data.T.copy()
                            logger.warn(
                                f"Initializer for {param.name} was provided transposed."
                            )
                        else:
                            raise RuntimeError(
                                f"Initializer {param.name} does not match shapes. \n"
                                f" Provided {data.shape}. Required {param.shape}")
                    param.value = data
                else:
                    param.value = normal_init_data(self._dtype,
                                                   param.shape,
                                                   mean=0,
                                                   std_dev=1)

                popart_tensor = self._builder.addInitializedInputTensor(
                    param.value, param.name)
                self.num_params += np.prod(param.value.shape)
                param.vgid = self.scope.vgid

            else:
                if param.vgid != self.scope.vgid:
                    raise RuntimeError(
                        'Shared parameter {} appears in different virtual graphs.' .format(
                            param.name))
                # Transpose shared weights
                if (self.builder.getTensorShape(param.popart_tensor) == reversed(param.shape)):
                    popart_tensor = self._builder.aiOnnx.transpose([param.popart_tensor])
                else:
                    popart_tensor = param.popart_tensor
                # Create copy of shared param so as to not modify
                # the param for the previous layer
                param = copy(param)

            param.popart_tensor = popart_tensor

    @property
    def params(self):
        """Return this Block's parameter dictionary, not recursive.

        Returns:
            Dict: List of parameters for this block.
        """
        return self._params

    @params.setter
    def params(self, value):
        self._params = value

    def next_phase(self):
        return self.scope_provider.get_next_phase()

    def total_phases(self):
        return self.scope_provider.get_prev_phase() + 1

    def __call__(self, *args):
        """Calls forward. Only accepts positional arguments."""
        with self.scope_provider(self._builder, self.scope):
            self.__create_params__()
            return self.forward(*args)

    @abstractmethod
    def forward(self, *args):
        raise NotImplementedError


"""Scrape data for all symbols in data/symbols/*.json

Called from the command line as:
python scrape_symbols.py <exchange> [start-symbol]
"""

import json
import sys
import argparse
import time
import requests
import getquote as getquote
from dbhandler import DbHandler

if __name__ == "__main__":
    # Start a timer for performance monitoring
    start_time = time.perf_counter()

    parser = argparse.ArgumentParser(description="Scrape symbols from the TSX or TSXV.")
    parser.add_argument(
        "exchange", choices=["TSX", "TSXV"], help="exchange from which to scrape. TSX or TSXV."
    )
    parser.add_argument(
        "-t",
        "--time",
        type=int,
        help="Time in seconds between network calls. To avoid getting blocked.",
    )
    group = parser.add_mutually_exclusive_group()
    group.add_argument("-s", "--start", help="symbol from which to start scraping")
    group.add_argument(
        "-r", "--range", nargs=2, help="first and last symbol of the range to scrape"
    )
    args = parser.parse_args()

    all_symbols = []
    exchange = args.exchange

    # Read the symbol list for the chosen exchange
    if exchange == "TSX":
        with open("data/symbols/TSX.json", "r") as infile:
            all_symbols.extend(json.load(infile))
    else:
        with open("data/symbols/TSXV.json", "r") as infile:
            all_symbols.extend(json.load(infile))

    if args.time:
        waittime = args.time
    else:
        waittime = 0

    # If we specified a start or a range, trim the symbol list
    if args.start:
        all_symbols = [x for x in all_symbols if x >= args.start]
    elif args.range:
        all_symbols = [x for x in all_symbols if x >= args.range[0] and x <= args.range[1]]

    # Uncomment to test parallel process launch
    # from random import randint
    # from time import sleep
    # i = randint(0, 5)
    # while i > 0:
    #     print(i)
    #     i = i - 1

    print(
        f"Preparing to scrape symbols from {all_symbols[0]} to {all_symbols[-1]} ({len(all_symbols)} symbols) on {exchange}"
    )

    s = requests.Session()
    db_handler = DbHandler()
    conn = db_handler.create_connection()
    suspended = json.load(open("data/symbols/suspended.json", "r"))

    for symbol in all_symbols:
        try:
            getquote.get_quote(s, conn, symbol, suspended)
        except Exception as e:
            print(e)
            continue
        # Sleep between each call
        time.sleep(waittime)

    end_time = time.perf_counter()
    total_time = int(round(end_time - start_time, 0))
    print(
        f"Finished. Scraped from {all_symbols[0]} to {all_symbols[-1]} ({len(all_symbols)} symbols) on {exchange} in {total_time} s"
    )


#!/usr/bin/env python

from google.appengine.ext.webapp import template
from google.appengine.ext import ndb

import logging
import os.path
import webapp2
import json

from webapp2_extras import auth
from webapp2_extras import sessions

from webapp2_extras.auth import InvalidAuthIdError
from webapp2_extras.auth import InvalidPasswordError

class AccessException(Exception):
  def __init__(self, value):
    self.value = value
  def __str__(self):
    return repr(self.value)

def user_required(handler):
  """
    Decorator that checks if there's a user associated with the current session.
    Will also fail if there's no session present.
    Remember that we are usually decorating a subclass of BaseHandler
    If you try to access a user from a BaseHandler, without this decorator -> no go.
    If you try to post to a BaseHandler, decorated thusly, without an auth cookie, you will get a redirect
  """
  def check_login(self, *args, **kwargs):
    auth = self.auth
    if not auth.get_user_by_session():
      logging.warn("Permission denied.")
      # todo: this should return some json failure
      #self.redirect(self.uri_for('login'), abort=True)

      self.addAccessHeaders()
      self.response.status = 403
      response = {"status": "fail", "data": { "title": "Permission denied." } }

      self.response.out.write(json.dumps(response) + "\n\n")
    else:
      logging.info("Permission granted.")
      return handler(self, *args, **kwargs)

  return check_login

class BaseHandler(webapp2.RequestHandler):

  def addAccessHeaders(self):
    '''Add headers needed for access control'''
    self.response.headers['Content-Type'] = "application/json"

    # you have to provide this header eg. Origin: http://localhost:8080, which is added automatically by a browser
    # browsers tend to be picky about seeing a wildcard origin
    if 'Origin' in self.request.headers:
      logging.info("Origin: " + self.request.headers['Origin'])
      # todo: we need a list here
      origin = self.request.headers['Origin']
      if origin.startswith('http://localhost') or origin.startswith('https://localhost') or origin.startswith('https://stratweb1.appspot.com'):
        self.response.headers['Access-Control-Allow-Credentials'] = 'true'
        self.response.headers['Access-Control-Allow-Origin'] = origin

  def options(self,stratfileId=0,themeId=0):
    '''Convenience method to add all the required headers, when backbone requests OPTIONS'''
    logging.debug("Returning options")
    self.response.headers['Access-Control-Request-Method'] = "*"
    self.response.headers['Access-Control-Allow-Methods'] = 'GET,PUT,POST,DELETE,OPTIONS'
    self.response.headers['Access-Control-Allow-Headers'] = '*,x-requested-with,Content-Type'
    self.response.headers["Access-Control-Max-Age"] = '1728000'
    self.addAccessHeaders()

  @webapp2.cached_property
  def auth(self):
    """Shortcut to access the auth instance as a property."""
    # http://webapp-improved.appspot.com/api/webapp2_extras/auth.html#api-webapp2-extras-auth
    return auth.get_auth()

  @webapp2.cached_property
  def user_info(self):
    """Shortcut to access a subset of the user attributes that are stored
    in the session.

    The list of attributes to store in the session is specified in
      config['webapp2_extras.auth']['user_attributes'].
    :returns
      A dictionary with most user information
    """
    return self.auth.get_user_by_session()

  @webapp2.cached_property
  def user(self):
    """Shortcut to access the current logged in user.

    Unlike user_info, it fetches information from the persistence layer and
    returns an instance of the underlying model.

    :returns
      The instance of the user model associated to the logged in user.
    """
    u = self.user_info
    return self.user_model.get_by_id(u['user_id']) if u else None

  @webapp2.cached_property
  def user_model(self):
    """Returns the implementation of the user model.

    It is consistent with config['webapp2_extras.auth']['user_model'], if set.
    """
    return self.auth.store.user_model

  @webapp2.cached_property
  def session(self):
      """Shortcut to access the current session."""
      return self.session_store.get_session(backend="datastore")

  # this is needed for webapp2 sessions to work
  def dispatch(self):
      # Get a session store for this request.
      self.session_store = sessions.get_store(request=self.request)

      try:
          # Dispatch the request.
          webapp2.RequestHandler.dispatch(self)
      finally:
          # Save all sessions.
          self.session_store.save_sessions(self.response)


#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import logging
import os
import sys

from core.crawl.crawler import Crawler
from core.lib.utils import *
from core.scan.scanner import Scanner
from core.util.util import Util

def split_argv(argv):
    argvs = []
    cur = 0
    for a in argv:
        if a == ";":
            cur += 1
            continue
        if len(argvs) == cur:
            argvs.append([])
        argvs[cur].append(a)
    return argvs

def usage():
    infos = get_program_infos()
    print((
        "eye1c ver " + infos['version'] + "\n"
        "usage: eye1c <command>\n"
        "commands are chainable using '\\;' and they share the same database\n"
        "  ex: eye1c crawl http://loadlhost:80/ tmp.db \\;"
        "Commands: \n"
        "  crawl                  run crawler\n"
        "  scan                   run scanner\n"
        "  util                   run utility\n"))

if __name__ == '__main__':
    if not os.path.exists("./log/"):
        os.makedirs("./log/")
    logging.basicConfig(format='%(name)s|%(asctime)s :%(message)s',
                        level=logging.DEBUG,
                        datefmt='%m/%d/%Y %I:%M:%S %p',
                        filename='./log/app.log',
                        filemode='w+')
    logging.getLogger("requests").setLevel(logging.CRITICAL)
    logging.getLogger("urllib3.connectionpool").setLevel(logging.CRITICAL)
    logging.getLogger("urllib3.util.retry").setLevel(logging.CRITICAL)
    log = logging.Logger('eye1c')

    logging.debug("python args:%s" % " ".join(sys.argv))

    if len(sys.argv) < 2:
        usage()
        sys.exit(0)

    argvs = split_argv(sys.argv[1:])
    for argv in argvs:
        if argv[0] not in ('crawl', 'scan', 'util'):
            print("Command not found: %s" % argv[0])
            sys.exit(1)
    cr = None
    sc = None
    for argv in argvs:

        if argv[0] == "crawl":
            cr = Crawler(argv[1:])
        elif argv[0] == "scan":
            if sc:
                dbfile = sc.db_file
            else:
                dbfile = cr.db_file if cr else None
            sc = Scanner(argv[1:], dbfile)
        elif argv[0] == "util":
            dbfile = cr.db_file if cr else (sc.db_file if sc else None)
            Util(argv[1:], dbfile)
    sys.exit(0)


import dataclasses
import functools
from typing import Callable, Optional

from acme import specs
from acme.agents.jax.mbop import models
from acme.jax import networks
import jax
from jax import random
import jax.numpy as jnp

# Function that takes (n_trajectories, horizon, action_dim) tensor of action
# trajectories and  (n_trajectories) vector of corresponding cumulative rewards,
# i.e. returns, for each trajectory as input and returns a single action
# trajectory.
ActionAggregationFn = Callable[[jnp.ndarray, jnp.ndarray], jnp.ndarray]

def return_weighted_average(action_trajectories: jnp.ndarray,
                            cum_reward: jnp.ndarray,
                            kappa: float) -> jnp.ndarray:
  r"""Calculates return-weighted average over all trajectories.

  This will calculate the return-weighted average over a set of trajectories as
  defined on l.17 of Alg. 2 in the MBOP paper:
  [https://arxiv.org/abs/2008.05556].

  Note: Clipping will be performed for `cum_reward` values > 80 to avoid NaNs.

  Args:
    action_trajectories: (n_trajectories, horizon, action_dim) tensor of action
      trajectories, corresponds to `A` in Alg. 2.
    cum_reward: (n_trajectories) vector of corresponding cumulative rewards
      (returns) for each trajectory. Corresponds to `\mathcal{R}` in Alg. 2.
    kappa: `\kappa` constant, changes the 'peakiness' of the exponential
      averaging.

  Returns:
    Single action trajectory corresponding to the return-weighted average of the
      trajectories.
  """
  # Substract maximum reward to avoid NaNs:
  cum_reward = cum_reward - cum_reward.max()
  # Remove the batch dimension of cum_reward allows for an implicit broadcast in
  # jnp.average:
  exp_cum_reward = jnp.exp(kappa * jnp.squeeze(cum_reward))
  return jnp.average(action_trajectories, weights=exp_cum_reward, axis=0)

def return_top_k_average(action_trajectories: jnp.ndarray,
                         cum_reward: jnp.ndarray,
                         k: int = 10) -> jnp.ndarray:
  r"""Calculates the top-k average over all trajectories.

  This will calculate the top-k average over a set of trajectories as
  defined in the POIR Paper:

  Note: top-k average is more numerically stable than the weighted average.

  Args:
    action_trajectories: (n_trajectories, horizon, action_dim) tensor of action
      trajectories.
    cum_reward: (n_trajectories) vector of corresponding cumulative rewards
      (returns) for each trajectory.
    k: the number of trajectories to average.

  Returns:
    Single action trajectory corresponding to the average of the k best
      trajectories.
  """
  top_k_trajectories = action_trajectories[jnp.argsort(
      jnp.squeeze(cum_reward))[-int(k):]]
  return jnp.mean(top_k_trajectories, axis=0)

@dataclasses.dataclass
class MPPIConfig:
  """Config dataclass for MPPI-style planning, used in mppi.py.

  These variables correspond to different parameters of `MBOP-Trajopt` as
  defined in MBOP [https://arxiv.org/abs/2008.05556] (Alg. 2).

  Attributes:
    sigma: Variance of action-additive noise.
    beta: Mixture parameter between old trajectory and new action.
    horizon: Planning horizon, corresponds to H in Alg. 2 line 8.
    n_trajectories: Number of trajectories used in `mppi_planner` to sample the
      best action. Corresponds to `N` in Alg. 2 line. 5.
    previous_trajectory_clip: Value to clip the previous_trajectory's actions
      to. Disabled if None.
    action_aggregation_fn: Function that aggregates action trajectories and
      returns a single action trajectory.
  """
  sigma: float = 0.8
  beta: float = 0.2
  horizon: int = 15
  n_trajectories: int = 1000
  previous_trajectory_clip: Optional[float] = None
  action_aggregation_fn: ActionAggregationFn = (
      functools.partial(return_weighted_average, kappa=0.5))

def get_initial_trajectory(config: MPPIConfig, env_spec: specs.EnvironmentSpec):
  """Returns the initial empty trajectory `T_0`."""
  return jnp.zeros((max(1, config.horizon),) + env_spec.actions.shape)

def _repeat_n(new_batch: int, data: jnp.ndarray) -> jnp.ndarray:
  """Create new batch dimension of size `new_batch` by repeating `data`."""
  return jnp.broadcast_to(data, (new_batch,) + data.shape)

def mppi_planner(
    config: MPPIConfig,
    world_model: models.WorldModel,
    policy_prior: models.PolicyPrior,
    n_step_return: models.NStepReturn,
    world_model_params: networks.Params,
    policy_prior_params: networks.Params,
    n_step_return_params: networks.Params,
    random_key: networks.PRNGKey,
    observation: networks.Observation,
    previous_trajectory: jnp.ndarray,
) -> jnp.ndarray:
  """MPPI-extended trajectory optimizer.

  This implements the trajectory optimizer described in MBOP
  [https://arxiv.org/abs/2008.05556] (Alg. 2) which is an extended version of
  MPPI that adds support for arbitrary sampling distributions and extends the
  return horizon using an approximate model of returns.  There are a couple
  notation changes for readability:
  A -> action_trajectories
  T -> action_trajectory

  If the horizon is set to 0, the planner will simply call the policy_prior
  and average the action over the ensemble heads.

  Args:
    config: Base configuration parameters of MPPI.
    world_model: Corresponds to `f_m(s_t, a_t)_s` in Alg. 2.
    policy_prior: Corresponds to `f_b(s_t, a_tm1)` in Alg. 2.
    n_step_return: Corresponds to `f_R(s_t, a_t)` in Alg. 2.
    world_model_params: Parameters for world model.
    policy_prior_params: Parameters for policy prior.
    n_step_return_params: Parameters for n_step return.
    random_key: JAX random key seed.
    observation: Normalized current observation from the environment, `s` in
      Alg. 2.
    previous_trajectory: Normalized previous action trajectory. `T` in Alg 2.
      Shape is [n_trajectories, horizon, action_dims].

  Returns:
    jnp.ndarray: Average action trajectory of shape [horizon, action_dims].
  """
  action_trajectory_tm1 = previous_trajectory
  policy_prior_state = policy_prior.init(random_key)

  # Broadcast so that we have n_trajectories copies of each:
  observation_t = jax.tree_map(
      functools.partial(_repeat_n, config.n_trajectories), observation)
  action_tm1 = jnp.broadcast_to(action_trajectory_tm1[0],
                                (config.n_trajectories,) +
                                action_trajectory_tm1[0].shape)

  if config.previous_trajectory_clip is not None:
    action_tm1 = jnp.clip(
        action_tm1,
        a_min=-config.previous_trajectory_clip,
        a_max=config.previous_trajectory_clip)

  # First check if planning is unnecessary:
  if config.horizon == 0:
    if hasattr(policy_prior_state, 'action_tm1'):
      policy_prior_state = policy_prior_state.replace(action_tm1=action_tm1)
    action_set, _ = policy_prior.select_action(policy_prior_params,
                                               observation_t,
                                               policy_prior_state)
    # Need to re-create an action trajectory from a single action.
    return jnp.broadcast_to(
        jnp.mean(action_set, axis=0), (1, action_set.shape[-1]))

  # Accumulators for returns and trajectories:
  cum_reward = jnp.zeros((config.n_trajectories, 1))

  # Generate noise once:
  random_key, noise_key = random.split(random_key)
  action_noise = config.sigma * random.normal(noise_key, (
      (config.horizon,) + action_tm1.shape))

  # Initialize empty set of action trajectories for concatenation in loop:
  action_trajectories = jnp.zeros((config.n_trajectories, 0) +
                                  action_trajectory_tm1[0].shape)

  for t in range(config.horizon):
    # Query policy prior for proposed action:
    if hasattr(policy_prior_state, 'action_tm1'):
      policy_prior_state = policy_prior_state.replace(action_tm1=action_tm1)
    action_t, policy_prior_state = policy_prior.select_action(
        policy_prior_params, observation_t, policy_prior_state)
    # Add action noise:
    action_t = action_t + action_noise[t]
    # Mix action with previous trajectory's corresponding action:
    action_t = (1 -
                config.beta) * action_t + config.beta * action_trajectory_tm1[t]

    # Query world model to get next observation and reward:
    observation_tp1, reward_t = world_model(world_model_params, observation_t,
                                            action_t)
    cum_reward += reward_t

    # Insert actions into trajectory matrix:
    action_trajectories = jnp.concatenate(
        [action_trajectories,
         jnp.expand_dims(action_t, axis=1)], axis=1)
    # Bump variable timesteps for next loop:
    observation_t = observation_tp1
    action_tm1 = action_t

  # De-normalize and append the final n_step return prediction:
  n_step_return_t = n_step_return(n_step_return_params, observation_t, action_t)
  cum_reward += n_step_return_t

  # Average the set of `n_trajectories` trajectories into a single trajectory.
  return config.action_aggregation_fn(action_trajectories, cum_reward)


'''
Split audio into segments for easier inference
'''

import math
import multiprocessing
import os
from multiprocessing import freeze_support

from pydub import AudioSegment

class SplitWavAudio:

    def __init__(self, file_path, file, dest_path):
        self.file_path = file_path
        self.file = file
        self.dest_path = dest_path
        self.filepath = os.path.join(file_path, file)
        self.audio = AudioSegment.from_wav(self.filepath)

    #  self.resample = self.audio.resample(sample_rate_Hz=22050, channels=1)

    def get_duration(self):
        return self.audio.duration_seconds

    def single_split(self, from_min, to_min, split_filename):
        t1 = from_min * 7 * 1000  # convert to milliseconds
        t2 = to_min * 7 * 1000
        split_audio = self.audio[t1:t2]
        resampled = split_audio.set_frame_rate(22050)  # change the sampling rate to 22050 Hz
        resampled.export(self.dest_path + '\\' + split_filename, format="wav")

    def multiple_split(self, min_per_split):
        total_mins = math.ceil(self.get_duration() / 7)
        for i in range(0, total_mins, min_per_split):
            split_fn = str(i) + '_' + self.file
            self.single_split(i, i + min_per_split, split_fn)
            print(str(i) + ' done')
            if i == total_mins - min_per_split:
                print('split successfully')

def split_audio_files(file_path: str, file: str, dest_path: str) -> None:
    split_wav = SplitWavAudio(file_path, file, dest_path)
    split_wav.multiple_split(1)

file_path = "E:/AlanWattsMaterialSorted/split_audio3/"
dest_path = "E:/AlanWattsMaterialSorted/split_audio4/"

# split_audio_files('E:/AlanWattsMaterialSorted/split_audio3/', '0_03_-_Myth_and_Religion_-_Not_What_Should_Be.mp3_2022-11-19_19_52_45.wav', 'E:/AlanWattsMaterialSorted/split_audio4/')

# create a list of input arguments for the function
inputs = [(file_path, file, dest_path) for file in os.listdir(file_path)]

print(inputs)
# create a Process pool with 16 worker processes
if __name__ == '__main__':
    freeze_support()
    p = multiprocessing.Pool(16)
    p.starmap(split_audio_files, inputs)

# for i, x, z in inputs:
#     split_audio_files(i, x, z)
'''With this implementation, the worker processes will execute the convert_audio_to_wav function
with each set of arguments in the inputs list, and each worker process will convert one audio file at a time.'''

# confirm sampling rate
# file_path = "E:/AlanWatts/dataset/split_audio/"
# import os
# import wave
#
# for file_name in os.listdir(file_path):
#     print(file_name)
#     with wave.open(os.path.join(file_path, file_name), "rb") as wave_file:
#         frame_rate = wave_file.getframerate()
#         print(frame_rate)
#         break


import os
import re
import subprocess
from typing import List, Optional, Set, Tuple

from bygg.common_types import CommandStatus

def create_shell_command(shell_command: str, message: Optional[str] = None):
    def call_shell_command(inputs: Optional[Set[str]], outputs: Optional[Set[str]]):
        # Map stderr onto stdout and return both as the output
        process = subprocess.run(
            shell_command,
            shell=True,
            stdout=subprocess.PIPE,
            stderr=subprocess.STDOUT,
            encoding="utf-8",
        )
        return CommandStatus(process.returncode, message, process.stdout)

    return lambda ctx: call_shell_command(ctx.inputs, ctx.outputs)

def filenames_from_pattern(
    input_files: List[str], in_pattern: str, out_pattern: str
) -> List[Tuple[str, str]]:
    """
    Generate a list of tuples with the input and output file names from a a list of
    input file names and a pattern like in Makefile pattern rules. File names that don't
    match the pattern are ignored. Example:

      ["/foo/bar/baz.txt.j2"], "%.txt.j2", "out_%.txt")
        => [("/foo/bar/baz.txt.j2", "/foo/bar/out_baz.txt")]
    """

    output_files = []
    matcher = re.compile(in_pattern.replace("%", "(.+)"))
    for input_file in input_files:
        head, tail = os.path.split(input_file)
        matches = matcher.match(tail)
        if matches:
            output_file = os.path.join(head, out_pattern.replace("%", matches.group(1)))
            output_files.append((input_file, output_file))
    return output_files


import os
import unittest
import json
from flask_sqlalchemy import SQLAlchemy

from flaskr import create_app
from models import setup_db, Question, Category

class TriviaTestCase(unittest.TestCase):
    """This class represents the trivia test case"""

    def setUp(self):
        """Define test variables and initialize app."""
        self.app = create_app()
        self.client = self.app.test_client
        self.database_name = "trivia_test"
        self.database_path = "postgres://{}:{}@{}/{}".format('postgres', 'password', 'localhost:5432', self.database_name)
        setup_db(self.app, self.database_path)

        self.dummy_data = {
            'question': 'TEST',
            'answer': 'TEST',
            'difficulty': 1,
            'category': 3
        }

        # binds the app to the current context
        with self.app.app_context():
            self.db = SQLAlchemy()
            self.db.init_app(self.app)
            # create all tables
            self.db.create_all()

    def tearDown(self):
        """Executed after reach test"""
        pass

    """
    TODO
    Write at least one test for each test for successful operation and for expected errors.
    """

    #test questions endpoint
    def test_get_paginated_questions(self):
        res = self.client().get('/questions')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)
        self.assertTrue(data['questions'])
        self.assertTrue(data['totalQuestions'])
        self.assertTrue(data['totalPages'])

    #test 404 error for invalid page of questions
    def test_error_for_invalid_questions_page(self):
        res = self.client().get('/questions?page=100003930')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 404)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], 'resource not found')

    #test categories endpoint
    def test_get_categories(self):
        res = self.client().get('/categories')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)
        self.assertTrue(data['categories'])
        self.assertEqual(data['total_categories'], 6)

    #test questions by category
    def test_get_questions_by_category(self):
        res = self.client().get('/categories/2/questions')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)
        self.assertTrue(len(data['questions']))
        self.assertTrue(data['totalQuestions'])
        self.assertTrue(data['totalPages'])
        self.assertEqual(data['currentCategory'], 3)

    #test adding a question
    def test_add_question(self):
        res = self.client().post('/questions', json=self.dummy_data)
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)
        self.assertTrue(data['question'])

    #test deleting a question which creates a question to be deleted
    #without relying on another API endpoint and check it was actually deleted
    def test_delete_question(self):
        question = Question(question = 'question', answer = '321answertest123', difficulty = 1, category = 2)
        question.insert()

        question = Question.query.filter(Question.answer=='321answertest123').first()
        res = self.client().delete(f'/questions/{question.id}')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)

        question_new = Question.query.filter(Question.answer=='321answertest123').first()
        self.assertFalse(question_new)

    #test deleting a question which doesn't exist
    def test_error_question_delete_id_no_exist(self):
        res = self.client().delete(f'/questions/38389940')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 404)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], "resource not found")

    #test trying to add a question without all the required fields
    def test_error_create_question_missing_fields(self):
        dummy_data = {
            'category': 1
        }
        res = self.client().post('/questions', json=dummy_data)
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 422)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], "unprocessable")

    #test trying to add a question with empty fields
    def test_error_create_question_empty_fields(self):
        dummy_data = {
            'question': '',
            'answer': '',
            'difficulty': 1,
            'category': 1
        }
        res = self.client().post('/questions', json=dummy_data)
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 422)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], "unprocessable")

    #test 405 error on PUT question
    def test_error_put_new_question(self):
        res = self.client().put('/questions', json=self.dummy_data)
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 405)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], "method not allowed")

    #test search
    def test_search(self):
        search = 'which'
        res = self.client().post(f'/questions/{search}')
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)
        self.assertTrue(data['questions'])

    #test quiz with all required info
    def test_quiz(self):
        res = self.client().post('/quizzes', json={'previous_questions':[], 'quiz_category': {"type": "Art", "id": "2"}})
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 200)
        self.assertEqual(data['success'], True)
        self.assertTrue(data['question'])

    #test error when missing previous questions
    def test_quiz_missing_prev_question(self):
        res = self.client().post('/quizzes', json={'quiz_category': {"type": "Art", "id": "2"}})
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 422)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], "unprocessable")

    #test error when missing quiz category
    def test_quiz_missing_quiz_category(self):
        res = self.client().post('/quizzes', json={'previous_questions':[]})
        data = json.loads(res.data)

        self.assertEqual(res.status_code, 422)
        self.assertEqual(data['success'], False)
        self.assertEqual(data['message'], "unprocessable")

# Make the tests conveniently executable
if __name__ == "__main__":
    unittest.main()


"""
Available commands:
 - fab release [--bump=minor] : insert new version to project settings and update Changelog file from git log
 - fab finish : commit updated ChangeLog file, update version line in project settings and commit changes with tag
 - fab check : checks code using isort, flake8, mypy, pylint, black with sensible defaults

Usage example: project release
 1. fab release --bump=major
 2. <prettify updated Changelog by hand>
 3. fab finish

Usage example to check code:
 1. fab check --path=t2f/api/v1/registration.py  # checks file `registretion.py`
 2. <fixing errors>
 3. fab check  # checks the entire project
"""
import os
import sys
from copy import copy
from dataclasses import dataclass, fields

from dateutil.utils import today
from invoke import task

file_dir_path = os.path.dirname(__file__)

CHANGELOG_FILE = "CHANGELOG.md"
VERSION_TITLE_TMPL = "## version {version} ({day})"
CHANGE_LINE_TMPL = "  - {line}"

# validate changelog file path on import
CHANGELOG_ABSPATH = os.path.abspath(os.path.join(file_dir_path, CHANGELOG_FILE))
if not os.path.isfile(CHANGELOG_ABSPATH):
    sys.stderr.write(f'Can\'t find "{CHANGELOG_FILE}" file at {CHANGELOG_ABSPATH}\n')
    sys.exit(1)

# validate that settings could be found
SETTINGS_PATH = os.path.abspath(os.path.join(file_dir_path, "t2f", "core", "config.py"))
if not os.path.isfile(SETTINGS_PATH):
    sys.stderr.write(f"Can't find settings file with VERSION constant at {SETTINGS_PATH}\n")
    sys.exit(1)

@dataclass
class VersionStructure:
    major: int
    minor: int
    patch: int

    @classmethod
    def from_str(cls, line) -> "VersionStructure":
        """
        return object from {line}, e.g. "0.8.16"
        """
        major, minor, patch = [int(item) for item in line.split(".")]
        return cls(major=major, minor=minor, patch=patch)

    @classmethod
    def from_settings(cls) -> "VersionStructure":
        """
        return last version from "settings.py" file
        :rtype: unicode
        """

        with open(SETTINGS_PATH) as f:
            for line in f.readlines():
                if line.startswith("VERSION"):
                    return cls.from_str(line.split("=", 1)[-1].strip("\n '\""))

    @classmethod
    def bump_version(cls, version, part="patch"):
        """
        increment {part} of version
        """
        resulting_version = copy(version)
        version_parts = [f.name for f in fields(resulting_version)]
        assert part in version_parts, f"{part} is not a version part"
        # setattr(self, part, (getattr(self, part, 0) + 1))
        old_version = getattr(resulting_version, part, 0)

        part_to_increment = version_parts.index(part)
        for index, value in enumerate(version_parts):
            if index == part_to_increment:
                setattr(resulting_version, value, old_version + 1)
            elif index > part_to_increment:
                setattr(resulting_version, value, 0)

        return resulting_version

    def __str__(self) -> str:
        return f"{self.major}.{self.minor}.{self.patch}"

    def to_release_brach_name(self) -> str:
        """
        Convert version for release branch name. Patch part is not used to allow release branch contain hotfixes.
        """
        return f"release/{self.major}.{self.minor}"

def _set_settings_version(c, settings_path, version_line):
    """
    set `VERSION` constant in project settings
    """
    version_const = "VERSION"

    print(f"Adjusting {version_const} in {settings_path} to {version_line}...")
    c.run(f'sed -i .orig \'s/^{version_const} =.*$/{version_const} = "{version_line}"/\' "{settings_path}"')

@task
def release(c, bump="patch"):
    """
    fab release will insert new version to project settings and update Changelog file from git log
    """
    assert bump in [f.name for f in fields(VersionStructure)], f'"{bump}" is not a version part'

    old_version = VersionStructure.from_settings()
    new_version = VersionStructure.bump_version(old_version, part=bump)

    # collecting changelog
    print(f'Collecting changelog from the last version tag "{old_version}"...')

    result = c.run(f'git log "{old_version}"..HEAD --pretty=format:"%s"', hide="out")

    commit_messages = filter(bool, result.stdout.splitlines())
    if not commit_messages:
        sys.stderr.write("Error: no new commits from last version, sorry\n")
        sys.exit(1)

    # updating changelog
    with open(CHANGELOG_ABSPATH, "r+", encoding="utf-8") as changelog:
        old_changelog = changelog.read().strip()

        changelog.seek(0)
        print("Inserting this to changelog file:\n-----\n")
        new_version_line = (
            VERSION_TITLE_TMPL.format(version=new_version, day=today().strftime("%Y-%m-%d")) + "\n"
        )
        changelog.write(new_version_line)

        print(new_version_line)
        for line in sorted(commit_messages):  # sort commit messages for easier edition afterwards
            line: str = line.strip()
            if line.startswith("Merge"):
                continue

            message_line = CHANGE_LINE_TMPL.format(line=line) + "\n"
            print(message_line)
            changelog.write(message_line)

        changelog.write("\n")
        changelog.write(old_changelog)

        print("-----")

    _set_settings_version(c, SETTINGS_PATH, str(new_version))

@task
def finish(c):
    """
    commit updated ChangeLog file, update version line in project settings and commit changes with tag
    """
    files_to_commit = [os.path.relpath(path, start=os.curdir) for path in [CHANGELOG_ABSPATH, SETTINGS_PATH]]
    version: VersionStructure = VersionStructure.from_settings()

    c.run(f"git add %s" % " ".join(files_to_commit))
    c.run(f'git commit -m "version {version}" --no-verify')
    c.run(f"git tag {version}")

@task
def check(c, path=None, lines=110):
    """
    check code using isort, flake8 and mypy
    """
    default_env = {
        "SECRET_KEY": os.environ.get("SECRET_KEY", "fab check key"),
        "PATH": os.environ["PATH"],
        "LANG": "en_US.UTF-8",
    }

    env = os.environ
    env.update(default_env)

    commands = [
        'echo "=> Checking in \\"%s\\":"' % (path or "t2f"),
        # black
        'echo "\n\n=> running `black --version` ...\n"',
        f"black --line-length={lines} %s" % (path or "."),
        'echo "\n=> done!"',
        # mypy
        'echo "\n\n=> running `mypy --version` ...\n"',
        "mypy --config-file ./mypy.ini %s" % (path or "t2f"),
        'echo "\n=> done!"',
        # flake8
        'echo "\n\n=> running flake8 `flake8 --version` ...\n"',
        "flake8 %s" % (path or "t2f"),
        'echo "\n=> done!"',
        # pylint
        'echo "\n\n=>running `pylint --version` ...\n"',
        "python pylint-checker.py %s --fail-under=9.8" % (path or "t2f"),
        'echo "\n=> done!"',
    ]

    [c.run(cmd, env=env, warn=True) for cmd in commands]

@task(name="load-testdb")
def load_testdb(c, dbname="test_template", fpath="tests/test_db.sql"):
    """
    Load db for tests from {fpath} file to {dbname} to allow for easy changing of data
    """
    default_env = {
        "PATH": os.environ["PATH"],
        "PYTHONPATH": os.path.abspath(os.path.dirname(__file__)),
        "LANG": "en_US.UTF-8",
        "POSTGRES_DB": dbname,
        "POSTGRES_HOST": "localhost",
        "POSTGRES_USER": "postgres",
        "POSTGRES_PORT": "5432",
    }

    env = os.environ
    env.update(default_env)

    psql_command = (
        f'psql -h {default_env["POSTGRES_HOST"]} '
        f'-p {default_env["POSTGRES_PORT"]} '
        f'-U {default_env["POSTGRES_USER"]}'
    )

    c.run(f'{psql_command} postgres -c "drop database if exists {dbname}";', env=env)
    c.run(f'{psql_command} postgres -c "create database {dbname}";', env=env)
    c.run(f"{psql_command} {dbname} < {fpath}", env=env)
    # update test db to the latest migrations
    c.run(f"alembic -c ./alembic.ini upgrade head", env=env)

@task(name="dump-testdb")
def dump_testdb(c, dbname="test_template", fpath="tests/test_db.sql"):
    """
    Dump {dbname} to test db file {fpath}
    """
    default_env = {
        "PATH": os.environ["PATH"],
        "LANG": "en_US.UTF-8",
    }

    env = os.environ
    env.update(default_env)

    c.run(f"pg_dump -h localhost -p 5432 -U postgres {dbname} > {fpath}", env=env)


from bs4 import BeautifulSoup
from .base import Base
import re

class Subscene(Base):
    async def search(self, title):
        """
        search function gives a title and search for it in subscene
        results will be passed as list of dicts, sample:
        {"name": "movie/series title", "link": "link to that title", "count": "counts"}
        """
        try:
            url = f"https://subscene.com/subtitles/searchbytitle?query={title}"
            resp = await self.aiorequest(url=url)  # send request to Subscene
            if " " in title:
                title = title.replace(" ", "+")
            soup = BeautifulSoup(resp, 'lxml')
            find_ul = soup.find('div', class_='search-result').find_all('ul')  # .find('ul')

            subtitles = []  # list for all finded subs to return
            for ul in find_ul:
                find_li = ul.find_all('li')
                for li in find_li:
                    base_li = li.find('div', class_='title').a
                    name = base_li.text  # movie/show name
                    link = base_li['href']  # movie/show url
                    try:  # movie/show subtitle counts
                        sub_count = li.find('div', class_='subtle count').text
                    except:
                        sub_count = li.find('span', class_='subtle count').text
                    sub_count = re.findall(r'\d+', sub_count)[0]

                    link = "https://subscene.com" + link

                    data = {"name": name, "link": link, "count": int(sub_count)}
                    subtitles.append(data)

            return subtitles
        except Exception as e:
            print(e)
            return []

    async def subtitles(self, url, lang=None):
        try:
            resp = await self.aiorequest(url, lang)
            soup = BeautifulSoup(resp, 'lxml')
            title = soup.find('div', class_='box clearfix').find('div', class_='top left').find('div',
                                                                                class_='header').h2.text
            try:
                title = title.replace("Flag", "")
                title = title.replace("Imdb", "").strip()
            except:
                pass

            table = soup.table.tbody.find_all('tr')

            subtitles = []
            for tr in table:
                try:
                    sub_name = tr.find('td', class_='a1').a.find_all('span')[1].text.strip()  # release title
                except AttributeError:
                    continue
                sub_link = tr.find('td', class_='a1').a['href']  # release link
                try:
                    sub_owner = tr.find('td', class_='a5').a.text.strip()  # sub owner
                except:
                    sub_owner = "Anonymous"
                try:
                    comments = tr.find('td', class_='a6').text.strip()
                except:
                    comments = ""
                sub_link = "https://subscene.com" + sub_link

                sub = {"name": sub_name, "link": sub_link, "owner": sub_owner, "comments": comments}
                subtitles.append(sub)

            re_subtitles = {"title": title, "subtitles": subtitles}
            return re_subtitles
        except Exception as e:
            print(e)
            return []

    async def down_page(self, url):
        resp = await self.aiorequest(url)
        soup = BeautifulSoup(resp, 'lxml')

        maindiv = soup.body.find('div', class_='subtitle').find('div', class_='top left')
        title = maindiv.find('div', class_='header').h1.span.text.strip()
        try:
            imdb = maindiv.find('div', class_='header').h1.a['href']
        except TypeError:
            imdb = ""
        try:
            poster = maindiv.find('div', class_='poster').a['href']
        except:
            poster = ""
        try:
            author_name = maindiv.find('div', class_='header').ul.find('li', class_='author').a.text.strip()
            author_link = f"https://subscene.com{maindiv.find('div', class_='header').ul.find('li', class_='author').a['href']}"
        except:
            author_link = ""
            author_name = "Anonymous"

        download_url = f"https://subscene.com{maindiv.find('div', class_='header').ul.find('li', class_='clearfix').find('div', class_='download').a['href']}"

        try:
            comments = maindiv.find('div', class_='header').ul.find('li', class_='comment-wrapper').find('div',
                                                                                class_='comment').text
        except:
            comments = ""
        try:
            release = maindiv.find('div', class_='header').ul.find('li', class_='release').find_all('div')
            releases = ""
            for i in range(2):
                r = release[i].text.strip()
                releases = releases + f"\n{r}"
        except Exception as e:
            releases = ""

        response = {"title": title, "imdb": imdb, "poster": poster, "author_name": author_name,
                    "author_url": author_link, "download_url": download_url, "comments": comments, "releases": releases}
        return response

    async def download(self, url, file_path):
        resp = await self.download_file(url, file_path)

        return resp


import cv2
import webbrowser

cap = cv2.VideoCapture(0)

detector = cv2.QRCodeDetector()

while True:
    ret, frame = cap.read()
    data = detector.detectAndDecode(frame)

    if data[0] != "":
        print(data[0])
        idata = str(data[0])
        webbrowser.open(idata, new=0, autoraise=True)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

cap.releasse()
cv2.destroyAllWindows()


import requests
from TOKEN import TOKEN

name_papka_unittest = 'папка_для_unittests'
name_papka_pytest = 'папка_для_pytest'

def header(TOKEN):
    headers = {'Content-Type': 'application/json',
            'Authorization': f'OAuth {TOKEN}'
            }
    return headers

def create(name_papka):
    headers = header(TOKEN)
    url = 'https://cloud-api.yandex.net/v1/disk/resources/'
    params = {'path': name_papka}
    response1 = requests.put(url, headers=headers, params = params)
    return response1.status_code

# create(name_papka)


from telebot.types import CallbackQuery
from telebot.types import InlineQuery, InlineQueryResultCachedDocument, InlineQueryResultArticle, \
    InputTextMessageContent

from app.models import User
from app.services.files import get_file
from app.utils.helper import generate_inline_id
from ...base import callback_query_base, inline_base
from ...helpers import mark_user
from ...keyboards.inline import get_edit_inline_markup
from ...loader import bot, bot_username

@bot.inline_handler(lambda q: q.query.startswith('file'))
@inline_base()
def inline_file(inline_query: InlineQuery):
    id = inline_query.query[4:]

    results = [InlineQueryResultArticle(
        id=generate_inline_id('not_found'),
        title='Файл не найден',
        thumb_url='https://images.emojiterra.com/google/android-11/512px/274c.png',
        input_message_content=InputTextMessageContent('Файл не найден ❌')
    )]

    if not id or not id.isdigit():
        return bot.answer_inline_query(inline_query.id, results=results, cache_time=1)

    file = get_file(int(id))

    if not file:
        return bot.answer_inline_query(inline_query.id, results=results, cache_time=1)

    file_available = True

    try:
        bot.get_file(file.file_id)
    except Exception as e:
        file_available = e.result_json['description'] == 'Bad Request: file is too big'

    if file_available:
        results = [InlineQueryResultCachedDocument(
            id=generate_inline_id(file.id),
            title=file.title,
            caption=file.title,
            document_file_id=file.file_id
        )]
    else:
        results = [InlineQueryResultArticle(
            id=generate_inline_id('error'),
            title=file.title,
            description='Похоже файл был удален',
            thumb_url='https://images.emojiterra.com/google/android-11/512px/274c.png',
            input_message_content=InputTextMessageContent(f'Файл "{file.title.lower()}" не найден ❌',
                                                          parse_mode='HTML')
        )]

    bot.answer_inline_query(inline_query.id, results=results, cache_time=1)

@bot.callback_query_handler(func=lambda call: call.data.startswith('file'))
@callback_query_base()
def inline_file_handler(call: CallbackQuery, current_user: User):
    deep_link = f'tg://resolve?domain={bot_username}&start=file'

    file_id = int(call.data[5:])

    file = get_file(file_id)
    if not file:
        return bot.answer_callback_query(call.id, 'Файл не найден', show_alert=True)

    text = f'{file.title}⠀'

    if call.message.chat.type != 'private':
        text = mark_user(text, call.from_user.id)

    markup = get_edit_inline_markup('edit_file', file.id) if current_user.is_admin() else None

    try:
        bot.send_document(call.message.chat.id, file.file_id, caption=text, reply_markup=markup)
        return bot.answer_callback_query(call.id, file.title)
    except Exception as e:
        if e.error_code == 400:
            return bot.answer_callback_query(call.id, 'Похоже файл был удален', show_alert=True)


from django.urls import path

from solf.apps.classes.api import views

urlpatterns = [
    path(
        "",
        views.ClassViewSet.as_view({"get": "list"}),
        name="class-list",
    ),
    path(
        "<int:pk>/",
        views.ClassViewSet.as_view(
            {
                "get": "retrieve",
            }
        ),
        name="class-details",
    ),
    path(
        "schedule/",
        views.ClassScheduleViewSet.as_view({"get": "list"}),
        name="class-schedule-list",
    ),
    path(
        "schedule/<int:pk>/",
        views.ClassScheduleViewSet.as_view(
            {
                "get": "retrieve",
            }
        ),
        name="class-schedule-details",
    ),
    path(
        "schedule/<int:pk>/sign-up/",
        views.ClassScheduleViewSet.as_view(
            {
                "post": "sign_up",
            }
        ),
        name="class-schedule-sign-up",
    ),
    path(
        "logs/",
        views.ClassLogViewSet.as_view({"get": "list"}),
        name="class-logs-list",
    ),
    path(
        "logs/<int:pk>/",
        views.ClassLogViewSet.as_view(
            {
                "get": "retrieve",
            }
        ),
        name="class-logs-details",
    ),
    path(
        "entries/my",
        views.ClassEntryViewSet.as_view({"get": "list"}),
        name="class-logs-list",
    ),
]


import time
import datetime

#run    "pip install win10toast"     if not done already
from win10toast import ToastNotifier

toaster = ToastNotifier()

toaster.show_toast("Toast Reminders","This is how you will be reminded",
                    icon_path="i.ico")

data = []
for d in open("times").read().split("\n"):
    if len(d.split("~")) == 3:
        data.append(d.split("~"))

while True:
    time.sleep(20)
    if datetime.datetime.today().weekday() < 5: # is a weekday (mon=0, sun=6)
        now = datetime.datetime.now()
        current_time = now.strftime("%H:%M")
        for t in data:
            if current_time == t[0]:  #if the time is the same, then show the notification
                toaster.show_toast(
                    t[1],
                    t[2],
                    icon_path="i.ico",
                    duration=60,
                    threaded=True
                    )
                time.sleep(70) # will mean that it never notifies more than needed (it may notify many times within the minute otherwise)


from default.framework.request_handler import SearchRequestHandler
from google.appengine.api import taskqueue

class LoadURLs(SearchRequestHandler):
    def get(self):
        queue = taskqueue.Queue('parser')

        with open('modules/parser/src/food_com_small.txt', 'r') as list_urls:
            for url in list_urls:
                task = taskqueue.Task(url='/_parser/parse', params={'url': url.strip()})
                queue.add(task)
class Parse(SearchRequestHandler):
    def post(self):
        url = self.request.get('url')


import http
import os
from base64 import b64encode
from typing import Dict
from urllib.parse import quote

import requests
from requests import Request, Session
from requests.adapters import HTTPAdapter
from requests.auth import CONTENT_TYPE_FORM_URLENCODED
from yarl import URL

class BasicAuth(requests.auth.AuthBase):
    def __init__(self, token: str):
        self.token = token

    def __call__(self, r: Request):
        r.headers["Authorization"] = "Basic " + self.token
        return r

class Admitad:
    API_URL = URL("https://api.admitad.com/")
    TOKEN_PATH = "token/"
    AUTH_PATH = "authorize/"
    DEEPLINK_URL = "deeplink/{website_id}/advcampaign/{campaign_id}/"
    COUPONS_URL = "coupons/"
    COUPON_URL = "coupons/{id}/"

    def __init__(self, client_id, client_secret: str, scopes: str):
        self.session = Session()
        self.session.mount(str(self.API_URL), HTTPAdapter(max_retries=5))
        user_data = self.get_oauth_token(client_id, client_secret, scopes)
        self.session.headers.update(
            {
                "Authorization": "Bearer " + user_data.get("access_token"),
                "Connection": "Keep-Alive",
            }
        )

    @staticmethod
    def encode_credentials(client_id, client_secret: str):
        return b64encode(
            "{}:{}".format(client_id, client_secret).encode()
        ).decode("utf-8")

    def get_oauth_token(self, client_id, client_secret, scopes: str):
        params = {
            "grant_type": "client_credentials",
            "client_id": client_id,
            "scope": scopes,
        }
        credentials = self.encode_credentials(client_id, client_secret)
        headers = {
            "Content-Type": CONTENT_TYPE_FORM_URLENCODED,
        }
        response = self.session.post(
            str(self.API_URL / self.TOKEN_PATH),
            data=params,
            headers=headers,
            auth=BasicAuth(credentials),
        )
        if response.status_code != http.HTTPStatus.OK:
            raise BaseException("Bad status code ", response.status_code)
        return response.json()

    def get_coupons(self, params: Dict):
        response = self.session.get(
            str(self.API_URL / self.COUPONS_URL), params=params
        )
        if response.status_code != http.HTTPStatus.OK:
            raise BaseException("Bad status code ", response.status_code)
        data = response.json()
        return data

    def generate_deeplink(self, website_id, campaign_id: int, ulp, subid: str):
        response = self.session.get(
            str(
                self.API_URL / self.DEEPLINK_URL.format(
                    website_id=website_id, campaign_id=campaign_id
                )
            ),
            params={"ulp": quote(ulp), "sibod": subid},
        )
        if response.status_code != http.HTTPStatus.OK:
            raise BaseException("Bad status code ", response.status_code)
        data = response.json()
        return data

if __name__ == "__main__":
    admitad = Admitad(
        os.getenv("CLIENT_ID"),
        os.getenv("CLIENT_SECRET"),
        "advcampaigns banners websites coupons deeplink_generator",
    )
    # тут получаем купон в c типом промокод, но в ответе промокода нет
    # нужно ли как-то отдельно получать промокод?
    coupons = admitad.get_coupons({"type": 1, "limit": 1, "region": "RU"})
    print(coupons.get("results"))

    # пытаемся сгенерить диплинку по доке
    # https://developers.admitad.com/ru/doc/api_ru/methods/deeplink/deeplink/
    # получаем 404
    admitad.generate_deeplink(
        22, 10, "https://admitad.com/some/", "AS32djkd31"
    )


"""Classe de template."""
import sys

from .factory import Factory
from .sh import Sh

class TProjects__others__ezored__src__maindot_cpp(Factory):
    """Classe de template."""

    def __init__(self, data_model, template_name):

        Factory.__init__(self, template_name)
        self.data_model = data_model
        self.tmpl.data = data_model["data"]
        self.tmpl.name = "%s/%s" % (
            self.tmpl.data["dir"],
            "projects/others/ezored/src/main.cpp".replace(
                "ezored", self.tmpl.data["project"]["name"]
            ),
        )

    def put(self):
        fileName = "%s" % self.tmpl.name
        print("File: %s" % fileName, file=sys.stderr)
        print(self.tmpl)

    def save(self):
        fileName = "%s" % self.tmpl.name
        sh = Sh(fileName)
        sh.mkdir()
        print("Save File: %s" % fileName)
        open(fileName, "w").write(str(self.tmpl))


from .client import VSphereClient

from pyVmomi import vim

class VSphereResource(object):

    def __init__(self, config):
        self.client = VSphereClient().create_client(config)
        self.content = self.client.RetrieveContent()

    def get_instances(self, params):

        vim_type = [vim.VirtualMachine]

        container_view = self.content.viewManager.CreateContainerView(
            self.content.rootFolder, vim_type, True)
        objects = container_view.view
        container_view.Destroy()
        res = []
        for server_id in params:
            for obj in objects:
                if server_id == obj._moId:
                    instance = {'id': str(obj._moId),
                                'name': str(obj.name),
                                'status': str(obj.guest.guestState)}
                    res.append(instance)

        return res