r3708 - in branches/2.0/varnish-cache/bin: varnishd varnishtest/tests

tfheen at projects.linpro.no tfheen at projects.linpro.no
Mon Feb 9 13:58:29 CET 2009


Author: tfheen
Date: 2009-02-09 13:58:27 +0100 (Mon, 09 Feb 2009)
New Revision: 3708

Modified:
   branches/2.0/varnish-cache/bin/varnishd/cache_ban.c
   branches/2.0/varnish-cache/bin/varnishtest/tests/c00021.vtc
Log:
Merge r3519: Add the ability to purge on random request or object headers.

For instance:

        purge req.http.host ~ www.foo.com && req.url ~ "\.png$"
        purge obj.http.set-cookie ~ USER=383839

Now, why would you want purge on request headers and not object headers ?

Simple, some information the object does not have, the Host: header is
a good example.

Assuming that the Host: header is part of the hash we use to lookup
an object (as is the default), we can avoid copying that field into
the object (saving memory: O(nObjects)) by using the request value
to purge against.



Modified: branches/2.0/varnish-cache/bin/varnishd/cache_ban.c
===================================================================
--- branches/2.0/varnish-cache/bin/varnishd/cache_ban.c	2009-02-09 12:55:03 UTC (rev 3707)
+++ branches/2.0/varnish-cache/bin/varnishd/cache_ban.c	2009-02-09 12:58:27 UTC (rev 3708)
@@ -75,6 +75,7 @@
 #define BAN_T_NOT		(1 << 1)
 	regex_t			re;
 	char			*dst;
+	char			*src;
 };
 
 struct ban {
@@ -191,7 +192,7 @@
 }
 
 /*--------------------------------------------------------------------
- * Test functions -- return 0 if the test does not match
+ * Test functions -- return 0 if the test matches
  */
 
 static int
@@ -199,13 +200,15 @@
 {
 	int i;
 
+	if (p == NULL)
+		return(!(bt->flags & BAN_T_NOT));
 	if (bt->flags & BAN_T_REGEXP)
 		i = regexec(&bt->re, p, 0, NULL, 0);
 	else
 		i = strcmp(bt->dst, p);
 	if (bt->flags & BAN_T_NOT)
-		return (i);
-	return (!i);
+		return (!i);
+	return (i);
 }
 
 static int
@@ -229,6 +232,30 @@
 	return(ban_cond_str(bt, o->objhead->hash));
 }
 
+static int
+ban_cond_req_http(const struct ban_test *bt, const struct object *o,
+   const struct sess *sp)
+{
+	char *s;
+
+	(void)o;
+	CHECK_OBJ_NOTNULL(sp, SESS_MAGIC);
+	http_GetHdr(sp->http, bt->src, &s);
+	return (ban_cond_str(bt, s));
+}
+
+static int
+ban_cond_obj_http(const struct ban_test *bt, const struct object *o,
+   const struct sess *sp)
+{
+	char *s;
+
+	(void)sp;
+	CHECK_OBJ_NOTNULL(o, OBJECT_MAGIC);
+	http_GetHdr(o->http, bt->src, &s);
+	return (ban_cond_str(bt, s));
+}
+
 /*--------------------------------------------------------------------
  * Parse and add a ban test specification
  */
@@ -252,6 +279,20 @@
 	return (0);
 }
 
+static void
+ban_parse_http(struct ban_test *bt, const char *a1)
+{
+	int l;
+
+	l = strlen(a1);
+	bt->src = malloc(l + 3);
+	XXXAN(bt->src);
+	bt->src[0] = l + 1;
+	memcpy(bt->src + 1, a1, l);
+	bt->src[l + 1] = ':';
+	bt->src[l + 2] = '\0';
+}
+
 static int
 ban_parse_test(struct cli *cli, struct ban *b, const char *a1, const char *a2, const char *a3)
 {
@@ -289,11 +330,19 @@
 		cli_result(cli, CLIS_PARAM);
 		return (-1);
 	}
+
+
 	if (!strcmp(a1, "req.url"))
 		bt->func = ban_cond_url;
 	else if (!strcmp(a1, "obj.hash"))
 		bt->func = ban_cond_hash;
-	else {
+	else if (!strncmp(a1, "req.http.", 9)) {
+		bt->func = ban_cond_req_http;
+		ban_parse_http(bt, a1 + 9);
+	} else if (!strncmp(a1, "obj.http.", 9)) {
+		bt->func = ban_cond_obj_http;
+		ban_parse_http(bt, a1 + 9);
+	} else {
 		cli_out(cli, "unknown or unsupported field \"%s\"", a1);
 		cli_result(cli, CLIS_PARAM);
 		return (-1);
@@ -439,7 +488,7 @@
 			if (bt->func(bt, o, sp))
 				break;
 		}
-		if (bt != NULL)
+		if (bt == NULL)
 			break;
 	}
 

Modified: branches/2.0/varnish-cache/bin/varnishtest/tests/c00021.vtc
===================================================================
--- branches/2.0/varnish-cache/bin/varnishtest/tests/c00021.vtc	2009-02-09 12:55:03 UTC (rev 3707)
+++ branches/2.0/varnish-cache/bin/varnishtest/tests/c00021.vtc	2009-02-09 12:58:27 UTC (rev 3708)
@@ -5,10 +5,19 @@
 server s1 {
 	rxreq
 	expect req.url == "/foo"
-	txresp -body "1111\n"
+	txresp -hdr "foo: bar5" -body "1111\n"
+
 	rxreq
 	expect req.url == "/foo"
-	txresp -body "11111\n"
+	txresp -hdr "foo: bar6" -body "11111\n"
+
+	rxreq
+	expect req.url == "/foo"
+	txresp -hdr "foo: bar7" -body "111111\n"
+
+	rxreq
+	expect req.url == "/foo"
+	txresp -hdr "foo: bar8" -body "1111111\n"
 } -start
 
 varnish v1 -vcl+backend { } -start
@@ -17,33 +26,101 @@
 	txreq -url "/foo"
 	rxresp
 	expect resp.status == 200
-	expect resp.http.content-length == 5
-} 
+	expect resp.http.foo == bar5
+	expect resp.bodylen == 5
+} -run
 
-client c1 -run
-
+# syntax checks
 varnish v1 -clierr 104 "purge"
 varnish v1 -clierr 104 "purge foo"
 varnish v1 -clierr 104 "purge foo bar"
 varnish v1 -clierr 106 "purge a b c && a"
 varnish v1 -clierr 106 "purge a b c && a b"
 varnish v1 -clierr 106 "purge a b c || a b c"
+varnish v1 -cliok "purge.list"
+
+# exact match, not matching
 varnish v1 -cliok "purge req.url == foo"
+varnish v1 -cliok "purge.list"
+
 client c1 {
 	txreq -url "/foo"
 	rxresp
 	expect resp.status == 200
-	expect resp.http.content-length == 5
-}
+	expect resp.http.foo == bar5
+	expect resp.bodylen == 5
+} -run
 
-varnish v1 -cliok "purge req.url ~ foo && req.url ~ \"[ o]\""
+# exact match, matching
+varnish v1 -cliok "purge req.url == /foo"
 varnish v1 -cliok "purge.list"
+client c1 {
+	txreq -url "/foo"
+	rxresp
+	expect resp.status == 200
+	expect resp.http.foo == bar6
+	expect resp.bodylen == 6
+} -run
 
+# regexp nonmatch
+varnish v1 -cliok "purge req.url ~ bar"
+varnish v1 -cliok "purge.list"
+
 client c1 {
 	txreq -url "/foo"
 	rxresp
 	expect resp.status == 200
-	expect resp.http.content-length == 6
-}
+	expect resp.http.foo == bar6
+	expect resp.bodylen == 6
+} -run
 
-client c1 -run
+
+# regexp match
+varnish v1 -cliok "purge req.url ~ foo"
+varnish v1 -cliok "purge.list"
+
+client c1 {
+	txreq -url "/foo"
+	rxresp
+	expect resp.status == 200
+	expect resp.http.foo == bar7
+	expect resp.bodylen == 7
+} -run
+
+# header check, nonmatch
+varnish v1 -cliok "purge obj.http.foo != bar7"
+varnish v1 -cliok "purge.list"
+
+client c1 {
+	txreq -url "/foo"
+	rxresp
+	expect resp.status == 200
+	expect resp.http.foo == bar7
+	expect resp.bodylen == 7
+} -run
+
+# header check, match
+varnish v1 -cliok "purge req.http.foo == barcheck"
+varnish v1 -cliok "purge.list"
+
+client c1 {
+	txreq -url "/foo" -hdr "foo: barcheck" 
+	rxresp
+	expect resp.status == 200
+	expect resp.http.foo == bar8
+	expect resp.bodylen == 8
+} -run
+
+# header check, no header
+varnish v1 -cliok "purge obj.http.bar == barcheck"
+varnish v1 -cliok "purge.list"
+
+client c1 {
+	txreq -url "/foo"
+	rxresp
+	expect resp.status == 200
+	expect resp.http.foo == bar8
+	expect resp.bodylen == 8
+} -run
+
+



More information about the varnish-commit mailing list