Welcome to our forums! Please take a few moments to read through our Community Guidelines (also conveniently linked in the header at the top of each page). There, you'll find guidelines on conduct, tips on getting the help you may be searching for, and more!

Fix for SNI SSL?

AeonLucidAeonLucid Members, Plex Pass Posts: 4 Plex Pass

Hi,

Plex runs on Python 2.7.4 and SNI SSL support got added in Python 2.7.9.
I've tried various things to get SNI working but everything I try, fails.

Last thing I tried:
I created a file MyPlugin.bundle/Contents/Libraries/Shared/requirements.txt:

pyOpenSSL==16.0.0
cryptography==1.3.4
idna==2.0
requests==2.12.3

Which should be right according to urllib3 in requests v2.12.3.

And then ran the following command in MyPlugin.bundle/Contents/Libraries/Shared/:
pip install -t . -r requirements.txt

All dependencies should be correctly installed.
PyOpenSSL is injected by the requests library, so I don't have to do that.

I created another file MyPlugin.bundle/Contents/Code/__init__.py:

import requests


def Start():
    # Just to test SSL connection.. Don't care about sending invalid data yet.
    r = requests.post("https://staging.kitsu.io/api/oauth/token", data=dict(grant_type="password"))
    Log.Info("[%s] Authentication status code %d" % r.status_code)

Which then produces the following error:

2016-12-08 03:34:25,601 (376c) :  CRITICAL (core:574) - Exception when calling function 'Start' (most recent call last):
  File "C:\Program Files (x86)\Plex\Plex Media Server\Resources\Plug-ins-1bef33a\Framework.bundle\Contents\Resources\Versions\2\Python\Framework\code\sandbox.py", line 294, in call_named_function
    result = f(*args, **kwargs)
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Code\__init__.py", line 7, in Start
    r = requests.post("https://staging.kitsu.io/api/oauth/token", data=dict(grant_type="password"))
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Libraries\Shared\requests\api.py", line 110, in post
    return request('post', url, data=data, json=json, **kwargs)
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Libraries\Shared\requests\api.py", line 56, in request
    return session.request(method=method, url=url, **kwargs)
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Libraries\Shared\requests\sessions.py", line 488, in request
    resp = self.send(prep, **send_kwargs)
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Libraries\Shared\requests\sessions.py", line 609, in send
    r = adapter.send(request, **kwargs)
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Libraries\Shared\requests\adapters.py", line 497, in send
    raise SSLError(e, request=request)
SSLError: [Errno 1] _ssl.c:504: error:14077438:SSL routines:SSL23_GET_SERVER_HELLO:tlsv1 alert internal error

I think that the injection is failing but I don't know why.
When I remove the try & catch of the injection, I receive the following output:

2016-12-08 03:41:21,450 (1cdc) :  CRITICAL (core:574) - Exception starting plug-in (most recent call last):
  File "C:\Program Files (x86)\Plex\Plex Media Server\Resources\Plug-ins-1bef33a\Framework.bundle\Contents\Resources\Versions\2\Python\Framework\core.py", line 608, in start
    self.sandbox.execute(self.init_code)
  File "C:\Program Files (x86)\Plex\Plex Media Server\Resources\Plug-ins-1bef33a\Framework.bundle\Contents\Resources\Versions\2\Python\Framework\code\sandbox.py", line 256, in execute
    exec(code) in self.environment
  File "C:\Users\Mike\AppData\Local\Plex Media Server\Plug-ins\KitsuScrobble.bundle\Contents\Code\__init__.py", line 2, in <module>
    import requests
  File "C:\Program Files (x86)\Plex\Plex Media Server\Resources\Plug-ins-1bef33a\Framework.bundle\Contents\Resources\Versions\2\Python\Framework\code\sandbox.py", line 345, in __import__
    raise e
ImportError: DLL load failed: The specified module could not be found.

Which means that it must be throwing something but I can not see what.

If you have any idea how to fix this or another way to connect to SNI SSL enabled sites, please let me know.

Tagged:

Answers

  • AeonLucidAeonLucid Members, Plex Pass Posts: 4 Plex Pass
    edited December 2016

    I couldn't figure out how to edit my post.
    Here is the GitHub link to the bundle with the code and libraries: https://github.com/AeonLucid/KitsuScrobble.bundle

    Edit: Figured out how to edit right after I posted this..

  • pannipanni Members, Plex Pass Posts: 849 Plex Pass
    edited December 2016

    Nah, you've updated your local Python installation with the requirements (you've run your local pip, there is no pip in the PMS python). Your plugin still gets executed in the crippled/sandboxed PMS Python environment and requests most likely uses the SSL packaged with that (and fails because of the so/dll version of /usr/lib/plexmediaserver/libssl.so.1.0.0?).

    Honestly, if you have access to a root server with an NGINX running, create a reverse proxy which listens on an unencrypted channel and have it forward the requests to the API via HTTPS. Will save you a lot of unfruitful effort when dealing with shared libraries in PMS (ssl or sql).

  • pannipanni Members, Plex Pass Posts: 849 Plex Pass
    edited December 2016

    Another thing you could perhaps try would be a pure python TLS client implementation like this for example.

    I'd love an updated python in PMS, although I don't think it's too easy for them, because they'd have to repackage most of the shared dependencies. (The internal python version being nearly 4 years old, the core PMS python core code is from 2012).

  • AeonLucidAeonLucid Members, Plex Pass Posts: 4 Plex Pass

    @panni said:
    Nah, you've updated your local Python installation with the requirements (you've run your local pip, there is no pip in the PMS python). Your plugin still gets executed in the crippled/sandboxed PMS Python environment and requests most likely uses the SSL packaged with that (and fails because of the so/dll version of /usr/lib/plexmediaserver/libssl.so.1.0.0?).

    Honestly, if you have access to a root server with an NGINX running, create a reverse proxy which listens on an unencrypted channel and have it forward the requests to the API via HTTPS. Will save you a lot of unfruitful effort when dealing with shared libraries in PMS (ssl or sql).

    I added the -t . flag to pip install which should install it to the current directory. (/Libraries/Shared/)
    Why would that update my local python installation? It just downloads all required libraries and puts them into that directory.

  • pannipanni Members, Plex Pass Posts: 849 Plex Pass

    @AeonLucid any progress here?

    @dane22 could you perhaps raise this issue up? It will continue to pop up as more services implement SNI.

  • dane22dane22 Members, Plex Pass, Plex Ninja Posts: 9,866 Plex Ninja
    edited February 6

    @panni :
    Python has been updated in 1.3 to a newer version

    /T

  • pannipanni Members, Plex Pass Posts: 849 Plex Pass

    Oh, OK. Then @AeonLucid and @Dingmatt is this issue resolved for you?

  • DingmattDingmatt Members, Plex Pass Posts: 79 Plex Pass

    @panni @dane22 Thats good to know though I'm afraid I can't test atm as I'm restricted to 1.2.7 until the Plex server metadata bug is fixed.

Sign In or Register to comment.