python-plexapi icon indicating copy to clipboard operation
python-plexapi copied to clipboard

AlertListener leaks socket

Open glensc opened this issue 2 years ago • 4 comments

Describe the issue

A socket is leaked when code is run in a loop and the server restarts.

Steps to reproduce

  1. start Plex Media Server
  2. start the snippet
  3. stop Plex Media Server
  4. inspect script output

Code snippets

#!/usr/bin/env python3
from plexapi.server import PlexServer

from plex_trakt_sync.factory import factory


def listener(plex: PlexServer, interval=5):
    def event_handler(data):
        print(data)

    from time import sleep
    import tracemalloc

    tracemalloc.start()
    while True:
        notifier = plex.startAlertListener(callback=event_handler)
        while notifier.is_alive():
            sleep(interval)

        sleep(interval)


listener(plex=PlexServer(...))

Click to see example output
➔ ./test_socket_leak.py
INFO: Starting AlertListener: ws://localhost:32400/:/websockets/notifications?X-Plex-Token=<hidden>
lib/python3.9/site-packages/websocket/_http.py:174: ResourceWarning: unclosed <socket.socket fd=10, family=AddressFamily.AF_INET6, type=SocketKind.SOCK_STREAM, proto=6, laddr=('::1', 62432, 0, 0)>
  sock = socket.socket(family, socktype, proto)
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
ERROR: AlertListener Error: Connection to remote host was lost.
INFO: Starting AlertListener: ws://localhost:32400/:/websockets/notifications?X-Plex-Token=<hidden>
lib/python3.9/site-packages/websocket/_http.py:174: ResourceWarning: unclosed <socket.socket fd=12, family=AddressFamily.AF_INET6, type=SocketKind.SOCK_STREAM, proto=6, laddr=('::1', 62437, 0, 0)>
  sock = socket.socket(family, socktype, proto)
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
ERROR: AlertListener Error: [Errno 61] Connection refused
INFO: Starting AlertListener: ws://localhost:32400/:/websockets/notifications?X-Plex-Token=<hidden>
lib/python3.9/site-packages/websocket/_http.py:174: ResourceWarning: unclosed <socket.socket fd=12, family=AddressFamily.AF_INET6, type=SocketKind.SOCK_STREAM, proto=6, laddr=('::1', 62446, 0, 0)>
  sock = socket.socket(family, socktype, proto)
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
ERROR: AlertListener Error: [Errno 61] Connection refused
INFO: Starting AlertListener: ws://localhost:32400/:/websockets/notifications?X-Plex-Token=<hidden>
lib/python3.9/site-packages/websocket/_http.py:174: ResourceWarning: unclosed <socket.socket fd=12, family=AddressFamily.AF_INET6, type=SocketKind.SOCK_STREAM, proto=6, laddr=('::1', 62454, 0, 0)>
  sock = socket.socket(family, socktype, proto)
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
ERROR: AlertListener Error: [Errno 61] Connection refused
INFO: Starting AlertListener: ws://localhost:32400/:/websockets/notifications?X-Plex-Token=<hidden>
lib/python3.9/site-packages/websocket/_http.py:174: ResourceWarning: unclosed <socket.socket fd=12, family=AddressFamily.AF_INET6, type=SocketKind.SOCK_STREAM, proto=6, laddr=('::1', 62462, 0, 0)>
  sock = socket.socket(family, socktype, proto)
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
ERROR: AlertListener Error: [Errno 61] Connection refused
INFO: Starting AlertListener: ws://localhost:32400/:/websockets/notifications?X-Plex-Token=<hidden>
lib/python3.9/site-packages/websocket/_http.py:174: ResourceWarning: unclosed <socket.socket fd=12, family=AddressFamily.AF_INET6, type=SocketKind.SOCK_STREAM, proto=6, laddr=('::1', 62464, 0, 0)>
  sock = socket.socket(family, socktype, proto)
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
ERROR: AlertListener Error: [Errno 61] Connection refused
^C


Traceback (most recent call last):
  File "test_socket_leak.py", line 23, in <module>
    listener(plex=factory.plex_api().plex)
  File "test_socket_leak.py", line 20, in listener
    sleep(interval)
KeyboardInterrupt

sys:1: ResourceWarning: unclosed <socket.socket fd=13, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 62438)>
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
sys:1: ResourceWarning: unclosed <socket.socket fd=14, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 62447)>
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
sys:1: ResourceWarning: unclosed <socket.socket fd=15, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 62455)>
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
sys:1: ResourceWarning: unclosed <socket.socket fd=16, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 62463)>
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)
sys:1: ResourceWarning: unclosed <socket.socket fd=17, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=6, laddr=('127.0.0.1', 62465)>
Object allocated at (most recent call last):
  File "lib/python3.9/site-packages/websocket/_http.py", lineno 174
    sock = socket.socket(family, socktype, proto)

Environment (please complete the following information):

  • OS: Irrelevant
  • Plex version: Irrelevant
  • Python Version: Irrelevant
  • PlexAPI version: 4.7.1

glensc avatar Sep 26 '21 07:09 glensc

This also makes it hard to test for server restarts, since we don't even get an Exception thrown (I found this while searching for a way to detect restarts...)

rcarmo avatar Jul 21 '22 12:07 rcarmo

@rcarmo I detect restarts with sending fake Error event:

  • https://github.com/Taxel/PlexTraktSync/blob/5019171a7f8292a1c36f886ea4556e0616a203dd/plextraktsync/listener.py#L91

glensc avatar Jul 21 '22 14:07 glensc

Well, I just submitted #985, which works for me and is much cleaner.

rcarmo avatar Jul 21 '22 15:07 rcarmo

Ok, for me this was sufficient:

  • https://github.com/pkkid/python-plexapi/pull/850

altho, I never updated my code to use it :)

glensc avatar Jul 21 '22 17:07 glensc