From: phk Date: Thu, 31 Jul 2008 12:50:36 +0000 (+0000) Subject: Complete the separation of synthetic from received objects. X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=0273d1bf97cd5db5295543cd1acf8d01a1b971ba;p=varnish Complete the separation of synthetic from received objects. Any object, also errors, we receive from the backend will go to vcl_fetch(), and can be cached if desired. Any object we create, for instance if we cannot contact the backend, will go to vcl_error() and will not be cached. Technical details: Implement VCL variable setting for booleans like obj.cacheable. Remove obj.valid, only valid objects go to vcl_fetch now. On fetch failure, drop the object and go to STP_ERROR with 503 Update testcase b00015.vtc accordingly. git-svn-id: svn+ssh://projects.linpro.no/svn/varnish/trunk@3044 d4fa192b-c00b-0410-8231-f00ffab90ce4 --- diff --git a/varnish-cache/bin/varnishd/cache.h b/varnish-cache/bin/varnishd/cache.h index e437f7ed..b4af870b 100644 --- a/varnish-cache/bin/varnishd/cache.h +++ b/varnish-cache/bin/varnishd/cache.h @@ -258,7 +258,6 @@ struct object { unsigned response; - unsigned valid; unsigned cacheable; unsigned busy; diff --git a/varnish-cache/bin/varnishd/cache_center.c b/varnish-cache/bin/varnishd/cache_center.c index 1b0ce8cd..3b789778 100644 --- a/varnish-cache/bin/varnishd/cache_center.c +++ b/varnish-cache/bin/varnishd/cache_center.c @@ -162,11 +162,6 @@ cnt_deliver(struct sess *sp) switch (sp->handling) { case VCL_RET_DELIVER: break; - case VCL_RET_ERROR: - HSH_Deref(sp->obj); - sp->obj = NULL; - sp->step = STP_ERROR; - return (0); default: INCOMPL(); } @@ -316,6 +311,8 @@ cnt_error(struct sess *sp) if (sp->obj == NULL) { HSH_Prealloc(sp); sp->obj = sp->wrk->nobj; + sp->obj->xid = sp->xid; + sp->obj->entered = sp->t_req; sp->wrk->nobj = NULL; } else { /* XXX: Null the headers ? */ @@ -384,15 +381,22 @@ cnt_fetch(struct sess *sp) i = Fetch(sp); CHECK_OBJ_NOTNULL(sp->director, DIRECTOR_MAGIC); - if (!i) - RFC2616_cache_policy(sp, sp->obj->http); /* XXX -> VCL */ - else { - http_PutStatus(sp->wrk, sp->fd, sp->obj->http, 503); - http_PutProtocol(sp->wrk, sp->fd, sp->obj->http, "HTTP/1.1"); - http_PutResponse(sp->wrk, sp->fd, sp->obj->http, - "Backend error"); + if (i) { +VSL(SLT_Debug, sp->fd, "Fetch = %d", i); + sp->err_code = 503; + sp->step = STP_ERROR; + VBE_free_bereq(sp->bereq); + sp->bereq = NULL; + sp->obj->ttl = 0; + sp->obj->cacheable = 0; + HSH_Unbusy(sp); + HSH_Deref(sp->obj); + sp->obj = NULL; + return (0); } + RFC2616_cache_policy(sp, sp->obj->http); /* XXX -> VCL */ + sp->err_code = http_GetStatus(sp->obj->http); VCL_fetch_method(sp); diff --git a/varnish-cache/bin/varnishd/cache_vrt.c b/varnish-cache/bin/varnishd/cache_vrt.c index ecbfb62f..ef54f184 100644 --- a/varnish-cache/bin/varnishd/cache_vrt.c +++ b/varnish-cache/bin/varnishd/cache_vrt.c @@ -413,7 +413,6 @@ VRT_r_obj_##onm(const struct sess *sp) \ return (sp->obj->field); \ } -VOBJ(unsigned, valid, valid) VOBJ(unsigned, cacheable, cacheable) /*--------------------------------------------------------------------*/ diff --git a/varnish-cache/bin/varnishd/mgt_vcc.c b/varnish-cache/bin/varnishd/mgt_vcc.c index 372ff455..6206bba3 100644 --- a/varnish-cache/bin/varnishd/mgt_vcc.c +++ b/varnish-cache/bin/varnishd/mgt_vcc.c @@ -135,9 +135,6 @@ static const char *default_vcl = "}\n" "\n" "sub vcl_fetch {\n" - " if (!obj.valid) {\n" - " error obj.status;\n" - " }\n" " if (!obj.cacheable) {\n" " pass;\n" " }\n" diff --git a/varnish-cache/bin/varnishd/rfc2616.c b/varnish-cache/bin/varnishd/rfc2616.c index 4d287f1a..961e7f9c 100644 --- a/varnish-cache/bin/varnishd/rfc2616.c +++ b/varnish-cache/bin/varnishd/rfc2616.c @@ -178,12 +178,10 @@ RFC2616_cache_policy(const struct sess *sp, const struct http *hp) case 410: /* Gone */ case 404: /* Not Found */ sp->obj->cacheable = 1; - sp->obj->valid = 1; body = 1; break; default: sp->obj->cacheable = 0; - sp->obj->valid = 1; /* XXX ? */ body = 0; break; } diff --git a/varnish-cache/bin/varnishtest/tests/b00015.vtc b/varnish-cache/bin/varnishtest/tests/b00015.vtc index ce5d318b..b0c249bf 100644 --- a/varnish-cache/bin/varnishtest/tests/b00015.vtc +++ b/varnish-cache/bin/varnishtest/tests/b00015.vtc @@ -2,19 +2,82 @@ test "Check synthetic error page caching" + +# First test that an internally generated error is not cached + +varnish v1 -vcl { + backend foo { + .host = "127.0.0.2"; + } +} -start + +client c1 { + txreq -url "/" + rxresp + expect resp.status == 503 + expect resp.http.X-varnish == "1001" +} -run + +client c1 { + txreq -url "/" + rxresp + expect resp.status == 503 + expect resp.http.X-varnish == "1002" +} -run + +# Then check that an cacheable error from the backend is + server s1 { rxreq - txresp -status 503 -msg "Server Error" + txresp -status 302 } -start -varnish v1 -vcl+backend { } -start +varnish v1 -vcl+backend { } client c1 { txreq -url "/" rxresp - expect resp.status == 503 - # Disable this for now to not upset automatic scripts - #txreq -url "/" - #rxresp - #expect resp.status == 503 + expect resp.status == 302 + expect resp.http.X-varnish == "1003" +} -run + +server s1 -wait + +client c1 { + txreq -url "/" + rxresp + expect resp.status == 302 + expect resp.http.X-varnish == "1004 1003" +} -run + +# Then check that a non-cacheable error from the backend can be + +server s1 { + rxreq + txresp -status 502 +} -start + +varnish v1 -vcl+backend { + sub vcl_fetch { + if (obj.status == 502) { + set obj.cacheable = true; + set obj.ttl = 10m; + } + } + } + +client c1 { + txreq -url "/2" + rxresp + expect resp.status == 502 + expect resp.http.X-varnish == "1005" +} -run + +server s1 -wait + +client c1 { + txreq -url "/2" + rxresp + expect resp.status == 502 + expect resp.http.X-varnish == "1006 1005" } -run diff --git a/varnish-cache/include/vrt_obj.h b/varnish-cache/include/vrt_obj.h index aaab2386..eae751b4 100644 --- a/varnish-cache/include/vrt_obj.h +++ b/varnish-cache/include/vrt_obj.h @@ -34,8 +34,6 @@ int VRT_r_obj_status(const struct sess *); void VRT_l_obj_status(const struct sess *, int); const char * VRT_r_obj_response(const struct sess *); void VRT_l_obj_response(const struct sess *, const char *, ...); -unsigned VRT_r_obj_valid(const struct sess *); -void VRT_l_obj_valid(const struct sess *, unsigned); unsigned VRT_r_obj_cacheable(const struct sess *); void VRT_l_obj_cacheable(const struct sess *, unsigned); double VRT_r_obj_ttl(const struct sess *); diff --git a/varnish-cache/lib/libvcl/vcc_action.c b/varnish-cache/lib/libvcl/vcc_action.c index 3a79fef4..6df3fa0e 100644 --- a/varnish-cache/lib/libvcl/vcc_action.c +++ b/varnish-cache/lib/libvcl/vcc_action.c @@ -280,9 +280,28 @@ parse_set(struct tokenlist *tl) } Fb(tl, 0, "vrt_magic_string_end);\n"); break; + case BOOL: + if (tl->t->tok != '=') { + illegal_assignment(tl, "boolean"); + return; + } + vcc_NextToken(tl); + ExpectErr(tl, ID); + if (vcc_IdIs(tl->t, "true")) { + Fb(tl, 0, " 1);\n", vp->lname); + } else if (vcc_IdIs(tl->t, "false")) { + Fb(tl, 0, " 0);\n", vp->lname); + } else { + vsb_printf(tl->sb, + "Expected true or false\n"); + vcc_ErrWhere(tl, tl->t); + return; + } + vcc_NextToken(tl); + break; default: vsb_printf(tl->sb, - "Assignments not possible for '%s'\n", vp->name); + "Assignments not possible for type of '%s'\n", vp->name); vcc_ErrWhere(tl, tl->t); return; } diff --git a/varnish-cache/lib/libvcl/vcc_gen_obj.tcl b/varnish-cache/lib/libvcl/vcc_gen_obj.tcl index a9b50025..18f354fa 100755 --- a/varnish-cache/lib/libvcl/vcc_gen_obj.tcl +++ b/varnish-cache/lib/libvcl/vcc_gen_obj.tcl @@ -150,11 +150,6 @@ set spobj { "const struct sess *" } - { obj.valid - RW BOOL - { hit fetch discard timeout error} - "const struct sess *" - } { obj.cacheable RW BOOL { hit fetch discard timeout error} diff --git a/varnish-cache/lib/libvcl/vcc_obj.c b/varnish-cache/lib/libvcl/vcc_obj.c index 754fa965..13449bed 100644 --- a/varnish-cache/lib/libvcl/vcc_obj.c +++ b/varnish-cache/lib/libvcl/vcc_obj.c @@ -151,13 +151,6 @@ struct var vcc_vars[] = { "HDR_OBJ", VCL_MET_HIT | VCL_MET_FETCH | VCL_MET_ERROR }, - { "obj.valid", BOOL, 9, - "VRT_r_obj_valid(sp)", - "VRT_l_obj_valid(sp, ", - V_RW, - 0, - VCL_MET_HIT | VCL_MET_FETCH | VCL_MET_DISCARD | VCL_MET_TIMEOUT | VCL_MET_ERROR - }, { "obj.cacheable", BOOL, 13, "VRT_r_obj_cacheable(sp)", "VRT_l_obj_cacheable(sp, ",