diff --git a/larigira/audioform_http.py b/larigira/audioform_http.py new file mode 100644 index 0000000..6fa175f --- /dev/null +++ b/larigira/audioform_http.py @@ -0,0 +1,25 @@ +from flask_wtf import Form +from wtforms import StringField, validators, SubmitField + + +class AudioForm(Form): + nick = StringField('Audio nick', validators=[validators.required()], + description='A simple name to recognize this audio') + urls = StringField('URLs', + validators=[validators.required()], + description='URL of the file to download') + submit = SubmitField('Submit') + + def populate_from_audiospec(self, audiospec): + if 'nick' in audiospec: + self.nick.data = audiospec['nick'] + if 'urls' in audiospec: + self.urls.data = ';'.join(audiospec['urls']) + + +def audio_receive(form): + return { + 'kind': 'http', + 'nick': form.nick.data, + 'urls': form.urls.data.split(';'), + } diff --git a/larigira/audiogen_http.py b/larigira/audiogen_http.py new file mode 100644 index 0000000..b3efff6 --- /dev/null +++ b/larigira/audiogen_http.py @@ -0,0 +1,48 @@ +import os +import logging +import posixpath +from tempfile import mkstemp +import urllib.request +from urllib.parse import urlparse + +log = logging.getLogger(__name__) + + +def put(url, destdir=None, copy=False): + if url.split(':')[0] not in ('http', 'https'): + log.warning('Not a valid URL: %s', url) + return None + ext = url.split('.')[-1] + if ext.lower() not in ('mp3', 'ogg', 'oga', 'wma', 'm4a'): + log.warning('Invalid format (%s) for "%s"', ext, url) + return None + if not copy: + return url + fname = posixpath.basename(urlparse(url).path) + # sanitize + fname = "".join(c for c in fname + if c.isalnum() or c in list('._-')).rstrip() + tmp = mkstemp(suffix='.' + ext, prefix='http-%s-' % fname, dir=destdir) + os.close(tmp[0]) + log.info("downloading %s -> %s", url, tmp[1]) + fname, headers = urllib.request.urlretrieve(url, tmp[1]) + return 'file://%s' % os.path.realpath(tmp[1]) + + +def generate(spec): + ''' + resolves audiospec-static + + Recognized argument is "paths" (list of static paths) + ''' + if 'urls' not in spec: + raise ValueError("Malformed audiospec: missing 'paths'") + + for url in spec['urls']: + ret = put(url, copy=True) + if ret is None: + continue + yield ret + + +generate.description = 'Fetch audio from an URL' diff --git a/setup.py b/setup.py index 009a50b..644117d 100644 --- a/setup.py +++ b/setup.py @@ -63,6 +63,7 @@ setup(name='larigira', 'larigira.audiogenerators': [ 'mpd = larigira.audiogen_mpdrandom:generate_by_artist', 'static = larigira.audiogen_static:generate', + 'http = larigira.audiogen_http:generate', 'randomdir = larigira.audiogen_randomdir:generate', 'mostrecent = larigira.audiogen_mostrecent:generate', 'script = larigira.audiogen_script:generate', @@ -81,12 +82,14 @@ setup(name='larigira', ], 'larigira.audioform_create': [ 'static = larigira.audioform_static:StaticAudioForm', + 'http = larigira.audioform_http:AudioForm', 'script = larigira.audioform_script:ScriptAudioForm', 'randomdir = larigira.audioform_randomdir:Form', 'mostrecent = larigira.audioform_mostrecent:AudioForm', ], 'larigira.audioform_receive': [ 'static = larigira.audioform_static:staticaudio_receive', + 'http = larigira.audioform_http:audio_receive', 'script = larigira.audioform_script:scriptaudio_receive', 'randomdir = larigira.audioform_randomdir:receive', 'mostrecent = larigira.audioform_mostrecent:audio_receive',