Tivo Telenet Driver

That did the trick! Much appreciated. I noticed you were able to implement a Netflix button; AFAIK Harmony doesn't support that (I wound up cobbling a Harmony sequence for that function which is quite slow) . Can other TiVo apps (like Hulu or Tubi) also have dedicated buttons?

@martinez.mp3 Have you seen this? Maybe some inspiration for new ideas .. for example accessing the program guide info. It's written for HA but I guess it's fairly adaptable at least on the Tivo protocol side.

@Tony I didn't see any other app with the telenet command but I'm trying to see if I could add some tricks I found in a site with some combination of keys, the one I like more is showing an on screen clock, im always lose track of time so will be nice to put remainder that show the time on the screen.

1 Like

@kevin that look very promising I'll take a look this weekend and learn some of the stuff they do there and see if I can duplicate it here, it will be nice to have some guide interaction.
Thanks for the share

First of all TiVo Telnet in Hubitat is fantastic. I'm having one issue with it and maybe someone has a fix. I have rules that change the channel on my Roamio at certain times. I do this by first defining a Custom Command to setCh and then create a Trigger in Rule Machine that triggers the command at the time I want. For example, I want my TiVo to change to my morning news channel before I wake up so when my TV turns on (my TiVo is in a central closet and feeds the whole house on a distribution system) it is on the right channel.

It works great. The problem is that once Hubitat "grabs" the TiVo, I can't use any other network remote (on my phone, for example) without rebooting the Hubitat hub. I use several network remte devices (phone, tablet) and as long as I close the app on any of them the port is free for a different network remote device or app to connect.

Is there any way to force TiVo Telnet to disconnect from TiVo once connected?

So, I'm no developer but I can hack together a little code and i think I figured it out. I added a "disconnect" command to the metadata:

  command "disconnect"

And then the following function:

  def disconnect() {

I was then able to create custom commands for Initialize, setCH and Disconnect and execute them in my triggered action in that order and the result is that the Telnet session released the network remote after the action is executed so I can use other network remotes. I added a few seconds delay between each command as it seems more reliable that way.

Awesome... Would you mind posting your version of the groovy? I see the OP last updated his code 6 months ago...

As I mentioned, I barely know what I am doing so proceed at your own risk, but here you go:

/********TiV0 Telnet Control


metadata {
	definition (name: "Tivo Telnet", namespace: "jorge.martinez", author: "Jorge Martinez") {
		capability "Telnet"
		capability "Initialize"
		capability "Switch"
		attribute "channel", "NUMBER"
		command "chUp"
		command "chDown"
		command "pause"
		command "myShows"
		command "liveTv"
		command "play"
		command "up"
		command "down"
		command "left"
		command "right"
		command "central"
		command "Netflix"
		command "select"
		command "standby"
		command "clear"
		command "stop"
		command "guide"
		command "setCH", ["STRING"]
		command "nextTrack"
		command "previousTrack"
		command "info"
		command "back"
		command "disconnect"
	preferences {
		section("Device Settings:") {
			input "TiVoIP", "string", title:"TiVoIP", description: "", required: true, displayDuringSetup: true
			input "TiVoMini", "bool", title:"", description: "Is this a tivo mini", required: true, displayDuringSetup: true
def one() 	{sendMsg("IRCODE NUM1")} 
def two()	{sendMsg("IRCODE NUM2")}
def three()	{sendMsg("IRCODE NUM3")}
def four()	{sendMsg("IRCODE NUM4")}
def five()	{sendMsg("IRCODE NUM5")}
def six()	{sendMsg("IRCODE NUM6")}
def seven()	{sendMsg("IRCODE NUM7")}
def eight()	{sendMsg("IRCODE NUM8")}
def nine()	{sendMsg("IRCODE NUM9")}
def zero()	{sendMsg("IRCODE NUM0")}
def info()	{sendMsg("IRCODE INFO")}
def guide()	{sendMsg("IRCODE GUIDE")}
def back()	{sendMsg("IRCODE BACK")}
def testCommand(Command){sendMsg(Command)}
def setCH (CH){
	if (settings.TiVoMini){ //if is mark as mini
	else{ //if is not a mini
		sendMsg("SETCH "+ CH)
def clear()	{sendMsg("IRCODE CLEAR")}
def standby(){sendMsg("IRCODE STANDBY")}
def select(){sendMsg("IRCODE SELECT")}
def Netflix(){sendMsg("IRCODE NETFLIX")}
def central(){sendMsg("IRCODE TIVO")}
def up (){sendMsg("IRCODE UP")}
def down (){sendMsg("IRCODE DOWN")}
def left (){sendMsg("IRCODE LEFT")}
def right (){sendMsg("IRCODE RIGHT")}
def play (){sendMsg("IRCODE PLAY")}
def liveTv(){sendMsg("IRCODE LIVETV")}
def chUp (){sendMsg("IRCODE CHANNELUP")}
def nextTrack(){chUp()}
def chDown (){sendMsg("IRCODE CHANNELDOWN")}
def previousTrack(){chDown ()}
def myShows (){sendMsg("IRCODE NOWSHOWING")}
def pause (){sendMsg("IRCODE PAUSE")}
def stop(){sendMsg("IRCODE STOP")}
def installed() {
	log.info('Tivo Telnet : installed()')
def updated() {
	log.info('Tivo Telnet: updated()')
def initialize() {
	log.info('Tivo Telnet: initialize()')
	log.info ("TiVo IP ${settings.TiVoIP}")
	telnetConnect([termChars:[13]], settings.TiVoIP, 31339, settings.username, settings.password)
def disconnect() {
def sendMsg(String msg){
	log.info("Sending telnet msg: " + msg)
	return new hubitat.device.HubAction(msg, hubitat.device.Protocol.TELNET)
private parse(String msg){
	log.debug("Parse: " + msg)
	if(msg.startsWith("CH_STATUS"))	{
		log.info "got channel update " + msg.substring(10,14)
		state.channel = msg.substring(10,14).toInteger()
		sendEvent(name: "channel", value: state.channel, isStateChange: true)

def telnetStatus(String status){
	log.warn "telnetStatus: error: " + status
	if (status != "receive error: Stream is closed"){
		log.error "Connection was dropped."
def pause(millis) {
   def passed = 0
   def now = new Date().time
   log.debug "pausing... at Now: $now"
   /* This loop is an impolite busywait. We need to be given a true sleep() method, please. */
   while ( passed < millis ) {
       passed = new Date().time - now
//   log.debug "... DONE pausing."

cool, thank you :smile:

Sorry for the super long delay, I want to update my GitHub with your code if you allow me


added below, to Find Remote Control only works with RF Remotes

command "findremote"

def findremote() {sendMsg("IRCODE FIND_REMOTE")}

Hi. I am trying to get this on my Tivo Bolt. Most seems to work, except set channel. I'd like to be able to have rule machine automatically switch for SD to the HD channel, but setCH doesn't seem to work. Anyone else have an issue?

In the log, I am receiving "Parse: CH_FAILED NO_LIVE"

I ended up doing several things to bypass setCH. First, it was easier in rule machine to add the actuator capability to the program to allow access to the finer details of the program, next I found out the code for the green, D button on the remote and simply added it to the code. It is called "ACTION_D" if anyone needs it.

I haven't updated this driver in a while (I'm using the Feb '19 version) and setCH is working on my Bolt+. For a channel change the logs show:

2021-02-05 08:30:44.098 am info got channel update 0503
2021-02-05 08:30:44.095 am debugParse: CH_STATUS 0503 LOCAL
2021-02-05 08:30:44.032 am infogot channel update 0503
2021-02-05 08:30:44.029 am debugParse: CH_STATUS 0503 REMOTE
2021-02-05 08:30:43.983 am infoSending telnet msg: SETCH 503

Would you be able to post the driver detail you are using successfully? Not sure what version driver I have, but I got it from inside the thread here.

Give me a sec and I'll try the Sept 2019 version referenced in the first post...

I just updated to the Sept 2019 version; setCH is working with that version as well. Github shows this was last updated Sept. 16 2019.

Okay, thank you for checking must be something weird with my tivo Bolt. Let me know if you would like to have any of my device edits (adds). Thanks - Brock

1 Like