From 217ad9cc5dfb7167ef48b660a548e9449c3c7009 Mon Sep 17 00:00:00 2001
From: ale <ale@incal.net>
Date: Sat, 15 Oct 2011 11:41:18 +0100
Subject: [PATCH] cache autocompletion results

---
 server/djrandom/frontend/frontend.py | 11 +++++++++--
 server/djrandom/frontend/views.py    | 17 ++++++++++++-----
 2 files changed, 21 insertions(+), 7 deletions(-)

diff --git a/server/djrandom/frontend/frontend.py b/server/djrandom/frontend/frontend.py
index d5bcb7c..1e1079c 100644
--- a/server/djrandom/frontend/frontend.py
+++ b/server/djrandom/frontend/frontend.py
@@ -13,18 +13,23 @@ from djrandom.frontend.mailer import Mailer
 from djrandom.frontend.search import Searcher
 from djrandom.model.markov import MarkovModel
 from djrandom.model.external import AlbumImageRetriever
+from werkzeug.contrib.cache import SimpleCache, MemcachedCache
 from gevent.wsgi import WSGIServer
 
 log = logging.getLogger(__name__)
 
 
 def run_frontend(port, solr_url, db_url, lastfm_api_key, album_art_dir,
-                 email_sender, markov_data_file, do_profile):
+                 email_sender, markov_data_file, do_profile, memcached_url):
     init_db(db_url, solr_url)
 
     svcs['searcher'] = Searcher(solr_url)
     svcs['album_images'] = AlbumImageRetriever(lastfm_api_key, album_art_dir)
     svcs['mailer'] = Mailer(email_sender)
+    if memcached_url:
+        svcs['cache'] = MemcachedCache([memcached_url])
+    else:
+        svcs['cache'] = SimpleCache()
     svcs['markov'] = MarkovModel()
     try:
         svcs['markov'].load(markov_data_file)
@@ -58,6 +63,7 @@ def main():
     parser.add_option('--album_art_dir', default='/var/tmp/album-image-cache')
     parser.add_option('--markov_data',
                       default='/var/lib/djrandom/djrandom-markov.dat')
+    parser.add_option('--memcached_url')
     parser.add_option('--profile', action='store_true')
     daemonize.add_standard_options(parser)
     utils.read_config_defaults(
@@ -71,7 +77,8 @@ def main():
     daemonize.daemonize(opts, run_frontend,
                         (opts.port, opts.solr_url, opts.db_url,
                          opts.lastfm_api_key, opts.album_art_dir,
-                         opts.email_sender, opts.markov_data, opts.profile),
+                         opts.email_sender, opts.markov_data, opts.profile,
+                         opts.memcached_url),
                         support_gevent=True)
 
 
diff --git a/server/djrandom/frontend/views.py b/server/djrandom/frontend/views.py
index d70ae5f..0811208 100644
--- a/server/djrandom/frontend/views.py
+++ b/server/djrandom/frontend/views.py
@@ -7,7 +7,7 @@ from djrandom.database import Session
 from djrandom.model.mp3 import MP3, PlayLog
 from djrandom.model.playlist import Playlist
 from djrandom.model.user import User
-from djrandom.frontend import app, require_auth
+from djrandom.frontend import app, require_auth, svcs
 from sqlalchemy import distinct, func
 
 log = logging.getLogger(__name__)
@@ -20,9 +20,15 @@ def autocomplete_search():
     term = request.args.get('term')
     if not term:
         abort(400)
-    possible_artists = Session.query(distinct(
-            MP3.artist)).filter(MP3.artist.like('%s%%' % term))
-    return jsonify(results=[x[0] for x in possible_artists])
+    if len(term) < 4:
+        cache_key = 'autocomplete|%s' % term
+        results = svcs['cache'].get(cache_key)
+        if not results:
+            possible_artists = Session.query(distinct(
+                    MP3.artist)).filter(MP3.artist.like('%s%%' % term))
+            results = [x[0] for x in possible_artists]
+            svcs['cache'].set(cache_key, results, timeout=86400)
+    return jsonify(results=results)
 
 
 @app.route('/fragment/songs', methods=['POST'])
@@ -77,7 +83,8 @@ def fileiter(path, pos, end):
 
 
 def download_song_python(mp3):
-    # Parse 'Range' HTTP header.
+    # Parse 'Range' HTTP header. This is a very dumb parser, it will
+    # only support a single range spec.
     start = 0
     end = os.path.getsize(mp3.path)
     partial = False
-- 
GitLab