torrents: clean up & optimize magnets further

Removes the specialized template ES magnet creator, since create_magnet()
can use both Torrents and ES objects. Search results will get the
properly escaped magnets, now.
Slightly optimizes the tracker adding and string joins.
RIP base32, wonder how many bad clients will break with sha1.
This commit is contained in:
TheAMM 2018-07-21 22:01:19 +03:00
parent ef7ff1b9ce
commit bf090c0fab
4 changed files with 20 additions and 24 deletions

View File

@ -1,15 +1,13 @@
import os.path
import re
from base64 import b32encode
from datetime import datetime
from email.utils import formatdate
from urllib.parse import urlencode
import flask
from werkzeug.urls import url_encode
from nyaa.backend import get_category_id_map
from nyaa.torrents import get_default_trackers
from nyaa.torrents import create_magnet
app = flask.current_app
bp = flask.Blueprint('template-utils', __name__)
@ -20,20 +18,9 @@ _static_cache = {} # For static_cachebuster
# For processing ES links
@bp.app_context_processor
def create_magnet_from_es_info():
def _create_magnet_from_es_info(display_name, info_hash, max_trackers=5, trackers=None):
if trackers is None:
trackers = get_default_trackers()
magnet_parts = [
('dn', display_name)
]
for tracker in trackers[:max_trackers]:
magnet_parts.append(('tr', tracker))
b32_info_hash = b32encode(bytes.fromhex(info_hash)).decode('utf-8')
return 'magnet:?xt=urn:btih:' + b32_info_hash + '&' + urlencode(magnet_parts)
return dict(create_magnet_from_es_info=_create_magnet_from_es_info)
def create_magnet_from_es_torrent():
# Since ES entries look like ducks, we can use the create_magnet as-is
return dict(create_magnet_from_es_torrent=create_magnet)
# ######################### TEMPLATE GLOBALS #########################

View File

@ -12,7 +12,7 @@
{% if torrent.has_torrent and not magnet_links %}
<link>{{ url_for('torrents.download', torrent_id=torrent.meta.id, _external=True) }}</link>
{% else %}
<link>{{ create_magnet_from_es_info(torrent.display_name, torrent.info_hash) }}</link>
<link>{{ create_magnet_from_es_torrent(torrent) }}</link>
{% endif %}
<guid isPermaLink="true">{{ url_for('torrents.view', torrent_id=torrent.meta.id, _external=True) }}</guid>
<pubDate>{{ torrent.created_time|rfc822_es }}</pubDate>

View File

@ -86,7 +86,7 @@
<td class="text-center" style="white-space: nowrap;">
{% if torrent.has_torrent %}<a href="{{ url_for('torrents.download', torrent_id=torrent_id) }}"><i class="fa fa-fw fa-download"></i></a>{% endif %}
{% if use_elastic %}
<a href="{{ create_magnet_from_es_info(torrent.display_name, torrent.info_hash) }}"><i class="fa fa-fw fa-magnet"></i></a>
<a href="{{ create_magnet_from_es_torrent(torrent) }}"><i class="fa fa-fw fa-magnet"></i></a>
{% else %}
<a href="{{ torrent.magnet_uri }}"><i class="fa fa-fw fa-magnet"></i></a>
{% endif %}

View File

@ -1,4 +1,3 @@
import base64
import os
from urllib.parse import quote, urlencode
@ -84,11 +83,21 @@ def create_magnet(torrent, max_trackers=5, trackers=None):
magnet_parts = [
('dn', torrent.display_name)
]
for tracker in trackers[:max_trackers]:
magnet_parts.append(('tr', tracker))
magnet_parts.extend(
('tr', tracker_url)
for tracker_url in trackers[:max_trackers]
)
b32_info_hash = base64.b32encode(torrent.info_hash).decode('utf-8')
return 'magnet:?xt=urn:btih:' + b32_info_hash + '&' + urlencode(magnet_parts, quote_via=quote)
# Since we accept both models.Torrents and ES objects,
# we need to make sure the info_hash is a hex string
info_hash = torrent.info_hash
if isinstance(info_hash, (bytes, bytearray)):
info_hash = info_hash.hex()
return ''.join([
'magnet:?xt=urn:btih:', info_hash,
'&', urlencode(magnet_parts, quote_via=quote)
])
def create_default_metadata_base(torrent, trackers=None, webseeds=None):