import json
import requests

with open('config.json') as config:
    cfg = json.loads(config.read())

response = requests.get(cfg["bse"]["url"], headers=cfg["bse"]["headers"])
status_code = response.status_code

if status_code == 200:
    data = json.loads(response.text)
    print(json.dumps(data, indent=4, sort_keys=True))
else:
    print(status_code)


# -*- coding: utf-8 -*-
"""
Created on Tue May 26 11:42:33 2020

@author: nikla
"""

from numpy import *
from ir_load import ir_load
import irbasis
import os

### Setting matplotlib details
def cm2inch(*tupl):
    inch = 2.54
    if isinstance(tupl[0], tuple):
        return tuple(i/inch for i in tupl[0])
    else:
        return tuple(i/inch for i in tupl)

import matplotlib
import matplotlib.pyplot as plt
import matplotlib.gridspec as gridspec
import matplotlib.ticker as tick
from matplotlib.ticker import (MultipleLocator, FormatStrFormatter,
                               AutoMinorLocator)
from matplotlib import rc
import seaborn as sns

plt.style.use('seaborn-paper')
sns.set_palette("muted")
rc('figure',figsize=cm2inch(14.5,5), dpi=300)
#rc('figure',figsize=cm2inch(7.2,5), dpi=300)
rc('text', usetex=True)
rc('text.latex', preamble=r'\usepackage{bm}')

SMALL_SIZE = 8
MEDIUM_SIZE = 11
BIGGER_SIZE = 10

plt.rc('font', size=SMALL_SIZE)          # controls default text sizes
plt.rc('axes', titlesize=SMALL_SIZE)     # fontsize of the axes title
plt.rc('axes', labelsize=MEDIUM_SIZE)    # fontsize of the x and y labels
plt.rc('xtick', labelsize=SMALL_SIZE)    # fontsize of the tick labels
plt.rc('ytick', labelsize=SMALL_SIZE)    # fontsize of the tick labels
plt.rc('legend', fontsize=SMALL_SIZE)    # legend fontsize
plt.rc('figure', titlesize=BIGGER_SIZE)  # fontsize of the figure title

rc('lines',linewidth=1.2, marker='x', markersize=0)
plt.rcParams["lines.markeredgewidth"] = 1
#plt.rcParams["xtick.major.pad"] = 2
#plt.rcParams["ytick.major.pad"] = 2
rc('xtick',direction='in')
rc('ytick',direction='in')
rc('font', family='serif')
rc('markersize')

#### Paths -----------------------------------------------
savepath = './/'

#### Calculation -----------------------------------------
Lambda = 10**linspace(1,7,7)
delta  = 10**linspace(-1,-15,281)

l_F = empty(len(Lambda),dtype='object')
l_B = empty(len(Lambda),dtype='object')
for it in range(len(Lambda)):
    print(it)

    b_F = irbasis.load('F', Lambda[it])
    b_B = irbasis.load('B', Lambda[it])

    ll_f = [ir_load.basis_cutoff(b_F, delta_it) for delta_it in delta]
    ll_b = [ir_load.basis_cutoff(b_B, delta_it) for delta_it in delta]

        #assert (b.f_l[-1]+1,) == b.fm.shape and (b.f_l[-1]+1,) == b.ft.shape
        #assert (b.b_l[-1]+1,) == b.bm.shape and (b.b_l[-1]+1,) == b.bt.shape

    l_F[it] = array(ll_f)
    l_B[it] = array(ll_b)

######################### Plotting -------------
fig = plt.figure(constrained_layout=True)
spec = gridspec.GridSpec(ncols=2, nrows=1, figure=fig)
f_ax1 = fig.add_subplot(spec[0, 0])
f_ax2 = fig.add_subplot(spec[0, 1])

###### plot
for it in range(len(Lambda)):
    f_ax1.semilogx(delta,l_F[it])
    f_ax2.semilogx(delta,l_B[it],\
                   label='$\\Lambda = 10^{' + str(int(log10(Lambda[it]))) + '}$')

### Fermi plot parameters
f_ax1.tick_params(top=True, right=True, which='both')
f_ax1.set_xlim([1e-15,1e-1])
f_ax1.set_ylim([0,202])
f_ax1.set_xlabel('$\\delta$')
f_ax1.set_ylabel('$N^{\\mathrm{F}}_{\\mathrm{IR}}$')

### Bose plot parameters
f_ax2.tick_params(top=True, right=True, which='both')
f_ax2.set_xlim([1e-15,1e-1])
f_ax2.set_ylim([0,175])
f_ax2.set_xlabel('$\\delta$')
f_ax2.set_ylabel('$N^{\\mathrm{B}}_{\\mathrm{IR}}$')

plt.figlegend(bbox_to_anchor=(1, 1.02), loc='upper left', ncol=1, labelspacing=0.9)

plt.savefig(savepath + 'IR_basis_size_accuracy.png', bbox_inches='tight')
plt.savefig(savepath + 'IR_basis_size_accuracy.pdf', bbox_inches='tight')


import os
import base64
import socket
import logging
import threading

from . import response
from . import events

class Client:
	_LOGS_FILE = "client.log"
	_EVENTS = {
		"on_data_recieved": events.void,	# param: data
		"on_connected_changed": events.void,	# param: connected
		"on_error": events.void,				# param: exception, message
		"on_host_changed": events.void,		# param: host
		"on_port_changed": events.void,		# param: port
		"on_handshake_started": events.void,	# no param
		"on_handshake_ended": events.void	# param: result
	}
	def __init__(self, port=80, host="0.0.0.0", debug=False, event={}):
		super(Client, self).__init__()
		self.connected = False
		self.sock = None
		self.host = host
		self.port = port
		self.debug = debug

		# Initialize log file format.
		logging.basicConfig(
			filename=Client._LOGS_FILE,
			filemode='w',
			format='%(levelname)s: %(asctime)s\t%(message)s',
			level=logging.DEBUG if self.debug else logging.INFO
		)

		# get events
		self.events = Client._EVENTS.copy()
		self.events.update(event.get() if type(event)==events.Event else event.copy())

	def updateevent(self, event):
		self.events.update(event.get() if type(event)==events.Event else event.copy())

	def sethost(self, host):
		self.host = host
		self.events["on_host_changed"](host)

	def setport(self, port):
		self.port = port
		self.events["on_port_changed"](port)

	def connect(self, authkey="0"):
		self.sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
		threading.Thread(target=self.connect_, args=(authkey,)).start()

	def connect_(self, authkey):
		try:
			self.sock.connect((self.host, self.port))
			logging.info("initial connection started")
			self.events["on_handshake_started"]()
			try:
				self.handshake(authkey)
			except (ConnectionAbortedError, ConnectionResetError) as e:
				err_msg = "server shutdown during handshake"
				self.events["on_error"](e, err_msg)
				logging.error(err_msg)
				self.close()
		except ConnectionRefusedError as e:
			err_msg = "no connection could be made because host doesnt exist"
			self.events["on_error"](e, err_msg)
			self.close()

	def handshake(self, authkey):
		self.send(authkey)
		logging.info("authkey sent")
		res = self.recv()
		self.events["on_handshake_ended"](res==response.HANDSHAKE_SUCCESSFUL)
		if res == response.HANDSHAKE_SUCCESSFUL:
			logging.info("handshake successful")
			self.connected = True
			self.events["on_connected_changed"](self.connected)
			threading.Thread(target=self.listen).start()
		elif res == response.HANDSHAKE_UNSUCCESSFUL:
			logging.error("handshake unsuccessful")
			self.close()

	def listen(self):
		while self.connected:
			try:
				data = self.recv()
				print("recieved", data)
				self.events["on_data_recieved"](data)
				logging.info("recieved data: "+data)
			except (ConnectionResetError, ConnectionAbortedError) as e:
				msg = "server shutdown unexpectedly"
				self.events["on_error"](e, msg)
				logging.error(msg)
				self.close()

	def send(self, data):
		if data:
			br = base64.b85encode(os.urandom(4)).decode("utf8")
			data = f"{br}::{data}::</{br}>"
			data = bytes(data, "utf8")
			res = self.sock.send(data)
			return res
		return 0

	def recv(self):
		res = self.sock.recv(2048).decode("utf8")

		br = res.split("::")[0]
		while not res.endswith(f"</{br}>"):
			res = res+self.sock.recv(2048).decode("utf8")

		return res[len(br)+2:][:-len(br)-5]

	def close(self):
		if self.sock is not None: self.sock.close()
		self.sock = None
		self.connected = False
		self.events["on_connected_changed"](self.connected)


import streamlit as st
import altair as alt

import functions.data_processor as data_processor
import functions.visualisation as visualisation

from streamlit_extras.dataframe_explorer import dataframe_explorer
import utils.design_format as format
import utils.utils as utils
import datetime

def run_index_tab(uploaded_data_filtered):
    # get list of themes sorted by sum of interactions
    themes_sorted = uploaded_data_filtered.groupby("theme")[
        "facebook_interactions"
    ].sum()
    themes_sorted = themes_sorted.sort_values(ascending=False)
    themes_sorted = themes_sorted.index.tolist()

    selected_theme = st.selectbox("Select Theme", options=themes_sorted)

    theme_data = data_processor.filter_data_by_theme(
        uploaded_data_filtered, selected_theme
    )

    visualisation.show_index_metrics(theme_data)

    format.horizontal_line()

    tab1, tab2, tab3, tab4, tab5 = st.tabs(
        ["Calendar", "Heatmap", "Count Analysis", "Mean Analysis", "Sum Analysis"]
    )

    with tab1:
        selected_index = st.multiselect(
            "Select Index",
            theme_data["index"].unique(),
            default=theme_data["index"].unique()[0],
        )

        # filter based on selected index
        theme_data_cal = theme_data[theme_data["index"].isin(selected_index)]

        subcol1, subcol2 = st.columns([10, 1])
        with subcol1:
            # st.markdown("##### Mean Facebook Interactions")
            st.plotly_chart(
                visualisation.plot_index_calplot(theme_data_cal),
                use_container_width=True,
            )
        with subcol2:
            st.plotly_chart(
                visualisation.show_colour_scale(theme_data_cal),
                use_container_width=True,
            )
    with tab2:
        st.altair_chart(
            visualisation.plot_index_heatmap(theme_data),
            use_container_width=True,
        )

    with tab3:
        col1, col2, col3 = st.columns([2, 1, 2])
        with col2:
            st.subheader("Count Analysis")

        st.markdown("###### Count of Articles by Index")
        index_count_chart = visualisation.plot_index_timeseries(
            theme_data, "count()", "Number of Articles"
        )

        st.altair_chart(index_count_chart, use_container_width=True)

        format.horizontal_line()

    with tab4:
        col1, col2, col3 = st.columns([2, 1, 2])
        with col2:
            st.subheader("Mean Analysis")

        col1, col2 = st.columns([2, 1])
        with col1:
            st.markdown("###### Mean of Facebook Interactions by Index")
            index_mean_chart = visualisation.plot_index_timeseries(
                theme_data,
                "mean(facebook_interactions)",
                "Mean of Facebook Interactions",
            )

            st.altair_chart(index_mean_chart, use_container_width=True)
        with col2:
            df_mean = (
                theme_data.groupby(["index", "date_extracted"])["facebook_interactions"]
                .mean()
                .sort_values(ascending=False)
                .reset_index()
            )
            with st.form("threshold_form_mean_index"):
                threshold = st.slider(
                    "Mean of Facebook Interaction Threshold",
                    min_value=0,
                    max_value=int(df_mean["facebook_interactions"].max()),
                    value=100,
                    step=10,
                )
                submit_threshold_mean = st.form_submit_button(
                    "View Articles Exceeding Threshold",
                    on_click=visualisation.show_articles_exceeding_threshold_index(
                        df_mean, theme_data, "facebook_interactions", threshold
                    ),
                )

        # pct change of mean

        col1, col2 = st.columns([2, 1])
        with col1:
            st.markdown(
                "###### Percent Change in Mean of Facebook Interactions by Index"
            )
            df_mean_agg = data_processor.aggregate_pct_change(
                theme_data, ["index", "date_extracted"], "facebook_interactions", "mean"
            )
            index_pct_change_chart = visualisation.plot_index_timeseries(
                df_mean_agg,
                "pct_change",
                "Percent Change in Mean of Facebook Interactions %",
            )
            st.altair_chart(index_pct_change_chart, use_container_width=True)
        with col2:
            with st.form("threshold_form_pct_change_index"):
                threshold = st.slider(
                    "Percent Change Threshold",
                    min_value=0,
                    max_value=int(df_mean_agg["pct_change"].max()),
                    value=50,
                    step=10,
                )
                submit_threshold_pct_change = st.form_submit_button(
                    "View Articles Exceeding Threshold",
                    on_click=visualisation.show_articles_exceeding_threshold_index(
                        df_mean_agg, theme_data, "pct_change", threshold
                    ),
                )

        format.horizontal_line()

    with tab5:
        col1, col2, col3 = st.columns([2, 1, 2])
        with col2:
            st.subheader("Sum Analysis")

        col1, col2 = st.columns([2, 1])
        with col1:
            st.markdown("###### Sum of Facebook Interactions by Index")
            index_sum_chart = visualisation.plot_index_timeseries(
                theme_data, "sum(facebook_interactions)", "Sum of Facebook Interactions"
            )

            st.altair_chart(index_sum_chart, use_container_width=True)
        with col2:
            df_sum = (
                theme_data.groupby(["index", "date_extracted"])["facebook_interactions"]
                .sum()
                .sort_values(ascending=False)
                .reset_index()
            )
            with st.form("threshold_form_sum_index"):
                threshold = st.slider(
                    "Sum of Facebook Interaction Threshold",
                    min_value=0,
                    max_value=int(df_sum.facebook_interactions.max()),
                    value=1000,
                    step=100,
                )
                submit_threshold_sum = st.form_submit_button(
                    "View Articles Exceeding Threshold",
                    on_click=visualisation.show_articles_exceeding_threshold_index(
                        df_sum, theme_data, "facebook_interactions", threshold
                    ),
                )

        # pct change of sum

        col1, col2 = st.columns([2, 1])
        with col1:
            st.markdown(
                "###### Percent Change in Sum of Facebook Interactions by Index"
            )
            df_sum_agg = data_processor.aggregate_pct_change(
                theme_data, ["index", "date_extracted"], "facebook_interactions", "sum"
            )
            index_pct_change_chart = visualisation.plot_index_timeseries(
                df_sum_agg,
                "pct_change",
                "Percent Change in Sum of Facebook Interactions %",
            )
            st.altair_chart(index_pct_change_chart, use_container_width=True)
        with col2:
            with st.form("threshold_form_pct_change_sum_index"):
                threshold = st.slider(
                    "Percent Change Threshold",
                    min_value=0,
                    max_value=int(df_sum_agg["pct_change"].max()),
                    value=50,
                    step=10,
                )
                submit_threshold_pct_change = st.form_submit_button(
                    "View Articles Exceeding Threshold",
                    on_click=visualisation.show_articles_exceeding_threshold_index(
                        df_sum_agg, theme_data, "pct_change", threshold
                    ),
                )


from ppadb.client import Client as AdbClient
import os # 터미널 접근용
import win32gui

#커스텀
import managerAdb as myAdb    # adb 관련 함수 모음
import managerJson as myJson

# 핸들, 경로
deviceHandleName = "블루 아카이브 - MuMu Player"
pathImg = "./resource/BlueArchive-UI-Img/"
pathScreen = "./temp/"
myJson.imgPathsCreate(pathImg)

# adb 연결
os.system("adb devices")
adbPort = 7555 # 에뮬레이터 포트
client = AdbClient(host="127.0.0.1", port=5037) # adb를 사용해 통신할 client 객체
client.remote_connect("localhost", int(adbPort)) # 에뮬레이터와 연결하는 메서드
deviceInfo = client.device("localhost:"+str(adbPort)) # device() 반환값, 에뮬의 참조 저장

print("Adb detected" if deviceInfo is not None else "Adb not detected")

# 핸들값 추출
deviceHandle = win32gui.FindWindow(None, deviceHandleName)
print("mumuplayer handle is " + str(deviceHandle)) # 이때 핸들은 32비트 정수값이다.

# 현재 에뮬레이터 스크린 캡쳐
myAdb.captureAppScreen(deviceInfo)
cmdCommand = "adb pull /sdcard/nowScreen.png" + " " + pathScreen
os.system(cmdCommand)

# 이미지 탐색 후 좌표 추출
# 이미지경로1, 이미지경로2, 찾을이미지, 현재스크린
print()
print()
print()
print("탐색")
imageNum = myAdb.findCoordinate(pathImg, pathScreen, "Universal/ok_button")
print()
print()
print()
print(imageNum)
print()
print()

# 이미지 좌표 클릭
myAdb.clickXY(deviceInfo, imageNum[0], imageNum[1])
#adbFun.clickImageCenter(findImagePath+"cafe.png")


# file: miles_to_km.py
# joelDay

# This program provides a GUI interface that will take a distance in miles
# and convert it to kilometers
from graphics import *

WINDOW_WIDTH = 600
WINDOW_HEIGHT = 600

def main():

  # Define Window
  win = GraphWin("Convert Miles To Kilometers", WINDOW_WIDTH, WINDOW_HEIGHT)
  win.setBackground("Light Gray")
  win.setCoords(0.0, 0.0, WINDOW_WIDTH, WINDOW_HEIGHT)

  # Define prompt for input
  header = Text(Point(WINDOW_WIDTH // 2, WINDOW_HEIGHT - 50), "Convert your miles to Kilometers!")
  header.setSize(30)
  header.setFill("Dark Slate Gray")
  header.setStyle("bold")
  header.draw(win)

  # Handle miles input
  miles = Entry(Point(WINDOW_WIDTH // 2, WINDOW_HEIGHT - 150), 10)
  miles.setSize(30)
  miles.setText("Enter miles")
  miles.setStyle("bold")
  miles.setFill("Dark Slate Blue")
  miles.draw(win)

  # Create CTA button
  button = Text(Point(WINDOW_WIDTH // 2, WINDOW_HEIGHT // 2), "Click to convert.")
  button.setSize(20)
  button.setFill("Dark Slate Blue")
  button.draw(win)
  win.getMouse()

  # Render output assets
  rectangle = Rectangle(Point(50, WINDOW_HEIGHT // 2 - 50), Point(WINDOW_WIDTH - 50, 50))
  rectangle.setFill("Forest Green")
  rectangle.setOutline("white")
  rectangle.setWidth(15)
  rectangle.draw(win)

  # Convert and output distance in km
  enteredText = miles.getText()
  mi = eval(enteredText)
  km = mi * 1.609
  output = Text(Point(WINDOW_WIDTH // 2, WINDOW_HEIGHT - 450), "%1.1f miles is %1.1f km" % (mi, km))
  output.setSize(36)
  output.setFill("white")
  output.draw(win)
  button.undraw()
  header.setText("Click anywhere to close.")

  # Exit the program
  win.getMouse()
  win.close()

main()


print('''
Python3-скрипт, считающий количество непустых
строк файлов, размещённых в дереве папок.
Автор: Платон Быкадоров (platon.work@gmail.com), 2017-2018.
Версия: V2.3.
Лицензия: GNU General Public License version 3.
Поддержать проект: https://money.yandex.ru/to/41001832285976

Простое руководство по установке среды разработки и запуску скриптов:
github.com/PlatonB/bioinformatic-python-scripts#Установка-среды-разработки

Скрипт генерирует JSON-файл такой структуры:
{
    "in_all_files": [
        61, #Общефайловое количество всех непустых строк.
        59, #Общефайловое количество непустых строк с вычетом их повторов в пределах каждого текста.
        57  #Общефайловое количество непустых строк с вычетом их повторов.
    ],
    "in_each_file": {
        "/home/platon/_0_Диссертация/Exp/os_walk_test_1": {
            "REF_os_walk_test_stat.txt": [
                27, #Количество всех непустых строк одного текста.
                25  #Количество непустых строк одного текста с вычетом их повторов.
            ],
            ...
        },
        ...
    }
}
''')

import os, json

src_dir_path = input('Путь к исходной верхней папке: ')
trg_dir_path = input('\nПуть к папке для конечного JSON-файла: ')
num_of_headers = input('''\nКоличество не учитываемых строк
в начале каждого исходного текста
(игнорирование ввода ==> хэдеров/шапок в текстах нет)
[0(|<enter>)|1|2|...]: ''')
if num_of_headers == '':
        num_of_headers = 0
else:
        num_of_headers = int(num_of_headers)

#Словарь верхнего уровня, в котором размещены такие структуры:
#- список со значаниями суммарного количества строк текстов,
#рассчитываемых без вычета и с вычетом одинаковых элементов;
#- словарь, в котором будут накапливаться пути к родительским папкам,
#имена расположенных в них файлов и длины соответствующих текстов.
statistics = {'in_all_files': [], 'in_each_file': {}}

#Суммарные длины текстов без ликвидации межфайловых повторений
#строк вычисляются без создания отдельного конкатенированного массива.
#Для вычета межфайловых повторений приходится накапливать множество.
#Это может привести к переполнению оперативной памяти.
#Пишите в Issues, если знаете способ решения проблемы.
all_strs_quan, all_files_uniq_strs_quan, all_uniq_strs = 0, 0, set()

#Работа со списком, содержащим кортежи, в каждом из
#которых находится строковый путь к текущей родительской папке,
#список с названиями её подпапок и список с названиями её файлов.
#Список названий папок и/или файлов остаётся пустым, если
#в родительской папке чего-либо из перечисленного нет.
for parent_dir_path, dir_names, file_names in sorted(os.walk(src_dir_path)):

        #Нас интересуют только те кортежи,
        #в которых есть имена файлов.
        if file_names != []:

                #Словарь {имя файла: [количество всех его строк, строк без повторов], ...}.
                files_n_stats = {}

                #Перебор файлов текущей родительской папки.
                for file_name in file_names:
                        with open(os.path.join(parent_dir_path, file_name)) as src_file_opened:

                                #Проверка исходного файла, представляет ли он собой plain text.
                                #Формирование списка из всех строк текста, кроме пустых.
                                try:
                                        one_file_strs = [line.split('\n')[0] for line in src_file_opened if line != '\n'][num_of_headers:]
                                except UnicodeDecodeError:
                                        continue

                                #Количество непустых строк одного текста.
                                one_file_strs_quan = len(one_file_strs)

                                #1) Непустые строки одного текста с удалёнными
                                #повторами и 2) количество этих строк.
                                one_file_uniq_strs = set(one_file_strs)
                                one_file_uniq_strs_quan = len(one_file_uniq_strs)

                                #Метрики текста привязывается к имени соответствующего файла.
                                files_n_stats[file_name] = [one_file_strs_quan, one_file_uniq_strs_quan]

                                #Подсчёт общефайлового количества строк c игнорированием
                                #1) только внутрифайловых повторов, 2) всех повторов.
                                all_files_uniq_strs_quan += one_file_uniq_strs_quan
                                all_strs_quan += one_file_strs_quan

                                #Накопление множества для дальнейшего
                                #рассчёта бесповторного количества всех строк.
                                all_uniq_strs |= one_file_uniq_strs

                #В случае, когда файлы в папке есть, но они все -
                #не plain text, условие if file_names != [] и блок
                #try-except не помогут избежать создания пустого
                #словаря (без пар "имя файла-количество строк").
                #Эта ситуация ниже предусмотрена.
                if files_n_stats != {}:

                        #Привязка словаря пофайловых показателей к родительской папке.
                        statistics['in_each_file'][parent_dir_path] = files_n_stats

#Пополнение словаря суммарных показателей.
statistics['in_all_files'].append(all_strs_quan)
statistics['in_all_files'].append(all_files_uniq_strs_quan)
statistics['in_all_files'].append(len(all_uniq_strs))

#Полученная структура прописывается в JSON-файл с правильной
#обработкой кириллицы, формированием отступов и сортировкой ключей.
trg_file_name = os.path.basename(src_dir_path) + '_stat' + '.json'
with open(os.path.join(trg_dir_path, trg_file_name), 'w', encoding='utf-8') as trg_file_opened:
        json.dump(statistics, trg_file_opened, ensure_ascii=False, indent=4, sort_keys=True)

##Бонус: пример парсера получаемого этим скриптом JSON-файла.
##Извлекаем пофайловые значения количества
##непустых строк без вычета их повторов.
##Созраняем результаты в список.
'''
import json
path = '/home/platon/_0_Диссертация/03_Рез/09_chr14/Biased_1000G/Biased_1000G_stat.json'
data = json.load(open(path))
res = []
for folder_key in data['in_each_file']:
        for file_key in data['in_each_file'][folder_key]:
                res.append(data['in_each_file'][folder_key][file_key][0])
print(res)
#[18, 0, 18, 13, 12]
'''


def is_spam(message: str) -> bool:
    import re

    # Checking for suspicious words indicating spam messages
    spam_words = ['목표달성기념', '추천', '상한가', '반입니다', 'AI사업본격화', 'C상장기업', 'MOU추친중']
    for word in spam_words:
        if word in message:
            return True

    # Checking for excessive usage of special characters
    special_characters = re.findall(r'[^a-zA-Z0-9가-힣\s]', message)
    if len(special_characters) > 5:
        return True

    # Checking for unusual URLs
    url_pattern = re.compile("https?://me2\.kr/[a-zA-Z0-9]*")
    url = re.findall(url_pattern, message)
    if len(url) > 0:
        return True

    return False


from PyQt5.QtWidgets import QWidget
from PyQt5 import QtWidgets

class Chose_worker(QWidget):
    def __init__(self, list_workers):
        super(Chose_worker, self).__init__()

        widget = QtWidgets.QHBoxLayout()
        self.chose = QtWidgets.QComboBox()
        self.chose.addItem("")
        for worker in list_workers:
            self.chose.addItem(worker[0])
        widget.addWidget(self.chose)

        self.setLayout(widget)


"""
server side implementation of subscription service
"""

import asyncio
import logging
from typing import Dict, Iterable

from asyncua import ua
from asyncua.common import utils, uamethod
from .address_space import AddressSpace
from .internal_subscription import InternalSubscription

class SubscriptionService:
    """
    Manages subscriptions on the server side.
    There is one `SubscriptionService` instance for every `Server`/`InternalServer`.
    """

    def __init__(self, aspace: AddressSpace):
        self.logger = logging.getLogger(__name__)
        self.aspace: AddressSpace = aspace
        self.subscriptions: Dict[int, InternalSubscription] = {}
        self._sub_id_counter = 77
        self.standard_events = {}
        self._conditions = {}

    async def create_subscription(self, params, callback, request_callback=None):
        self.logger.info("create subscription")
        result = ua.CreateSubscriptionResult()
        result.RevisedPublishingInterval = params.RequestedPublishingInterval
        result.RevisedLifetimeCount = params.RequestedLifetimeCount
        result.RevisedMaxKeepAliveCount = params.RequestedMaxKeepAliveCount
        self._sub_id_counter += 1
        result.SubscriptionId = self._sub_id_counter
        internal_sub = InternalSubscription(result, self.aspace, callback, request_callback=request_callback)
        await internal_sub.start()
        self.subscriptions[result.SubscriptionId] = internal_sub
        return result

    def modify_subscription(self, params):
        # Requested params are ignored, result = params set during create_subscription.
        self.logger.info("modify subscription")
        result = ua.ModifySubscriptionResult()
        try:
            sub = self.subscriptions[params.SubscriptionId]
            result.RevisedPublishingInterval = sub.data.RevisedPublishingInterval
            result.RevisedLifetimeCount = sub.data.RevisedLifetimeCount
            result.RevisedMaxKeepAliveCount = sub.data.RevisedMaxKeepAliveCount

            return result
        except KeyError:
            raise utils.ServiceError(ua.StatusCodes.BadSubscriptionIdInvalid)

    async def delete_subscriptions(self, ids):
        self.logger.info("delete subscriptions: %s", ids)
        res = []
        existing_subs = []
        for i in ids:
            sub = self.subscriptions.pop(i, None)
            if sub is None:
                res.append(ua.StatusCode(ua.StatusCodes.BadSubscriptionIdInvalid))
            else:
                existing_subs.append(sub)
                res.append(ua.StatusCode())
        stop_results = await asyncio.gather(
            *[sub.stop() for sub in existing_subs], return_exceptions=True
        )
        for stop_result in stop_results:
            if isinstance(res, Exception):
                self.logger.warning("Exception while stopping subscription", exc_info=stop_result)
        return res

    def publish(self, acks: Iterable[ua.SubscriptionAcknowledgement]):
        self.logger.info("publish request with acks %s", acks)
        for subid, sub in self.subscriptions.items():
            sub.publish([ack.SequenceNumber for ack in acks if ack.SubscriptionId == subid])

    async def create_monitored_items(self, params: ua.CreateMonitoredItemsParameters):
        self.logger.info("create monitored items")
        if params.SubscriptionId not in self.subscriptions:
            res = []
            for _ in params.ItemsToCreate:
                response = ua.MonitoredItemCreateResult()
                response.StatusCode = ua.StatusCode(ua.StatusCodes.BadSubscriptionIdInvalid)
                res.append(response)
            return res
        return await self.subscriptions[params.SubscriptionId].monitored_item_srv.create_monitored_items(params)

    def modify_monitored_items(self, params):
        self.logger.info("modify monitored items")
        if params.SubscriptionId not in self.subscriptions:
            res = []
            for _ in params.ItemsToModify:
                result = ua.MonitoredItemModifyResult()
                result.StatusCode = ua.StatusCode(ua.StatusCodes.BadSubscriptionIdInvalid)
                res.append(result)
            return res
        return self.subscriptions[params.SubscriptionId].monitored_item_srv.modify_monitored_items(params)

    def delete_monitored_items(self, params):
        self.logger.info("delete monitored items")
        if params.SubscriptionId not in self.subscriptions:
            res = []
            for _ in params.MonitoredItemIds:
                res.append(ua.StatusCode(ua.StatusCodes.BadSubscriptionIdInvalid))
            return res
        return self.subscriptions[params.SubscriptionId].monitored_item_srv.delete_monitored_items(
            params.MonitoredItemIds)

    def republish(self, params):
        if params.SubscriptionId not in self.subscriptions:
            # TODO: what should I do?
            return ua.NotificationMessage()
        return self.subscriptions[params.SubscriptionId].republish(params.RetransmitSequenceNumber)

    async def trigger_event(self, event, subscription_id=None):
        if hasattr(event, 'Retain') and hasattr(event, 'NodeId'):
            if event.Retain:
                self._conditions[event.NodeId] = event
            elif event.NodeId in self._conditions:
                del self._conditions[event.NodeId]
        if subscription_id is not None:
            if subscription_id in self.subscriptions:
                await self.subscriptions[subscription_id].monitored_item_srv.trigger_event(event)
        else:
            for sub in self.subscriptions.values():
                await sub.monitored_item_srv.trigger_event(event)

    @uamethod
    async def condition_refresh(self, parent, subscription_id, mid=None):
        if subscription_id not in self.subscriptions:
            return ua.StatusCode(ua.StatusCodes.BadSubscriptionIdInvalid)
        sub = self.subscriptions[subscription_id]
        if mid is not None and mid not in sub.monitored_item_srv._monitored_items:
            return ua.StatusCode(ua.StatusCodes.BadMonitoredItemIdInvalid)
        if ua.ObjectIds.RefreshStartEventType in self.standard_events:
            await self.standard_events[ua.ObjectIds.RefreshStartEventType].trigger(subscription_id=subscription_id)
        for event in self._conditions.values():
            await sub.monitored_item_srv.trigger_event(event, mid)
        if ua.ObjectIds.RefreshEndEventType in self.standard_events:
            await self.standard_events[ua.ObjectIds.RefreshEndEventType].trigger(subscription_id=subscription_id)


#!/usr/bin/env python3
import sys, os, glob

def main():
    try:
        module_paths = sys.argv[1]
        group_paths = sys.argv[2]
    except IndexError:
        print("Usage: <Module Paths> <KO IDs> \n",
        "Module Paths: Module Paths tsv from enrichm classify \n",
        "KO IDs: Clusters, Orthologs, and KO IDs from getEnrichMKOs.py")
        return
    modules = open(module_paths)
    groups = open(group_paths)
    ko_dict = {}
    for line in modules:
        mod = line.split("\t")[1]
        KOs = line.split("\t")[-1].strip().split(',')
        for ko in KOs:
            ko_dict[ko] = mod.strip()

    print('cluster\tortholog\tko\tmodule')
    for line in groups:
        line = line.split('\t')
        try:
            print('%s\t%s\t%s\t%s' % (line[0], line[1], line[2].strip(), ko_dict[line[2].strip()]))
        except KeyError:
            pass

if __name__ == '__main__':
	main()


# 下载一个牛仔合集网页上的多个专辑：
# cd "python/meitulu"
# python meitulu3.py https://www.tujidao.com/s/?id=24 (牛仔合集的一个网页)
import os
import requests
from bs4 import BeautifulSoup
from requests.packages import urllib3
os.chdir(r'E:\MyGit\python\meitulu')
# 定义函数:输入一个合集网页，得到一个网页下所有专辑的链接:
def get_add(url):
    headers = {'user-agent': 'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.110 Mobile Safari/537.36 Edg/96.0.1054.62',
    'cookie':'UM_distinctid=17bf81bb0772ae-07ff0e6c48d262-57341040-240000-17bf81bb078b2b; PHPSESSID=isijdiah8msh88rln1tgqp0i0j; CNZZDATA1257039673=1055518379-1615096700-%7C1641000419; uid=46423; name=frozenevil; leixing=3'}
    urllib3.disable_warnings()
    r = requests.get(url, headers=headers,timeout=10,verify = False)
    r.encoding = r.status_code
    soup = BeautifulSoup(r.text,'lxml')
    text1 = soup.find_all(attrs={'class':'biaoti'})
    address = []
    for i in text1:
        address.append('https://www.tujidao.com'+i.a['href'])
    return address

# 定义函数:输入某个模特的合集网页,下面自动爬取所有专辑的图片
def get_pics(url):
    address = get_add(url)
    for i in address:
        os.system("python meitulu2.py {0}".format(i))

#if __name__ == '__main__':
    #url = sys.argv[1]       # 输入的多个专辑合集的网址赋值给url；
    #get_pics(url)     # 获取该合集下的多个专辑的网址；

'''
url = "https://www.tujidao.com/s/?id=24"
address = get_add(url)
'''


import requests
from scraper.newspaper_git.newspaper import Article, Config, Source
from waybackpy import Url
from time import sleep
from random import randint

def get_article(url):
    article=Article(url)
    article.download()
    article.parse()
    return article.text

class wayback_scraper:
    def __init__(self, url, agent='Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:78.0) Gecko/20100101 Firefox/78.0'):
        self.agent=agent
        self.wayback_obj = Url(url, agent)
        #print(self.wayback_obj)
        self.wayback_url = None

    def set_date(self, y, m, d):
        self.wayback_url = str(self.wayback_obj.near(year=y, month=m, day=d))
        updated_url = self.wayback_url.split("/")
        #print(updated_url)
        updated_url[5] = "https:"
        self.wayback_url = "/".join(updated_url)
        #print(self.wayback_url)

    def get_articles(self, timeout=None):
        #Returns a list of newspaper articles

        if self.wayback_url == None:
            raise ValueError("Must set date with set_date function")

        config = Config()
        config.browser_user_agent = self.agent
        config.request_timeout = timeout
        config.memoize_articles = False
        config.language='en'
        config.number_threads = 20
        config.threat_timeout_seconds=2
        config.verbose=False
        wayback = Source(url=self.wayback_url, config=config)
        wayback.build()

        return wayback.articles

    def search_by_title(self, keywords):

        articles=self.get_articles()
        ret_articles = []

        for article in articles:
            #print(article.url)
            if type(article.title) == str:
                if any(word in article.title for word in keywords):
                    if article not in ret_articles:
                        ret_articles.append(article)

        return ret_articles
    def search_by_text(self,keywords):
        articles=self.get_articles()
        ret_articles = []

        for article in articles:
            #print(article.url)
            try:
                article.download()
                article.parse()
            except:
                continue
            else:
                if type(article.title) == str:
                    if any(word in article.title for word in keywords):
                        if article not in ret_articles:
                            ret_articles.append(article)


import os, asyncio, datetime, json
import discord
from discord.ext import commands
from dotenv import load_dotenv
from gtts import gTTS
from collections import deque
from tempfile import TemporaryFile

load_dotenv()
TOKEN = os.getenv("DISCORD_TOKEN")
PREFIX = os.getenv("DISCORD_PREFIX")

tts_focusing = {}

bot = commands.Bot(command_prefix=PREFIX, description="WowZa bot V0.2")

async def getTTS(message):
    tts = gTTS(message, lang='th')
    f = TemporaryFile()
    tts.write_to_fp(f)
    f.seek(0)
    return f

@bot.event
async def on_ready():
    print("WowZa is ready to serve!")

@bot.command()
async def ping(ctx):
    await ctx.send("pong")

@bot.command()
async def info(ctx):
    embed = discord.Embed(title=f"{ctx.guild.name}", description="Hello World!", timestamp=datetime.datetime.utcnow(), color=discord.Color.blue())
    embed.add_field(name="Server created at", value=f"{ctx.guild.created_at}")
    embed.add_field(name="Server Owner", value=f"{ctx.guild.owner}")
    embed.add_field(name="Server Region", value=f"{ctx.guild.region}")
    embed.add_field(name="Server ID", value=f"{ctx.guild.id}")
    embed.set_thumbnail(url=f"{ctx.guild.icon_url}")

    await ctx.send(embed=embed)

@bot.command()
async def clear(ctx):
    botQuestionMessage = await ctx.message.channel.send("Are you sure you want to clear the messages? type \"Yes or No\"")
    clearingMessage = "👍 Clearing "

    def check(m):
        return (m.content == "Yes" or m.content == "No") and m.channel == ctx.message.channel and m.author == ctx.message.author
    msg=None
    try:
        msg = await ctx.bot.wait_for('message', check=check, timeout=6)
    except asyncio.TimeoutError:
        await ctx.message.channel.send('👎 Timed out')

    if msg.content != "Yes":
        botRecentMessage = await ctx.message.channel.send("Okay, I won't clear the messages.")
        await asyncio.sleep(5)
        await msg.delete(delay=3)
        await botQuestionMessage.delete(delay=3)
        await botRecentMessage.delete(delay=3)
        return
    if ctx.message.mentions:
        if not ctx.message.author.guild_permissions.administrator and ctx.message.mentions[0] != ctx.message.author:
            await ctx.message.channel.send("You don't have permission to clear messages")
            return

        if ctx.message.author == ctx.message.author:
            clearingMessage += "all your messages"

    clearingMessage += ".."
    botRecentMessage = await ctx.message.channel.send(clearingMessage)
    async for m in ctx.message.channel.history(limit=100):
        if m == botRecentMessage:
            continue
        if not ctx.message.mentions or (m.author == ctx.message.mentions[0]):
            await m.delete(delay=3)

    await asyncio.sleep(5)
    await botRecentMessage.delete(delay=3)
    await msg.delete(delay=3)
    await botQuestionMessage.delete(delay=3)

@bot.command()
async def join(ctx):
    try:
        channel = ctx.message.author.voice.channel
        await channel.connect()
        return
    except(TypeError, AttributeError):
        await ctx.send("Either you are not in a voice channel, or I can't see the channel!")
        return

@bot.command()
async def leave(ctx):
    try:
        await ctx.voice_client.disconnect(force=True)
        return
    except(TypeError, AttributeError):
        await ctx.send("Can't disconnect from a voice channel when I'm not in one!")
        return

@bot.command()
async def say(ctx):
    message_queue = deque([])
    message = ctx.message.content[5:]
    usernick = ctx.message.author.display_name
    message = usernick + " พูดว่า " + message
    try:
        vc = ctx.message.guild.voice_client
        if not vc.is_playing():
            f = await getTTS(message)
            vc.play(discord.FFmpegPCMAudio(f, pipe=True))
        else:
            message_queue.append(message)
            while vc.is_playing():
                await asyncio.sleep(0.1)
            f = await getTTS(message_queue)
            vc.play(discord.FFmpegPCMAudio(f, pipe=True))
    except(TypeError, AttributeError):
        try:
            f = await getTTS(message)
            channel = ctx.message.author.voice.channel
            vc = await channel.connect()
            vc.play(discord.FFmpegPCMAudio(f, pipe=True))
        except(AttributeError, TypeError):
            await ctx.send("I'm not in a voice channel and neither are you!")
        return
    f.close()

@bot.event
async def on_voice_state_update(ctx, before, after):
    channel = ctx.guild.text_channels[4]
    if before.channel != after.channel:
        embed = discord.Embed(title=f"{ctx.guild.name}", description="Leave/Join",
                    timestamp=datetime.datetime.utcnow(), color=discord.Color.blue())
        if before.channel : embed.add_field(name="Leaved", value=f"{before.channel.mention}")
        if after.channel : embed.add_field(name="Joined", value=f"{after.channel.mention}")
        embed.set_thumbnail(url=f"{ctx.avatar_url}")
        await channel.send(embed=embed)

@bot.command()
async def populate(ctx):
    for i in range(10):
        await ctx.message.channel.send("Hello~" + str(i))
        asyncio.sleep(5)

@bot.command()
async def focus_on_me(ctx):
    if ctx.author.id in tts_focusing:
        await ctx.message.channel.send(str(f"I am focusing you {ctx.author.display_name}"))
        return
    if not ctx.author.voice.channel:
        await ctx.message.channel.send(str(f"{ctx.author.display_name} you are not in the voice channel."))
        return
    tts_focusing[ctx.author.id] = True

@bot.event
async def on_message(message):
    if message.content[0:len(PREFIX)] != PREFIX and message.author != bot.user:
        print(message.guild.voice_client)
        return

    await bot.process_commands(message)

bot.run(TOKEN)


#!/usr/bin/python3
# -*- coding: utf-8 -*-

# author: Thomas Kaergel kaergel at b1-systems.de>
# last-modified:: 2019-01-17
# purpose: backupscript for use with cron and borg
# name: borgcron

import os
import datetime
import argparse
import sys
import yaml
import logging
import re
import socket
import struct
import subprocess
import sys
import time

defaultlogfile = 'borgcron.log'
defaultloglevel = logging.WARNING

LOG = logging.getLogger(__name__)

class options(object):
    def __init__(self):
        self._init_parser()

    def _init_parser(self):
        self.parser = argparse.ArgumentParser()
        self.parser.add_argument('-s', "--stdout",
                                 help='print log to stdout too',
                                 action='store_true')
        self.group = self.parser.add_mutually_exclusive_group(required=False)
        self.group.add_argument('-d', '--debug',
                                help="print lots of debugging statements",
                                action="store_const",
                                default=defaultloglevel,
                                dest="loglevel", const=logging.DEBUG)
        self.group.add_argument('-v', '--verbose',
                                help="be verbose",
                                action="store_const",
                                default=defaultloglevel,
                                dest="loglevel", const=logging.INFO)
        self.parser.add_argument('-p', "--pretend",
                                 help='nothing is really done! '
                                      'borgcron just generates the borg '
                                      'command-lines, prints them to stdout'
                                      'and exits',
                                 action='store_true')
        self.parser.add_argument('configfile',
                                 nargs='?',
                                 type=argparse.FileType('r'),
                                 default=sys.stdin,
                                 help='a config file in YAML format.'
                                      ' Can also be read from stdin.')
        self.parser.add_argument('-l', "--logfile",
                                 metavar='logfile',
                                 # nargs='*',
                                 type=argparse.FileType('a'),
                                 default=defaultlogfile,
                                 help='default logfile is borgcron.log')

    def parse(self, args=None):
        return self.parser.parse_args(args)

class clicommand(object):
    def __init__(self, cmdline, logfile):
        self._cmdline = cmdline
        self._logfile = logfile

    def execute(self):
        LOG.info("executing cli-command: \n")
        proc = subprocess.Popen(self._cmdline,
                                stdout = self._logfile,
                                stderr = subprocess.STDOUT,
                                universal_newlines = True,
                                shell = False)
        returncode = proc.wait()
        LOG.info("command returned: %s" % returncode)
        return returncode

class backupdir(object):
    def __init__(self, directory):
        self._name = directory["name"]
        self._days = directory["days"]
        self._month = directory["month"]
        self._years = directory["years"]
        self._namedepth = directory["namedepth"]

    def _get_title(self):
        LOG.debug("_get_title says self._name is %s" % self._name)
        title = ""
        path = self._name
        depth = self._namedepth
        while path is not "/" and depth > -1:
            path, folder = os.path.split(path)
            LOG.debug("path prefix is %s. foldername is %s" % (path, folder))
            if depth > 0:
                title = "°" + folder + title
            else:
                title = folder + title
            depth -= 1
        LOG.debug("title is: %s" % title)
        return title

    def generate_cmds(self, args, flags, comp, repo):
        LOG.info("Starting backup of directroy %s" % self._name)
        LOG.debug("pretend is: %s" % args.pretend)
        now = datetime.datetime.today().strftime('%Y-%m-%d_%H%M%S')
        create = ['/usr/local/bin/borg', 'create', '-C']
        create += [comp]
        create += flags.split()
        create += [repo + '::' + self._get_title() + '-' + now]
        create += [self._name]
        LOG.info("generated borg create command is:")
        LOG.info(create)
        prune = ['/usr/local/bin/borg', 'prune']
        prune += flags.split()
        prune += '-d', str(self._days)
        prune += '-m', str(self._month)
        prune += '-y', str(self._years)
        prune += repo,
        prune += '-P', self._get_title()
        LOG.info("generated borg prune command is:")
        LOG.info(prune)
        return create, prune

def wake_on_lan(cfg):

    LOG.info("Sending WakeOnLAN magic paket.")
    mac_str = cfg["config"]["wol_mac_address"]
    net_bcast = cfg["config"]["remote_bcast_address"]
    addr_byte = mac_str.split(':')
    hw_addr = struct.pack('BBBBBB', int(addr_byte[0], 16),
                                    int(addr_byte[1], 16),
                                    int(addr_byte[2], 16),
                                    int(addr_byte[3], 16),
                                    int(addr_byte[4], 16),
                                    int(addr_byte[5], 16))
    msg = b'\xff' * 6 + hw_addr * 16
    sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    sock.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
    sock.sendto(msg, (net_bcast, 7))
    sock.sendto(msg, (net_bcast, 9))
    sock.close()
    return

def check_server(cfg):

    LOG.info("Checking if ssh on remote host is listening... plz wait")
    wol_ip = cfg["config"]["remote_host_address"]
    sock = socket.socket()
    count = 0
    res = sock.connect_ex((wol_ip, 22))
    while res != 0 and count < 300:
        time.sleep(1)
        count += 1
        sock.close()
        sock = socket.socket()
        res = sock.connect_ex((wol_ip, 22))
    if res != 0:
        LOG.critical("Remote host did not come up!")
        exit(1)
    LOG.info("Remote host is now up!")
    time.sleep(3)
    return

def configlogger(args):
    LOG.setLevel(defaultloglevel)
    logfile = open(args.logfile.name, 'a')
    fh = logging.StreamHandler(logfile)
    fh.setFormatter(logging.Formatter(
                    '%(asctime)s - %(levelname)s - %(message)s'))
    LOG.addHandler(fh)
    if args.stdout:
        LOG.warn('duplicating log to stdout')
        ch = logging.StreamHandler()
        ch.setFormatter(logging.Formatter(
                        '%(asctime)s - '
                        '%(levelname)s - %(message)s'))
        LOG.addHandler(ch)
    LOG.warn('-' * 80)
    LOG.warn("borgcron by Thomas Kärgel - starting new backup run")
    LOG.warn('Switching to loglevel %s' % args.loglevel)
    LOG.setLevel(args.loglevel)
    return logfile

def parseconfig(args):
    if os.path.isfile(args.configfile.name):
        LOG.info("Reading YAML config from file")
        stream = open(args.configfile.name, 'r')
    else:
        LOG.warn("Awaiting YAML config from stdin")
        stream = sys.stdin
    try:
        config = yaml.safe_load(stream)
        LOG.debug("YAML config is:\n" + yaml.dump(config,
                                                  explicit_start=True,
                                                  default_flow_style=False))
    except yaml.YAMLError as exc:
        logging.critical(exc)
        exit(1)
    return config

def pretendoutput(createcmd, prunecmd):
    createstr = ''
    for i in createcmd:
        createstr = createstr + str(i) + ' '
    print("-" * 80)
    print("create command is:")
    print(createstr)
    prunestr = ''
    for i in prunecmd:
        prunestr = prunestr + str(i) + ' '
    print("-" * 80)
    print("prune command is:")
    print(prunestr)

def main():
    args = options().parse()
    logfile = configlogger(args)
    LOG.debug("args:\n" + str(args))
    cfg = parseconfig(args)
    repo = cfg["config"]["target_repository"]
    comp = cfg["config"]["compression"]
    flags = cfg["config"]["borg_options"]
    prescript = cfg["config"]["prerun_script"]
    if cfg["config"]["wake_remote_host"] and not args.pretend:
        wake_on_lan(cfg)
        check_server(cfg)
    LOG.debug("prescript is: %s" % prescript.split())
    if prescript != "":
        returncode = clicommand(prescript.split(), logfile).execute()
        if returncode == 1:
            LOG.critical("execution of prerun_script failed! -> bailing out.")
            exit(1)
    if "directories" in cfg["config"]:
        for directory in cfg["config"]["directories"]:
            LOG.debug("item config is:\n" +
                      yaml.dump(directory,
                                explicit_start=True,
                                default_flow_style=False))
            dir_item = backupdir(directory)
            LOG.debug("dir_item.name is %s" % dir_item._name)
            createcmd, prunecmd = dir_item.generate_cmds(args, flags, comp, repo)
            if args.pretend:
                pretendoutput(createcmd, prunecmd)
            else:
                clicommand(createcmd, logfile).execute()
                if directory["prune"]:
                    clicommand(prunecmd, logfile).execute()
    if cfg["config"]["shutdown_remote_host"]:
        sshtarget = repo.split(':')
        shutdowncmd = ("ssh %s %s" % (sshtarget[0],
                       cfg["config"]["shutdown_command"]))
        LOG.debug("shutdowncmd is: %s" % shutdowncmd)
        if not args.pretend:
            LOG.info("Shuting down remote host.")
            returncode = clicommand(shutdowncmd.split(),
                                    logfile).execute()
            if returncode == 1:
                LOG.critical("Shutdown of remote failed!")
                exit(1)
    postscript = cfg["config"]["postrun_script"]
    LOG.debug("postscript is: %s" % postscript.split())
    if postscript != "":
        returncode = clicommand(postscript.split(), logfile).execute()
        if returncode == 1:
            LOG.critical("execution of postrun_script failed! -> bailing out.")
            exit(1)

if __name__ == "__main__":
    main()
    exit(0)


# list = [['foobar', 'a', 'b'], ['x', 'c'], ['y', 'd', 'e', 'foobar'], ['z', 'f']]
# x = sum(x.count('foobar') for x in list)
# print(x)

a = [[1, 2], [3, "s"], [5, 6]]

x = [x for x in a if "s" in x][0]

print(f'The index is (%d,%d)' % (a.index(x), x.index("s")))


# converter.py
# This file will contain the source code for converting csv files to json

import csv
import os
import ERROR

# A function that returns "In CLI". This function is called in main.py to signify that the GUI has not been started.
def cli():
    return "In CLI"

joint_order = ["Head",
               "Neck",
               "LeftShoulder",
               "RightShoulder",
               "LeftElbow",
               "RightElbow",
               "LeftWrist",
               "RightWrist",
               "LeftHand",
               "RightHand",
               "TopSpine",
               "MidSpine",
               "BaseSpine",
               "LeftHip",
               "RightHip",
               "LeftKnee",
               "RightKnee",
               "LeftFoot",
               "RightFoot"]

# A function which converts a vertically aligned csv to the strict json required
def convert_vertical(filename, output, c):

    if (os.path.isdir(output)):
      base = os.path.splitext(os.path.basename(filename))[0]
      output = output + base + ".json"
    # Open the output file in write mode and write the header fields of the json
    try:
      out = open(output, "w")
    except Exception as e:
      ERROR.error("while trying to open " + output + " for output: " + str(e))
      return
    out.write("{\"d\":" + str(c.config["Device"]) + ","
              + "\"g\":\"(" + str(c.config["Ground"][0]) + "," + str(c.config["Ground"][1]) + "," + str(
        c.config["Ground"][2]) + "," + str(c.config["Ground"][3]) + ")\","
              + "\"o\":\"" + str(c.config["Offset"]) + "\","
              + "\"t\":\"{\\\"Items\\\":[")

    if(c.config["ColumnSeparator"] == "Spaces"):
      column_separator = None # the default separator for str.split() is any whitespace so we can use the default
    elif (c.config["ColumnSeparator"] == "Comma"):
      column_separator = ','
    else: # default column separator is comma
      column_separator = c.config["ColumnSeparator"]

    # Read every row of the csv (or other filetype) and process the data accordingly
    with open(filename) as f:
      row_idx = 0
      frame = 0
      for line in f:
        try:
          row = line.split(column_separator)
        except Exception as e:
          ERROR.error("While trying to split line: \"" + line + "\" into an array with column separator: " + str(column_separator) + "\n\tAborting conversion of this file: " + filename)
          return
        if row_idx > c.config["StartRow"]:
          # Write the frame field
          if frame > 0:
            out.write(",")
          out.write("{\\\"f\\\":")

          if c.config["Frames"]["FramesInfo"]:
            time = row[c.config["Frames"]["FrameIdx"]]
            if frame >= int(float(time) * 33):
              frame = frame + 1
            else:
              frame = int(float(time) * 33)
            out.write(str(frame))
          else:
            out.write(str((frame + 1) * 33))
            frame = frame + 1

          out.write(",")

          # Write the joint information appropriately
          out.write("\\\"b\\\":{\\\"i\\\":" + str(frame + 1) + ",")
          out.write("\\\"j\\\":[")

          for joint in joint_order:
            out.write("{\\\"s\\\":" + str(c.config["Joints"][joint]["status"]).strip() + ",")
            try:
             out.write(
             "\\\"p\\\":\\\"("
             + str(
              float(row[c.config["Joints"][joint]["x-column"]]) * float(c.config["magnify"]["x"])
              + float(
                c.config["x-offset"]
              )
             ).strip() + ","
             + str(
              float(row[c.config["Joints"][joint]["y-column"]]) * float(c.config["magnify"]["y"])
              + float(
                c.config["y-offset"]
              )
             ).strip() + ","
             + str(
              float(
                row[c.config["Joints"][joint]["z-column"]]) * float(c.config["magnify"]["z"])
                + float(
                  c.config["z-offset"]
                )
             ).strip()
             + ")\\\","
             )
            except Exception as e:
              ERROR.warn("Exception raised: " + str(e) + ": for joint: " + joint + " in frame: " + str(frame) + " for file: " + filename)
            out.write("\\\"q\\\":\\\"(0,0)\\\",")
            out.write("\\\"o\\\":\\\"(0,0,0,0)\\\"}")
            if joint != joint_order[len(joint_order) - 1]:
              out.write(",")

          out.write("],")
          out.write("\\\"r\\\":0,")
          out.write("\\\"l\\\":0,")
          out.write("\\\"_negativeGroundOffset\\\":0.0,")
          out.write("\\\"_previousNegativeGroundOffset\\\":0.0")
          out.write("}")
          out.write("}")

        row_idx = row_idx + 1

      out.write("]}\"}")

# A function which converts a vertically aligned csv to the strict json required
def convert_ntu(filename, output, c):
    body_id_and_file = {}

    # Open the output file in write mode and write the header fields of the json
    if os.path.isfile(output):
      out = open(output, "w")
    elif os.path.isdir(output):
      base = os.path.slitext(os.path.basename(filename))
      output = os.path.join(output, base + ".json")
      try:
        out = open(output, "w")
      except Exception as e:
        ERROR.warn("Failed to open file for writing: " + output + "\n\tAborting conversion of " + filename)
    out.write("{\"d\":" + str(c.config["Device"]) + ","
              + "\"g\":\"(" + str(c.config["Ground"][0]) + "," + str(c.config["Ground"][1]) + "," + str(
        c.config["Ground"][2]) + "," + str(c.config["Ground"][3]) + ")\","
              + "\"o\":\"" + str(c.config["Offset"]) + "\","
              + "\"t\":\"{\\\"Items\\\":[")

    if(c.config["ColumnSeparator"] == "Spaces"):
      column_separator = None # the default separator for str.split() is any whitespace so we can use the default
    else: # default column separator is comma
      column_separator = ','

    # Read every row of the csv (or other filetype) and process the data accordingly
    with open(filename) as f:
      framecount = int(f.readline())
      for frame in range(framecount):
       bodycount = int(f.readline())
       for body_number in range(bodycount):
          body_meta_data = f.readline()
          body_meta_data = body_meta_data.split(column_separator)
          bodyID = body_meta_data[0]
          trackingState = body_meta_data[9]
          number_of_joints = int(f.readline())

          # Write the frame field
          if frame > 0:
            out.write(",")
          out.write("{\\\"f\\\":")

          out.write(str((frame + 1) * 33))
          frame = frame + 1

          out.write(",")

          # Write the joint information appropriately
          out.write("\\\"b\\\":{\\\"i\\\":" + str(bodyID) + ",")
          out.write("\\\"j\\\":[")

          all_joints  = []

          for joint in range(number_of_joints):
            joint_info = f.readline().split(column_separator)
            x = str(joint_info[0]).strip()
            y = str(joint_info[1]).strip()
            z = str(joint_info[2]).strip()
            trackingState = str(joint_info[len(joint_info) -1]).strip()
            joint_info = {
                "x": x,
                "y": y,
                "z": z,
                "trackingState": trackingState}
            all_joints.append(joint_info)

          for joint in joint_order:
            try:
              ntu_joint = all_joints[int(c.config["JointMap"][joint])]
            except Exception as e:
              ERROR.warn("Exception getting joint from list of joints: " + str(e) + ": for joint: " + joint + " in frame: " + str(frame) + " for file: " + filename + " in dir: " + os.getcwd())
            try:
              out.write("{\\\"s\\\":" + ntu_joint["trackingState"] + ",")
            except Exception as e:
              ERROR.warn("Exception raised while setting tracking state: " + str(e) + ": for joint: " + joint + " in frame: " + str(frame) + " for file: " + filename + " in dir: " + os.getcwd())
              return
            try:
             out.write("\\\"p\\\":\\\"("
             + str(float(ntu_joint["x"]) * float(c.config["magnify"]["x"])
              + float(c.config["x-offset"])).strip() + ","
             + str(float(ntu_joint["y"]) * float(c.config["magnify"]["y"])+ float(c.config["y-offset"])).strip() + ","
             + str(float(ntu_joint["z"]) * float(c.config["magnify"]["z"])
                + float(c.config["z-offset"])).strip()+ ")\\\",")
            except Exception as e:
              ERROR.warn("Exception raised: " + str(e) + ": for joint: " + joint + " in frame: " + str(frame) + " for file: " + filename + " in dir: " + os.getcwd())
              return
            out.write("\\\"q\\\":\\\"(0,0)\\\",")
            out.write("\\\"o\\\":\\\"(0,0,0,0)\\\"}")
            if joint != joint_order[len(joint_order) - 1]:
              out.write(",")

          out.write("],")
          out.write("\\\"r\\\":0,")
          out.write("\\\"l\\\":0,")
          out.write("\\\"_negativeGroundOffset\\\":0.0,")
          out.write("\\\"_previousNegativeGroundOffset\\\":0.0")
          out.write("}")
          out.write("}")

      out.write("]}\"}")


# Import
import requests
import zipfile
import io

class GitApi():
    """docstring for GitApi"""

    def __init__(self):

        # self.is_username = False
        print('but firstly you need to set user to explore:')

        try:
            while True:
                self.user = input("SET USER>")
                self.user_info = self.get_user_git()
                self.status = self.user_info.status_code

                if self.status == 200:
                    print('You got this user name right!')
                    break
                else:
                    print("You have entered wrong user name. Try Again")
                    print('')

        except EOFError:
            print("You have done something wrong")

        self.repo_list = None

    def get_user_git(self):
        url = 'https://api.github.com/users/{}'.format(self.user)
        self.r = requests.get(url)
        return self.r

    def git_user_info(self):

        print('')
        print('Here is all info for git user {}'.format(self.user))
        return self.user_info.json()

    def get_repos(self):

        get_repos = self.user_info.json()['repos_url']
        r = requests.get(get_repos)
        repos = r.json()
        list_of_repos = [repo["name"] for repo in repos]
        self.repo_list = list_of_repos
        print('')
        print("User {} has the following repos: ".format(self.user))

        for i in range(len(list_of_repos)):
            print('[{}] {}'.format(i + 1, list_of_repos[i]))

        return "These are all of {} repos".format(self.user)

    def get_zip(self, repo_num):

        url = 'https://github.com/{}/{}/archive/master.zip'.format(self.user, self.repo_list[int(repo_num) - 1])

        repo = requests.get(url)

        zfile = io.BytesIO(repo.content)

        read_zfile = zipfile.ZipFile(zfile, 'r')

        for name in read_zfile.namelist():
            print("File: ", name)

        read_zfile.close()

        return "All files in his repo"

    def create_help(self):
        help_menu = [
            '',
            'Here is full list of commands:',
            '',
            '*user_repo',
            '*get_repos',
            '*user_zipfiles <repo ID>',
            '*exit']

        return '\n'.join(help_menu)

    def unknown_command(self):
        false_command = [
            ''
            'you have entered invalid command',
            'type "help" to get all available commands']

        return '\n'.join(false_command)

    def parse_command(self, command):
        return tuple(command.split(" "))

    def is_command(self, command_tuple, command_string):
        return command_tuple[0] == command_string

def create_menu():
    menu = [
        '',
        'Welcome to this brainfuck app',
        'if you are confused, just type "help"']

    return '\n'.join(menu)

def main():

    print(create_menu())
    spy = GitApi()

    while True:

        print('')
        command = spy.parse_command(input("Enter command>"))

        if spy.is_command(command, "help"):
            print(spy.create_help())

        elif spy.is_command(command, "user_repo"):
            print(spy.git_user_info())

        elif spy.is_command(command, "get_repos"):
            print(spy.get_repos())

        elif spy.is_command(command, "user_zipfiles"):
            print(spy.get_zip(command[1]))

        elif spy.is_command(command, "exit"):
            break

        else:
            print(spy.unknown_command())

    # elif is_command(command, "list"):
    #     trigger_list(command)

if __name__ == '__main__':
    main()