#author("2025-02-04T08:04:47+09:00","default:BotComputing-WikiIoT","BotComputing-WikiIoT") #author("2025-02-08T11:19:40+09:00","default:BotComputing-WikiIoT","BotComputing-WikiIoT") [[FrontPage]] #code(Python){{ # -*- coding: utf-8 -*- # # wiki_bot_05.py # Takashi Yamanoue # 20250204 # 20250208 # import time import requests from requests_toolbelt import MultipartEncoder import socket try: import ustruct as struct except: import struct from time import sleep import gc import copy import threading import sys from tkinter import * from tkinter import Label from tkinter import Button import tkinter as tk from tkinter import scrolledtext #from PIL import Image, ImageTk, ImageOps import tkinter.ttk as ttk from tkinter import messagebox from tkinter import filedialog import time import json import pickle import serial import mimetypes initials = {'bot_id':'yama_bot_0000_0000_0000_0001', 'waiting_term':600000, 'object_page_1':'http://192.168.10.10/fwb4pi/index.php?work20240902-01', 'object_page_2':'http://192.168.10.11/fwb4pi/index.php?work20240902-01', 'object_page_pass_1':'', 'object_page_pass_2':'', 'read_interval': 20000, 'exec_interval': 0, 'write_interval':0, 'report_length':120 } class Properties: def __init__(self): self.properties=initials self.file_name="bot.properties" def set_gui(self,gui): self.gui=gui def load(self,fn): try: with open(fn,mode='rb') as f: prop_w=pickle.load(f) for key in prop_w: self.properties[key]=prop_w[key] self.map_to_gui() except Exception as e: print("file "+fn+" read error") tb=sys.exc_info()[2] print("message:{0}".format(e.with_traceback(tb))) def map_to_gui(self): for key in self.properties: self.gui.map_to_gui(key,self.properties[key]) def map_from_gui(self): for key in self.properties: v=self.gui.lookup_prop(key) self.properties[key]=v def get(self,key): if key in self.properties: return self.properties[key] return None def set(self,key,value): self.properties[key]=value def save(self,fn): self.map_from_gui() try: with open(fn,mode='wb') as f: pickle.dump(self.properties,f) except Exception as e: print("file "+fn+" write error") tb=sys.exc_info()[2] print("message:{0}".format(e.with_traceback(tb))) class GUI: def __init__(self,root,bot): self.bot=bot self.recv_queue=[] self.root=root self.root.title("Wiki Bot panel") self.root.configure(background="white") self.root.geometry("850x800") self.notebook =ttk.Notebook(root) self.main_tab=tk.Frame(self.notebook, bg='white') self.script_tab=tk.Frame(self.notebook, bg='white') self.notebook.add(self.main_tab, text="main", underline=0) self.notebook.add(self.script_tab, text="script") self.notebook.pack(expand=True, fill='both', padx=10, pady=10) yy=10 # command list self.start_button=Button(self.main_tab, text="start",bd=2,bg='white',command=self.click_start_button, width=12, relief=RIDGE) self.start_button.place(x=10,y=yy) self.stop_button=Button(self.main_tab, text="stop",bd=2,bg='white',command=self.click_stop_button, width=12, relief=RIDGE) self.stop_button.place(x=80,y=yy) self.save_prop_button=Button(self.main_tab, text="save prop",bd=2,bg='white',command=self.click_save_prop_button, width=24, relief=RIDGE) self.save_prop_button.place(x=150,y=yy) self.clear_message_button=Button(self.main_tab, text="clear",bd=2,bg='white',command=self.clear_message, width=15, relief=RIDGE) self.clear_message_button.place(x=280,y=yy) yy=40 # this bot id, waiting term self.bot_label=Label(self.main_tab,text="bot", width=6) self.bot_label.place(x=10,y=yy) self.bot_id_field=Entry(self.main_tab,width=50) self.bot_id_field.place(x=50,y=yy) self.waiting_term_label=Label(self.main_tab,text="wait", width=8) self.waiting_term_label.place(x=380,y=yy) self.waiting_term_field=Entry(self.main_tab,width=10) self.waiting_term_field.place(x=450,y=yy) yy=70 self.page_frame = ttk.Frame(self.main_tab) self.page_frame.grid(row=0, column=0) # 項目をつくる items = ['URI', 'name', 'pass'] for i in range(0, len(items)): label_item = ttk.Label(self.page_frame,text=items[i]) label_item.grid(row=0, column=i) n = 2 # 行数 # 項目1 self.object_page_table_uri = [0] * n for i in range(0, n): self.object_page_table_uri[i] = ttk.Entry(self.page_frame, width=40) self.object_page_table_uri[i].grid(row=i+1, column=0) # 項目2 self.object_page_table_name = [0] * n for i in range(0, n): self.object_page_table_name[i] = ttk.Entry(self.page_frame, width=10) self.object_page_table_name[i].grid(row=i+1, column=1) # 項目3 self.object_page_table_pass = [0] * n for i in range(0, n): self.object_page_table_pass[i] = ttk.Entry(self.page_frame, show='*', width=10) self.object_page_table_pass[i].grid(row=i+1, column=2) self.page_frame.place(x=10,y=yy) self.param_frame = ttk.Frame(self.main_tab) self.param_frame.grid(row=0, column=0) # 項目をつくる param_items = ['property', 'value'] for i in range(0, len(param_items)): label_param_item = ttk.Label(self.param_frame,text=param_items[i]) label_param_item.grid(row=0, column=i) n = 4 # 行数 # 項目1 self.param_table_property = [0] * n for i in range(0, n): self.param_table_property[i] = ttk.Entry(self.param_frame, width=20) self.param_table_property[i].grid(row=i+1, column=0) # 項目2 self.param_table_value = [0] * n for i in range(0, n): self.param_table_value[i] = ttk.Entry(self.param_frame, width=10) self.param_table_value[i].grid(row=i+1, column=1) self.param_frame.place(x=550,y=yy) self.param_table_property[0].insert(END,'read_interval') self.param_table_property[1].insert(END,'exec_interval') self.param_table_property[2].insert(END,'write_interval') self.param_table_property[3].insert(END,'report_length') yy=200 self.command_field_label=Label(self.main_tab,text="command", width=10) self.command_field_label.place(x=10,y=yy) self.command_field=Entry(self.main_tab,width=50) self.command_field.place(x=150,y=yy) self.command_enter_button=Button(self.main_tab,text="enter",bd=2,bg='white',command=self.enter_all_command,width=8,relief=RIDGE) self.command_enter_button.place(x=500,y=yy) self.clear_command_button=Button(self.main_tab,text="clear_message",bd=2,bg='white',command=self.clear_message,width=12,relief=RIDGE) self.clear_command_button.place(x=580,y=yy) yy=230 # script area self.script_frame=tk.Frame(self.main_tab,width=50,height=5) self.script_frame.place(x=10,y=yy) self.script_area=scrolledtext.ScrolledText(self.script_frame) self.script_area.pack() yy=600 # output area self.message_frame=tk.Frame(self.main_tab,width=50,height=5) self.message_frame.place(x=10,y=yy) self.message_area=scrolledtext.ScrolledText(self.message_frame) self.message_area.pack() #script tab yy=10 self.dir_name_label=Label(self.script_tab,text="dir name",width=10) self.dir_name_label.place(x=30,y=yy) self.dir_name_field=Entry(self.script_tab,width=50) self.dir_name_field.place(x=100,y=yy) #self.read_button=Button(self.script_tab, text="read",bd=2,bg='white',command=self.click_read_button, width=8, relief=RIDGE) #self.read_button.place(x=500,y=yy) self.dir_button=Button(self.script_tab, text="directory",bd=2,bg='white',command=self.click_dir_button, width=10, relief=RIDGE) self.dir_button.place(x=570,y=yy) self.run_script_button2=Button(self.script_tab,text="run script",bd=2,bg='white',command=self.run_script,width=8, relief=RIDGE) self.run_script_button2.place(x=680,y=yy) yy=50 self.file_name_label=Label(self.script_tab,text="file name",width=10) self.file_name_label.place(x=30,y=yy) self.file_name_field=Entry(self.script_tab,width=50) self.file_name_field.place(x=100,y=yy) self.read_button=Button(self.script_tab, text="read",bd=2,bg='white',command=self.click_read_button, width=8, relief=RIDGE) self.read_button.place(x=500,y=yy) self.dir_button=Button(self.script_tab, text="select",bd=2,bg='white',command=self.click_select_file_button, width=10, relief=RIDGE) self.dir_button.place(x=570,y=yy) yy=100 self.script_frame2=tk.Frame(self.script_tab,width=50,height=100) self.script_frame2.place(x=50,y=yy) self.script_area2=scrolledtext.ScrolledText(self.script_frame2) self.script_area2.pack() #self.run_script() #self.set_script() #self.display_help() self.prop=Properties() self.prop.set_gui(self) def set_Pico_Time(self,time): self.Pico_Time=time def init_params(self): self.prop.load(self.prop.file_name) self.prop.map_to_gui() def click_read_button(self): fn=self.file_name_field.get() print("fn="+fn) f=None try: f=open(fn,"r") except Exception as e: print("file open error.") tb=sys.exec_info()[2] print("message:{0}".format(e.with_traceback(tb))) return try: self.script_area.delete(1.0,END) line=f.readline() while line: print(line) self.script_area.insert(END,line) line=f.readline() f.close() except Exception as e: print("file "+fn+" read error") tb=sys.exec_info()[2] print("message:{0}".format(e.with_traceback(tb))) def click_dir_button(self): iDir = os.path.abspath(os.path.dirname(__file__)) folder_name=tk.filedialog.askdirectory(initialdir=iDir) if len(folder_name)==0: print("cancel selcting folder") else: self.dir_name_field.insert(END,folder_name) def click_select_file_button(self): fType = [("python", "*.py")] iDir="" xdir=self.dir_name_field.get() if xdir==None or xdir=="": iDir=os.path.abspath(os.path.dirname(__file__)) else: iDir=xdir iFilePath=filedialog.askopenfilename(filetypes=fType, initialdir=iDir) if iFilePath==None or iFilePath=="": print("cancel") else: self.file_name_field.delete(0,END) self.file_name_field.insert(END,iFilePath) def enter_command(self): print("enter_command") command=self.command_field.get() self.ex(command) def click_start_button(self): print('click_start_button') #exec(self.script) self.script_thread=threading.Thread(target=self.start_script) print('new thread, start thread') #self.start_script() self.script_thread.start() print('script_started.') def click_stop_button(self): print('click_stop_button') #exec(self.script) if self.bot==None: return self.bot.stop_read_eval_print_loop() def start_script(self): print('start_script') #self.script=self.script_area.get(0.,END) #print("run_script:"+self.script) #exec(self.script) if self.bot==None: return self.bot.read_eval_print_loop() def run_script(self): print('run_script') def click_save_prop_button(self): self.prop.save(self.prop.file_name) def add_uri(self,uri,i): if i<2 and i >= 0: self.object_page_table_uri[i].delete(0,END) self.object_page_table_uri[i].insert(END,uri) def map_to_gui(self,key,value): if key=='bot_id': self.bot_id_field.delete(0,END) self.bot_id_field.insert(END,value) elif key=='waiting_term': self.waiting_term_field.delete(0,END) self.waiting_term_field.insert(END,str(value)) elif key=='object_page_1': self.object_page_table_uri[0].delete(0,END) self.object_page_table_uri[0].insert(END,value) elif key=='object_page_2': self.object_page_table_uri[1].delete(0,END) self.object_page_table_uri[1].insert(END,value) elif key=='object_page_pass_1': self.object_page_table_pass[0].delete(0,END) self.object_page_table_pass[0].insert(END,value) elif key=='object_page_pass_2': self.object_page_table_pass[1].delete(0,END) self.object_page_table_pass[1].insert(END,value) elif key=='read_interval': self.param_table_value[0].delete(0,END) self.param_table_value[0].insert(END,str(value)) elif key=='exec_interval': self.param_table_value[1].delete(0,END) self.param_table_value[1].insert(END,str(value)) elif key=='write_interval': self.param_table_value[2].delete(0,END) self.param_table_value[2].insert(END,str(value)) elif key=='report_length': self.param_table_value[3].delete(0,END) self.param_table_value[3].insert(END,str(value)) def lookup_prop(self,key): if key=='bot_id': return self.bot_id_field.get() elif key=='waiting_term': return int(self.waiting_term_field.get()) elif key=='object_page_1': return self.object_page_table_uri[0].get() elif key=='object_page_2': return self.object_page_table_uri[1].get() elif key=='object_page_pass_1': return self.object_page_table_pass[0].get() elif key=='object_page_pass_2': return self.object_page_table_pass[1].get() elif key=='read_interval': return int(self.param_table_value[0].get()) elif key=='exec_interval': return int(self.param_table_value[1].get()) elif key=='write_interval': return int(self.param_table_value[2].get()) elif key=='report_length': return int(self.param_table_value[3].get()) return None def update(self): self.prop.map_from_gui() self.prop.save(self.prop.file_name) def ini_recv_queue(self): self.recv_queue=[] def is_not_empty_recv_queue(self): if len(self.recv_queue)>0 : print('recv_queue is empty') return True print('recv_queue is not empty') return False def are_in_the_recv_queue(self,messages): print('start are_in_the_recv_queue') for x in messages: print('is '+x+' in the recv_queue?') flag=False for m in self.recv_queue: print(m+' in the received queue') if x in m: print(x + ' is in the '+m) flag=True self.write_message("message "+x+" found!") break if flag==False: return False return True def enter_all_command(self): command=self.command_field_for_all_server.get() print("send "+command+" to all") self.write_message("send "+command+" to all") self.coms.send_command_to_all(command) self.command_field_for_all_server.delete(0,END) def ex(self,command): print("parse "+command) command=self.r_b(command) if self.parse_command(command): self.write_message("OK") print("OK") else: self.write_message("ERROR") print("ERROR") def write_script(self, message): self.clear_script() self.append_script(message) def write_script_start(self,message): self.write_script_thread=threading.Thread(target=self.write_script_lines, args=(message,)) self.write_script_thread.start() def write_script_lines(self,lines): print('start write_script_lines') self.write_message('start_write_script_lines') xlines=lines.splitlines() self.clear_script() for l in xlines: self.append_script(l) self.script_area.update() print('end write_script_lines') def append_script(self, message): self.script_area.insert(tk.END,message) self.script_area.insert(tk.END,'\n') #self.script_area.yview_moveto(1) def clear_script(self): self.script_area.delete("1.0",END) self.script_area.update() def write_message(self, message): #self.write_message_thread=threading.Thread(target=self.clear_and_append_message, args=(message,)) #self.write_message_thread.start() self.append_message(message) def clear_and_append_message(self, message): self.clear_message() self.append_message(message) def append_message(self, message): now = self.Pico_Time.get_now() addline=now+': '+message #print('start append_message') self.message_area.insert(tk.END,addline) self.message_area.insert(tk.END,'\n') self.message_area.yview_moveto(1) tx=self.message_area.get(0.0,tk.END) count_lines = tx.count('\n') + 1 if count_lines>=500: self.message_area.delete(0.0,99.0-1) self.message_area.update() #print('end append_message') def clear_message(self): self.message_area.delete("1.0",END) self.message_area.update() class pico_net: def __init__(self): print('current ssid= '+ssid) def set_access_point(self, ssid, password): self.ssid = ssid self.password = password def connect(self): self.wlan = network.WLAN(network.STA_IF) self.wlan.active(True) chipid = int.from_bytes(self.wlan.config('mac'), 'big') % 65536 self.wlan.connect(ssid, password) max_wait = 10 while max_wait > 0: if self.wlan.status() < 0 or self.wlan.status() >= 3: break max_wait -= 1 print('waiting for connection...') time.sleep(1) if self.wlan.status() != 3: raise RuntimeError('network connection failed') else: print('connected') self.status = self.wlan.ifconfig() print('ip = ' + self.status[0]) class pico_http: def __init__(self): print('pico_http') def set_url(self, url): self.url = url def get(self, url): #print('pico_http.get(urL='+url+')') self.url=url #print('urL='+url) try: r = requests.get(url) #print(r) r_text=r.text r.close() #print('pico_http.get...return') return r_text except: print('pico_http.get...exception') return "" def put(self, url, payload): #print('pico_http.put(urL='+url+'payload='+str(payload)+')') #payload is a dictionary uri=url+'?' for key in payload: #print(key+'=',end="") #print(payload[key]) uri=uri+key+'='+payload[key]+'&' uri=uri[:-1] #print('uri='+uri) #r = urequests.post(uri) #r = urequests.post(url,data=payload) r = requests.get(uri) if r=="": print('pico_http.put...exception') return "" #print(r) r_text=r.text r.close() #print(r_json) return r_text #post, ref: https://docs.micropython.org/en/latest/library/urequests.html def post(self, url, body, headers): #print('pico_http.post(url='+url+' headers='+str(headers)+')') try: r = requests.post(url,data=body,headers=headers) #print(r) r_text=r.text #print(r_text) #r_json=r.json() r.close() #print(r_json) print('pico_http.post...return') return r_text except: print('pico_http.post...exception') return "" import datetime class pico_time: # reference: https://wisteriahill.sakura.ne.jp/CMS/WordPress/2023/05/10/raspberry-pi-pico-w-ntp-server/ # NTPサーバー #ntp_host = "time-c.nist.gov" #ntp_host = "time.cloudflare.com" #ntp_host = "time.google.com" ntp_host = "ntp.nict.jp" def __init__(self): print('pico_time') def ptime(self): NTP_DELTA = 2208988800 NTP_QUERY = bytearray(48) NTP_QUERY[0] = 0x1b #addr = socket.getaddrinfo(self.ntp_host, 123)[0][-1] addr=(self.ntp_host, 123) s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # s.settimeout(1) res = s.sendto(NTP_QUERY, addr) msg = s.recv(48) s.close() val = struct.unpack("!I", msg[40:44])[0] return val - NTP_DELTA wday = ['Mon','Tue','Wed','Thu','Fri','Sat','Sun'] def zfill(self, s, width): if len(s) < width: return ("0" * (width - len(s))) + s else: return s def get_now(self): #t=self.ptime() #t = t + 9*60*60 ##print(t) #datetimetuple = time.gmtime(t) #year = str(datetimetuple[0]) #month = self.zfill(str(datetimetuple[1]),2) #mday = self.zfill(str(datetimetuple[2]),2) #hour = self.zfill(str(datetimetuple[3]),2) #minute = self.zfill(str(datetimetuple[4]),2) #seconds = self.zfill(str(datetimetuple[5]),2) #wd_index = datetimetuple[6] ##日付と時刻を分けるデリミター("|")を付加 ##datetime = year + "/" + month + "/" + mday + " " + self.wday[wd_index] + "|" + hour + ":" + minute + ":" + seconds #datetime = year + "/" + month + "/" + mday + " " + hour + ":" + minute + ":" + seconds dt=str(datetime.datetime.now()) return dt class html_parser: html="" tokens=[] reserved_words={'<':'<','>':'>','&':'&','"':'"','\'':''', ' ':' ','\n':'<br>','\t':' ','\r':'', '\\':'\','{':'{','}':'}','[':'[',']':']' } a2c={' ':"+",'\n':"%0D%0A",'\r':"%0D",'\t':"%09",'!':"%21",'"':"%22", '#':"%23",'$':"%24",'%':"%25",'&':"%26", '\'':"%27",'(': "%28",')':"%29", '*':"%2A",'+':"%2B",',':"%2C",'-':"%2D",'/':"%2F",':':"%3A", ';':"%3B",'<':"%3C",'=':"%3D",'>':"%3E",'?':"%3F", '@':"%40",'[':"%5B",'\\':"%5C",']':"%5D",'^':"%5E", '`':"%60",'{':"%7B",'|':"%7C",'}':"%7D",'~':"%7E"} #Spechal char to ascii code sc2a={'<':"<",'>':">",'&':"&",'"':'"',''':"\'"} def __init__(self,html): self.html=html def html_tokenizer(self): #print("html_tokenizer") self.token_ith=0 w="" tx=[""] rest=[""] inx=self.html xlen=len(self.html) while xlen>0: if self.parse_tag(inx,tx,rest): if w!="": self.tokens.append(w) w="" self.tokens.append('<'+tx[0]+'>') #print('<'+tx[0]+'>') inx=rest[0] xlen=len(inx) elif self.parse_String_Constant(inx,tx,rest): if w!="": self.tokens.append(w) w="" self.tokens.append('"'+tx[0]+'"') #print('"'+tx[0]+'"') inx=rest[0] xlen=len(inx) else: wc=inx[0] inx=inx[1:xlen] xlen=len(inx) w=w+wc if w!="": self.tokens.append(w) w="" def get_html(self): return self.html def parse_key(self,key,inx,rest): #print("parse_key-"+key) keylen=len(key) inlen=len(inx) if inx.startswith(key): rest[0]=inx[keylen:inlen] return True rest[0]=inx return False def parse_String_Constant(self,inx,strc,rest): rx=[""] xstr="" if self.parse_key('"',inx,rx): #print("parse_String_Constant") inx=rx[0] fx=inx[0] xlen=len(inx) while fx!='"': if xlen==0: return False if fx=='\\': inx=inx[1:xlen] else: xstr=xstr+fx xlen=len(inx) inx=inx[1:xlen] fx=inx[0] if self.parse_key('"',inx,rx): strc[0]=xstr rest[0]=rx[0] return True return False def parse_tag(self,inx,tag,rest): rx=[""] xstr="" wstr=[""] if self.parse_key('<',inx,rx): #print("parse_tag") inx=rx[0] fx=inx[0] xlen=len(inx) while fx!='>': if xlen<=0: return False if fx=='\\': inx=inx[1:xlen] if self.parse_String_Constant(inx,wstr,rx): inx=rx[0] xstr=xstr+'"'+wstr[0]+'"' else: xstr=xstr+fx inx=inx[1:xlen] fx=inx[0] xlen=len(inx) if self.parse_key('>',inx,rx): tag[0]=xstr rest[0]=rx[0] return True return False def get_tokens(self): return self.tokens def next_token(self): if self.token_ith<len(self.tokens): self.token_ith=self.token_ith+1 return self.tokens[self.token_ith-1] return "" def has_more_tokens(self): if self.token_ith<len(self.tokens): return True return False def index_from(self,i,str): p=self.html[i:].index(str) return p def p_url(self,p,url): #print("p_url p="+str(p)+' '+self.html[p:p+10]) rx=[""] xurl="" pw=p xlen=len(self.html) q=self.p_key('http://',p) if p!=q: xurl='http://' else: q=self.p_key('https://',p) if p!=q: xurl='https://' else: return pw p=q while not (self.html[p] in [' ','\n','\t','\r']): p=p+1 if p>=xlen: p=xlen break url[0]=xurl+self.html[q:p] return p def p_key(self,key,p): #print("p_key key="+key+" p="+str(p)+" "+self.html[p:p+10]) keylen=len(key) if p+keylen>=len(self.html): if p+keylen>len(self.html): return p q=p if self.html[q:q+keylen]==key: #print("key="+key+" have found, q="+str(q+keylen)) return q+keylen #print("key="+key+" is not found, p="+str(p)) return p def p_String_Constant(self,p,strc): #print("p_String_Constant p="+str(p)+' '+self.html[p:p+10]) rx=[""] xstr="" pw=p q=self.p_key('"',p) if p!=q: #print("p_String_Constant p="+str(p)+' '+self.html[p:p+10]) p=q fx=self.html[p] xlen=len(self.html)-p while fx!='"': if xlen==0: return pw if fx in ['\n','\t','\r']: return pw if fx=='\\': p=p+1 p=p+1 fx=self.html[p] xlen=len(self.html)-p q=self.p_key('"',p) if p!=q: strc[0]=self.html[pw+1:q-1] #print("p_string_constant, strc="+str(strc[0])) return q #print("p_String_Constant, fail to find \"") return pw def p_Date(self,p,date_str): #print("p_Date p="+str(p)+' '+self.html[p:p+10]) rx=[""] xstr="" pw=p year=[0] q=self.p_number(p,year) if p==q: return pw p=q q=self.p_key('/',p) if p==q: q=self.p_key('-',p) if p==q: return pw p=q month=[0] q=self.p_number(p,month) if p==q: return pw p=q q=self.p_key('/',p) if p==q: q=self.p_key('-',p) if p==q: return pw p=q day=[0] q=self.p_number(p,day) if p==q: return False p=q q=self.p_b(p) if p==q: return pw p=q hour=[0] q=self.p_number(p,hour) if p==q: return pw p=q q=self.p_key(':',p) if p==q: return pw p=q minute=[0] q=self.p_number(p,minute) if p==q: return pw p=q q=self.p_key(':',p) if p==q: return pw p=q second=[0] q=self.p_number(p,second) if p==q: return pw p=q date_str[0]=str(year[0])+'-'+str(month[0])+'-'+str(day[0])+' '+str(hour[0])+':'+str(minute[0])+':'+str(second[0]) return p def p_b(self,p): #print("parse_b") #print("p="+str(p)) xlen=len(self.html) if p>=xlen: return p while self.html[p]==' ': p=p+1 if p>=xlen: p=xlen break return p def p_name(self,p,name): #print("p_name, self.html="+ self.html[p:p+10]) #print("p="+str(p)+"..."+self.html[p:p+10]) q=p last_p=len(self.html) while self.html[q] in 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_': #print("self.html["+str(q)+"]="+self.html[q]) q=q+1 if q>=last_p: break name[0]=self.html[p:q] #print("p_name p="+str(p)+" q="+str(q)+" name="+str(name[0])) #print("p="+str(p)+" q="+str(q)+" name="+name[0]) #print("name[0]= "+name[0]) return q def p_number(self,p,num): #print("p_number") #print("p="+str(p)) n="" last_p=len(self.html) q=p while self.html[p] in '0123456789': q=q+1 if q>=last_p: break num[0]=int(self.html[p:q]) #print("p_number p="+str(p)+" q="+str(q)+" num="+str(num[0])) return q def p_an_equation(self,p,eqs): #print("p_an_equation p="+str(p)+' '+self.html[p:p+10]) pw=p p=self.p_b(p) nx=[""] strc=[""] q=self.p_name(p,nx) #print("p_an_equation name="+nx[0]) if p==q: #print("p_an_equation fail to find name") return pw p=q p=self.p_b(p) q=self.p_key('=',p) if p==q: #print("p_an_equation fail to find =") return pw p=q p=self.p_b(p) q=self.p_String_Constant(p,strc) if p==q: num=[0] q=self.p_number(p,num) if p==q: return pw else: eqs[nx[0]]=num[0] #print("p_qn_equation get "+nx[0]+"="+str(num[0])) return q else: eqs[nx[0]]=strc[0] #print("p_an_equation get "+nx[0]+"="+str(strc[0])) return q def p_equations(self,p,eqs): #print("parse_equations") #print("p="+str(p)) pw=p while True: q=self.p_an_equation(p,eqs) if p==q: return p p=q def p_get_equations_of_the_tag(self,p,tag_name,eqs): #print("p_get_equations_of_the_tag <"+tag_name) #print("p="+str(p)+' '+self.html[p:p+10]) pw=p try: q=self.html.index('<'+tag_name,pw) except: #print("p_get_equation_of_the_tag fail to find <"+tag_name) return p #print("q="+str(q)+' '+self.html[q:q+10]) q=q+len('<'+tag_name) #print("q="+str(q)+' '+self.html[q:q+10]) if pw==q: #print("p_get_equation_of_the_tag fail to find <"+tag_name) return p pw=q q=self.p_equations(pw,eqs) #print("after equations q="+str(q) +' '+self.html[q:q+10]) if pw==q: return p pw=q pw=self.p_b(pw) #print("pw="+str(pw)) q=self.p_key('>',pw) #print("after > q="+str(q)+' '+self.html[q:q+10]) if pw!=q: return q q=self.p_key('/>',pw) if pw!=q: return q return p def p_get_between_tag_with_cond(self,p,tag_name,cond,rtn): #print("p_get_between_with_cond <"+tag_name+">...</"+tag_name+">") #print("p="+str(p)+' '+self.html[p:p+10]) pw=p q=pw while True: try: q=self.html.index('<'+tag_name,p) #print("p_get_between_with_cond p="+str(p)+" q="+str(q)+' '+self.html[q:q+20]) if p==q: return pw q=q+len('<'+tag_name) p=q eqs={} q=self.p_equations(p,eqs) #print("after equations q="+str(q) +' '+self.html[q:q+10]) if p!=q: if cond[0] in eqs: #print("cond[0]="+cond[0]+" eqs[cond[0]]="+eqs[cond[0]]+" cond[1]="+cond[1]) if eqs[cond[0]]!=cond[1]: continue else: break except: #print("fail to find <"+tag_name) return pw p=self.p_b(p) #print("p_get_between q="+str(q)+' '+self.html[q:q+10]) #print("pw="+str(pw)) q=self.p_key('>',p) if p!=q: start_p=q else: q=self.p_key('/>',p) if pw!=q: start_p=q else: return p try: q=self.html.index('</'+tag_name,start_p) except: return pw end_p=q-1 p=q q=q+len('</'+tag_name) p=self.p_b(q) #print("pw="+str(pw)) q=self.p_key('>',p) if q==p: return pw rtn[0]=(start_p,end_p) #rx=self.html[start_p:end_p] #print("rx="+rx) return q def p_get_between(self,p,tag_name,eqs,rtn): #print("p_get_between <"+tag_name+">...</"+tag_name+">") #print("p="+str(p)+' '+self.html[p:p+10]) pw=p q=pw try: q=self.html.index('<'+tag_name,p) except: return pw #print("p_get_between 2 q="+str(q)+' '+self.html[q:q+10]) q=q+len('<'+tag_name) #print("p_get_between 3 q="+str(q)+' '+self.html[q:q+10]) if p==q: return pw p=q q=self.p_equations(p,eqs) #print("after equations q="+str(q) +' '+self.html[q:q+10]) p=q p=self.p_b(p) #print("p="+str(p)) q=self.p_key('>',p) #print("after > q="+str(q)+' p='+str(p)+' '+self.html[p:q+10]) if p!=q: start_p=q else: q=self.p_key('/>',p) if p!=q: end_p=q rtn[0]="" return q else: #print("get between "+tag_name+",fail to find <"+tag_name+"/>") return pw try: q=self.html.index('</'+tag_name,start_p) except: #print("get between "+tag_name+",fail to find </"+tag_name) return pw end_p=q-1 p=q q=q+len('</'+tag_name) p=self.p_b(q) #print("p="+str(p)) q=self.p_key('>',p) if q==p: return pw rtn[0]=(start_p,end_p) #rx=self.html[start_p:end_p+1] #print("get between "+tag_name+" rx="+rx) return q #def text_to_post_form(self,text): # #print("html_parser.text_to_post_form") # #print(text) # post_form="" # for i in range(len(text)): # post_form=post_form+self.code_convert(text[i]) # #print("html_parser.text_to_post_form return") # return post_form def code_convert(self,code): if code in self.a2c: return self.a2c[code] else: return code def text_to_post_form(self,text): #print("html_parser.text_to_post_form") #print(text) rtn="" for i in range(len(text)): rtn+=self.code_convert(text[i]) return rtn def special_char_to_text(self,text): #print("special_char_to_text") #print(text) text=text.replace("<","<") text=text.replace(">",">") text=text.replace("&","&") text=text.replace(""",'"') text=text.replace("'","'") return text def post(self,url,body): #payload is a dictionary headers={'Content-Type': 'application/x-www-form-urlencoded'} #def http_post(url, value): # https://docs.openmv.io/library/urequests.html #body = "value=%s" % (value) #headers = {'Content-Type': 'application/x-www-form-urlencoded'} try: response = requests.post(url, data=body.encode('utf-8'), headers=headers) r_text=response.text response.close() return r_text except Exception as e: print(e) return "" class pico_wiki_driver: url="" def __init__(self): print('pico_wiki_driver') #self.url=url #self.page=page #self.Pico_Net=pico_net() self.Pico_Time=pico_time() self.Pico_Http=pico_http() #self.Pico_Net.connect() t=self.Pico_Time.get_now() print('time now='+t) def set_url(self,url): self.url=url def set_page(self,page): self.page=page def get_url(self): return self.url def get_html(self): uri = self.url+"?"+self.page all_page=self.Pico_Http.get(uri) #print("get_html..."+uri) #print(all_page) return all_page def get_wiki_page(self): uri = self.url+"?"+self.page all_page=self.Pico_Http.get(uri) print("get_wiki_page...") #print(all_page) parser=html_parser(all_page) p=0 rtn=[(0,0)] q=parser.p_get_between_tag_with_cond(p,"div",('id',"body"),rtn) if p!=q: #print("get_wiki_page id=body..."+all_page[rtn[0][0]:rtn[0][1]]) body_x=all_page[rtn[0][0]:rtn[0][1]] body=parser.special_char_to_text(body_x) return body def replace_wiki_page(self,new_body): print("pico_wiki_driver.replace_wiki_page...") payload={'cmd':'edit', 'page':self.page} #r=Pico_Http.get(url+'index.php?work202401') #print('uri='+r) r = self.Pico_Http.put(self.url,payload) #print(r) edit_html=html_parser(r) #edit_html.html_tokenizer() p=0 array_of_equations=[] equations={} q=edit_html.p_get_equations_of_the_tag(p,'input',equations) while p!=q: #print('p='+str(p)+' q='+str(q)+' <input....>') array_of_equations.append(equations) p=q equations={} q=edit_html.p_get_equations_of_the_tag(p,'input',equations) for i in range(len(array_of_equations)): #print('i='+str(i)) eqs=array_of_equations[i] for key in eqs: #print(key+'='+array_of_equations[i][key]) if key=='name' and array_of_equations[i][key]=="encode_hint": payload['encode_hint']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="template": payload['template']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="cmd": payload['cmd']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="page": payload['page']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="digest": payload['digest']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="write": payload['write']=array_of_equations[i]['value'] #tokens=edit_html.get_tokens() #for i in range(len(tokens)):_ # print(str(i)+'-'+tokens[i]) eqs_msg={} rtn=[(0,0)] p=edit_html.p_get_between(0,'textarea',eqs_msg,rtn) if rtn[0]!=(0,0): start_p=rtn[0][0] end_p=rtn[0][1] body=r[0:start_p]+new_body+r[end_p+1:] #print("body=......") #print(new_body) payload['msg']=edit_html.text_to_post_form(new_body) #print('msg=......') #print(payload['msg']) eqs_original={} rtn=[(0,0)] p=edit_html.p_get_between(p,'textarea',eqs_original,rtn) if rtn[0]!=(0,0): start_p=rtn[0][0] end_p=rtn[0][1] original_pre=r[start_p:end_p+1] original=edit_html.special_char_to_text(original_pre) payload['original']=edit_html.text_to_post_form(original) body="" body=body+'encode_hint='+(payload['encode_hint'])+'&' body=body+'template_page=&' body=body+'cmd='+payload['cmd']+'&' body=body+'page='+payload['page']+'&' body=body+'digest='+payload['digest']+'&' body=body+'msg='+payload['msg']+'&' body=body+'write='+payload['write']+'&' body=body+'original='+payload['original'] #print('body='+body) edit_html.post(self.url,body) #print(r) def upload_file(self,file_dir,file_name,pass_word): # MIMEタイプの定義 #XLSX_MIMETYPE = 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' #file_Name = '2024-12-20-222611.jpg' #file_dir='C:/vscode/python/bot_computing/' file_path=file_dir+file_name MIMETYPE = mimetypes.guess_type(file_path)[0] print('upload file '+file_path) # ファイル名とデータの取得 file_Data_Binary = open(file_path, 'rb').read() # アップロード先のURL #url = 'http://www.yama-lab.org/fwb4pi/index.php' #page = 'test02' url=self.url page=self.page # アップロードするファイルの情報を辞書に格納 files = {'attach_file': (file_name, file_Data_Binary, MIMETYPE), 'encode_hint': 'ぷ', 'pass': pass_word, 'refer': page, 'pcmd': 'post', 'plugin': 'attach'} m = MultipartEncoder(files) hx={'Content-Type': m.content_type, # 'Accept:': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7', 'Referer': url+'?'+'plugin=attach&pcmd=upload&page='+page # 'Accept-Language': 'ja,en;q=0.9,en-GB;q=0.8,en-US;q=0.7' } # ファイルのアップロード response = requests.post(url, data=m, headers=hx) # レスポンスの表示 print(response.status_code) #print(response.content) #wfile_path=file_dir+'return.html' #result_file= open(wfile_path, 'w') #result_file.write((response.content).decode(encoding='utf-8')) return response.status_code def get_attachment_list(self): uri = self.url+"?"+self.page all_page=self.Pico_Http.get(uri) print("get_wiki_page...") #print(all_page) parser=html_parser(all_page) p=0 rtn=[(0,0)] q=parser.p_get_between_tag_with_cond(p,"div",('id',"attach"),rtn) attach_end=q attach_list=[] if p==q: return attach_list #print("get_wiki_page id=body..."+all_page[rtn[0][0]:rtn[0][1]]) p=rtn[0][0] eqs={} while True: q=parser.p_get_between(p,'a',eqs,rtn) if p==q: break if q>attach_end: break print(parser.html[rtn[0][0]:rtn[0][1]]) eqs_img={} q2=parser.p_get_equations_of_the_tag(rtn[0][0],'img',eqs_img) fname=parser.html[q2:(rtn[0][1]+1)] print(fname) attach_list.append(fname) q=parser.p_get_between(q2,'a',eqs,rtn) p=q print(attach_list) return attach_list def delete_attachment(self,attach_name,pass_word): # アップロードするファイルの情報を辞書に格納 files = {'encode_hint': 'ぷ', 'plugin': 'attach', 'refer': self.page, 'file': attach_name, 'age': '0', 'pcmd': 'delete', 'newname': attach_name, 'pass': pass_word} m = MultipartEncoder(files) hx={'Content-Type': m.content_type, # 'Accept:': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7', 'Referer': self.url+'?'+'plugin=attach&pcmd=info&' +'file='+attach_name+'&refer='+self.page # 'Accept-Language': 'ja,en;q=0.9,en-GB;q=0.8,en-US;q=0.7' } # ファイルのアップロード response = requests.post(self.url, data=m, headers=hx) # レスポンスの表示 print(response.status_code) #print(response.content) #wfile_path='return2.html' #result_file= open(wfile_path, 'w') #result_file.write((response.content).decode(encoding='utf-8')) return response.status_code def get_wiki_source(self): payload={'cmd':'edit', 'page':self.page} #r=Pico_Http.get(url+'index.php?work202401') #print('uri='+r) r = self.Pico_Http.put(self.url,payload) #print(r) edit_html=html_parser(r) #edit_html.html_tokenizer() p=0 array_of_equations=[] equations={} q=edit_html.p_get_equations_of_the_tag(p,'input',equations) while p!=q: #print('p='+str(p)+' q='+str(q)+' <input....>') array_of_equations.append(equations) p=q equations={} q=edit_html.p_get_equations_of_the_tag(p,'input',equations) for i in range(len(array_of_equations)): #print('i='+str(i)) eqs=array_of_equations[i] for key in eqs: #print(key+'='+array_of_equations[i][key]) if key=='name' and array_of_equations[i][key]=="encode_hint": payload['encode_hint']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="template": payload['template']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="cmd": payload['cmd']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="page": payload['page']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="digest": payload['digest']=array_of_equations[i]['value'] elif key=='name' and array_of_equations[i][key]=="cancel": payload['cancel']=array_of_equations[i]['value'] #tokens=edit_html.get_tokens() #for i in range(len(tokens)):_ # print(str(i)+'-'+tokens[i]) eqs_msg={} rtn=[(0,0)] p=edit_html.p_get_between(0,'textarea',eqs_msg,rtn) wiki_source="" if rtn[0]!=(0,0): start_p=rtn[0][0] end_p=rtn[0][1] wiki_source=r[start_p:end_p] #body="" #body=body+'encode_hint='+payload['encode_hint']+'&' #body=body+'cmd='+payload['cmd']+'&' #body=body+'page='+payload['page']+'&' #body=body+'cancel='+payload['cancel'] ##print('body='+body) #r=edit_html.post(self.url,body) wiki_source=edit_html.special_char_to_text(wiki_source) return wiki_source def get_result(self): #print("pico_wiki_bot.get_result") #r=self.get_script_and_result() all_text=self.get_wiki_source() if all_text==None: return None if all_text=="": return "" #parser=html_parser(all_text) p=all_text.index("result:")+len("result:") q=all_text.index("current_device=",p) if q<0: q=len(all_text) else: q=q-1 print('pico_wiki_bot.get_result return') #print(all_text[p+1:q]) return all_text[p+1:q] def get_script(self): #print("pico_wiki_bot.get_script") #r=self.get_script_and_result() all_text=self.get_wiki_source() if all_text==None: return None if all_text=="": return "" #parser=html_parser(all_text) p=0 try: q=all_text.index("result:",p) q=q-1 except: q=len(all_text) return all_text[p:q] class USB_Serial: PORT0 = '/dev/ttyACM0' # Windows �̏ꍇCOM* PORT1 = '/dev/ttyACM1' def __init__(self): try: self.ser = serial.Serial(port=self.PORT0,baudrate=115200,timeout=2) except Exception as e: try: self.ser = serial.Serial(port=self.PORT1,baudrate=115200,timeout=2) except Exception as e: print(e) #self.GUI.write_message(str(e)) self.ser=None self.usb_serial_input_thread=threading.Thread(target=self.receive_loop) self.usb_serial_input_thread.start() def set_gui(self,gui): self.GUI=gui; def send_command(self,command): self.rtn=None print('writing '+command) send_bytes = bytes(command+'\r\n','utf-8') try: if self.ser!=None: self.ser.write(send_bytes) self.ser.flush() except Exception as e: print("serial write error") self.GUI.write_message("serial write error.") print(e) self.GUI.write_message(str(e)) self.rtn="0" count=0 while True: if self.rtn!=None: rtnx=self.rtn self.rtn=None return rtnx if count>1000: self.rtn=None return "0" time.sleep(0.01) count=count+1 def receive_loop(self): while True: try: if self.ser==None: continue buf = self.ser.readlines() buf = [i.decode().strip() for i in buf] if len(buf)>0: print(buf) for l in buf: if '>>>' in l: print('please reset pico.') continue #print("buf[i]="+buf) self.rtn= buf[1] except Exception as e: print("error receiving") #self.GUI.write_message("error receiving") print(e) #self.GUI.write_message(str(e)) try: self.ser = serial.Serial(port=self.PORT0,baudrate=115200,timeout=2) except Exception as e: print(e) try: self.ser = serial.Serial(port=self.PORT1,baudrate=115200,timeout=2) except Exception as e: print(e) #self.GUI.write_message('error '+str(e)+' at receive_loop') self.ser=None self.rtn="0" time.sleep(0.01) class pico_wiki_bot: result_lines=[] script_lines=[] urls=[] programs={} environments={} time_millis=0 timer=None current_program_name="" current_program="" report=[] #reportLength=120 current_url="" current_page="" current_text="" next_url_index="" def __init__(self): print('wiki_bot') #self.Pico_Net=pico_net() self.Pico_Time=pico_time() self.Pico_Http=pico_http() #self.Pico_Net.connect() t=self.Pico_Time.get_now() self.bot=None print('time now='+t) self.read_initials() #self.current_url=url #self.current_page=page self.next_url_index=0 self.Pico_Wiki_Driver=pico_wiki_driver() self.all_text="" self.u_serial=USB_Serial() if self.Pico_Wiki_Driver.get_url()=="": return self.timer=Timer() #all_text=self.Pico_Wiki_Driver.get_wiki_page() #if all_text==None: # return None #self.timer.init(mode=Timer.PERIODIC, freq=1, callback=self.add_one_second_to_time_millis) def read_initials(self): print("read_initials") if self.bot==None: return if self.bot.prop==None: return self.environments['waiting_term']=self.bot.prop.get('waiting_term') self.environments['read_interval']=self.bot.prop.get('read_interval') self.environments['exec_interval']=self.bot.prop.get('exec_interval') self.environments['write_interval']=self.bot.prop.get('write_interval') self.environments['report_length']=self.bot.prop.get('report_length') uri=self.bot.prop.get('object_page_1') url=uri.split('?')[0] self.page=uri.split('?')[1] def set_current_page(self,page): self.current_page=page def set_current_url(self,url): self.current_url=url def set_current_pass(self,pass_w): self.pass_word=pass_w def clear_report(self): self.report.clear() def add_report_line(self,send): #print("add_report_line, report_length="+str(self.environments['report_length'])) #print(" current report_length="+str(len(self.report))) #print(" adding..."+send) while len(self.report)>(int(self.environments['report_length']-1)): for i in range(len(self.report)-1): self.report[i]=self.report[i+1] self.report.pop() self.report.append(send) def set_GUI(self,gui): self.GUI=gui self.u_serial.set_gui(gui) def init_params(self): if self.GUI==None: return self.GUI.init_params() def add_one_second_to_time_millis(self,timer): #print("pico_wiki_bot.add_one_second_to_time_millis") self.time_millis=self.time_millis+1000 #print("pico_wiki_bot.add_one_second_to_time_millis return") def stop_timer(self): self.timer=None def get_the_object_page(self): #print("pico_wiki_bot.get_the_object_page") #print("uri="+uri) if self.GUI!=None: try: object_page=self.GUI.lookup_prop('object_page_1') pass_word=self.GUI.lookup_prop('object_page_pass_1') except: object_page=initials['object_page_1'] pass_word=initials['object_page_pass_1'] url_page=object_page.split('?') self.url=url_page[0] self.page=url_page[1] self.pass_word=pass_word self.Pico_Wiki_Driver.set_url(self.url) self.Pico_Wiki_Driver.set_page(self.page) html=self.Pico_Wiki_Driver.get_html() if html!="": return html try: object_page=self.GUI.lookup_prop('object_page_2') pass_word=self.GUI.lookup_prop('object_page_pass_2') except: object_page=initials['object_page_2'] pass_word=initials['object_page_pass_1'] url_page=object_page.split('?') self.url=url_page[0] self.page=url_page[1] self.pass_word=pass_word self.Pico_Wiki_Driver.set_url(self.url) self.Pico_Wiki_Driver.set_page(self.page) html=self.Pico_Wiki_Driver.get_html() if html!="": return html else: return "" def get_script_and_result(self): #print("pico_wiki_bot.get_script_and_result") html=self.get_the_object_page() if html=="": return "" parser=html_parser(html) p=0 eqs={} rtn=[(0,0)] q=parser.p_get_between(p,'pre',eqs,rtn) be=rtn[0] command_and_result=parser.html[be[0]:be[1]] self.current_text=parser.special_char_to_text(command_and_result) return self.current_text def get_result(self): #print("pico_wiki_bot.get_result") #r=self.get_script_and_result() all_text=self.current_text if all_text==None: return None if all_text=="": return "" #parser=html_parser(all_text) p=all_text.index("result:")+len("result:") q=all_text.index("current_device=",p) if q<0: q=len(all_text) else: q=q-1 print('pico_wiki_bot.get_result return') return all_text[p+1:q] def get_script(self): #print("pico_wiki_bot.get_script") r=self.get_script_and_result() all_text=self.current_text if all_text==None: return None if all_text=="": return "" #parser=html_parser(all_text) p=0 try: q=all_text.index("result:",p) q=q-1 except: q=len(all_text) return all_text[p:q] def get_current_device_line(self): #command_and_result=self.get_script_and_result() command_and_result=self.current_text parser=html_parser(command_and_result) if command_and_result==None: return None p=command_and_result.index("current_device=") p=p+len("current_device=") try: q=command_and_result.index("\n",p) except: q=len(command_and_result) return parser.special_char_to_text(command_and_result[p:q]) def replace_wiki(self,new_wiki): self.Pico_Wiki_Driver.replace_wiki_page(new_wiki) #print(r) def replace_result(self): #print("pico_wiki_bot.replace_result") payload={'cmd':'edit', 'page':self.page} #r=Pico_Http.get(url+'index.php?work202401') #print('uri='+r) r = self.Pico_Http.put(self.url,payload) #print(r) edit_html=html_parser(r) #edit_html.html_tokenizer() p=0 eqs_msg={} rtn=[(0,0)] body="" p=edit_html.p_get_between(0,'textarea',eqs_msg,rtn) if rtn[0]!=(0,0): start_p=rtn[0][0] end_p=rtn[0][1] body=edit_html.special_char_to_text(r[start_p:end_p]) #print("body=......") #print(body) eqs_original={} rtn=[(0,0)] p=edit_html.p_get_between(p,'textarea',eqs_original,rtn) if rtn[0]!=(0,0): start_p=rtn[0][0] end_p=rtn[0][1] original_pre=r[start_p:end_p+1] original=edit_html.special_char_to_text(original_pre) payload['original']=edit_html.text_to_post_form(original) #print("body="+body) px=body.index("result:")+len("result:") q=body.index("current_device=",px) if q<0: q=len(body) head_area=body[0:px] #tail_area=msg[q:] #result_area=msg[px:q] new_area=head_area+'\n' for i in range(len(self.report)): new_area=new_area+' '+self.report[i]+'\n' bot_id=self.GUI.lookup_prop('bot_id') new_area=new_area+" current_device=\""+bot_id+"\". Date="+self.Pico_Time.get_now() gc.collect() self.Pico_Wiki_Driver.replace_wiki_page(new_area) def get_attachment_list(self): return self.Pico_Wiki_Driver.get_attachment_list() def upload_file(self,file_path,file_name): self.Pico_Wiki_Driver.upload_file(file_path,file_name,self.pass_word) def delete_attachment(self,attach_name): self.Pico_Wiki_Driver.delete_attachment(attach_name,self.pass_word) def read_script(self): #print("read_script") all_text=self.get_script() if all_text==None or all_text=="": self.script_lines=[] return False else: self.script_lines=all_text.split('\n') #print("-----script_lines-----") #for i in range(len(self.script_lines)): # print(str(i)+' - '+self.script_lines[i]) if self.GUI != None: #self.GUI.write_script_start(all_text) self.GUI.write_script_lines(all_text) return True def eval_script(self): print("eval_script") self.interpret_lines() #def print_result(self): # print("print_result") def is_object_page(self,parser): #print("is_object_page, line="+line[:10]+"...") p=0 p=parser.p_b(p) q=parser.p_key("object_page ",p) if p==q: #print("is_object_page return False") return False p=q p=parser.p_b(p) self.urls=[] xurl=[""] i=0 q=parser.p_url(p,xurl) #print(str(i)+"th url="+xurl[0]) while p!=q: i=i+1 self.urls.append(xurl[0]) p=q p=parser.p_b(p) q=parser.p_key("or ",p) #print("after key or p="+str(p)+" q="+str(q)) if p==q: break p=q p=parser.p_b(p) xurl=[""] q=parser.p_url(p,xurl) #print(str(i)+"th url="+xurl[0]) #print("p="+str(p)+" q="+str(q)) #for i in range(len(self.urls)): # print("url["+str(i)+"]="+self.urls[i]) return True def is_device(self,parser): p=0 p=parser.p_b(p) q=parser.p_key("current_device=",p) if p==q: return False p=q p=parser.p_b(p) xname=[""] q=parser.p_String_Constant(p,xname) if p==q: return False p=parser.p_b(q) self.current_device=xname[0] q=parser.p_key(",",p) if p==q: return False p=parser.p_b(q) q=parser.p_key("Date=",p) xdate=[] q=parser.p_Date(p,xdate) def set_page_name(self,eq): rv=eq['pageName'] print("set pageName="+rv) date=self.Pico_Time.get_now() #date=2024-12-31 14:25:16.61944 time_x=(date.split())[1] print('time_x='+time_x) if "<hour>" in rv: time_xx=time_x.split(':') #hm=time_xx[0]+'_'+time_xx[1] xrv=rv.replace("<hour>",time_xx[0]) page_1=self.GUI.lookup_prop('object_page_1') url_and_page=page_1.split('?') url_and_page[1]=xrv new_page_1=url_and_page[0]+'?'+url_and_page[1] print(new_page_1) self.GUI.map_to_gui('object_page_1',new_page_1) page_2=self.GUI.lookup_prop('object_page_2') url_and_page=page_2.split('?') url_and_page[1]=xrv new_page_2=url_and_page[0]+'?'+url_and_page[1] print(new_page_2) self.GUI.map_to_gui('object_page_2',new_page_2) if "<day>" in rv: date_x=(date.split())[0] print('date_x='+date_x) date_xx=date_x.split('-') xrv=rv.replace("<day>",date_xx[2]) page_1=self.GUI.lookup_prop('object_page_1') url_and_page=page_1.split('?') url_and_page[1]=xrv new_page_1=url_and_page[0]+'?'+url_and_page[1] print(new_page_1) self.GUI.add_uri(new_page_1,0) page_2=self.GUI.lookup_prop('object_page_2') url_and_page=page_2.split('?') url_and_page[1]=xrv new_page_2=url_and_page[0]+'?'+url_and_page[1] print(new_page_2) self.GUI.add_uri(new_page_2,1) def is_set_command(self,parser,p): #print("is_set_command.."+parser.html[p:p+10]) #p=parser.p_b(p) q=parser.p_key("set ",p) if p==q: #print("is_set_command return False") return False p=parser.p_b(q) eq={} q=parser.p_an_equation(p,eq) if p==q: return False if "pageName" in eq: print(eq) self.set_page_name(eq) return True for key in eq: self.environments[key]=eq[key] self.GUI.write_message("set "+str(key)+"="+str(eq[key])) self.GUI.map_to_gui(key,self.environments[key]) return True def is_py_command(self,parser,p): #print("is_py_command.."+parser.html[p:p+10]) #p=parser.p_b(p) q=parser.p_key("py ",p) if p==q: return False p=parser.p_b(q) #print("p="+str(p)+",line[p:10]="+parser.html[p:p+10]) xname=[""] q=parser.p_name(p,xname) self.current_program_name=xname[0] self.current_program="" def is_end_command(self,parser,p): #print("is_end_command.."+parser.html[p:p+10]) #p=parser.p_b(p) q=parser.p_key("end ",p) if p==q: return False p=parser.p_b(q) xname=[""] q=parser.p_name(p,xname) self.programs[self.current_program_name]=self.current_program def ex_pico(self,command): return(self.u_serial.send_command(command)) def is_run_command(self,parser,p): # reference : https://qiita.com/kyoshidajp/items/57ae371b3f5d8a84fb13 # reference : https://qiita.com/kammultica/items/3201f43eec53e3e56f54 print("is_run_command.."+parser.html[p:p+10]) q=parser.p_key("run ",p) if p==q: #print("is_run_command return False") return False p=parser.p_b(q) xname=[""] q=parser.p_name(p,xname) if p==q: #print("is_run_command return False") return False r=self.get_result() if r!=None and r!="": self.clear_report() lines=r.split('\n') for i in range(len(lines)): self.add_report_line(lines[i]) exec_locals={'self':self} #print("line="+parser.html) #print("xname[0]="+xname[0]) program=self.programs[xname[0]] print("program="+program) try: exec(program,globals(),exec_locals) except Exception as e: print("fail to exec "+program) self.add_report_line("fail to exec:"+xname[0]) self.GUI.write_message("fail to exec "+program) print(str(e)) self.GUI.write_message(str(e)) #self.add_report_line(str(e)) #sys.print_exception() #try: # exec(program) #except: # print("fail to exec "+program) # self.add_report_line("fail to exec:"+xname[0]) # sys.print_exception() def is_command(self,parser): p=0 p=parser.p_b(p) q=parser.p_key("command:",p) #print("line="+parser.html) #print("command="+parser.html[q:]) if p==q: return False q=parser.p_b(q) #lx=line[q:] if self.is_set_command(parser,q): return True if self.is_py_command(parser,q): return True if self.is_end_command(parser,q): return True if self.is_run_command(parser,q): return True return False def is_py(self,parser): #print("is_py line="+line[:10]) p=0 p=parser.p_b(p) q=parser.p_key("py: ",p) if p==q: return False lx=parser.html[q:] self.current_program=self.current_program+lx+'\n' def interpret_a_line(self,line): #print("interpret_a_line:"+line) parser=html_parser(line) if self.is_object_page(parser): for i in range(len(self.urls)): uri=self.urls[i] self.GUI.add_uri(uri,i) return if self.is_device(parser): return if self.is_command(parser): return if self.is_py(parser): return def interpret_lines(self): #print("interpret_lines") for i in range(len(self.script_lines)): try: self.interpret_a_line(self.script_lines[i]) except Exception as e: line="error in '"+self.script_lines[i]+"'" print(line) self.write_line(line) line="...:{e}" print(line) self.write_line(line) self.send_result() def next_url(self): print("next_url") if len(self.urls)==0: return if int(self.next_url_index)>=len(self.urls): self.next_url_index=0 urlx=self.urls[int(self.next_url_index)] p=urlx.index("?") self.current_page=urlx[p+1:] #self.current_url=urlx[0:p-1] self.current_url=urlx[0:p] print("current_url="+self.current_url) print("current_page="+self.current_page) self.next_url_index=int(self.next_url_index)+1 self.Pico_Wiki_Driver.set_url(self.current_url) self.Pico_Wiki_Driver.set_page(self.current_page) def send_result(self): #print("send_result") self.GUI.write_message("send_result") self.replace_result() def write_line(self,line): #print("write_line") self.GUI.write_message("add_report "+line) self.add_report_line(line) def read_eval_print_loop(self): print("read_eval_print_loop") self.continue_read_eval_print_loop=True last_read_time=int(time.time() * 1000) last_eval_time=last_read_time last_write_time=last_read_time while self.continue_read_eval_print_loop: gc.collect() current_time=int(time.time() * 1000) if current_time<last_read_time: last_read_time=current_time if current_time-last_read_time>self.GUI.lookup_prop('read_interval'): last_read_time=current_time if self.read_script(): if self.GUI.lookup_prop('exec_interval')==0: self.eval_script() self.GUI.update() else: self.next_url() continue if self.GUI.lookup_prop('exec_interval')>0: exec_interval_time=self.GUI.lookup_prop('exec_interval') if current_time-last_eval_time>exec_interval_time: last_eval_time=current_time self.eval_script() if self.GUI.lookup_prop('write_interval')>0: if current_time-last_write_time>self.GUI.lookup_prop('exec_interval'): last_write_time=current_time self.send_result() #time.sleep_ms(100) time.sleep(0.1) def stop_read_eval_print_loop(self): self.continue_read_eval_print_loop=False def init_params(self): uri=self.GUI.lookup_prop('object_page_1') pass_word=self.GUI.lookup_prop('object_page_pass_1') page=uri.split('?')[1] url=uri.split('?')[0] self.set_current_url(url) self.set_current_page(page) self.set_current_pass(pass_word) self.next_url_index=0 def start_thread(gui): gui.click_start_button() def main() -> None: args = sys.argv if len(args)>=2: fst_opt=args[1] else: fst_opt=None print('fst_opt='+str(fst_opt)) root=Tk() bot=pico_wiki_bot() gui=GUI(root,bot) bot.set_GUI(gui) gui.set_Pico_Time(bot.Pico_Time) gui.init_params() bot.init_params() if fst_opt=='-s': start_thread(gui) root.mainloop() #print("-----------get_script_and_result-----------------") #print(bot.get_script_and_result()) #print("-----------get_result-----------------") #print(bot.get_result()) #print("-----------get_script-----------------") #print(bot.get_script()) #print("-----------get_current_device_line-----------------") #print(bot.get_current_device_line()) #print("-----------replace_result-----------------") #bot.replace_result("Hello!\nThis is a test2....\nxxxx") #print("-----------stop_timer--------------------") #bot.stop_timer() #bot.read_eval_print_loop() if __name__=='__main__': main() }}