mirror of
https://github.com/clinton-hall/nzbToMedia.git
synced 2025-08-20 13:23:18 -07:00
Update beets to 1.4.7
Also updates: - colorama-0.4.1 - jellyfish-0.6.1 - munkres-1.0.12 - musicbrainzngs-0.6 - mutagen-1.41.1 - pyyaml-3.13 - six-1.12.0 - unidecode-1.0.23
This commit is contained in:
parent
05b0fb498f
commit
e854005ae1
193 changed files with 15896 additions and 6384 deletions
|
@ -6,22 +6,51 @@
|
|||
host: localhost
|
||||
port: 8096
|
||||
username: user
|
||||
apikey: apikey
|
||||
password: password
|
||||
"""
|
||||
from __future__ import division, absolute_import, print_function
|
||||
|
||||
from beets import config
|
||||
from beets.plugins import BeetsPlugin
|
||||
from urllib import urlencode
|
||||
from urlparse import urljoin, parse_qs, urlsplit, urlunsplit
|
||||
import hashlib
|
||||
import requests
|
||||
|
||||
from six.moves.urllib.parse import urlencode
|
||||
from six.moves.urllib.parse import urljoin, parse_qs, urlsplit, urlunsplit
|
||||
|
||||
from beets import config
|
||||
from beets.plugins import BeetsPlugin
|
||||
|
||||
|
||||
def api_url(host, port, endpoint):
|
||||
"""Returns a joined url.
|
||||
|
||||
Takes host, port and endpoint and generates a valid emby API url.
|
||||
|
||||
:param host: Hostname of the emby server
|
||||
:param port: Portnumber of the emby server
|
||||
:param endpoint: API endpoint
|
||||
:type host: str
|
||||
:type port: int
|
||||
:type endpoint: str
|
||||
:returns: Full API url
|
||||
:rtype: str
|
||||
"""
|
||||
joined = urljoin('http://{0}:{1}'.format(host, port), endpoint)
|
||||
# check if http or https is defined as host and create hostname
|
||||
hostname_list = [host]
|
||||
if host.startswith('http://') or host.startswith('https://'):
|
||||
hostname = ''.join(hostname_list)
|
||||
else:
|
||||
hostname_list.insert(0, 'http://')
|
||||
hostname = ''.join(hostname_list)
|
||||
|
||||
joined = urljoin(
|
||||
'{hostname}:{port}'.format(
|
||||
hostname=hostname,
|
||||
port=port
|
||||
),
|
||||
endpoint
|
||||
)
|
||||
|
||||
scheme, netloc, path, query_string, fragment = urlsplit(joined)
|
||||
query_params = parse_qs(query_string)
|
||||
|
||||
|
@ -33,34 +62,62 @@ def api_url(host, port, endpoint):
|
|||
|
||||
def password_data(username, password):
|
||||
"""Returns a dict with username and its encoded password.
|
||||
|
||||
:param username: Emby username
|
||||
:param password: Emby password
|
||||
:type username: str
|
||||
:type password: str
|
||||
:returns: Dictionary with username and encoded password
|
||||
:rtype: dict
|
||||
"""
|
||||
return {
|
||||
'username': username,
|
||||
'password': hashlib.sha1(password).hexdigest(),
|
||||
'passwordMd5': hashlib.md5(password).hexdigest()
|
||||
'password': hashlib.sha1(password.encode('utf-8')).hexdigest(),
|
||||
'passwordMd5': hashlib.md5(password.encode('utf-8')).hexdigest()
|
||||
}
|
||||
|
||||
|
||||
def create_headers(user_id, token=None):
|
||||
"""Return header dict that is needed to talk to the Emby API.
|
||||
|
||||
:param user_id: Emby user ID
|
||||
:param token: Authentication token for Emby
|
||||
:type user_id: str
|
||||
:type token: str
|
||||
:returns: Headers for requests
|
||||
:rtype: dict
|
||||
"""
|
||||
headers = {
|
||||
'Authorization': 'MediaBrowser',
|
||||
'UserId': user_id,
|
||||
'Client': 'other',
|
||||
'Device': 'empy',
|
||||
'DeviceId': 'beets',
|
||||
'Version': '0.0.0'
|
||||
}
|
||||
headers = {}
|
||||
|
||||
authorization = (
|
||||
'MediaBrowser UserId="{user_id}", '
|
||||
'Client="other", '
|
||||
'Device="beets", '
|
||||
'DeviceId="beets", '
|
||||
'Version="0.0.0"'
|
||||
).format(user_id=user_id)
|
||||
|
||||
headers['x-emby-authorization'] = authorization
|
||||
|
||||
if token:
|
||||
headers['X-MediaBrowser-Token'] = token
|
||||
headers['x-mediabrowser-token'] = token
|
||||
|
||||
return headers
|
||||
|
||||
|
||||
def get_token(host, port, headers, auth_data):
|
||||
"""Return token for a user.
|
||||
|
||||
:param host: Emby host
|
||||
:param port: Emby port
|
||||
:param headers: Headers for requests
|
||||
:param auth_data: Username and encoded password for authentication
|
||||
:type host: str
|
||||
:type port: int
|
||||
:type headers: dict
|
||||
:type auth_data: dict
|
||||
:returns: Access Token
|
||||
:rtype: str
|
||||
"""
|
||||
url = api_url(host, port, '/Users/AuthenticateByName')
|
||||
r = requests.post(url, headers=headers, data=auth_data)
|
||||
|
@ -70,6 +127,15 @@ def get_token(host, port, headers, auth_data):
|
|||
|
||||
def get_user(host, port, username):
|
||||
"""Return user dict from server or None if there is no user.
|
||||
|
||||
:param host: Emby host
|
||||
:param port: Emby port
|
||||
:username: Username
|
||||
:type host: str
|
||||
:type port: int
|
||||
:type username: str
|
||||
:returns: Matched Users
|
||||
:rtype: list
|
||||
"""
|
||||
url = api_url(host, port, '/Users/Public')
|
||||
r = requests.get(url)
|
||||
|
@ -84,8 +150,10 @@ class EmbyUpdate(BeetsPlugin):
|
|||
|
||||
# Adding defaults.
|
||||
config['emby'].add({
|
||||
u'host': u'localhost',
|
||||
u'port': 8096
|
||||
u'host': u'http://localhost',
|
||||
u'port': 8096,
|
||||
u'apikey': None,
|
||||
u'password': None,
|
||||
})
|
||||
|
||||
self.register_listener('database_change', self.listen_for_db_change)
|
||||
|
@ -104,6 +172,12 @@ class EmbyUpdate(BeetsPlugin):
|
|||
port = config['emby']['port'].get()
|
||||
username = config['emby']['username'].get()
|
||||
password = config['emby']['password'].get()
|
||||
token = config['emby']['apikey'].get()
|
||||
|
||||
# Check if at least a apikey or password is given.
|
||||
if not any([password, token]):
|
||||
self._log.warning(u'Provide at least Emby password or apikey.')
|
||||
return
|
||||
|
||||
# Get user information from the Emby API.
|
||||
user = get_user(host, port, username)
|
||||
|
@ -111,17 +185,18 @@ class EmbyUpdate(BeetsPlugin):
|
|||
self._log.warning(u'User {0} could not be found.'.format(username))
|
||||
return
|
||||
|
||||
# Create Authentication data and headers.
|
||||
auth_data = password_data(username, password)
|
||||
headers = create_headers(user[0]['Id'])
|
||||
|
||||
# Get authentication token.
|
||||
token = get_token(host, port, headers, auth_data)
|
||||
if not token:
|
||||
self._log.warning(
|
||||
u'Could not get token for user {0}', username
|
||||
)
|
||||
return
|
||||
# Create Authentication data and headers.
|
||||
auth_data = password_data(username, password)
|
||||
headers = create_headers(user[0]['Id'])
|
||||
|
||||
# Get authentication token.
|
||||
token = get_token(host, port, headers, auth_data)
|
||||
if not token:
|
||||
self._log.warning(
|
||||
u'Could not get token for user {0}', username
|
||||
)
|
||||
return
|
||||
|
||||
# Recreate headers with a token.
|
||||
headers = create_headers(user[0]['Id'], token=token)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue