# Authentication changes for tivo



## jbernardis (Oct 22, 2003)

It's been a while since I last wrote a program to talk to my tivo, so I'm not sure when this issue really started, but all of a sudden, the techniques I used to use to retrieve a tivo container now return an SSL Certificate error:


> urllib2.URLError: <urlopen error [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed (_ssl.c:661)>


Here is the python code in question:

```
url = "https://" + addr + "/TiVoConnect?Command=QueryContainer&Container=%2FNowPlaying&AnchorOffset=" + str(offset) + "&Recurse=Yes";
        auth_handler.add_password('TiVo DVR', addr, 'tivo', MAK)
        f = tivo_opener.open(url)
```
Apparently the authorization technique has changed, but I'm at a loss as to what needs to be modified. Any help would be appreciated.

Thanks


----------



## wmcbrine (Aug 2, 2003)

Well, pyTivo is still working, so maybe you can figure out what it does differently than you were doing? I'm not aware of any changes in this area.


----------



## jbernardis (Oct 22, 2003)

Looking at pyTivo was the first thing I did, but I haven't located the authentication logic yet. Still combing through it.


----------



## jbernardis (Oct 22, 2003)

Still no luck. Based on togo.py, I changed my code to the following:


```
def null_cookie(name, value):
    return cookielib.Cookie(0, name, value, None, False, '', False,
        False, '', False, False, None, False, None, None, None)

auth_handler = urllib2.HTTPPasswordMgrWithDefaultRealm()
cj = cookielib.CookieJar()
cj.set_cookie(null_cookie('sid', 'ADEADDA7EDEBAC1E'))
tivo_opener = urllib2.build_opener(urllib2.HTTPCookieProcessor(cj),
                                   urllib2.HTTPBasicAuthHandler(auth_handler),
                                   urllib2.HTTPDigestAuthHandler(auth_handler))

NPL = []
for (tsn, name, addr) in zb:
    print time.asctime(), "Retrieving NPL for \"%s\"" % name
    print time.asctime(), "Adding TSN \"%s\" to header" % tsn
    tivo_opener.addheaders.append(('TSN', tsn))
    offset = 0
    ipaddr = addr + ":443"
    moreRecordings = True
    recordings = []
    while moreRecordings:
        url = "https://" + ipaddr + "/TiVoConnect?Command=QueryContainer&Container=/NowPlaying&AnchorOffset=" + str(offset) + "&Recurse=Yes"
        print time.asctime(), "Attempting to open URL \"%s\"" % url
        auth_handler.add_password('TiVo DVR', ipaddr, 'tivo', MAK)
        f = tivo_opener.open(url)
```
I've tried it both with and without the 443 port number, but I always get the same error. I'm thinking I need to change a setting on the Tivo itself, or perhaps something in the windows environment.


----------



## jbernardis (Oct 22, 2003)

Now I am really confused. I tried copying the files over to an Ubuntu machine (also running python 2.7.13) and i had the same behavior there - Certificate error. So then I tried copying it to my netgear readyNAS server, running an older Linux and python 2.5, and the code worked fine - no errors at all and the NPL was properly retrieved. I then reverted to the original code and that worked in this environment also. 

To me, these tests rule out the Windows environment, but they also rule out the Tivo configuration as well. The only thing I have to go on is the difference in python versions. More testing to be done.


----------



## jbernardis (Oct 22, 2003)

Well I finally solved it. Turns out that with version 2.7.9 (IIRC) python started validating certificates a bit more than in the past. The "work-around" is to change the above code to the following:

```
ctx = ssl.create_default_context()
ctx.check_hostname = False
ctx.verify_mode = ssl.CERT_NONE

tivo_opener = urllib2.build_opener(urllib2.HTTPSHandler(context=ctx),
                                   urllib2.HTTPCookieProcessor(cj),
                                   urllib2.HTTPBasicAuthHandler(auth_handler),
                                   urllib2.HTTPDigestAuthHandler(auth_handler))
```
From what I've read, this handler needs to be the first passed to build_opener


----------



## wmcbrine (Aug 2, 2003)

Ah yes, I remember now.  I didn't make the connection before, because that mod in pyTivo happened back in 2014 --


```
commit 6b352c204a2c0bda49bbd9e2edbac1f3789a30bc
Author: William McBrine <[email protected]>
Date:   Tue Dec 23 16:36:55 2014 -0500

    Restore pre-Python-2.7.9 behavior. Neither individual TiVos' nor
    (apparently) the mind server's SSL certificates validate. Reported by
    "dcrowell77".

diff --git a/pyTivo.py b/pyTivo.py
index 47799a1..aec9232 100755
--- a/pyTivo.py
+++ b/pyTivo.py
@@ -10,6 +10,12 @@ if sys.version_info[0] != 2 or sys.version_info[1] < 5:
     print ('ERROR: pyTivo requires Python >= 2.5, < 3.0.\n')
     sys.exit(1)
+try:
+    import ssl
+    ssl._create_default_https_context = ssl._create_unverified_context
+except:
+    pass
+
 import beacon
 import config
 import httpserver
```


----------

