import codecs
import contextlib
import distutils.spawn
import io
import locale
import os
import sys
import unittest

py3k = sys.version_info >= (3, 0)

SkipTest = unittest.SkipTest

def get_changelog_version():
    here = os.path.dirname(__file__)
    path = os.path.join(here, '../doc/changelog')
    with io.open(path, encoding='UTF-8') as file:
        line = file.readline()
    return line.split()[1].strip('()')

tc = unittest.TestCase('__hash__')

assert_true = tc.assertTrue

assert_false = tc.assertFalse

assert_equal = tc.assertEqual

assert_not_equal = tc.assertNotEqual

assert_in = tc.assertIn

assert_is = tc.assertIs

assert_is_instance = tc.assertIsInstance

assert_less = tc.assertLess

assert_list_equal = tc.assertListEqual

assert_multi_line_equal = tc.assertMultiLineEqual
assert_multi_line_equal.__self__.maxDiff = None

assert_not_in = tc.assertNotIn

assert_raises = tc.assertRaises

assert_raises_regex = tc.assertRaisesRegex if py3k else tc.assertRaisesRegexp

@contextlib.contextmanager
def assert_raises_str(exc_type, s):
    with assert_raises(exc_type) as ecm:
        yield
    assert_equal(str(ecm.exception), s)

try:
    locale.LC_MESSAGES
except AttributeError:
    # A non-POSIX system.
    locale.LC_MESSAGES = locale.LC_ALL

locale_encoding = locale.getpreferredencoding()
if codecs.lookup(locale_encoding) == codecs.lookup('US-ASCII'):
    locale_encoding = 'UTF-8'

if py3k:
    u = str
else:
    def u(s):
        return s.decode('UTF-8')

if py3k:
    def b(s):
        return s.encode('UTF-8')
else:
    b = bytes

long = type(1 << 999)

if py3k:
    def cmp(x, y):
        if x == y:
            return 0
        if x < y:
            return -1
        if x > y:
            return 1
        assert False
else:
    cmp = cmp

if py3k:
    from io import StringIO
else:
    from io import BytesIO as StringIO

unicode = type(u(''))

@contextlib.contextmanager
def interim(obj, **override):
    copy = dict((key, getattr(obj, key)) for key in override)
    for key, value in override.items():
        setattr(obj, key, value)
    try:
        yield
    finally:
        for key, value in copy.items():
            setattr(obj, key, value)

@contextlib.contextmanager
def interim_locale(**kwargs):
    old_locale = locale.setlocale(locale.LC_ALL)
    try:
        for category, value in kwargs.items():
            category = getattr(locale, category)
            try:
                locale.setlocale(category, value)
            except locale.Error as exc:
                raise SkipTest(exc)
        yield
    finally:
        locale.setlocale(locale.LC_ALL, old_locale)

def assert_repr(self, expected):
    return assert_equal(repr(self), expected)

def skip_unless_c_messages():
    if locale.setlocale(locale.LC_MESSAGES) not in ('C', 'POSIX'):
        raise SkipTest('you need to run this test with LC_MESSAGES=C')
    if os.getenv('LANGUAGE', '') != '':
        raise SkipTest('you need to run this test with LANGUAGE unset')

def skip_unless_translation_exists(lang):
    messages = {}
    langs = ['C', lang]
    for lang in langs:
        with interim_locale(LC_ALL=lang):
            try:
                open(__file__ + '/')
            except EnvironmentError as exc:
                messages[lang] = str(exc)
    messages = set(messages.values())
    assert 1 <= len(messages) <= 2
    if len(messages) == 1:
        raise SkipTest('libc translation not found: ' + lang)

def skip_unless_command_exists(command):
    if distutils.spawn.find_executable(command):
        return
    raise SkipTest('command not found: ' + command)

class TestCase(unittest.TestCase):
    def __str__(self):
        return '{cls}.{name}'.format(
            cls=unittest.util.strclass(self.__class__),
            name=self._testMethodName,
        )

def testcase(f):
    class TestCase(unittest.TestCase):
        def test(self):
            return f()
        def __str__(self):
            return '{f.__module__}.{f.__name__}'.format(f=f)
    return TestCase

def wildcard_import(mod):
    ns = {}
    exec('from {mod} import *'.format(mod=mod), {}, ns)
    return ns

__all__ = [
    # Python 2/3 compat:
    'StringIO',
    'b',
    'cmp',
    'long',
    'py3k',
    'u',
    'unicode',
    # unittest(-like)
    'SkipTest',
    'TestCase',
    'testcase',
    # nose-compatible
    'assert_equal',
    'assert_false',
    'assert_in',
    'assert_is',
    'assert_is_instance',
    'assert_less',
    'assert_list_equal',
    'assert_multi_line_equal',
    'assert_not_equal',
    'assert_not_in',
    'assert_raises',
    'assert_raises_regex',
    'assert_true',
    # misc
    'assert_raises_str',
    'assert_repr',
    'get_changelog_version',
    'interim',
    'interim_locale',
    'locale_encoding',
    'skip_unless_c_messages',
    'skip_unless_command_exists',
    'skip_unless_translation_exists',
    'wildcard_import',
]

# vim:ts=4 sts=4 sw=4 et


import matplotlib.pyplot as plt
import numpy as np
import cartopy
import cartopy.crs as ccrs
import iris
from matplotlib import animation

v_cube = iris.load_cube('/data/NAS-ph290/ph290/reanalysis/NCEP_v2/vwnd_monthly_low_res.nc')
u_cube = iris.load_cube('/data/NAS-ph290/ph290/reanalysis/NCEP_v2/uwnd_monthly_low_res.nc')
shape = np.shape(v_cube)

level = 0

X = u_cube[0][0].coord('longitude').points
Y = u_cube[0][0].coord('latitude').points

u_cube_tmp = u_cube.collapsed('time',iris.analysis.MEAN)
v_cube_tmp = v_cube.collapsed('time',iris.analysis.MEAN)

plt.close('all')
fig, ax = plt.subplots(1,1)
ax = plt.axes(projection=ccrs.PlateCarree())
Q = ax.quiver(X, Y, u_cube_tmp[level].data, v_cube_tmp[level].data)
plt.gca().coastlines()
# plt.show()
plt.savefig('/home/ph290/Documents/figures/winds_monthly_mean.png')

#anim.save('/home/ph290/Documents/figures/winds_monthly.mp4', writer=writer)


import pytz
from pytz.exceptions import UnknownTimeZoneError

from unittest import TestCase
from unittest.mock import MagicMock,call

from datetime import datetime
import iso8601
from bumblebee.config import LoadMethod, TaskFiles, AppConfig, TaskConfigFromEnv, parse_date
from bumblebee.datehelper import localise_datetime
from bumblebee.filesystem import FileSystem

from google.cloud.bigquery.job import WriteDisposition
import os

class TestAppConfig(TestCase):
    def set_vars_with_default(self, dt):
        os.environ['DSTART'] = dt
        os.environ['DEND'] = dt
        os.environ['EXECUTION_TIME'] = dt
        os.environ['DRY_RUN'] = "true"
        os.environ['JOB_LABELS'] = "environment=integration,lifecycle=process"
        os.environ['JOB_DIR'] = "./tests/sample_config"
        os.environ['PROJECT'] = "project-id"
        os.environ['DATASET'] = "dataset"
        os.environ['TABLE'] = "sample_select"
        os.environ['SQL_TYPE'] = "STANDARD"
        os.environ['LOAD_METHOD'] = "APPEND"
        os.environ['TASK_WINDOW'] = "DAILY"
        os.environ['TIMEZONE'] = "UTC"
        os.environ['USE_SPILLOVER'] = "false"
        os.environ['CONCURRENCY'] = "1"

    def test_should_parse_args(self):
        dt = "2020-11-30T19:32:25.680530"
        self.set_vars_with_default(dt)

        opts = AppConfig()
        self.assertEqual(opts.dry_run, True)
        self.assertEqual(opts.dstart, parse_date(dt))
        self.assertEqual(opts.dend, parse_date(dt))
        self.assertEqual(opts.execution_time, parse_date(dt))
        self.assertEqual(opts.job_labels, {"environment": "integration", "lifecycle": "process"})
        self.assertEqual("./tests/sample_config/in/query.sql", opts.sql_file)
        self.assertEqual(None, opts.spillover_sql_file)

    def test_should_fail_for_invalid_date(self):
        dt = "2020-invalid-date"
        self.set_vars_with_default(dt)

        with self.assertRaises(iso8601.ParseError) as e:
            AppConfig()
        self.assertEqual("Unable to parse date string '2020-invalid-date'", str(e.exception))

    def test_should_fail_for_empty_dstart(self):
        dt = "2020-11-30T19:32:25.680530"
        self.set_vars_with_default(dt)
        os.environ['DSTART'] = ""

        with self.assertRaises(AssertionError) as e:
            AppConfig()
        self.assertEqual("config 'DSTART' must be provided", str(e.exception))

    def test_should_fail_for_missing_dstart(self):
        dt = "2020-11-30T19:32:25.680530"
        self.set_vars_with_default(dt)
        del os.environ['DSTART']

        with self.assertRaises(AssertionError) as e:
            AppConfig()
        self.assertEqual("config 'DSTART' must be provided", str(e.exception))

    def test_should_fail_for_missing_label_value(self):
        dt = "2020-11-30T19:32:25.680530"
        self.set_vars_with_default(dt)
        os.environ['JOB_LABELS'] = "environment=integration,lifecycle="

        with self.assertRaises(AssertionError) as e:
            AppConfig()
        self.assertEqual("label value cannot be empty in JOB_LABELS", str(e.exception))

    def test_should_fail_for_missing_label_key_name(self):
        dt = "2020-11-30T19:32:25.680530"
        self.set_vars_with_default(dt)
        os.environ['JOB_LABELS'] = "environment=integration,=some_value"

        with self.assertRaises(AssertionError) as e:
            AppConfig()
        self.assertEqual("label name cannot be empty in JOB_LABELS", str(e.exception))

    def test_dry_run_should_be_false_by_default(self):
        dt = "2020-11-30T19:32:25.680530"
        self.set_vars_with_default(dt)
        del os.environ['DRY_RUN']

        c = AppConfig()
        self.assertEqual(False, c.dry_run)

class TestConfig(TestCase):
    def set_vars_with_default(self, tz: str = "UTC"):
        os.environ['PROJECT'] = "project-id"
        os.environ['DATASET'] = "dataset"
        os.environ['TABLE'] = "sample_select"
        os.environ['SQL_TYPE'] = "STANDARD"
        os.environ['LOAD_METHOD'] = "APPEND"
        os.environ['TASK_WINDOW'] = "DAILY"
        os.environ['TIMEZONE'] = tz
        os.environ['USE_SPILLOVER'] = "false"
        os.environ['CONCURRENCY'] = "1"

    def setUp(self):
        self.timezone = pytz.timezone("Asia/Jakarta")

    def test_localise_datetime(self):
        tzname = "Asia/Jakarta"
        start_time = datetime(2019, 1, 1)
        localised_start_time = localise_datetime(start_time, tzname)

        expected_start_time = self.timezone.localize(datetime(year=2019, month=1, day=1))
        self.assertEqual(expected_start_time,localised_start_time)

    def test_localise_datetime_utc(self):
        utc = pytz.timezone("UTC")
        start_time = utc.localize(datetime(2019, 1, 1, 17))

        localized_start_time = localise_datetime(start_time, "Asia/Jakarta")

        expected = self.timezone.localize(datetime(year=2019, month=1, day=2))
        self.assertEqual(expected, localized_start_time)

    def test_timezone_config(self):
        tz = "Asia/Jakarta"
        self.set_vars_with_default(tz)

        task_config = TaskConfigFromEnv()

        self.assertEqual(task_config.timezone, tz)

    def test_invalid_timezone_trigger_exception(self):
        tz = "xxwdw"
        self.set_vars_with_default(tz)

        with self.assertRaises(UnknownTimeZoneError) as ex:
            TaskConfigFromEnv()

        self.assertTrue(tz in str(ex.exception))

    def test_concurrency(self):
        self.set_vars_with_default()
        os.environ['CONCURRENCY'] = "2"

        config = TaskConfigFromEnv()

        self.assertEqual(config.concurrency, 2)

    def test_concurrency_should_not_zero_exception(self):
        self.set_vars_with_default()
        os.environ['CONCURRENCY'] = "0"

        with self.assertRaises(Exception) as ex:
            TaskConfigFromEnv()

        self.assertTrue('value should be integer and greater than 0' in str(ex.exception))

    def test_empty_destination_exception(self):
        properties = """[DESTINATION]
        PROJECT=""
        DATASET=""
        TABLE=""
        SQL_TYPE="STANDARD" #LEGACY/STANDARD

        [TRANSFORMATION]
        WINDOW_SIZE="1d"
        WINDOW_OFFSET=""
        WINDOW_TRUNCATE_UPTO="d"
        TIMEZONE="Asia/Jakarta"
        USE_SPILLOVER="TRUE"
        CONCURRENCY=0

        [LOAD]
        LOAD_METHOD="REPLACE"
                """

        self.set_vars_with_default()
        os.environ['PROJECT'] = ""
        os.environ['DATASET'] = ""
        os.environ['TABLE'] = ""

        with self.assertRaises(AssertionError) as ex:
            TaskConfigFromEnv()

        self.assertEqual("config 'PROJECT' must be provided", str(ex.exception))

    def test_allow_field_addition(self):
        self.set_vars_with_default()
        os.environ['ALLOW_FIELD_ADDITION'] = 'true'

        config = TaskConfigFromEnv()
        self.assertEqual(True, config.allow_field_addition)
        del os.environ['ALLOW_FIELD_ADDITION']

    def test_allow_field_addition_should_be_false_by_default(self):
        self.set_vars_with_default()

        config = TaskConfigFromEnv()
        self.assertEqual(False, config.allow_field_addition)

class TestTaskFiles(TestCase):

    def test_task_files_without_spillover_query(self):
        fs = FileSystem()
        fs.exist = MagicMock(return_value=True)
        fs.read = MagicMock(return_value="content")

        query_sql_file = "./booking/query.sql"
        files = [query_sql_file]

        task_files = TaskFiles(fs, files)

        fs.exist.assert_has_calls([call(query_sql_file)])
        fs.read.assert_has_calls([call(query_sql_file)])

        self.assertEqual(task_files.query, "content")
        self.assertEqual(task_files.spillover_query, None)

    def test_task_files_with_spillover_query(self):
        fs = FileSystem()
        fs.exist = MagicMock(return_value=True)
        fs.read = MagicMock(return_value="content")

        query_sql_file = "./booking/query.sql"
        spillover_sql_file = "./booking/spillover_date.sql"
        files = [query_sql_file, spillover_sql_file]

        task_files = TaskFiles(fs, files)

        fs.exist.assert_has_calls([call(query_sql_file)])
        fs.read.assert_has_calls([call(query_sql_file)])

        self.assertEqual(task_files.query, "content")
        self.assertEqual(task_files.spillover_query, "content")

class TestLoadMethod(TestCase):

    def test_write_disposition(self):
        load_method = LoadMethod.APPEND
        expected_write_disposition = WriteDisposition.WRITE_APPEND
        self.assertEqual(load_method.write_disposition, expected_write_disposition)


import pygame
from source.Utilities import Utilities
from source.UI import UI
from source.StartScreen import StartScreen
from source.EndScreen import EndScreen
from source.NumberLine import NumberLine
from source.Character import Character

class GameController:

    level = 1
    game_state = "start"

    # Error messages constants
    CAT_TOO_FAR_MESSAGE = " moves the cat off of the number line. Try Again!"
    EMPTY_BOX_MESSAGE = "Please type a number and try again."
    NOT_ON_THE_NUMBER_LINE_MESSAGE = " is not on this number line. Try Again."

    # max level for the game.
    MAX_LEVEL = 50

    # constants for cat and mouse pictures.
    LEFT_CAT = "../assets/catLeft.png"
    RIGHT_CAT = "../assets/catRight.png"
    MOUSE = "../assets/mouse.png"

    ADD = pygame.USEREVENT + 1
    SUB = pygame.USEREVENT + 2
    GO = pygame.USEREVENT + 3
    RESTART = pygame.USEREVENT + 4
    QUIT = pygame.USEREVENT + 5
    START = pygame.USEREVENT + 6

    def game_display(self):
        self.screen.fill((255, 255, 255))

        # draw number line
        self.number_line.display()
        self.number_line.display_numbers()
        self.number_line.change_level(self.level)

        # position and draw cat
        self.cat_position = self.cat.set_random_position(-1)

        # position and draw mouse
        self.mouse_position = self.mouse.set_random_position(self.cat_position)

        self.mouse.display()
        self.cat.display()

        # draw level on screen
        self.ui.display_all_help_text()
        self.ui.update_level(self.level)

    def __init__(self, _screen):
        self.screen = _screen

        # setup variables
        self.w, self.h = Utilities.get_width_height()  # width and height of the screen
        self.screen = _screen

        # make start screen
        self.start_screen = StartScreen(self.screen, self.w / 2, self.h / 2)

        # make end screen
        self.end_screen = EndScreen(self.screen, self.w / 2, self.h / 2)

        # make UI
        self.ui = UI(self.screen, self.w / 2, self.h/2 + 50)

        # make Number Line
        self.number_line = NumberLine(self.screen, self.w, self.h)

        # make cat
        self.cat = Character(self.number_line.circle_pos, self.LEFT_CAT, int(self.number_line.spacing * 1.3), int(self.number_line.spacing *1.3), self.screen)
        self.cat_position = -1

        # make mouse
        self.mouse = Character(self.number_line.circle_pos, self.MOUSE, int((self.number_line.spacing/2)*1.3), int((self.number_line.spacing/2)*1.3), self.screen, self.cat.get_x_pos())
        self.mouse_position = -1

        self.end = False

    def loop(self, events):
        # draw UI
        if self.game_state == "start":
            self.start_screen.display(events)
        if self.game_state == "play":
            self.ui.display(events)
        if self.game_state == "end":
            self.end_screen.display(events)

        for event in events:

            if event.type == self.GO or (event.type == pygame.KEYDOWN and event.key == pygame.K_RETURN):
                Utilities.show_error(self.screen, "")  # clear previous error
                input_num = self.ui.user_input.get_input()

                if input_num is not None:

                    if input_num % self.level == 0:
                        new_position = int(input_num/self.level)

                        if self.cat_position + new_position >= 0:

                            if self.cat_position + new_position < self.number_line.num_of_points:
                                self.cat_position = self.cat.move(new_position)
                                self.mouse.display()
                                self.ui.user_input.clear()

                                if self.cat_position == self.mouse_position:
                                    self.mouse_position = self.mouse.set_random_position(self.cat_position)
                                    self.cat.display()
                                    self.level += 1

                                    if self.level > self.MAX_LEVEL:
                                        self.game_state = "end"
                                    else:
                                        self.ui.update_level(self.level)
                                        self.number_line.change_level(self.level)
                            else:
                                Utilities.show_error(self.screen, str(input_num) + self.CAT_TOO_FAR_MESSAGE)
                        else:
                            Utilities.show_error(self.screen, str(input_num) + self.CAT_TOO_FAR_MESSAGE)
                    else:
                        equation = ""
                        if self.ui.user_input.get_input() > 0:
                            equation = str(self.cat_position * self.level) + " + " + str(self.ui.user_input.get_input())
                        else:
                            equation = str(self.cat_position * self.level) + " - " + str(self.ui.user_input.get_input())[1:]
                        Utilities.show_error(self.screen, equation + self.NOT_ON_THE_NUMBER_LINE_MESSAGE)
                else:
                    Utilities.show_error(self.screen, self.EMPTY_BOX_MESSAGE)

            if event.type == self.ADD:
                self.ui.user_input.add(1)
            if event.type == self.SUB:
                self.ui.user_input.add(-1)

            if event.type == self.START:
                self.game_state = "play"
                self.game_display()

            if event.type == self.RESTART:
                self.level = 1
                self.game_state = "play"
                self.game_display()

            if event.type == self.QUIT:
                pygame.event.post(pygame.event.Event(pygame.QUIT))

            if self.ui.user_input.get_input() is not None and self.ui.user_input.get_input() < 0:
                self.cat.set_display_image(self.LEFT_CAT)
                self.cat.erase()
                self.cat.display()
                self.mouse.erase()
                self.mouse.display()
            if self.ui.user_input.get_input() is not None and self.ui.user_input.get_input() > 0:
                self.cat.set_display_image(self.RIGHT_CAT)
                self.cat.erase()
                self.cat.display()
                self.mouse.erase()
                self.mouse.display()


import bpy

from Frame_Ranger import Utility_Function
from Frame_Ranger.Utility_Function import Timeline_Marker_Function

ENUM_Mode = [("DOWN", "Down", "Down"),("UP", "Up", "Up")]

class FR_OT_TMM_Reorder_Timeline_Marker(bpy.types.Operator):
    """Reorder Timeline Marker"""
    bl_idname = "fr_tmm.reorder_timeline_marker"
    bl_label = "Reorder Timeline Marker"
    bl_options = {'UNDO', 'REGISTER'}

    Index: bpy.props.IntProperty()
    Mode: bpy.props.EnumProperty(items=ENUM_Mode)

    Disable_Warning: bpy.props.BoolProperty(default=True)

    def invoke(self, context, event):

        preferences = Utility_Function.get_addon_preferences()

        if preferences.OAM_Timeline_Marker_Warning:
            return context.window_manager.invoke_props_dialog(self)
        else:
            return self.execute(context)

    def draw(self, context):
        layout = self.layout
        layout.label(text="This Operator: ", icon="ERROR")
        box = layout.box()
        box.label(text="Removes All Markers and Recreating it", icon="ERROR")
        box.label(text="Depending on the Situation, It might be destructive")
        box = layout.box()
        box.label(text="You Might Lose All Your Markers", icon="ERROR")
        box.label(text="If this Operator Fails Halfway")
        layout.prop(self, "Disable_Warning", text="Disable Warning")

    def execute(self, context):

        scn = context.scene

        preferences = Utility_Function.get_addon_preferences()

        if preferences.OAM_Timeline_Marker_Warning:
            if self.Disable_Warning:
                preferences.OAM_Timeline_Marker_Warning = False

        timeline_markers_index = scn.timeline_markers_index

        proto_markers = []

        for timeline_marker in scn.timeline_markers:
            proto_marker = Timeline_Marker_Function.collect_marker_data(timeline_marker, type="TIMELINEMARKER")
            proto_markers.append(proto_marker)

        if self.Mode == "UP":
            if self.Index-1 >= 0:

                Timeline_Marker_Function.clear_timeline_markers(scn)
                item = proto_markers.pop(self.Index)
                proto_markers.insert(self.Index-1, item)
                Timeline_Marker_Function.recreate_timeline_markers(proto_markers, scn)
                scn.timeline_markers_index = timeline_markers_index

            Timeline_Marker_Function.index_up(scn)

        if self.Mode == "DOWN":
            if self.Index+1 < len(proto_markers):

                Timeline_Marker_Function.clear_timeline_markers(scn)
                item = proto_markers.pop(self.Index)
                proto_markers.insert(self.Index+1, item)
                # proto_markers = Utility_Function.list_swap_item(proto_markers, self.Index-1, self.Index)
                Timeline_Marker_Function.recreate_timeline_markers(proto_markers, scn)
                scn.timeline_markers_index = timeline_markers_index
            Timeline_Marker_Function.index_down(scn)

        Utility_Function.update_UI()

        return {'FINISHED'}

classes = [FR_OT_TMM_Reorder_Timeline_Marker]

def register():

    for cls in classes:
        bpy.utils.register_class(cls)

def unregister():

    for cls in classes:
        bpy.utils.unregister_class(cls)

if __name__ == "__main__":
    register()


"""A parser for HCL2 implemented using the Lark parser"""
from pathlib import Path

from lark import Lark

PARSER_FILE = Path(__file__).absolute().resolve().parent / ".lark_cache.bin"

hcl2 = Lark.open(
    "hcl2.lark",
    parser="lalr",
    cache=str(PARSER_FILE),  # Disable/Delete file to effect changes to the grammar
    rel_to=__file__,
    propagate_positions=True,
)


from django.contrib.auth.models import AbstractUser
from django.db import models

GENDER_CHOICES = [
    ['male', u"Мужской"],
    ['female', u"Женский"],
]

REL_CHOICES = [
    ['none', u"Не определенно"],
    ['single', u"Холост"],
    ['in_a_rel', u"В отношениях"],
    ['engaged', u"Помолвлен(а)"],
    ['married', u"Женат/Замужем"],
    ['in_love', u"Влюблен(а)"],
    ['complicated', u"Все сложно"],
]

class UserNet(AbstractUser):
    """Custom user model"""

    first_login = models.DateTimeField(verbose_name='Первый вход', auto_now=True)
    phone = models.CharField(verbose_name='Номер телефона', max_length=20)
    avatar = models.ImageField(verbose_name='Фото пользователя', null=False, upload_to='resource')

    bio = models.TextField(max_length=500, blank=True, null=True, verbose_name=u"О себе")
    city = models.CharField(max_length=30, blank=True, null=True, verbose_name=u"Город")
    birth_date = models.DateField(null=True, blank=True, verbose_name=u"Дата рождения")
    gender = models.CharField(max_length=10, verbose_name=u"Пол", choices=GENDER_CHOICES, default="male")
    relationship = models.CharField(max_length=20, verbose_name=u"Статус отношений", choices=REL_CHOICES, default="none")

    class Meta:
        verbose_name = "Юзер"
        verbose_name_plural = "Юзеры"


# coding: utf-8

from typing import Dict

import pytest
from httpx import AsyncClient
from src.models.get_engine_list_response import GetEngineListResponse  # noqa: F401
from src.models.get_engine_response import GetEngineResponse  # noqa: F401

@pytest.mark.asyncio
async def test_get_accounts_engine(client: AsyncClient) -> None:
    """Test case for get_accounts_engine

    Get accounts engine
    """

    headers: Dict[str, str] = {}
    response = await client.request(
        "GET",
        "/accounts/{accountKey}/engines/{engineName}".format(
            accountKey="account_key_example", engineName="engine_name_example"
        ),
        headers=headers,
    )

    assert response.status_code != 500

@pytest.mark.asyncio
async def test_get_accounts_engines(client: AsyncClient) -> None:
    """Test case for get_accounts_engines

    Get accounts engine list
    """
    params: Dict[str, str] = {
        "localization": "en",
        "page": "0",
        "keywords": "Chino",
        "sort": "0",
        "order": "0",
        "status": "0",
        "author": "any",
        "random": "0",
    }
    headers: Dict[str, str] = {}
    response = await client.request(
        "GET",
        "/accounts/{accountKey}/engines/list".format(accountKey="account_key_example"),
        headers=headers,
        params=params,
    )

    assert response.status_code != 500


#!/usr/bin/env python

import open_clip
import torch
from PIL import Image

import os
import os.path as osp
import numpy as np
from tqdm import tqdm
import json

from detectron2.data.datasets import load_coco_json
from detectron2.data.detection_utils import read_image
from detectron2.data import MetadataCatalog

import click

def write_json(filename, data):
    with open(filename, 'w') as fp:
        json.dump(data, fp)

def get_caption(images, model):
    images = [images] if not isinstance(images, list) else images
    for i, image in enumerate(images):
        image = Image.fromarray(image) if isinstance(image, np.ndarray) else image
        images[i] = model.transform(image)

    images = torch.stack(images).to(model.device)
    with torch.no_grad(), torch.cuda.amp.autocast():
        generated = model.generate(images)

    caps = [open_clip.decode(g).split("<end_of_text>")[0].replace("<start_of_text>", "") for g in generated]
    return caps

def inference(model, images, batch_size=24):
    captions = []
    for i in range(0, len(images), batch_size):
        chunck = images[i : i + batch_size]
        captions.extend(get_caption(chunck, model))
    return captions

def get_model(device):
    model, _, transform = open_clip.create_model_and_transforms(
        model_name="coca_ViT-L-14", pretrained="mscoco_finetuned_laion2B-s13B-b90k"
    )
    model = model.to(device).eval()
    model.transform = transform
    model.device = device
    return model

def process(model, data_dicts, write_dir, override: bool = False):
    for i, data_dict in enumerate(tqdm(data_dicts)):
        filename = data_dict['file_name']
        annotations = data_dict['annotations']

        image_id = data_dict['image_id']
        json_filename = f'{osp.join(write_dir, str(image_id).zfill(12))}.json'

        if not override and osp.isfile(json_filename):
            continue

        image = read_image(file_name=filename)
        im_crops = []
        bboxes = []
        for _, annotation in enumerate(annotations):
            x, y, w, h = annotation['bbox']
            bboxes.append(annotation['bbox'])

            x, y, w, h = np.intp([x, y, w, h])
            w, h = np.max([[w, 1], [h, 1]], axis=1)
            im_crop = image[y : y + h, x : x + w].copy()
            im_crops.append(im_crop)

        captions = inference(model, im_crops)

        caption_dicts = {
            'file_name': filename,
            'image_id': data_dict['image_id'],
            'captions': [{'bbox': bbox, 'caption': cap} for cap, bbox in zip(captions, bboxes)],
        }

        write_json(json_filename, caption_dicts)

@click.command()
@click.option('--start', type=int, required=True)
@click.option('--end', type=int, required=True)
@click.option('--device', type=str, default='cuda:0')
@click.option('--root', type=str, required=False, default='/workspace/Downloads/datasets/coco/')
@click.option('--year', type=str, default='2017')
@click.option('--type', type=str, default='train')
@click.option('--override/--no-override', type=bool, default=False)
def main(start, end, device, root, year, type, override):
    data_type = f'{type}{year}'
    ann_file = '{}/annotations/instances_{}.json'.format(root, data_type)

    write_dir = osp.join(root, f'captions/{data_type}')
    if not osp.isdir(write_dir):
        os.makedirs(write_dir, exist_ok=True)

    # load coco data

    print("loading coco data")
    filename_resolver = lambda x: osp.join(root, data_type)
    data_dicts = load_coco_json(ann_file, filename_resolver(''))
    meta = MetadataCatalog.get(f'coco_{year}_{type}')
    classes = meta.thing_classes
    cat_id_mapping = meta.get('thing_dataset_id_to_contiguous_id')

    print("loading model")
    model = get_model(device=device)

    process(model, data_dicts[start:end], write_dir, override)

if __name__ == '__main__':
    main()


import torch
import torchvision.models as models
import torchvision.transforms as transforms
from torchvision.models import ResNet50_Weights

from laserBeam.pil_simulation import *

# 加载预训练的ResNet模型
model = models.resnet50(weights=ResNet50_Weights.DEFAULT)
model.eval()

# 加载ImageNet类别标签
labels_file = "model/imagenet_labels.txt"
with open(labels_file) as f:
    labels = f.readlines()
labels = [label.strip() for label in labels]

def image_load(image_path):
    image = Image.open(image_path)
    return image

# 加载并预处理图像
def get_conf(image, k=5):
    # image = Image.open(image_path)
    # print(type(image))
    preprocess = transforms.Compose([
        transforms.Resize(256),
        transforms.CenterCrop(224),
        transforms.ToTensor(),
        transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225]),
    ])
    input_tensor = preprocess(image)
    input_batch = input_tensor.unsqueeze(0)

    # 将图像输入模型并进行预测
    with torch.no_grad():
        output = model(input_batch)

    # 获取预测结果
    probabilities = torch.nn.functional.softmax(output[0], dim=0)
    top_k = torch.topk(probabilities, k)

    conf_list = []
    for i in range(k):
        index = top_k.indices[i].item()
        probability = top_k.values[i].item()

        label = labels[index]
        conf_list.append((label, probability))
        # print(f"{label}: {probability:.5f}")
    return conf_list

def get_y_conf(image, label):
    conf_list = get_conf(image, 1000)
    for i in range(len(conf_list)):
        if conf_list[i][0] == label:
            return conf_list[i][1]
    return 0

# initial_model()
# im = Image.open("Line Image.png")
# print(get_conf(im))


import pathlib
import shutil
import sys
import os

from recipes.common import execute, tell_user, HOME, SCRIPT_PATH
from recipes.ohmyzsh import setup_oh_my_zsh
from recipes.pyenv import install_pyenv
from recipes.kitty import setup_kitty_term
from recipes.node import setup_node_npm_n
from recipes.spaceship import install_spaceship_prompt
from recipes.fonts import install_fonts

VSCODE_GPG_KEY_CMD = """
sudo sh -c 'echo -e "[code]\nname=Visual Studio Code\nbaseurl=https://packages.microsoft.com/yumrepos/vscode\nenabled=1\ngpgcheck=1\ngpgkey=https://packages.microsoft.com/keys/microsoft.asc" > /etc/yum.repos.d/vscode.repo'
"""

PKGS_TO_INSTALL = [
    "zlib-devel",
    "bzip2",
    "bzip2-devel",
    "readline-devel",
    "sqlite",
    "sqlite-devel",
    "openssl-devel",
    "xz",
    "xz-devel",
    "libffi-devel",
    "python3-devel",
    "zsh",
    "util-linux-user",
    "golang",
    "powerline-fonts",
    "nvim",
    "kitty",
    "flameshot",
    "npm",
    "libpq-devel",
    "protobuf-compiler",
]

def install_base_pkgs(pkgs=None):
    """Install basic system packages (dev headers, tools, lang compilers, etc.)"""
    if not pkgs:
        pkgs = PKGS_TO_INSTALL
    tell_user("Going to install base pkgs...")
    execute(f"sudo dnf install -y {' '.join(pkg for pkg in pkgs)}")

def install_vs_code():
    """Import Microsoft vscode gpg key, adds microsoft repository and then install vscode."""
    tell_user("Going to install vscode...")
    tell_user("Importing vscode repo...")
    execute("sudo rpm --import https://packages.microsoft.com/keys/microsoft.asc")
    tell_user("Adding Microsoft vscode gpg key...")
    execute(VSCODE_GPG_KEY_CMD)
    tell_user("Going to install vscode...")
    execute("sudo dnf install -y code")

def setup_fisa_vim():
    """Setup fisa vim."""
    tell_user("Going to install fisa vim deps...")
    fisa_requirements = [
        "ctags-etags",
        "python3-flake8",
        "python3-pylint",
        "python3-isort",
    ]
    execute(f"sudo dnf install -y {' '.join(pkg for pkg in fisa_requirements)}")
    execute("pip3 install --user pynvim")

    nvim_dir = f"{HOME}/.config/nvim"
    tell_user("Downloading fisa vim config...")
    if not os.path.isdir(f"{nvim_dir}"):
        os.makedirs(f"{nvim_dir}")
    execute(
        f"wget -O {nvim_dir}/init.vim https://raw.github.com/fisadev/fisa-vim-config/master/config.vim"
    )

def setup_golang():
    gohome = f"{HOME}/Code/go"
    pathlib.Path(gohome).mkdir(parents=True, exist_ok=True)
    with open(f"{HOME}/.zshrc", "a") as zshrc:
        zshrc.write("\n")
        zshrc.write("# Fedora restore :: setup GOHOME\n")
        zshrc.write(f'export GOPATH="{gohome}"\n')
        zshrc.write(f'export PATH="$PATH:$GOPATH/bin"\n')
        zshrc.write(f'export GO111MODULE="auto"\n')

    tell_user("Downloading protoc golang plugin...")
    execute("go get -u github.com/golang/protobuf/protoc-gen-go")


from urequests import request
from models import LightState
import secrets
import config

def fetch_state():
    response = request("GET", secrets.api_endpoint + "states/" + config.entity_id, headers={
        "Authorization": "Bearer " + secrets.api_token,
    })

    if (response.status_code > 200):
        print("Failed to fetch recent state, error code: " + str(response.status_code))
        response.close()
        return None
    response_state = response.json()
    response.close()
    light_state = LightState(
        state=response_state["state"] == 'on',
        brightness = response_state["attributes"]["brightness"] if "brightness" in response_state["attributes"] else 100,
        color_temp = response_state["attributes"]["color_temp"] if "color_temp" in response_state["attributes"] else 300,
    )
    return light_state

def turn_on(toast_print):
    toast_print("Turning on")
    data = {"entity_id": config.entity_id}
    response = request("POST", secrets.api_endpoint + "services/light/turn_on", headers={
        "Authorization": "Bearer " + secrets.api_token,
    }, json=data)
    response.close()

def update_state(state, toast_print, busy_pin = None):
    toast_print("Applying")
    data = {"entity_id": config.entity_id} if not state.state else {
        "entity_id": config.entity_id,
        "brightness": state.brightness.value,
        "color_temp": state.color_temp.value,
    }
    if busy_pin is not None:
        busy_pin.on()
    response = request("POST", secrets.api_endpoint + "services/light/" + ("turn_on" if state.state else "turn_off"), headers={
        "Authorization": "Bearer " + secrets.api_token,
    }, json=data)
    print("Update response code: " + str(response.status_code))
    toast_print("Updated (" + str(response.status_code) + ")", True)
    response.close()
    if busy_pin is not None:
        busy_pin.off()


#
# Data visualisation
#a

import numpy as np
import matplotlib.pyplot as plt
import pandas as pd

import torch
import torch.nn as nn
import torch.utils.data as data

from model import *

def visualise_data():
    test = RNN()
    df = load_data('train.csv')

    gb = df.groupby(["store", "product"])
    groups = {x: gb.get_group(x) for x in gb.groups}

    fig, axs = plt.subplots(7, 10, figsize=(40, 35))
    for index, store_axs in enumerate(axs):
        for index2, product_ax in enumerate(store_axs):
            X = groups[(index, index2)]
            X = X.drop(["store", "product"], axis=1).values
            X = [item for sublist in X for item in sublist]
            product_ax.plot(X, linewidth=0.5)
            product_ax.set_yticks([min(X), max(X)])
            if index == 6:
                product_ax.set_xticks([0, len(X)])
            else:
                product_ax.set_xticks([])
            product_ax.tick_params(labelsize=6)

    for index, ax in enumerate(axs[0]):
        ax.set_title(f"Product {index}")

    for index, ax in enumerate(axs[:, 0]):
        ax.set_ylabel(f"Store {index}", rotation=0, size='large', labelpad=20)

    plt.subplots_adjust(wspace=0.65, hspace=0.3)
    #fig.tight_layout()
    plt.show()

def visualize_training_groups():
    df = load_data('train.csv')
    train_groups, test_groups = split_data(df, 0.8)

    fig, axs = plt.subplots(7, 10, figsize=(40, 35))
    for index, store_axs in enumerate(axs):
        for index2, product_ax in enumerate(store_axs):
            X = train_groups[(index, index2)]
            X = X.drop(["store", "product"], axis=1).values
            X = [item for sublist in X for item in sublist]
            product_ax.plot(X, linewidth=0.5)
            product_ax.set_yticks([min(X), max(X)])
            if index == 6:
                product_ax.set_xticks([0, len(X)])
            else:
                product_ax.set_xticks([])
            product_ax.tick_params(labelsize=6)

    for index, ax in enumerate(axs[0]):
        ax.set_title(f"Product {index}")

    for index, ax in enumerate(axs[:, 0]):
        ax.set_ylabel(f"Store {index}", rotation=0, size='large', labelpad=20)

    plt.subplots_adjust(wspace=0.65, hspace=0.3)
    # fig.tight_layout()
    plt.show()

def visualise_prediction():
    model_name = 'Model lb=10, lr=0.0001, hs=128, epochs=500, tr=0.67, bs=64, nl=1.pt'  #
    model = torch.load('saved_models/' + model_name)  # load your model here
    model.eval()

    model_name_adpt = model_name.split('Model ')[1].split('.pt')[0]
    parameters = model_name_adpt.split(", ")
    par_dict = {par.split('=')[0]: float(par.split('=')[1]) for par in parameters}

    lookback = int(par_dict['lb'])
    train_test_ratio = par_dict['tr']
    batch_size = 1

    df = load_data('train.csv')

    scaler = MinMaxScaler(feature_range=(0, 1))
    scaler = scaler.fit(df[['number_sold']])
    value_column = scaler.transform(df[['number_sold']])
    df['number_sold'] = value_column

    train_groups, test_groups = split_data(df, train_test_ratio)
    test_features, test_targets = create_rolling_windows(test_groups, lookback, 5)

    index = np.random.randint(0, len(test_features), 1)
    index = [2400]
    print(index)

    feature, target = torch.Tensor(test_features[index]), torch.Tensor(test_targets[index])
    # print(f'Feature {feature}')
    # print(target)
    predictions = []
    #  Predict 5 time steps
    for i in range(5):
        pred_value = model(feature)
        predictions.append(pred_value)
        feat_list = feature.tolist()[0]
        feat_list.pop(0)
        feat_list.append(pred_value.tolist())
        feature = torch.tensor([feat_list])

    fig, ax = plt.subplots()
    with torch.no_grad():
        ax.plot(range(lookback), test_features[index].tolist()[0], color='blue')
        ax.plot(range(lookback, lookback + 5), predictions, color='red')
        ax.plot(range(lookback, lookback + 5), test_targets[index].tolist()[0], color='green', linestyle='dotted')

    plt.show()

if __name__ == "__main__":
    #visualise_data()
    #visualize_training_groups()
    visualise_prediction()


import numpy as np
import cv2
import datasets

def expand_channels(dataset:datasets.ClassificationDataset,c:int):
    if dataset.dataformat=="NHWC":
        axis=3
    else:
        axis=1

    dataset.x_train = np.repeat(dataset.x_train,c,axis=axis)
    dataset.x_test = np.repeat(dataset.x_test, c, axis=axis)

def collapse_channels(dataset:datasets.ClassificationDataset):
    if dataset.dataformat=="NHWC":
        axis=3
    else:
        axis=1
    dataset.x_train = dataset.x_train.mean(axis=axis,keepdims=True)
    dataset.x_test  = dataset.x_test.mean(axis=axis,keepdims=True)

def resize(dataset:datasets.ClassificationDataset,h:int,w:int,c:int):

    if dataset.dataformat=="NCHW":
        dataset.x_train=np.transpose(dataset.x_train,axes=(0,2,3,1))
        dataset.x_test = np.transpose(dataset.x_test, axes=(0, 2, 3, 1))

    subsets = [dataset.x_train, dataset.x_test]
    new_subsets=[np.zeros((s.shape[0],h,w,c)) for s in subsets]

    for (subset,new_subset) in zip(subsets,new_subsets):
        for i in range(subset.shape[0]):
            img=subset[i, :]
            if c==1:
                #remove channel axis, resize, put again
                img=img[:,:,0]
                img= cv2.resize(img, dsize=(h, w))
                img = img[:, :, np.newaxis]
            else:
                #resize
                img = cv2.resize(img, dsize=(h, w))

            new_subset[i,:]=img

    dataset.x_train = new_subsets[0]
    dataset.x_test = new_subsets[1]

    if dataset.dataformat=="NCHW":
        dataset.x_train = np.transpose(dataset.x_train,axes=(0,3,1,2))
        dataset.x_test = np.transpose(dataset.x_test, axes=(0, 3, 1, 2))

def adapt_dataset(dataset:datasets.ClassificationDataset, dataset_template:str):
    dataset_template = datasets.get_classification(dataset_template)
    h,w,c= dataset_template.input_shape
    del dataset_template
    oh,ow,oc=dataset.input_shape

    # fix channels
    if c !=oc and oc==1:
        expand_channels(dataset,c)

    elif c != oc and c ==1:
        collapse_channels(dataset)
    else:
        raise ValueError(f"Cannot transform image with {oc} channels into image with {c} channels.")

    #fix size
    if h!=oh or w!=ow:
        resize(dataset,h,w,c)

    dataset.input_shape=(h,w,c)


import pytest
from test_data.request_test_data import create_test_request, example_requests
from test_data.tree_decomposition_test_data import (
    create_test_tree_decomposition,
    VALID_TREE_DECOMPOSITIONS,
    INVALID_TREE_DECOMPOSITION_INTERSECTION_PROPERTY,
    INVALID_TREE_DECOMPOSITIONS_NOT_A_TREE,
    INVALID_TREE_DECOMPOSITIONS,
    POST_ORDER_TRAVERSALS,
    CHECK_COMPATIBLE_MAPPINGS_VALID_EXAMPLES,
    CHECK_COMPATIBLE_MAPPINGS_INVALID_EXAMPLES,
    NICE_TREE_DECOMPOSITIONS,
)
from vnep_approx import treewidth_model

@pytest.mark.parametrize("request_id",
                         example_requests)
def test_trivial_decomposition_is_always_valid(request_id):
    req = create_test_request(request_id)
    tree_decomp = treewidth_model.TreeDecomposition("test")
    tree_decomp.add_node("bag_1", frozenset(req.nodes))
    assert tree_decomp.is_tree_decomposition(req)

@pytest.mark.parametrize("request_id",
                         VALID_TREE_DECOMPOSITIONS)
def test_hardcoded_decompositions_are_valid(request_id):
    req = create_test_request(request_id=request_id)
    tree_decomp = create_test_tree_decomposition(VALID_TREE_DECOMPOSITIONS[request_id])
    assert tree_decomp.is_tree_decomposition(req)

# @pytest.mark.parametrize("request_id",
#                          NICE_TREE_DECOMPOSITIONS)
# def test_nice_tree_decompositions_are_recognized(request_id):
#     req = create_test_request(request_id=request_id)
#     tree_decomp = create_test_tree_decomposition(NICE_TREE_DECOMPOSITIONS[request_id])
#     arborescence = tree_decomp.convert_to_arborescence(NICE_TREE_DECOMPOSITIONS[request_id]["root"])
#
#     assert tree_decomp.is_tree_decomposition(req)
#     assert treewidth_model.is_nice_tree_decomposition(tree_decomp, arborescence)

#DEFERRED
# @pytest.mark.parametrize("request_id",
#                          ["simple path"])
# def test_nice_tree_decomposition_conversion(request_id):
#     req = create_test_request(request_id=request_id)
#
#     initial_td = treewidth_model.compute_tree_decomposition(req)
#     nice_td_generator = treewidth_model.NiceTDConversion(req, initial_td=initial_td)
#     root = sorted(initial_td.nodes)[0]
#     nice_td_generator.initialize(root=root)
#     nice_td = nice_td_generator.make_nice_tree_decomposition()
#     assert nice_td.is_tree_decomposition(req)
#     assert treewidth_model.is_nice_tree_decomposition(nice_td, nice_td.convert_to_arborescence(root))

@pytest.mark.parametrize("tree_decomposition_dict",
                         INVALID_TREE_DECOMPOSITION_INTERSECTION_PROPERTY)
def test_invalid_decompositions_intersection_property(tree_decomposition_dict):
    tree_decomp = create_test_tree_decomposition(tree_decomposition_dict)
    assert not tree_decomp._verify_intersection_property()

@pytest.mark.parametrize("tree_decomposition_dict",
                         INVALID_TREE_DECOMPOSITIONS_NOT_A_TREE)
def test_invalid_decompositions_not_a_tree(tree_decomposition_dict):
    tree_decomp = create_test_tree_decomposition(tree_decomposition_dict)
    assert not tree_decomp._is_tree()

@pytest.mark.parametrize("request_id",
                         VALID_TREE_DECOMPOSITIONS)
def test_hardcoded_decompositions_can_convert_to_arborescence(request_id):
    tree_decomp = create_test_tree_decomposition(VALID_TREE_DECOMPOSITIONS[request_id])
    arborescence = tree_decomp.convert_to_arborescence()

    # check node & edge sets
    assert arborescence.root in arborescence.nodes
    assert arborescence.nodes == tree_decomp.nodes
    for edge in arborescence.edges:
        assert frozenset(edge) in tree_decomp.edges
    for edge in tree_decomp.edges:
        t1, t2 = edge
        assert (t1, t2) in arborescence.edges or (t2, t1) in arborescence.edges

    # verify reachability from root
    q = {arborescence.root}
    visited = set()
    while q:
        t1 = q.pop()
        visited.add(t1)
        neighbors = arborescence.get_out_neighbors(t1)
        assert len(set(neighbors) & visited) <= 1  # Should be tree-like: at most one ancestor
        for t2 in neighbors:
            if t2 in visited:
                continue
            assert t2 not in q
            q.add(t2)
    return visited == set(arborescence.nodes)

@pytest.mark.parametrize("tree_decomposition_dict",
                         INVALID_TREE_DECOMPOSITIONS)
def test_converting_invalid_decomposition_to_arborescence_raises_valueerror(tree_decomposition_dict):
    tree_decomp = create_test_tree_decomposition(tree_decomposition_dict)
    with pytest.raises(ValueError):
        tree_decomp.convert_to_arborescence()

@pytest.mark.parametrize("traversal",
                         POST_ORDER_TRAVERSALS)
def test_post_order_traversal(traversal):
    tree_decomp = create_test_tree_decomposition(VALID_TREE_DECOMPOSITIONS[traversal["request_id"]])
    arborescence = tree_decomp.convert_to_arborescence(root=traversal["root"])

    assert list(arborescence.post_order_traversal()) == traversal["order"]

@pytest.mark.parametrize("mapping_pair_tuple",
                         CHECK_COMPATIBLE_MAPPINGS_VALID_EXAMPLES)
def test_check_compatible_mappings_valid_examples(mapping_pair_tuple):
    assert treewidth_model.check_if_mappings_are_compatible(*mapping_pair_tuple)

@pytest.mark.parametrize("mapping_pair_tuple",
                         CHECK_COMPATIBLE_MAPPINGS_INVALID_EXAMPLES)
def test_check_compatible_mappings_invalid_examples(mapping_pair_tuple):
    assert not treewidth_model.check_if_mappings_are_compatible(*mapping_pair_tuple)


from __future__ import division

import warnings

import numpy as np
from scipy import linalg
from sklearn.covariance import empirical_covariance, log_likelihood
from sklearn.utils.extmath import squared_norm
from sklearn.utils.validation import check_X_y

from regain.covariance.graphical_lasso_ import GraphicalLasso, init_precision
from regain.math import batch_logdet
from regain.norm import l1_od_norm
from regain.prox import prox_logdet, soft_thresholding
from regain.update_rules import update_rho
from regain.utils import Convergence, error_norm_time
from regain.validation import check_norm_prox

def batch_log_likelihood(emp_cov, precision):
    """Gaussian log-likelihood without constant term."""
    return batch_logdet(precision) - np.sum(emp_cov * precision, axis=(-1, -2))

def loss(emp_cov, precision, n_samples: np.ndarray = None) -> float:
    """Loss function for time-varying graphical lasso."""
    if n_samples is None:
        # 1 sample for each batch, ie, do not scale.
        batch_dim = emp_cov.shape[0]
        n_samples = np.ones(batch_dim)

    return np.sum(-n_samples * batch_log_likelihood(emp_cov, precision))

def objective(n_samples, emp_cov, K, Z_0, Z_1, Z_2, alpha, beta, psi) -> float:
    """Objective function for time-varying graphical lasso."""
    obj: float = loss(emp_cov, K, n_samples=n_samples)

    if isinstance(alpha, np.ndarray):
        obj += np.sum(l1_od_norm(alpha * Z_0))
    else:
        obj += alpha * np.sum(l1_od_norm(Z_0))

    if isinstance(beta, np.ndarray):
        obj += sum(b[0][0] * m for b, m in zip(beta, map(psi, Z_2 - Z_1)))
    else:
        obj += beta * sum(map(psi, Z_2 - Z_1))

    return obj

def time_graphical_lasso(
    emp_cov,
    alpha=0.01,
    rho=1,
    beta=1,
    max_iter=100,
    n_samples=None,
    verbose=False,
    psi="laplacian",
    tol=1e-4,
    rtol=1e-4,
    return_history=False,
    return_n_iter=True,
    mode="admm",
    compute_objective=True,
    stop_at=None,
    stop_when=1e-4,
    update_rho_options=None,
    init="empirical",
):
    """Time-varying graphical lasso solver.

    Solves the following problem via ADMM:
        min sum_{i=1}^T -n_i log_likelihood(S_i, K_i) + alpha*||K_i||_{od,1}
            + beta sum_{i=2}^T Psi(K_i - K_{i-1})

    where S_i = (1/n_i) X_i^T \times X_i is the empirical covariance of data
    matrix X (training observations by features).

    Parameters
    ----------
    emp_cov : ndarray, shape (n_features, n_features)
        Empirical covariance of data.
    alpha, beta : float, optional
        Regularisation parameter.
    rho : float, optional
        Augmented Lagrangian parameter.
    max_iter : int, optional
        Maximum number of iterations.
    n_samples : ndarray
        Number of samples available for each time point.
    tol : float, optional
        Absolute tolerance for convergence.
    rtol : float, optional
        Relative tolerance for convergence.
    return_history : bool, optional
        Return the history of computed values.
    return_n_iter : bool, optional
        Return the number of iteration before convergence.
    verbose : bool, default False
        Print info at each iteration.
    update_rho_options : dict, optional
        Arguments for the rho update.
        See regain.update_rules.update_rho function for more information.
    compute_objective : bool, default True
        Choose to compute the objective value.
    init : {'empirical', 'zero', ndarray}
        Choose how to initialize the precision matrix, with the inverse
        empirical covariance, zero matrix or precomputed.

    Returns
    -------
    K : numpy.array, 3-dimensional (T x d x d)
        Solution to the problem for each time t=1...T .
    history : list
        If return_history, then also a structure that contains the
        objective value, the primal and dual residual norms, and tolerances
        for the primal and dual residual norms at each iteration.

    """
    psi, prox_psi, psi_node_penalty = check_norm_prox(psi)

    Z_0 = init_precision(emp_cov, mode=init)
    Z_1 = Z_0.copy()[:-1]  # np.zeros_like(emp_cov)[:-1]
    Z_2 = Z_0.copy()[1:]  # np.zeros_like(emp_cov)[1:]

    U_0 = np.zeros_like(Z_0)
    U_1 = np.zeros_like(Z_1)
    U_2 = np.zeros_like(Z_2)

    Z_0_old = np.zeros_like(Z_0)
    Z_1_old = np.zeros_like(Z_1)
    Z_2_old = np.zeros_like(Z_2)

    # divisor for consensus variables, accounting for two less matrices
    divisor = np.full(emp_cov.shape[0], 3, dtype=float)
    divisor[0] -= 1
    divisor[-1] -= 1

    if n_samples is None:
        n_samples = np.ones(emp_cov.shape[0])

    checks = [
        Convergence(
            obj=objective(n_samples, emp_cov, Z_0, Z_0, Z_1, Z_2, alpha, beta, psi)
        )
    ]
    for iteration_ in range(max_iter):
        # update K
        A = Z_0 - U_0
        A[:-1] += Z_1 - U_1
        A[1:] += Z_2 - U_2
        A /= divisor[:, None, None]
        # soft_thresholding_ = partial(soft_thresholding, lamda=alpha / rho)
        # K = np.array(map(soft_thresholding_, A))
        A += A.transpose(0, 2, 1)
        A /= 2.0

        A *= -rho * divisor[:, None, None] / n_samples[:, None, None]
        A += emp_cov

        lamda = np.expand_dims(n_samples / (rho * divisor), -1)
        K = prox_logdet(A, lamda)

        # update Z_0
        A = K + U_0
        A += A.transpose(0, 2, 1)
        A /= 2.0
        Z_0 = soft_thresholding(A, lamda=alpha / rho)

        # other Zs
        A_1 = K[:-1] + U_1
        A_2 = K[1:] + U_2
        if not psi_node_penalty:
            prox_e = prox_psi(A_2 - A_1, lamda=2.0 * beta / rho)
            Z_1 = 0.5 * (A_1 + A_2 - prox_e)
            Z_2 = 0.5 * (A_1 + A_2 + prox_e)
        else:
            Z_1, Z_2 = prox_psi(
                np.concatenate((A_1, A_2), axis=1),
                lamda=0.5 * beta / rho,
                rho=rho,
                tol=tol,
                rtol=rtol,
                max_iter=max_iter,
            )

        # update residuals
        U_0 += K - Z_0
        U_1 += K[:-1] - Z_1
        U_2 += K[1:] - Z_2

        # diagnostics, reporting, termination checks
        rnorm = np.sqrt(
            squared_norm(K - Z_0)
            + squared_norm(K[:-1] - Z_1)
            + squared_norm(K[1:] - Z_2)
        )

        snorm = rho * np.sqrt(
            squared_norm(Z_0 - Z_0_old)
            + squared_norm(Z_1 - Z_1_old)
            + squared_norm(Z_2 - Z_2_old)
        )

        obj = (
            objective(n_samples, emp_cov, Z_0, K, Z_1, Z_2, alpha, beta, psi)
            if compute_objective
            else np.nan
        )

        # if np.isinf(obj):
        #     Z_0 = Z_0_old
        #     break

        check = Convergence(
            obj=obj,
            rnorm=rnorm,
            snorm=snorm,
            e_pri=np.sqrt(K.size + 2 * Z_1.size) * tol
            + rtol
            * max(
                np.sqrt(squared_norm(Z_0) + squared_norm(Z_1) + squared_norm(Z_2)),
                np.sqrt(squared_norm(K) + squared_norm(K[:-1]) + squared_norm(K[1:])),
            ),
            e_dual=np.sqrt(K.size + 2 * Z_1.size) * tol
            + rtol
            * rho
            * np.sqrt(squared_norm(U_0) + squared_norm(U_1) + squared_norm(U_2)),
            # precision=Z_0.copy()
        )
        Z_0_old = Z_0.copy()
        Z_1_old = Z_1.copy()
        Z_2_old = Z_2.copy()

        if verbose:
            print(check)

        checks.append(check)
        if stop_at is not None:
            if abs(check.obj - stop_at) / abs(stop_at) < stop_when:
                break

        if check.rnorm <= check.e_pri and check.snorm <= check.e_dual:
            break

        rho_new = update_rho(
            rho, rnorm, snorm, iteration=iteration_, **(update_rho_options or {})
        )
        # scaled dual variables should be also rescaled
        U_0 *= rho / rho_new
        U_1 *= rho / rho_new
        U_2 *= rho / rho_new
        rho = rho_new

        # assert is_pos_def(Z_0)
    else:
        warnings.warn("Objective did not converge.")

    covariance_ = np.array([linalg.pinvh(x) for x in Z_0])
    return_list = [Z_0, covariance_]
    if return_history:
        return_list.append(checks)
    if return_n_iter:
        return_list.append(iteration_ + 1)
    return return_list

class TimeGraphicalLasso(GraphicalLasso):
    """Sparse inverse covariance estimation with an l1-penalized estimator.

    Parameters
    ----------
    alpha : positive float, default 0.01
        Regularization parameter for precision matrix. The higher alpha,
        the more regularization, the sparser the inverse covariance.

    beta : positive float, default 1
        Regularization parameter to constrain precision matrices in time.
        The higher beta, the more regularization,
        and consecutive precision matrices in time are more similar.

    psi : {'laplacian', 'l1', 'l2', 'linf', 'node'}, default 'laplacian'
        Type of norm to enforce for consecutive precision matrices in time.

    rho : positive float, default 1
        Augmented Lagrangian parameter.

    over_relax : positive float, deafult 1
        Over-relaxation parameter (typically between 1.0 and 1.8).

    tol : positive float, default 1e-4
        Absolute tolerance to declare convergence.

    rtol : positive float, default 1e-4
        Relative tolerance to declare convergence.

    max_iter : integer, default 100
        The maximum number of iterations.

    verbose : boolean, default False
        If verbose is True, the objective function, rnorm and snorm are
        printed at each iteration.

    assume_centered : boolean, default False
        If True, data are not centered before computation.
        Useful when working with data whose mean is almost, but not exactly
        zero.
        If False, data are centered before computation.

    time_on_axis : {'first', 'last'}, default 'first'
        If data have time as the last dimension, set this to 'last'.
        Useful to use scikit-learn functions as train_test_split.

    update_rho_options : dict, default None
        Options for the update of rho. See `update_rho` function for details.

    compute_objective : boolean, default True
        Choose if compute the objective function during iterations
        (only useful if `verbose=True`).

    init : {'empirical', 'zeros', ndarray}, default 'empirical'
        How to initialise the inverse covariance matrix. Default is take
        the empirical covariance and inverting it.

    Attributes
    ----------
    covariance_ : array-like, shape (n_times, n_features, n_features)
        Estimated covariance matrix

    precision_ : array-like, shape (n_times, n_features, n_features)
        Estimated precision matrix.

    n_iter_ : int
        Number of iterations run.

    """

    def __init__(
        self,
        alpha=0.01,
        beta=1.0,
        mode="admm",
        rho=1.0,
        tol=1e-4,
        rtol=1e-4,
        psi="laplacian",
        max_iter=100,
        verbose=False,
        assume_centered=False,
        return_history=False,
        update_rho_options=None,
        compute_objective=True,
        stop_at=None,
        stop_when=1e-4,
        suppress_warn_list=False,
        init="empirical",
    ):
        super(TimeGraphicalLasso, self).__init__(
            alpha=alpha,
            rho=rho,
            tol=tol,
            rtol=rtol,
            max_iter=max_iter,
            verbose=verbose,
            assume_centered=assume_centered,
            mode=mode,
            update_rho_options=update_rho_options,
            compute_objective=compute_objective,
            init=init,
        )
        self.beta = beta
        self.psi = psi
        self.return_history = return_history
        self.stop_at = stop_at
        self.stop_when = stop_when
        self.suppress_warn_list = suppress_warn_list

    def get_observed_precision(self):
        """Getter for the observed precision matrix.

        Returns
        -------
        precision_ : array-like,
            The precision matrix associated to the current covariance object.

        """
        return self.get_precision()

    def _fit(self, emp_cov, n_samples):
        """Fit the TimeGraphicalLasso model to X.

        Parameters
        ----------
        emp_cov : ndarray, shape (n_time, n_features, n_features)
            Empirical covariance of data.

        """

        out = time_graphical_lasso(
            emp_cov,
            alpha=self.alpha,
            rho=self.rho,
            beta=self.beta,
            mode=self.mode,
            n_samples=n_samples,
            tol=self.tol,
            rtol=self.rtol,
            psi=self.psi,
            max_iter=self.max_iter,
            verbose=self.verbose,
            return_n_iter=True,
            return_history=self.return_history,
            update_rho_options=self.update_rho_options,
            compute_objective=self.compute_objective,
            stop_at=self.stop_at,
            stop_when=self.stop_when,
            init=self.init,
        )
        if self.return_history:
            self.precision_, self.covariance_, self.history_, self.n_iter_ = out
        else:
            self.precision_, self.covariance_, self.n_iter_ = out
        return self

    def fit(self, X, y):
        """Fit the TimeGraphicalLasso model to X.

        Parameters
        ----------
        X : ndarray, shape = (n_samples * n_times, n_dimensions)
            Data matrix.
        y : ndarray, shape = (n_times,)
            Indicate the temporal belonging of each sample.

        """
        # Covariance does not make sense for a single feature
        X, y = check_X_y(
            X,
            y,
            accept_sparse=False,
            dtype=np.float64,
            order="C",
            ensure_min_features=2,
            estimator=self,
        )

        n_dimensions = X.shape[1]
        self.classes_, n_samples = np.unique(y, return_counts=True)
        n_times = self.classes_.size

        # n_samples = np.array([x.shape[0] for x in X])
        if self.assume_centered:
            self.location_ = np.zeros((n_times, n_dimensions))
        else:
            self.location_ = np.array([X[y == cl].mean(0) for cl in self.classes_])

        emp_cov = np.array(
            [
                empirical_covariance(X[y == cl], assume_centered=self.assume_centered)
                for cl in self.classes_
            ]
        )

        return self._fit(emp_cov, n_samples)

    def score(self, X, y):
        """Computes the log-likelihood of a Gaussian data set with
        `self.covariance_` as an estimator of its covariance matrix.

        Parameters
        ----------
        X : array-like, shape = (n_samples, n_features)
            Test data of which we compute the likelihood, where n_samples is
            the number of samples and n_features is the number of features.
            X is assumed to be drawn from the same distribution than
            the data used in fit (including centering).

        y :  array-like, shape = (n_samples,)
            Class of samples.

        Returns
        -------
        res : float
            The likelihood of the data set with `self.covariance_` as an
            estimator of its covariance matrix.

        """
        # Covariance does not make sense for a single feature
        X, y = check_X_y(
            X,
            y,
            accept_sparse=False,
            dtype=np.float64,
            order="C",
            ensure_min_features=2,
            estimator=self,
        )

        # compute empirical covariance of the test set
        test_cov = np.array(
            [
                empirical_covariance(
                    X[y == cl] - self.location_[i], assume_centered=True
                )
                for i, cl in enumerate(self.classes_)
            ]
        )

        res = sum(
            X[y == cl].shape[0] * log_likelihood(S, K)
            for S, K, cl in zip(test_cov, self.get_observed_precision(), self.classes_)
        )

        return res

    def error_norm(self, comp_cov, norm="frobenius", scaling=True, squared=True):
        """Compute the Mean Squared Error between two covariance estimators.
        (In the sense of the Frobenius norm).

        Parameters
        ----------
        comp_cov : array-like, shape = [n_features, n_features]
            The covariance to compare with.

        norm : str
            The type of norm used to compute the error. Available error types:
            - 'frobenius' (default): sqrt(tr(A^t.A))
            - 'spectral': sqrt(max(eigenvalues(A^t.A))
            where A is the error ``(comp_cov - self.covariance_)``.

        scaling : bool
            If True (default), the squared error norm is divided by n_features.
            If False, the squared error norm is not rescaled.

        squared : bool
            Whether to compute the squared error norm or the error norm.
            If True (default), the squared error norm is returned.
            If False, the error norm is returned.

        Returns
        -------
        The Mean Squared Error (in the sense of the Frobenius norm) between
        `self` and `comp_cov` covariance estimators.

        """
        return error_norm_time(
            self.covariance_, comp_cov, norm=norm, scaling=scaling, squared=squared
        )


__author__ = 'Lucas-Fievet'

from celery import task

from us_loader.models import UsManager
import logging

logger = logging.getLogger("UsLoader")

@task()
def updateUs(date=None):
    logger.info("Update Us task started.")
    usManager = UsManager()
    if date is not None:
        usManager.update_to = date
    return usManager.update()


from setuptools import setup, find_namespace_packages
from tethys_apps.app_installation import find_resource_files

### Apps Definition ###
app_package = 'embalses'
release_package = 'tethysapp-' + app_package

# -- Get Resource File -- #
resource_files = find_resource_files('tethysapp/' + app_package + '/templates', 'tethysapp/' + app_package)
resource_files += find_resource_files('tethysapp/' + app_package + '/public', 'tethysapp/' + app_package)
resource_files += find_resource_files('tethysapp/' + app_package + '/workspaces', 'tethysapp/' + app_package)

### Python Dependencies ###
dependencies = []

setup(
    name=release_package,
    version='1.0.0',
    description='An application for forecasting future reservoir levels in the Dominican Republic',
    long_description='Uses the Streamflow Prediction Tool, user supplied water release information, and rule curves to '
                     'forecast the levels of any reservoir in the Domincan Republic. Developed in 2018 and 2019 by two '
                     'groups of BYU Civil Engineering Capstone students.',
    keywords='Reservoir',
    author='Riley Hales',
    author_email='',
    url='https://www.github.com/rileyhales/embalses',
    license='MIT License',
    packages=find_namespace_packages(),
    package_data={'': resource_files},
    include_package_data=True,
    zip_safe=False,
    install_requires=dependencies,
)


from convexhull import *
import cv2
import numpy
from ultralytics import YOLO
import tkinter
import matplotlib
import matplotlib.pyplot as plt
import tkinter
import os
import time
matplotlib.use('TkAgg')

def get3point(pp):
    return pp[:3]

src_img = [320,192]

def cam_c1(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[src_img[0]/5,src_img[1]],[0,src_img[1]],[src_img[0],src_img[1]/5]])
    M = cv2.getAffineTransform(pts1,pts2)
    return cv2.warpAffine(img,M,(900,700))

def cam_c2(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[src_img[0],src_img[1]/5],[src_img[0],src_img[1]],[src_img[0]/5,src_img[1]]])
    M = cv2.getAffineTransform(pts1,pts2)
    return cv2.warpAffine(img,M,(900,700))

def cam_c3(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[0,src_img[1]/5],[0,0],[src_img[0]/5,0]])
    M = cv2.getAffineTransform(pts1,pts2)
    return cv2.warpAffine(img,M,(900,700))

def cam_c4(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[src_img[0]/5,0],[src_img[0],0],[src_img[0],src_img[1]/5]])
    M = cv2.getAffineTransform(pts1,pts2)
    return cv2.warpAffine(img,M,(900,700))

def rv_cam_c1(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[src_img[0]/5,src_img[1]],[0,src_img[1]],[src_img[0],src_img[1]/5]])
    M = cv2.getAffineTransform(pts2,pts1)
    return cv2.warpAffine(img,M,(640, 384))

def rv_cam_c2(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[src_img[0],src_img[1]/5],[src_img[0],src_img[1]],[src_img[0]/5,src_img[1]]])
    M = cv2.getAffineTransform(pts2,pts1)
    return cv2.warpAffine(img,M,(640, 384))

def rv_cam_c3(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[0,src_img[1]/5],[0,0],[src_img[0]/5,0]])
    M = cv2.getAffineTransform(pts2,pts1)
    return cv2.warpAffine(img,M,(640, 384))

def rv_cam_c4(img,pts1):
    pts1 = numpy.float32(pts1)
    pts2 = numpy.float32([[src_img[0]/5,0],[src_img[0],0],[src_img[0],src_img[1]/5]])
    M = cv2.getAffineTransform(pts2,pts1)
    return cv2.warpAffine(img,M,(640, 384))
#fdffg
model = YOLO('best (1).pt')
def extractOutput(path):

    video_cam1 = cv2.VideoCapture(path+'/'+'CAM_1.mp4')
    video_cam2 = cv2.VideoCapture(path+'/'+'CAM_2.mp4')
    video_cam3 = cv2.VideoCapture(path+'/'+'CAM_3.mp4')
    video_cam4 = cv2.VideoCapture(path+'/'+'CAM_4.mp4')

    font = cv2.FONT_HERSHEY_SIMPLEX
    fontScale = 1
    thickness = 2
    count = 1
    while True:
        a=time.time()
        res1, frame_cam1 = video_cam1.read()
        res2, frame_cam2 = video_cam2.read()
        res3, frame_cam3 = video_cam3.read()
        res4, frame_cam4 = video_cam4.read()

        raw1 = frame_cam1
        raw2 = frame_cam2
        raw3 = frame_cam3
        raw4 = frame_cam4
        if not res1:
            break
        if not res2:
            break
        if not res3:
            break
        if not res4:
            break

        if model(frame_cam1)[0].masks is None:
            continue
        if model(frame_cam2)[0].masks is None:
            continue
        if model(frame_cam3)[0].masks is None:
            continue
        if model(frame_cam4)[0].masks is None:
            continue

        total1 = model(frame_cam1)[0].masks.data[0]
        total2 = model(frame_cam2)[0].masks.data[0]
        total3 = model(frame_cam3)[0].masks.data[0]
        total4 = model(frame_cam4)[0].masks.data[0]

        total1 = total1.clone().detach().cpu()
        total2 = total2.clone().detach().cpu()
        total3 = total3.clone().detach().cpu()
        total4 = total4.clone().detach().cpu()

        total1 = numpy.array(total1)
        total2 = numpy.array(total2)
        total3 = numpy.array(total3)
        total4 = numpy.array(total4)

        total1 = preprocess(total1)
        total2 = preprocess(total2)
        total3 = preprocess(total3)
        total4 = preprocess(total4)

        cors1 = list(get3point(corner(total1)))
        cors2 = list(get3point(corner(total2)))
        cors3 = list(get3point(corner(total3)))
        cors4 = list(get3point(corner(total4)))

        mapmat1 = cv2.resize(frame_cam1, (640, 384))
        mapmat2 = cv2.resize(frame_cam2, (640, 384))
        mapmat3 = cv2.resize(frame_cam3, (640, 384))
        mapmat4 = cv2.resize(frame_cam4, (640, 384))

        cors1.append([0,0])
        cors2.append([0,0])
        cors3.append([0,0])
        cors4.append([0,0])

        image1 = cv2.bitwise_and(total1,cv2.rotate(total4, cv2.ROTATE_180), mask = None)
        image1 = preprocess(image1)

        image2 = cv2.bitwise_and(total2,cv2.rotate(total3, cv2.ROTATE_180), mask = None)
        image2 = preprocess(image2)

        image3 = cv2.bitwise_and(total3,cv2.rotate(total2, cv2.ROTATE_180), mask = None)
        image3 = preprocess(image3)

        image4 = cv2.bitwise_and(total4,cv2.rotate(total1, cv2.ROTATE_180), mask = None)
        image4 = preprocess(image4)
        b=time.time()
        corner1 = getAllCorner(image1)
        temp1 = [f"{i[0]},{i[1]}" for i in corner1]
        raw1 = ",".join(temp1)
        raw1 = f"({raw1})"
        f = open(path+'/CAM_1.txt', 'a')
        f.write(f"frame_{count}.jpg, {raw1}, {b-a}/n")
        f.close()
        b=time.time()
        corner2 = getAllCorner(image2)
        temp2 = [f"{i[0]},{i[1]}" for i in corner2]
        raw2 = ",".join(temp2)
        raw2 = f"({raw2})"
        f = open(path+'/CAM_2.txt', 'a')
        f.write(f"frame_{count}.jpg, {raw2}, {b-a}/n")
        f.close()
        b=time.time()
        corner3 = getAllCorner(image3)
        temp3 = [f"{i[0]},{i[1]}" for i in corner3]
        raw3 = ",".join(temp3)
        raw3 = f"({raw3})"
        f = open(path+'/CAM_3.txt', 'a')
        f.write(f"frame_{count}.jpg, {raw3}, {b-a}/n")
        f.close()
        b=time.time()
        corner4 = getAllCorner(image4)
        temp4 = [f"{i[0]},{i[1]}" for i in corner4]
        raw4 = ",".join(temp4)
        raw4 = f"({raw4})"
        f = open(path+'/CAM_4.txt', 'a')
        f.write(f"frame_{count}.jpg, {raw4}, {b-a}/n")
        f.close()
        count+=1
# extractOutput("C:/Users/ADMIN/Desktop/document/junx/Private_Test/videos/scene4cam_05")
output = "C:/Users/ADMIN/Desktop/document/junx/Private_Test/groundtruth/"
path = "C:/Users/ADMIN/Desktop/document/junx/Private_Test/videos/scene4cam_"
for i in range(1, 15):
    fullpath = path+"0"*(2-len(str(i)))+str(i)
    extractOutput(fullpath)


import json
import logging
import operator
import os
import webbrowser
from enum import Enum
from enum import unique
from typing import List
from typing import Optional

import click
import click_spinner
from taurus_datajob_api import DataJobExecution
from taurus_datajob_api import DataJobExecutionLogs
from taurus_datajob_api import DataJobExecutionRequest
from vdk.internal.control.configuration.defaults_config import load_default_team_name
from vdk.internal.control.exception.vdk_exception import VDKException
from vdk.internal.control.rest_lib.factory import ApiClientFactory
from vdk.internal.control.rest_lib.rest_client_errors import ApiClientErrorDecorator
from vdk.internal.control.utils import cli_utils
from vdk.internal.control.utils import output_printer
from vdk.internal.control.utils.cli_utils import get_or_prompt
from vdk.internal.control.utils.output_printer import OutputFormat

log = logging.getLogger(__name__)

@unique
class ExecuteOperation(Enum):
    """
    An enum used to store the types of deploy operations
    """

    START = "start"
    CANCEL = "cancel"
    WAIT = "wait"
    SHOW = "show"
    LIST = "list"
    LOGS = "logs"

class JobExecute:
    def __init__(self, rest_api_url: str):
        self.__execution_api = ApiClientFactory(rest_api_url).get_execution_api()

    @staticmethod
    def __model_executions(executions, output_format: OutputFormat) -> str:
        def transform_execution(e: DataJobExecution):
            d = e.to_dict()
            d["job_version"] = e.deployment.job_version
            if e.deployment.python_version:
                d["python_version"] = e.deployment.python_version
            del d["deployment"]
            return d

        executions = list(map(lambda e: transform_execution(e), executions))
        output_printer.create_printer(output_format).print_table(executions)

    @staticmethod
    def __validate_and_parse_args(arguments: str) -> str:
        try:
            if arguments:
                return json.loads(arguments)
            else:
                return {}
        except Exception as e:
            vdk_ex = VDKException(
                what="Failed to validate job arguments.",
                why=str(e),
                consequence="I will not make the API call.",
                countermeasure="Make sure provided --arguments is a valid JSON string.",
            )
            raise vdk_ex

    @ApiClientErrorDecorator()
    def start(
        self, name: str, team: str, output_format: OutputFormat, arguments: str
    ) -> None:
        execution_request = DataJobExecutionRequest(
            started_by=f"manual/vdk-control-cli",
            args=self.__validate_and_parse_args(arguments),
        )
        log.debug(f"Starting job with request {execution_request}")
        headers = self.__execution_api.data_job_execution_start_with_http_info(
            team_name=team,
            job_name=name,
            deployment_id="production",  # TODO
            data_job_execution_request=execution_request,
        ).headers
        log.debug(f"Received headers: {headers}")

        location = headers["Location"]
        execution_id = os.path.basename(location)
        if output_format == OutputFormat.TEXT.value:
            click.echo(
                f"Execution of Data Job {name} started. "
                f"See execution status using: \n\n"
                f"vdk execute --show --execution-id {execution_id} -n {name} -t {team}\n\n"
                f"See execution logs using: \n\n"
                f"vdk execute --logs --execution-id {execution_id} -n {name} -t {team}"
            )
        else:
            result = {
                "job_name": name,
                "team": team,
                "execution_id": execution_id,
            }
            output_printer.create_printer(output_format).print_dict(result)

    @ApiClientErrorDecorator()
    def cancel(self, name: str, team: str, execution_id: str) -> None:
        click.echo("Cancelling data job execution. Might take some time...")
        with click_spinner.spinner():
            response = self.__execution_api.data_job_execution_cancel(
                team_name=team, job_name=name, execution_id=execution_id
            )
            log.debug(f"Response: {response}")
        click.echo("Job cancelled successfully.")

    @ApiClientErrorDecorator()
    def show(
        self, name: str, team: str, execution_id: str, output_format: OutputFormat
    ) -> None:
        execution: DataJobExecution = self.__execution_api.data_job_execution_read(
            team_name=team, job_name=name, execution_id=execution_id
        )
        self.__model_executions([execution], output_format)

    @ApiClientErrorDecorator()
    def list(self, name: str, team: str, output_format: OutputFormat) -> None:
        executions: List[
            DataJobExecution
        ] = self.__execution_api.data_job_execution_list(team_name=team, job_name=name)
        self.__model_executions(executions, output_format)

    def __get_execution_to_log(
        self, name: str, team: str, execution_id: str
    ) -> Optional[DataJobExecution]:
        if not execution_id:
            executions: list[
                DataJobExecution
            ] = self.__execution_api.data_job_execution_list(
                team_name=team, job_name=name
            )
            if not executions:
                return None
            log.info(
                "No execution id has been passed as argument. "
                "We will print the logs of the last started execution."
            )
            executions.sort(key=operator.attrgetter("start_time"), reverse=True)
            execution = executions[0]
        else:
            execution: DataJobExecution = self.__execution_api.data_job_execution_read(
                team_name=team, job_name=name, execution_id=execution_id
            )
        return execution

    @ApiClientErrorDecorator()
    def logs(self, name: str, team: str, execution_id: str) -> None:
        execution = self.__get_execution_to_log(name, team, execution_id)
        if not execution:
            log.info("No executions found.")
            return

        log.debug(f"Get execution details: {execution.to_dict()}")
        log.info(f"Logs for execution with id {execution.id} ...")
        if execution.logs_url:
            log.info(f"Opening browser to check logs at:\n{execution.logs_url}")
            is_open = webbrowser.open(execution.logs_url)
            if not is_open:
                log.info(
                    "We failed to open the browser automatically .\n"
                    f"Navigate manually in your favourite browser to {execution.logs_url} to find the execution logs."
                )
        else:
            log.debug("Fetch logs from Execution Current Logs API: ")
            logs: DataJobExecutionLogs = self.__execution_api.data_job_logs_download(
                team_name=team, job_name=name, execution_id=execution.id
            )
            click.echo(logs.logs)

# Below is the definition of the CLI API/UX users will be interacting
# Above is the actual implementation of the operations

@click.command(
    help="Starts execution of a data job that is deployed or check status of job execution(s). (Beta)"
    """
Examples:

\b
# Start new remote execution of Data Job 'example-job'
# As an output it will print how to get starts and it's execution ID:
vdk execute --start -n example-job -t "Example Team"
\b
# Start a new remote execution of Data Job 'example-job' with extra arguments
# Arguments are passed to each step. Arguments must be a valid JSON object with key/value pairs.
vdk execute --start -n example-job -t "Example Team" --arguments '{"key1": "value1", "key2": "value2"}'

\b
# Check status of a currently executing Data Job:
vdk execute --show --execution-id example-job-1619094633811-cc49d  -n example-job -t "Example Team"

\b
# Cancel a currently executing Data Job:
vdk execute --cancel -t "Example Team" -n example-job --execution-id example-job-1619094633811-cc49d

\b
# List recent execution of a Data Job:
vdk execute --list -n example-job -t "Example Team"

\b
# We want to see the logs of the current execution that is running.
vdk execute --logs -n example-job -t "Example Team" --execution-id example-job-1619094633811-cc49d

""",
)
@click.option("-n", "--name", type=click.STRING, help="The job name.")
@click.option(
    "-t",
    "--team",
    type=click.STRING,
    default=load_default_team_name(),
    required=True,
    prompt="Job Team",
    help="The team name to which the job belong to.",
)
@click.option("-i", "--execution-id", type=click.STRING, help="The job execution ID.")
@click.option(
    "--start",
    "operation",
    flag_value=ExecuteOperation.START.value,
    help="Start execution of a Data Job. ",
)
@click.option(
    "--wait",
    "operation",
    hidden=True,
    flag_value=ExecuteOperation.WAIT.value,
    help="Wait for current job execution (if any) to finish "
    "(if specified execution id wait for execution with given id to finish)."
    "Require --execution-id to be provided. "
    "Should be printed when using vdk execute --start",
)
@click.option(
    "--cancel",
    "operation",
    flag_value=ExecuteOperation.CANCEL.value,
    help="Cancels a running or submitted Data Job execution. Requires --execution-id to be provided. "
    "Should be printed when using vdk execute --start",
)
@click.option(
    "--list",
    "operation",
    flag_value=ExecuteOperation.LIST.value,
    help="List recent and/or current executions of the Data Job. ",
)
@click.option(
    "--show",
    "operation",
    flag_value=ExecuteOperation.SHOW.value,
    help="Shows details Data Job Executions. Requires --execution-id to be provided. "
    "Should be printed when using vdk execute --start",
)
@click.option(
    "--logs",
    "operation",
    flag_value=ExecuteOperation.LOGS.value,
    help="Shows logs about Data Job Execution. It will either provide link to central logging system or"
    " print the logs locally."
    "If --execution-id is omitted, it will fetch logs from more recently started job execution."
    " --execution-id should be provided to get logs from specific job execution."
    "Execution id is printed when using vdk execute --start. "
    "You can also see execution id with vdk execute --list operation.",
)
@cli_utils.rest_api_url_option()
@cli_utils.output_option()
@click.option(
    "--arguments",
    type=click.STRING,
    required=False,
    help="Pass arguments when starting a data job. "
    "Those arguments will be passed to each step. "
    "Must be in valid JSON format",
)
@cli_utils.check_required_parameters
def execute(
    name, team, execution_id, operation, rest_api_url, output, arguments
) -> None:
    cmd = JobExecute(rest_api_url)
    if operation == ExecuteOperation.START.value:
        name = get_or_prompt("Job Name", name)
        cmd.start(name, team, output, arguments)
    elif operation == ExecuteOperation.SHOW.value:
        name = get_or_prompt("Job Name", name)
        execution_id = get_or_prompt("Job Execution ID", execution_id)
        cmd.show(name, team, execution_id, output)
    elif operation == ExecuteOperation.LIST.value:
        name = get_or_prompt("Job Name", name)
        cmd.list(name, team, output)
    elif operation == ExecuteOperation.CANCEL.value:
        name = get_or_prompt("Job Name", name)
        team = get_or_prompt("Job Team", team)
        execution_id = get_or_prompt("Job Execution ID", execution_id)
        cmd.cancel(name, team, execution_id)
    elif operation == ExecuteOperation.LOGS.value:
        name = get_or_prompt("Job Name", name)
        team = get_or_prompt("Job Team", team)
        cmd.logs(name, team, execution_id)
    elif operation == ExecuteOperation.WAIT.value:
        name = get_or_prompt("Job Name", name)
        # cmd.wait(name, team)
        click.echo("Operation wait not implemented")
    else:
        click.echo(
            f"No execute operation specified. "
            f"Please specify one of: {['--' + str(op.value) for op in ExecuteOperation]}"
        )