diff options
-rwxr-xr-x | app.py | 29 | ||||
-rw-r--r-- | db.py | 12 |
2 files changed, 39 insertions, 2 deletions
@@ -1,6 +1,6 @@ #!/usr/bin/env python2 -import os, mimetypes, json, cgi, recode, time, urllib, events, db, itertools +import os, mimetypes, json, cgi, recode, time, urllib, events, db, itertools, re from config import config from directory import Directory, File @@ -136,6 +136,32 @@ class Application(object): start_response('200 OK', [('Content-Type', 'text/plain')]) return [] + re_search = re.compile(r'(")?((?(1)[^"]|[^ ])+)(?(1)")') + + def json_search(self, environ, start_response, path): + args = cgi.FieldStorage(environ = environ) + query = args.getvalue('query') + r = self.re_search.findall(query) + d = {} + l = [] + for _, v in r: + if ':' in v: + k, v = v.split(':', 1) + d[k] = v + else: + l.append(v) + + results = [] + try: + session = db.Session() + r = db.Track.search(session, *l, **d) + results = [File(x.get_path(), metadata = x.get_metadata()).json() for x in r] + finally: + session.close() + + start_response('200 OK', []) + return json.dumps(results) + handlers = { 'files': files, 'static': static, @@ -143,6 +169,7 @@ class Application(object): 'list': json_list, 'recode': json_recode, 'play': json_play, + 'search': json_search, 'events': events.EventSubscriber, } @@ -100,7 +100,7 @@ class Track(Base): album_id = Column(Integer, ForeignKey('albums.id')) directory = relationship(Directory, backref = backref('tracks', order_by = filename)) - artist = relationship(Artist, backref = backref('artists')) + artist = relationship(Artist, backref = backref('tracks')) album = relationship(Album, backref = backref('tracks')) def __init__(self, name, num, filename, file_index, directory_id, artist_id, album_id): @@ -129,6 +129,16 @@ class Track(Base): directory, filename = os.path.split(path) return session.query(Track).filter(and_(Track.filename == filename, Directory.path == directory, Track.file_index == track)).one() + @staticmethod + def search(session, *args, **kwargs): + r = session.query(Track) + for f, n in ((Artist, 'artist'), (Track, 'title'), (Album, 'album')): + if n in kwargs: + if f != Track: + r = r.join(f) + r = r.filter(f.name.ilike('%{0}%'.format(kwargs[n]))) + return r.all() + def get_path(self): return os.path.join(self.directory.path, self.filename) |