pour ceux qui veulent modifier la consigne "normale" de température (je rappelle que cela ne marche par avec la commande à distance vitotrol 300)
2/ il faut ajouter un widget virtuel "Consigne de Thermostat" (setpoint thermostat)
Code : Tout sélectionner
#!/usr/bin/python
# domo2vito
# JS MARTIN
# version 2.11 - 07032017
import telnetlib
import sys
import os
import time
import requests
from requests.auth import HTTPBasicAuth
import json
############# Parameters #################################
#~~~~~~~~~~ Parameters Domoticz ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
domoticz_ip='192.168.10.40'
domoticz_port='8080'
user=''
password=''
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# Commands viTalk
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#autorized commands
commands = ["mode","saving","party","party_soll_temp","outdoor_temp","raum_soll_temp","raum_ist_temp","k_ist_temp","ww_soll_temp","ww_ist_temp","k_abgas_temp","power","errors","runtime","red_raum_soll_temp"]
#write only commands
write_only_commands = ["mode","saving","party","party_soll_temp","ww_soll_temp","red_raum_soll_temp","raum_soll_temp"]
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# IDX de Domoticz
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# remplacer XXX par votre idx de votre widget
dummy_idx={'mode':343, 'saving': 344, 'party':345, 'party_soll_temp':346, 'outdoor_temp':347, 'raum_soll_temp':355, 'raum_ist_temp':349, 'k_ist_temp':350, 'ww_soll_temp':351, 'ww_ist_temp':352, 'k_abgas_temp':353, 'power':354, 'error_log':371, 'problem':416, 'delta-rt': 537, 'gas':538, 'red_raum_soll_temp':548, 'holiday_temp':549, 'raum_soll_temp_W':577}
user_idx={'runtime-boiler':1} # please create a user variable [integer] (overall boiler time) - see https://www.domoticz.com/wiki/User_variables
# 0 mode : dummy selector switch OFF/Water/Heating (Boiler [FR:chaudiere] stand-by/water only/water+heating) {read/write}
# 1 saving : dummy switch ON/OFF (Boiler eco ON/OFF) {read/write}
# 2 party : dummy switch ON/OFF (party temporary manual control) - note : party ON does not work (vitalk bug ?) {read/write}
# 3 party_soll_temp : dummy thermostat setpoint (party temperature) {write only}
# 4 outdoor_temp : dummy temp (outdoor temperature) {read only}
# 5 raum_soll_temp : dummy temp (heating [FR:consigne] temperature ) {read only} - note : without vitotronic, you could use thermostat setpoint
# 6 raum_ist_temp : dummy temp (heating current [FR:actuelle] temperature) {read only}
# 7 k_ist_temp : dummy temp (boiler current temperature) {read only}
# 8 ww_soll_temp : dummy thermostat setpoint (hot water setpoint temperature) {write only}
# 9 ww_ist_temp : dummy temp (hot water current temperature) {read only}
#10 k_abgas_temp : dummy temp (exhaust gas [FR:gaz evacue'] temperature) {read only}
#11 power : dummy percentage (% boiler power) {read only}
#12 error_log : dummy alert (show the two last log codes) {read only}
# problem : dummy switch (set switch to On if there is a internal boiler problem)
#13 runtime : custom sensor [seconds] (Operating time of boiler since last script call) {read only}
# gas : dummy incremental counter [gas] (Estimation of Gas consumtion)
#14 red_raum_soll_temp: dummy thermostat setpoint (reduced temperature) {write only}
# holiday_temp : dummy thermostat setpoint (holiday temperature)
# raum_soll_temp_W : dummy thermostat setpoint (normal temperature) {write only} - note : does not work with vitotrol 300
# |_ for raum_soll_temp_W, you need to put the bolean Use_normal_temperature_setpoint to True
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# Mode debug
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# if debug = True => verbose
debug=True
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# Variable
#~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#Debit max gas (need to be adjust to synchronize estimated and real gas consumption)
Deb=0.12 #0.132 = trop fort 1200 l - 1min
# 0.136 - 3min
# Activated normal temperature setpoint
Use_normal_temperature_setpoint=True
#######################################################################
###### viTalk_connect() : connect to viTalk localhost:83
#######################################################################
def viTalk_connect():
global debug
retry=3
while retry!=0:
try:
tn = telnetlib.Telnet("localhost", 83)
if debug:
print "Connected to viTalk telnet !"
return tn
except:
print "Connection ERROR - I try to restart viTalk deamon"
#I try to restart viTalk
cmd = 'sudo service vitalk restart'
os.system(cmd)
time.sleep(10)
retry-=1
else:
tn.read_until(b"$", 5)
if retry==0:
tn.close()
print "Connection ERROR - I could not restart viTalk deamon"
sys.exit()
######
#######################################################################
###### viTalk_read(cmd) : read a value
#######################################################################
def viTalk_read(cmd):
global debug
global tn
retry=3
value=""
while retry!=0:
tn.read_until(b"$", 5)
tn.write(b"g "+cmd+"\n")
value=tn.read_until(b"$", 5).strip("\n$")
if value!="" and value!='NULL':
break
retry-=1
if retry==0:
print "Connection ERROR - I try to restart viTalk deamon"
os.system('sudo service vitalk restart')
#tn.close()
print(cmd+": "+value+" error")
sys.exit()
value = value.strip("\n$")
if debug:
print "get "+cmd+" : answer = "+value
return value
######
#######################################################################
###### viTalk_check() : test viTalk and restart it if needed
#######################################################################
def viTalk_check():
global debug
global tn
retry=3
value=""
while retry!=0:
tn.read_until(b"$", 5)
tn.write(b"g saving \n")
value=tn.read_until(b"$", 5).strip("\n$")
if value!="" and value!='NULL':
if debug:
print "Check viTalk data OK ! (no NULL data received)"
break
retry-=1
if retry==0:
print "Connection ERROR - I try to restart viTalk deamon"
os.system('sudo service vitalk restart')
sys.exit()
######
#######################################################################
###### viTalk_set(cmd,val) : unsecured write
#######################################################################
def viTalk_set(cmd,val):
global debug
global tn
if cmd!="mode":
tn.write(b"s "+cmd+" "+val+"\n")
else: # vitalk does not manage mode 3 and 4 => raw set directly
tn.write(b"rs 2323 "+val+"\n")
tn.read_until(b"$", 5).strip("\n$")
if debug: print("set "+cmd+" "+val)
######
#######################################################################
###### viTalk_write(cmd,val) : secured write (I check if value is
###### really updated)
#######################################################################
def viTalk_write(cmd,val):
global debug
global tn
retry=3
value=""
while retry!=0:
viTalk_set(cmd,val)
tn.read_until(b"$", 5)
time.sleep(1)
value=viTalk_read(cmd)
if val==value:
break
retry-=1
if retry==0:
tn.close()
print(cmd+" "+val+" : error")
sys.exit()
if debug:
print "check last command set "+cmd+" "+val+" : OK"
#########
#######################################################################
###### check_command(cmd) : is it an authorized command ?
#######################################################################
def check_command(cmd):
global commands
global debug
try:
#check position of cmd in commands list
commands.index(cmd)
except:
print "command not found"
return False
else:
if debug:
print "this command "+cmd+" is known"
return True
####
#######################################################################
###### check_set_command(cmd) : is it an authorized write command ?
#######################################################################
def check_set_command(cmd):
global commands
global debug
try:
#check position of cmd in write only commands list
write_only_commands.index(cmd)
except:
print "set command not found (I can't write with this command)"
return False
else:
if debug:
print "this command "+cmd+" is known for writing"
return True
####
#######################################################################
###### get_setpoint_temp(idx) : get temperature from domoticz setpoint
#######################################################################
def get_setpoint_temp(idx):
r = requests.get('http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=devices&rid='+str(idx),auth=HTTPBasicAuth(user,password))
status=r.status_code
if status == 200:
r=r.json()
result={}
return r['result'][0]['Data']
else:
print "Get setpoint temp error - IDX:"+str(idx)
####
########################################################################
###### get_state(idx) : get dummy state from domoticz
########################################################################
def get_state(idx):
r = requests.get('http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=devices&rid='+str(idx),auth=HTTPBasicAuth(user,password))
status=r.status_code
if status == 200:
r=r.json()
result={}
return r['result'][0]['Data']
else:
print "Get state error - IDX:"+str(idx)+" not found ?"
####
########################################################################
###### get_last_runtime(idx) : get last runtime value from domoticz
########################################################################
def get_last_runtime(idx):
r = requests.get('http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=getuservariable&idx='+str(idx),auth=HTTPBasicAuth(user,password))
status=r.status_code
if status == 200:
r=r.json()
result={}
return r['result'][0]['Value']
else:
print "Get state error - IDX:"+str(idx)
####
#-----------------------------------### START ###--------------------------------------------#
# arguments in command line
nb_arg=len(sys.argv)-1
if nb_arg==0:
print "HELP : "
print "domo2vito update : update all domoticz values"
print "domo2vito command : get command (e.g. domo2vito mode <=> get mode)"
print "domo2vito command value : set command value (e.g. domo2vito mode 1 <=> set mode 1)"
print "--> supported commands :"
for command in commands:
print " - "+command
if nb_arg==1 and sys.argv[1]!="update":
if check_command(sys.argv[1]):
if debug:
print "get "+sys.argv[1]
tn=viTalk_connect()
viTalk_read(sys.argv[1])
tn.close()
if nb_arg==1 and sys.argv[1]=="update":
tn=viTalk_connect()
viTalk_check()
values=[]
i=0
tn.read_until(b"$", 5)
for command in commands:
tn.write(b"g "+command+"\n")
value=tn.read_until(b"$", 5).strip("\n$")
if debug:
print str(i)+") command : get "+command+ " => "+value
values.append(value)
i+=1
if debug: print "+Now I check if I need to update some values into Viessmann boiler or into Domoticz..."
mcur=time.localtime().tm_min # to update setpoint one time every hour - get minute of current hour
if mcur>40 and mcur<46: # Heartbeat - update setpoint in Domoticz one time per hour just to avoid "lost widget status"
setpoint_heartbeat=True
else:
setpoint_heartbeat=False
# party_soll_temp : get setpoint party_soll_temp and update boiler if needed
temp=int(float(get_setpoint_temp(dummy_idx['party_soll_temp'])))
if temp!=int(float(values[3])): #Viessmann ignore decimales
if temp<10: temp=10 # party mini temp
if temp>30: temp=30 # party maxi temp
if debug: print "3) party setpoint has changed : I update Viessmann boiler with party temperature = "+str(temp)
viTalk_set("party_soll_temp",str(temp))
else:
if setpoint_heartbeat:
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['party_soll_temp'])+'&nvalue=0&svalue='+str(temp)
requests.get(req,auth=HTTPBasicAuth(user,password))
# get setpoint ww_soll_temp and update boiler if needed
temp=int(float(get_setpoint_temp(dummy_idx['ww_soll_temp'])))
if temp!=int(float(values[8])): #Viessmann ignore decimales
if temp<20: temp=20 # hot water mini temp
if temp>70: temp=70 # hot water maxi temp
if debug: print "8) hot water setpoint has changed : I update Viessmann boiler with hot water temperature = "+str(temp)
viTalk_set("ww_soll_temp",str(temp))
else:
if setpoint_heartbeat:
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['ww_soll_temp'])+'&nvalue=0&svalue='+str(temp)
requests.get(req,auth=HTTPBasicAuth(user,password))
# holiday mode : emulated* holiday mode *I put boiler in permanent reduce mode with a custom holiday temp
if int(values[0])==3: # mode 'permanent reduce'
if debug: print "Holiday mode : I check if reduced temp. = domoticz holiday setpoint temp."
temp=int(float(get_setpoint_temp(dummy_idx['holiday_temp'])))
if temp!=int(float(values[14])):
if temp<10: temp=10 # holidays mini temp
if temp>30: temp=30 # holidays maxi temp
viTalk_set("red_raum_soll_temp",str(temp)) # Reduced temp = domoticz holiday temp
if debug: print "- I update reduced temperature with domoticz holiday setpoint temperature"
else:
# get setpoint red_raum_soll_temp and update boiler if needed
if debug: print "NOT Holiday mode : I check if reduced temp. = domoticz reduced setpoint temp."
temp=int(float(get_setpoint_temp(dummy_idx['red_raum_soll_temp'])))
if temp!=int(float(values[14])): #Viessmann ignore decimales
if temp<10: temp=10 # reduced mini temp
if temp>30: temp=30 # reduced maxi temp
if debug: print "14) Reduced temp setpoint has changed : I update Viessmann boiler with reduced temperature = "+str(temp)
viTalk_set("red_raum_soll_temp",str(temp))
if Use_normal_temperature_setpoint:
if debug: print "Use_normal_temperature_setpoint => activated"
temp=int(float(get_setpoint_temp(dummy_idx['raum_soll_temp_W'])))
if temp!=int(float(values[5])): #Viessmann ignore decimales
if temp<10: temp=10 # reduced mini temp
if temp>30: temp=30 # reduced maxi temp
if debug: print "15) Normal temp setpoint has changed : I update Viessmann boiler with normal temperature = "+str(temp)
viTalk_set("raum_soll_temp",str(temp))
if setpoint_heartbeat:
temp=int(float(get_setpoint_temp(dummy_idx['holiday_temp'])))
if temp<10: temp=10 # holidays mini temp
if temp>30: temp=30 # holidays maxi temp
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['holiday_temp'])+'&nvalue=0&svalue='+str(temp)
requests.get(req,auth=HTTPBasicAuth(user,password))
temp=int(float(get_setpoint_temp(dummy_idx['red_raum_soll_temp'])))
if temp<10: temp=10 # reduced mini temp
if temp>30: temp=30 # reduced maxi temp
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['red_raum_soll_temp'])+'&nvalue=0&svalue='+str(temp)
requests.get(req,auth=HTTPBasicAuth(user,password))
if Use_normal_temperature_setpoint:
temp=int(float(get_setpoint_temp(dummy_idx['raum_soll_temp_W'])))
if temp<10: temp=10 # normal mini temp
if temp>30: temp=30 # normal maxi temp
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['raum_soll_temp_W'])+'&nvalue=0&svalue='+str(temp)
requests.get(req,auth=HTTPBasicAuth(user,password))
tn.close()
# mode (selector level : 0=OFF 10=water 20=heating 30=holidays 40=always On)
previous_value=get_state(dummy_idx['mode'])
if previous_value=="Off": previous_value="Set Level: 0 %"
if int(previous_value[11:-1])!=int(values[0])*10:
if debug: print "0) Value MODE has changed : I update domoticz with mode = "+values[0]
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['mode'])+'&switchcmd=Set%20Level&level='+str(int(values[0])*10)
requests.get(req,auth=HTTPBasicAuth(user,password))
# saving : dummy switch ON/OFF (Boiler eco ON/OFF) : if a user modify boiler or vitotrol, update Domoticz
previous_value=get_state(dummy_idx['saving'])
if (previous_value=="On" and values[1]=="0") or (previous_value=="Off" and values[1]=="1"):
if debug: print "1) Value SAVING has changed : I update domoticz with saving = "+values[1]
if values[1]=="0":
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['saving'])+'&switchcmd=Off'
else:
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['saving'])+'&switchcmd=On'
requests.get(req,auth=HTTPBasicAuth(user,password))
# party : dummy switch ON/OFF (party temporary manual control) : if a user modify boiler or vitotrol, update Domoticz
previous_value=get_state(dummy_idx['party'])
if (previous_value=="On" and values[2]=="0") or (previous_value=="Off" and values[2]=="1"):
if debug: print "2) Value PARTY has changed : I update domoticz with party = "+values[2]
if values[2]=="0":
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['party'])+'&switchcmd=Off'
else:
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['party'])+'&switchcmd=On'
requests.get(req,auth=HTTPBasicAuth(user,password))
# outdoor_temp : dummy temp (outdoor temperature)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['outdoor_temp'])+'&nvalue=0&svalue='+values[4]
requests.get(req,auth=HTTPBasicAuth(user,password))
# raum_soll_temp : dummy temp (heating setpoint [FR:consigne] temperature) - note : without vitotronic, use thermostat setpoint
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['raum_soll_temp'])+'&nvalue=0&svalue='+values[5]
requests.get(req,auth=HTTPBasicAuth(user,password))
# raum_ist_temp : dummy temp (heating current [FR:actuelle] temperature)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['raum_ist_temp'])+'&nvalue=0&svalue='+values[6]
requests.get(req,auth=HTTPBasicAuth(user,password))
# k_ist_temp : dummy temp (boiler current temperature)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['k_ist_temp'])+'&nvalue=0&svalue='+values[7]
requests.get(req,auth=HTTPBasicAuth(user,password))
# ww_ist_temp : dummy temp (hot water current temperature)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['ww_ist_temp'])+'&nvalue=0&svalue='+values[9]
requests.get(req,auth=HTTPBasicAuth(user,password))
# k_abgas_temp : dummy temp (exhaust gas [FR:gaz evacue'] temperature)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['k_abgas_temp'])+'&nvalue=0&svalue='+values[10]
requests.get(req,auth=HTTPBasicAuth(user,password))
# power : dummy percentage (% boiler power)
previous_power_value=get_state(dummy_idx['power'])[:-1] # on supprime le % a la fin de la chaine
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['power'])+'&nvalue=0&svalue='+values[11]
requests.get(req,auth=HTTPBasicAuth(user,password))
# Get previous boiler runtime value from Domoticz database (user variable)
last_rt=int(get_last_runtime(user_idx['runtime-boiler']))
delta_rt=int(values[13])-last_rt # delta-runtime
# update boiler-runtime since last update
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['delta-rt'])+'&nvalue=0&svalue='+str(delta_rt)
requests.get(req,auth=HTTPBasicAuth(user,password))
# Set overall boiler runtime into Domoticz database (user variable)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=updateuservariable&idx='+str(user_idx['runtime-boiler'])+'&vname=runtime-boiler&vtype=0&vvalue='+values[13]
requests.get(req,auth=HTTPBasicAuth(user,password))
if debug: print "+Now I calculate the gas consumed since last script call:"
# gas : gas estimation
power_average=(float(previous_power_value)+float(values[11]))/2
gas_used=delta_rt*Deb*power_average/100
if debug:
print " -Viessmann boiler runtime since last script call (sec) = "+str(delta_rt)
print " -Viessmann boiler power average (%) = "+ str(power_average)
print " -Estimated gas used (liter) = "+str(gas_used)
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['gas'])+'&nvalue=0&svalue='+str(gas_used)
requests.get(req,auth=HTTPBasicAuth(user,password))
if debug: print "+Now I check boiler error..."
# error_log : dummy alert (show the two last log codes)
# problem : dummy switch (set switch to On if there is a internal boiler problem)
#values[12]="123,255,235,244,244,244,244,244,244,244 ;"
V_error=values[12][0:3]
V_previous_error=values[12][4:7]
V_error_hexa=str(hex(int(V_error)))[2:4] # hexa convertion
V_previous_error_hexa=str(hex(int(V_previous_error)))[2:4] # hexa convertion
V_previous_error_state=get_state(str(dummy_idx['error_log']))[0:2]
V_previous_problem_state=get_state(str(dummy_idx['problem']))
if V_error=="000":
if debug: print " -no internal error : all it is OK"+" (previous code="+V_previous_error_hexa+")"
if V_previous_error_state!="OK": # I update error_log alert only if state is modified
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['error_log'])+'&nvalue=1&svalue='+'OK (previous='+V_previous_error_hexa+')'
requests.get(req,auth=HTTPBasicAuth(user,password))
if V_previous_problem_state=="On": # I update problem switch only if state is modified
if debug: print " -state of boiler error status changed (no problem): I update the Domotics boiler problem switch"
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['problem'])+'&switchcmd=Off'
requests.get(req,auth=HTTPBasicAuth(user,password))
else:
if debug: print " -there is an internal error : code="+V_error_hexa+" ( previous ="+V_previous_error_hexa+")"
if V_previous_error_state!=V_error_hexa: # I update error_log alert only if state is modified
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=udevice&idx='+str(dummy_idx['error_log'])+'&nvalue=4&svalue='+V_error_hexa+' error (previous='+V_previous_error_hexa+')'
requests.get(req,auth=HTTPBasicAuth(user,password))
if V_previous_problem_state=="Off": # I update problem switch only if state is modified
if debug: print " -state of boiler error status changed (problem): I update the Domotics boiler problem switch"
req='http://'+domoticz_ip+':'+domoticz_port+'/json.htm?type=command¶m=switchlight&idx='+str(dummy_idx['problem'])+'&switchcmd=On'
requests.get(req,auth=HTTPBasicAuth(user,password))
if nb_arg==2:
if check_set_command(sys.argv[1]):
print "set "+sys.argv[1]+" "+sys.argv[2]
tn=viTalk_connect()
viTalk_write(sys.argv[1],sys.argv[2])
tn.close()