dtgbot - Domoticz TeleGram BOT

Client tools or tools that can connect with Domoticz. Tools for Windows, iOS, Android, Linux etc.

Moderator: leecollings

DennisD
Posts: 51
Joined: Friday 18 September 2015 21:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by DennisD »

Hmmm just removed the device (kodi) and dtgbot seems to have come alive, weird.
User avatar
jvdz
Posts: 2189
Joined: Tuesday 30 December 2014 19:25
Target OS: Raspberry Pi / ODroid
Domoticz version: 4.107
Location: Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by jvdz »

Strange.. You have exactly the same issue! That JSON should contain a RESULT section with more information.
What is that device exactly and which version of Domoticz are you running?
I have a test version of dtg_domoticz.lua you could test to see if that ignores these type of device responses, but it clearly is a wrong response for a regular device.

Jos

test version code of dtg_domoticz.lua:

Code: Select all

-- A set of support functions currently aimed at dtgbot,
-- but probably more general

function form_device_name(parsed_cli)
-- joins together parameters after the command name to form the full "device name"
	command = parsed_cli[2]
	DeviceName = parsed_cli[3]
	len_parsed_cli = #parsed_cli
	if len_parsed_cli > 3 then
	for i = 4, len_parsed_cli do
		DeviceName = DeviceName..' '..parsed_cli[i]
	end
	end
	return DeviceName
end

-- returns list of all user variables - called early by dtgbot
-- in case Domoticz is not running will retry
-- allowing Domoticz time to start
function variable_list()
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type=command&param=getuservariables"
	jresponse = nil
	domoticz_tries = 1
	-- Domoticz seems to take a while to respond to getuservariables after start-up
	-- So just keep trying after 1 second sleep
	while (jresponse == nil) do
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	if (jresponse == nil) then
		socket.sleep(1)
		domoticz_tries = domoticz_tries + 1
		if domoticz_tries > 100 then
		print_to_log(0,'Domoticz not sending back user variable list')
		break
		end
	end
	end
	print_to_log(0,'Domoticz returned getuservariables after '..domoticz_tries..' attempts')
	decoded_response = JSON:decode(jresponse)
	return decoded_response
end

-- returns idx of a user variable from name
function variable_list_names_idxs()
	local idx, k, record, decoded_response
	decoded_response = variable_list()
	result = decoded_response["result"]
	variables = {}
	for i = 1, #result do
	record = result[i]
	if type(record) == "table" then
		variables[record['Name']] = record['idx']
	end
	end
	return variables
end

function idx_from_variable_name(DeviceName)
	return Variablelist[DeviceName]
end

-- returns the value of the variable from the idx
function get_variable_value(idx)
	local t, jresponse, decoded_response
	if idx == nill then
	return ""
	end
	t = server_url.."/json.htm?type=command&param=getuservariable&idx="..tostring(idx)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	print_to_log(0,'Decoded '..decoded_response["result"][1]["Value"])
	return decoded_response["result"][1]["Value"]
end

function set_variable_value(idx,name,type,value)
	-- store the value of a user variable
	local t, jresponse, decoded_response
	t = server_url.."/json.htm?type=command&param=updateuservariable&idx="..idx.."&vname="..name.."&vtype="..type.."&vvalue="..tostring(value)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	return
end

function create_variable(name,type,value)
	-- creates user variable
	local t, jresponse, decoded_response
	t = server_url.."/json.htm?type=command&param=saveuservariable&vname="..name.."&vtype="..type.."&vvalue="..tostring(value)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	return
end

-- returns a device table of Domoticz items based on type i.e. devices or scenes
function device_list(DeviceType)
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type="..DeviceType.."&order=name&used=true"
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	return decoded_response
end

-- returns a list of Domoticz items based on type i.e. devices or scenes
function device_list_names_idxs(DeviceType)
	--returns a devcie idx based on its name
	local idx, k, record, decoded_response
	decoded_response = device_list(DeviceType)
	result = decoded_response['result']
	devices = {}
	devicesproperties = {}
	for i = 1, #result do
	record = result[i]
	if type(record) == "table" then
		if DeviceType == "plans" then
		devices[record['Name']] = record['idx']
		else
		devices[string.lower(record['Name'])] = record['idx']
		devices[record['idx']] = record['Name']
		if DeviceType == 'scenes' then
			devicesproperties[record['idx']] = {Type=record['Type'], SwitchType = record['Type']}
		end
		end
	end
	end
	return devices, devicesproperties
end

function idx_from_name(DeviceName,DeviceType)
	--returns a devcie idx based on its name
	if DeviceType == "devices" then
	return Devicelist[string.lower(DeviceName)]
	elseif DeviceType == "scenes" then
	return Scenelist[string.lower(DeviceName)]
	else
	return Roomlist[DeviceName]
	end
end

function retrieve_status(idx,DeviceType)
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type="..DeviceType.."&rid="..tostring(idx)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	return decoded_response
end

-- support function to scan through the Devices and Scenes idx tables and retrieve the required information for it
function devinfo_from_name(idx,DeviceName,DeviceScene)
	local k, record, Type,DeviceType,SwitchType
	local found = 0
	local rDeviceName=""
	local status=""
	local MaxDimLevel=100
	local ridx=0
	local tvar
	if DeviceScene~="scenes" then
	-- Check for Devices
	-- Have the device name
	if DeviceName ~= "" then
		idx = idx_from_name(DeviceName,'devices')
	end
	print_to_log(2,"==> start devinfo_from_name", idx,DeviceName)
		if idx ~= nil then
		 test   = retrieve_status(idx,"devices")['result']
		 if test ~= nil then
			record = test[1]
--~      record = retrieve_status(idx,"devices")['result'][1]
			print_to_log(2,'device ',DeviceName,record.Name,idx,record.idx)
			if type(record) == "table" then
				 ridx = record.idx
				 rDeviceName = record.Name
				 DeviceType="devices"
				 Type=record.Type
				 -- as default simply use the status field
				 -- use the dtgbot_type_status to retrieve the status from the "other devices" field as defined in the table.
				 if dtgbot_type_status[Type] ~= nil then
					if dtgbot_type_status[Type].Status ~= nil then
					 status = ''
					 CurrentStatus = dtgbot_type_status[Type].Status
					 for i=1, #CurrentStatus do
						if status ~= '' then
							 status = status .. ' - '
						end
						cindex, csuffix = next(CurrentStatus[i])
						status = status .. tostring(record[cindex])..tostring(csuffix)
					 end
					end
				 else
					SwitchType=record.SwitchType
					MaxDimLevel=record.MaxDimLevel
					status = tostring(record.Status)
				 end
				 found = 1
				 print_to_log(2," !!!! found device",record.Name,rDeviceName,record.idx,ridx)
			end
		 end
		end
	print_to_log(2," !!!! found device",rDeviceName,ridx)
	end
-- Check for Scenes
	if DeviceScene=="scenes" then
		if found == 0 then
			if DeviceName ~= "" then
				idx = idx_from_name(DeviceName,'scenes')
			else
				DeviceName = idx_from_name(idx,'scenes')
			end
			if idx ~= nil then
				DeviceName = Scenelist[idx]
				DeviceType="scenes"
				ridx = idx
				rDeviceName = DeviceName
				SwitchType = Sceneproperties[tostring(idx)]['SwitchType']
				Type = Sceneproperties[tostring(idx)]['Type']
				found = 1
			end
		end
	end
-- Check for Scenes
	if found == 0 then
	ridx = 9999
	DeviceType="command"
	Type="command"
	SwitchType="command"
	end
	print_to_log(2," --< devinfo_from_name:",found,ridx,rDeviceName,DeviceType,Type,SwitchType,status)
	return ridx,rDeviceName,DeviceType,Type,SwitchType,MaxDimLevel,status
end

function file_exists(name)
	local f=io.open(name,"r")
	if f~=nil then io.close(f) return true else return false end
end

function domoticz_language()
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type=command&param=getlanguage"
	jresponse = nil
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	local language = decoded_response['language']
	if language ~= nil then
	return language
	else
	return 'en'
	end
end
New Garbage collection scripts: https://github.com/jvanderzande/GarbageCalendar
User avatar
G3rard
Posts: 669
Joined: Wednesday 04 March 2015 22:15
Target OS: -
Domoticz version: No
Location: The Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by G3rard »

maomanna wrote:
G3rard wrote:I have dtgbot working on my Ubuntu server. It took some extra steps which I think I have written down. Will have a look at it this weekend and share the steps here.
but do you have a x86 or x64 ubuntu server?
My Ubuntu server is 64 bit.
Not using Domoticz anymore
maomanna
Posts: 94
Joined: Monday 30 November 2015 16:21
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by maomanna »

How did you compile the lua libraries?
In the OP is a 32bit version supplied.
DennisD
Posts: 51
Joined: Friday 18 September 2015 21:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by DennisD »

jvdz wrote:Strange.. You have exactly the same issue! That JSON should contain a RESULT section with more information.
What is that device exactly and which version of Domoticz are you running?
I have a test version of dtg_domoticz.lua you could test to see if that ignores these type of device responses, but it clearly is a wrong response for a regular device.

Jos

test version code of dtg_domoticz.lua:

Code: Select all

-- A set of support functions currently aimed at dtgbot,
-- but probably more general

function form_device_name(parsed_cli)
-- joins together parameters after the command name to form the full "device name"
	command = parsed_cli[2]
	DeviceName = parsed_cli[3]
	len_parsed_cli = #parsed_cli
	if len_parsed_cli > 3 then
	for i = 4, len_parsed_cli do
		DeviceName = DeviceName..' '..parsed_cli[i]
	end
	end
	return DeviceName
end

-- returns list of all user variables - called early by dtgbot
-- in case Domoticz is not running will retry
-- allowing Domoticz time to start
function variable_list()
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type=command&param=getuservariables"
	jresponse = nil
	domoticz_tries = 1
	-- Domoticz seems to take a while to respond to getuservariables after start-up
	-- So just keep trying after 1 second sleep
	while (jresponse == nil) do
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	if (jresponse == nil) then
		socket.sleep(1)
		domoticz_tries = domoticz_tries + 1
		if domoticz_tries > 100 then
		print_to_log(0,'Domoticz not sending back user variable list')
		break
		end
	end
	end
	print_to_log(0,'Domoticz returned getuservariables after '..domoticz_tries..' attempts')
	decoded_response = JSON:decode(jresponse)
	return decoded_response
end

-- returns idx of a user variable from name
function variable_list_names_idxs()
	local idx, k, record, decoded_response
	decoded_response = variable_list()
	result = decoded_response["result"]
	variables = {}
	for i = 1, #result do
	record = result[i]
	if type(record) == "table" then
		variables[record['Name']] = record['idx']
	end
	end
	return variables
end

function idx_from_variable_name(DeviceName)
	return Variablelist[DeviceName]
end

-- returns the value of the variable from the idx
function get_variable_value(idx)
	local t, jresponse, decoded_response
	if idx == nill then
	return ""
	end
	t = server_url.."/json.htm?type=command&param=getuservariable&idx="..tostring(idx)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	print_to_log(0,'Decoded '..decoded_response["result"][1]["Value"])
	return decoded_response["result"][1]["Value"]
end

function set_variable_value(idx,name,type,value)
	-- store the value of a user variable
	local t, jresponse, decoded_response
	t = server_url.."/json.htm?type=command&param=updateuservariable&idx="..idx.."&vname="..name.."&vtype="..type.."&vvalue="..tostring(value)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	return
end

function create_variable(name,type,value)
	-- creates user variable
	local t, jresponse, decoded_response
	t = server_url.."/json.htm?type=command&param=saveuservariable&vname="..name.."&vtype="..type.."&vvalue="..tostring(value)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	return
end

-- returns a device table of Domoticz items based on type i.e. devices or scenes
function device_list(DeviceType)
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type="..DeviceType.."&order=name&used=true"
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	return decoded_response
end

-- returns a list of Domoticz items based on type i.e. devices or scenes
function device_list_names_idxs(DeviceType)
	--returns a devcie idx based on its name
	local idx, k, record, decoded_response
	decoded_response = device_list(DeviceType)
	result = decoded_response['result']
	devices = {}
	devicesproperties = {}
	for i = 1, #result do
	record = result[i]
	if type(record) == "table" then
		if DeviceType == "plans" then
		devices[record['Name']] = record['idx']
		else
		devices[string.lower(record['Name'])] = record['idx']
		devices[record['idx']] = record['Name']
		if DeviceType == 'scenes' then
			devicesproperties[record['idx']] = {Type=record['Type'], SwitchType = record['Type']}
		end
		end
	end
	end
	return devices, devicesproperties
end

function idx_from_name(DeviceName,DeviceType)
	--returns a devcie idx based on its name
	if DeviceType == "devices" then
	return Devicelist[string.lower(DeviceName)]
	elseif DeviceType == "scenes" then
	return Scenelist[string.lower(DeviceName)]
	else
	return Roomlist[DeviceName]
	end
end

function retrieve_status(idx,DeviceType)
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type="..DeviceType.."&rid="..tostring(idx)
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	return decoded_response
end

-- support function to scan through the Devices and Scenes idx tables and retrieve the required information for it
function devinfo_from_name(idx,DeviceName,DeviceScene)
	local k, record, Type,DeviceType,SwitchType
	local found = 0
	local rDeviceName=""
	local status=""
	local MaxDimLevel=100
	local ridx=0
	local tvar
	if DeviceScene~="scenes" then
	-- Check for Devices
	-- Have the device name
	if DeviceName ~= "" then
		idx = idx_from_name(DeviceName,'devices')
	end
	print_to_log(2,"==> start devinfo_from_name", idx,DeviceName)
		if idx ~= nil then
		 test   = retrieve_status(idx,"devices")['result']
		 if test ~= nil then
			record = test[1]
--~      record = retrieve_status(idx,"devices")['result'][1]
			print_to_log(2,'device ',DeviceName,record.Name,idx,record.idx)
			if type(record) == "table" then
				 ridx = record.idx
				 rDeviceName = record.Name
				 DeviceType="devices"
				 Type=record.Type
				 -- as default simply use the status field
				 -- use the dtgbot_type_status to retrieve the status from the "other devices" field as defined in the table.
				 if dtgbot_type_status[Type] ~= nil then
					if dtgbot_type_status[Type].Status ~= nil then
					 status = ''
					 CurrentStatus = dtgbot_type_status[Type].Status
					 for i=1, #CurrentStatus do
						if status ~= '' then
							 status = status .. ' - '
						end
						cindex, csuffix = next(CurrentStatus[i])
						status = status .. tostring(record[cindex])..tostring(csuffix)
					 end
					end
				 else
					SwitchType=record.SwitchType
					MaxDimLevel=record.MaxDimLevel
					status = tostring(record.Status)
				 end
				 found = 1
				 print_to_log(2," !!!! found device",record.Name,rDeviceName,record.idx,ridx)
			end
		 end
		end
	print_to_log(2," !!!! found device",rDeviceName,ridx)
	end
-- Check for Scenes
	if DeviceScene=="scenes" then
		if found == 0 then
			if DeviceName ~= "" then
				idx = idx_from_name(DeviceName,'scenes')
			else
				DeviceName = idx_from_name(idx,'scenes')
			end
			if idx ~= nil then
				DeviceName = Scenelist[idx]
				DeviceType="scenes"
				ridx = idx
				rDeviceName = DeviceName
				SwitchType = Sceneproperties[tostring(idx)]['SwitchType']
				Type = Sceneproperties[tostring(idx)]['Type']
				found = 1
			end
		end
	end
-- Check for Scenes
	if found == 0 then
	ridx = 9999
	DeviceType="command"
	Type="command"
	SwitchType="command"
	end
	print_to_log(2," --< devinfo_from_name:",found,ridx,rDeviceName,DeviceType,Type,SwitchType,status)
	return ridx,rDeviceName,DeviceType,Type,SwitchType,MaxDimLevel,status
end

function file_exists(name)
	local f=io.open(name,"r")
	if f~=nil then io.close(f) return true else return false end
end

function domoticz_language()
	local t, jresponse, status, decoded_response
	t = server_url.."/json.htm?type=command&param=getlanguage"
	jresponse = nil
	print_to_log(1,"JSON request <"..t..">");
	jresponse, status = http.request(t)
	decoded_response = JSON:decode(jresponse)
	local language = decoded_response['language']
	if language ~= nil then
	return language
	else
	return 'en'
	end
end
I'm running the latest beta 3.7450, but i think i figured it out. Because the hardware i removed (kodi) can't be found in the hardware list any more (now called kodi players). So i figure it has to do with that and not with the script. Maybe this is the solution for maomanna and his raspberry pi, remove the device that doesn't give any results and add the new "updated" hardware.

Thanks for the help!
maomanna
Posts: 94
Joined: Monday 30 November 2015 16:21
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by maomanna »

nice findings!

Meaning that there will be some check if a JSON request is failed, that the device will be skipped and the script will continue.
User avatar
jvdz
Posts: 2189
Joined: Tuesday 30 December 2014 19:25
Target OS: Raspberry Pi / ODroid
Domoticz version: 4.107
Location: Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by jvdz »

That is what I have tried to do in the posted updated script... It should at least continue in case data is missing.

Jos
New Garbage collection scripts: https://github.com/jvanderzande/GarbageCalendar
User avatar
G3rard
Posts: 669
Joined: Wednesday 04 March 2015 22:15
Target OS: -
Domoticz version: No
Location: The Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by G3rard »

maomanna wrote:How did you compile the lua libraries?
In the OP is a 32bit version supplied.
I did the following steps to make dtgbot working on my Ubuntu server 14.04 x64.
Not using Domoticz anymore
DennisD
Posts: 51
Joined: Friday 18 September 2015 21:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by DennisD »

Strange question, when somebody enters our house and both me and the wife aren't at home, i get a msg (telegram) that somebody is in my house. Would it be possible to interact with that via dtgbot so that you get a question which you can answer yes or no. So for example: Somebody is in your home, is that correct? If you will reply with yes, nothing will happen and you will get no further notifications, answering no would mean sounding the alarm etc.
User avatar
jvdz
Posts: 2189
Joined: Tuesday 30 December 2014 19:25
Target OS: Raspberry Pi / ODroid
Domoticz version: 4.107
Location: Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by jvdz »

Anything is possible as long as DTGBOT understands the Yes/No command. So maybe your script that sends the warning should also set a uservariable which you then check when a Yes/No command is received... just thinking out loud here.

Jos
New Garbage collection scripts: https://github.com/jvanderzande/GarbageCalendar
DennisD
Posts: 51
Joined: Friday 18 September 2015 21:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by DennisD »

Good thinking, i have to come up with something!
u01pei

Re: dtgbot - Domoticz TeleGram BOT

Post by u01pei »

Hi Jos,

I wanted to try DTGBOT, but I can't seem to get it to work. I have tried changing all kinds of settings, but DTGBOT starts, than exits after a minute or two.
The TelegramBotOffset variable stays at 1.
setting the TelegramBotLoglevel variable to 1 or 2 does not create more log output.

My error log:

Code: Select all

/usr/bin/lua5.2: /usr/local/share/lua/5.2/JSON.lua:383: nil passed to JSON:decode()
stack traceback:
	[C]: in function 'assert'
	/usr/local/share/lua/5.2/JSON.lua:383: in function 'onDecodeOfNilError'
	/usr/local/share/lua/5.2/JSON.lua:644: in function 'decode'
	/home/pi/dtgbot//dtg_domoticz.lua:40: in function 'variable_list'
	/home/pi/dtgbot//dtg_domoticz.lua:47: in function 'variable_list_names_idxs'
	/home/pi/dtgbot/dtgbot.lua:184: in function 'dtgbot_initialise'
	/home/pi/dtgbot/dtgbot.lua:229: in main chunk
	[C]: in ?
These messages are repeated every exit and always the same.

log:

Code: Select all

2017-05-22 15:51:59 - DomoticzIP: USER:[email protected]
2017-05-22 15:51:59 - DomoticzPort: 8010
2017-05-22 15:51:59 - BotHomePath: /home/pi/dtgbot/
2017-05-22 15:51:59 - BotLuaScriptPath: /home/pi/dtgbot/lua/
2017-05-22 15:51:59 - TempFileDir: /home/pi/domoticz/scripts/temp/
2017-05-22 15:51:59 - BotBashScriptPath: /home/pi/dtgbot/bash/
2017-05-22 15:51:59 - TelegramBotToken: BOT:Token
2017-05-22 15:51:59 - TelegramBotOffset: TelegramBotOffset
2017-05-22 15:51:59 - -----------------------------------------
2017-05-22 15:51:59 - Starting Telegram api Bot message handler
2017-05-22 15:51:59 - -----------------------------------------
2017-05-22 15:51:59 - Using DTGBOT config file:/home/pi/dtgbot//dtgbot.cfg
2017-05-22 15:53:39 - Domoticz not sending back user variable list
2017-05-22 15:53:39 - Domoticz returned getuservariables after 101 attempts
Setting IP to 192.168.1.11, changes nothing
Setting IP to NOT use login credentials also changes nothing.

I did notice one thing: The chatID is single quoted ('TOKEN'), while the rest of the data is double quoted ("DATA"). is this correct?

If you have any pointers on how I can overcome this problem and get the system working, I would much appreciate it!

Thanks!

EDIT:
I feel a bit stupid right now.... found the problem: I entered the external domoticz port (8010) which is forwarded to internal 8080, so changing the port number to 8080 in DomoticzData.sh solved the problem....duh...
User avatar
jvdz
Posts: 2189
Joined: Tuesday 30 December 2014 19:25
Target OS: Raspberry Pi / ODroid
Domoticz version: 4.107
Location: Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by jvdz »

Glad you solved it. ;)
Jos
New Garbage collection scripts: https://github.com/jvanderzande/GarbageCalendar
EBOOZ
Posts: 11
Joined: Wednesday 30 December 2015 9:50
Target OS: Raspberry Pi / ODroid
Domoticz version: V3.8153
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by EBOOZ »

DennisD wrote:Good thinking, i have to come up with something!
Did you manage to find a solution for this? I'm also thinking of implementing a couple of yes/no questions on certain times.
DennisD
Posts: 51
Joined: Friday 18 September 2015 21:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by DennisD »

@ebooz, no sorry still haven't found the time to dig into it.
Nautilus
Posts: 722
Joined: Friday 02 October 2015 12:12
Target OS: Raspberry Pi / ODroid
Domoticz version: beta
Location: Finland
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by Nautilus »

Thanks for the awesome project including the pre-made scripts which really help you to get started! :) Sometimes when there is something "hectic" going on at home it might be difficult to reach anyone by phone. So I thought it might be nice if I send a message to Dtgbot and it would read it aloud at home as there are speakers all around and I already was using the iZsynth script to make Domoticz talk. This was relatively easy to do, I chose a shell script and it just takes the sent message (input variable $2, after the keyword) and passes that string to the already existing script that reads it aloud with iZsynth.

But then it came to my mind that you can send voice message to chats as well so would there be anyway for the bot to capture this kind of message and store the audio file somewhere so that the script could play it? Has anyone played with anything like that or do you have any thoughts whether it could be achievable in some "not too difficult" way? :)
User avatar
jvdz
Posts: 2189
Joined: Tuesday 30 December 2014 19:25
Target OS: Raspberry Pi / ODroid
Domoticz version: 4.107
Location: Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by jvdz »

This is indeed possible and just needs some support added for downloading files that are send to the bot.
the original message contains something like this in the received message:

Code: Select all

voice: {
duration: 1,
mime_type: "audio/ogg",
file_id: "AwADBAADWgEAAhtjXXXXKFGC7DJusDAI",
file_size: 4067
}
in stead of text message containing:

Code: Select all

text: "Test"
DTGBot would then have to perform this API call:

Code: Select all

https://api.telegram.org/bot<bot_token>/getFile?file_id=the_file_id
Which returns:

Code: Select all

{
ok: true,
result: {
file_id: "AwADBAADWgEAAhtjXXXXFGC7DJusDAI",
file_size: 4067,
file_path: "voice/111111088413725018.oga"
}
}
It would then be able to retrieve the OGA file with this API call:

Code: Select all

https://api.telegram.org/file/bot<token>/<file_path>
That is all to it and just needs to be coded now :)

Jos
New Garbage collection scripts: https://github.com/jvanderzande/GarbageCalendar
Nautilus
Posts: 722
Joined: Friday 02 October 2015 12:12
Target OS: Raspberry Pi / ODroid
Domoticz version: beta
Location: Finland
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by Nautilus »

Thanks! Need to start looking into the code a bit more carefully to see how to maybe catch the audio messages for further processing...:)

By the way, now I implemented the text based notification so that is sent like "Announcement This-is-a-test-announcement" as I noticed the script needs to strip the spaces away. Is there perhaps some more elegant way to allow the use of spaces in the announcement text and just catch this in the script so that it would not strip the spaces in this case? Also, it has happened a couple of times now that dtgbot is still running but not acting on any received messages. I've enabled full logging to hopefully get into bottom of this but do you already know what could be causing this? Restarting the service always solves it.
User avatar
jvdz
Posts: 2189
Joined: Tuesday 30 December 2014 19:25
Target OS: Raspberry Pi / ODroid
Domoticz version: 4.107
Location: Netherlands
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by jvdz »

I will wip something up probably this evening to support voice files. What I am considering is to have it perform the following command when a voice file is received:

Code: Select all

voice url-for-filedownload
So you would need to have a voice.sh or lua that will download the file with curl and then process it.

As to your question: How do you process the Announcement commands? Need to check but though all parameters are copied to the shelled process.

Jos
New Garbage collection scripts: https://github.com/jvanderzande/GarbageCalendar
Nautilus
Posts: 722
Joined: Friday 02 October 2015 12:12
Target OS: Raspberry Pi / ODroid
Domoticz version: beta
Location: Finland
Contact:

Re: dtgbot - Domoticz TeleGram BOT

Post by Nautilus »

jvdz wrote: Thursday 10 August 2017 9:32 I will wip something up probably this evening to support voice files. What I am considering is to have it perform the following command when a voice file is received:

Code: Select all

voice url-for-filedownload
So you would need to have a voice.sh or lua that will download the file with curl and then process it.

As to your question: How do you process the Announcement commands? Need to check but though all parameters are copied to the shelled process.

Jos
Great, looking forward to this! :)

I cannot access the script now, but basically what I first tried was something like

Code: Select all

Announcement This is a test announcement
and when I passed the $2 parameter to the script it was changed to "thisisatestannouncement". So I looked into dtgbot.lua and noticed the line that is parsing the input variables for the script from the message and it was something like [%w-_] i.e. stripping other than non-alphanumericals except - and _. I then changed it to [%w-_åäö] to allow the use of local characters and in the announcement.sh script I just replace - and/or _ with space so that it passes the correct string to the iZsynth script that creates the audio file. So now I would send

Code: Select all

Announcement This-is-a-test-announcement
or
Announcement This_is_a_test_announcement
and it will read it out loud correctly with pauses between the words. Was just thinking if there was a nice way to avoid it and be able to use spaces in the message sent to the bot. But this is probably something we will not be using anymore if the bot can soon pass the audio message to a script as well :D
Post Reply

Who is online

Users browsing this forum: No registered users and 0 guests