Browse files

Add support for varnish purging based on expressions

Previously we would only purge based on URLs, but some of the upcoming
new work requires arbitrary expression purging.

NOTE! Require the creation of the new SQL procecure in the database,
either from varnish.sql or varnish_local.sql depending on if it's prod
or dev.
  • Loading branch information...
1 parent aa0fc31 commit 33ed40343b6f0074226106c199666e9891430d80 @mhagander mhagander committed Oct 3, 2012
Showing with 27 additions and 5 deletions.
  1. +1 −1 pgweb/core/views.py
  2. +5 −0 sql/varnish.sql
  3. +6 −0 sql/varnish_local.sql
  4. +15 −4 tools/pgq/varnish_consumer.py
View
2 pgweb/core/views.py
@@ -190,7 +190,7 @@ def admin_purge(request):
# Fetch list of latest purges
curs = connection.cursor()
- curs.execute("SELECT ev_time, ev_data FROM pgq.event_1 WHERE ev_type='P' ORDER BY ev_time DESC LIMIT 20")
+ curs.execute("SELECT ev_time, ev_data FROM pgq.event_1 WHERE ev_type IN ('P', 'X') ORDER BY ev_time DESC LIMIT 20")
latest = [{'t': r[0], 'u': r[1]} for r in curs.fetchall()]
return render_to_response('core/admin_purge.html', {
View
5 sql/varnish.sql
@@ -13,4 +13,9 @@ AS $$
SELECT pgq.insert_event('varnish', 'P', $1);
$$ LANGUAGE 'sql';
+CREATE OR REPLACE FUNCTION varnish_purge_expr(expr text)
+RETURNS bigint
+AS $$
+ SELECT pgq.insert_event('varnish', 'X', $1);
+$$ LANGUAGE 'sql';
COMMIT;
View
6 sql/varnish_local.sql
@@ -12,4 +12,10 @@ AS $$
SELECT 1::bigint;
$$ LANGUAGE 'sql';
+CREATE OR REPLACE FUNCTION varnish_purge_expr(url text)
+RETURNS bigint
+AS $$
+ SELECT 1::bigint;
+$$ LANGUAGE 'sql';
+
COMMIT;
View
19 tools/pgq/varnish_consumer.py
@@ -45,25 +45,31 @@ def process_batch(self, db, batch_id, ev_list):
for ev in ev_list:
if ev.type == 'P':
- # 'P' events means purge. Currently it's the only event
- # type we support.
+ # 'P' events means purge.
print_t("Purging '%s' on %s" % (ev.data, self.frontend))
try:
if self.do_purge(ev.data):
ev.tag_done()
except Exception, e:
print_t("Failed to purge '%s' on '%s': %s" % (ev.data, self.frontend, e))
+ elif ev.type == 'X':
+ # 'X' events means ban expression (rather than just urls)
+ print_t("Purging expression '%s' on %s" % (ev.data, self.frontend))
+ try:
+ if self.do_purge_expr(ev.data):
+ ev.tag_done()
+ except Exception, e:
+ print_t("Failed to purge expression '%s' on '%s': %s" % (ev.data, self.frontend, e))
else:
print_t("Unknown event type '%s'" % ev.type)
- def do_purge(self, url):
+ def internal_purge(self, headers):
"""
Send the actual purge request, by contacting the frontend this
purger is running for and sending a GET request to the special URL
with our regexp in a special header.
"""
- headers = {'X-Purge-URL': url}
conn = httplib.HTTPConnection('%s.postgresql.org' % self.frontend)
conn.request("GET", "/varnish-purge-url", '', headers)
resp = conn.getresponse()
@@ -74,6 +80,11 @@ def do_purge(self, url):
print_t("Varnish purge returned status %s (%s)" % (resp.status, resp.reason))
return False
+ def do_purge(self, url):
+ return self.internal_purge({'X-Purge-URL': url})
+
+ def do_purge_expr(self, expr):
+ return self.internal_purge({'X-Purge-Expr': expr})
class PurgerProcess(object):
"""

0 comments on commit 33ed403

Please sign in to comment.