Commit 8e5c7a0a authored by Lasse Karstensen's avatar Lasse Karstensen

Add fallback on std conversion functions.

Handle that conversion between VCL data type can fail,
and return a user-specificed fallback in those cases.

Mostly identical to patch from Arianna Aondio.
parent a6a6e97a
varnishtest "Test std.real2time, std.time2integer and std.time2real"
varnishtest "Test real2integer, real2time, time2integer and time2real in std"
server s1 {
rxreq
......@@ -10,8 +10,18 @@ varnish v1 -vcl+backend {
sub vcl_deliver {
set resp.http.x-foo = std.integer(req.http.foo, 0);
set resp.http.x-bar = std.time2integer(std.real2time(std.real(resp.http.x-foo, 0.0)));
set resp.http.x-baz = std.time2real(std.real2time(std.real(resp.http.x-foo, 0.0)));
set resp.http.x-bar = std.time2integer(std.real2time(
std.real(resp.http.x-foo, 0.0), now), 1);
set resp.http.x-baz = std.time2real(std.real2time(
std.real(resp.http.x-foo, 0.0), now), 1.0);
set resp.http.x-qux = std.real2integer(
std.real(req.http.foo, 2.0), 2);
# Representation of 9e99, which is larger than what fits in the
# 128bit integers on $exotic_platform.
set resp.http.x-int-fallback = std.real2integer(9000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000.000, 2);
}
} -start
......@@ -20,4 +30,15 @@ client c1 {
rxresp
expect resp.http.x-foo == resp.http.x-bar
expect resp.http.x-baz == 1140618699.000
expect resp.http.x-qux == 1140618699
expect resp.http.x-int-fallback == 2
} -run
# check we get the fallback if the conversion fails
client c2 {
txreq -hdr "foo: -9e99+1"
rxresp
expect resp.http.x-bar == 0
expect resp.http.x-baz == 0.000
expect resp.http.x-qux == 2
} -run
......@@ -9,7 +9,7 @@ varnish v1 -vcl+backend {
import ${vmod_std};
sub vcl_deliver {
set resp.http.x-foo = std.real2time(1140618699.00);
set resp.http.x-foo = std.real2time(1140618699.00, now);
}
} -start
......
......@@ -128,7 +128,7 @@ Example
$Function INT integer(STRING s, INT fallback)
Description
Converts the string *s* to an integer. If conversion fails,
Converts the string *s* to an integer. If conversion fails,
*fallback* will be returned.
Example
| if (std.integer(req.http.foo, 0) > 5) {
......@@ -139,7 +139,7 @@ $Function IP ip(STRING s, IP fallback)
Description
Converts the string *s* to the first IP number returned by
the system library function getaddrinfo(3). If conversion
the system library function getaddrinfo(3). If conversion
fails, *fallback* will be returned.
Example
| if (std.ip(req.http.X-forwarded-for, "0.0.0.0") ~ my_acl) {
......@@ -149,33 +149,44 @@ Example
$Function REAL real(STRING s, REAL fallback)
Description
Converts the string *s* to a real. If conversion fails,
Converts the string *s* to a real. If conversion fails,
*fallback* will be returned.
Example
| if (std.real(req.http.foo, 0.0) > 5.5) {
| ...
| }
$Function TIME real2time(REAL r)
$Function INT real2integer(REAL r, INT fallback)
Description
Converts the real *r* to a time.
Converts the real *r* to an integer. If conversion fails,
*fallback* will be returned.
Example
set req.http.integer = std.real2integer(1140618699.00, 0);
$Function TIME real2time(REAL r, TIME fallback)
Description
Converts the real *r* to a time. If conversion fails,
*fallback* will be returned.
Example
set req.http.time = std.real2time(1140618699.00);
set req.http.time = std.real2time(1140618699.00, now);
$Function INT time2integer(TIME t)
$Function INT time2integer(TIME t, INT fallback)
Description
Converts the time *t* to a integer.
Converts the time *t* to a integer. If conversion fails,
*fallback* will be returned.
Example
set req.http.int = std.time2integer(now);
set req.http.int = std.time2integer(now, 0);
$Function REAL time2real(TIME t)
$Function REAL time2real(TIME t, REAL fallback)
Description
Converts the time *t* to a real.
Converts the time *t* to a real. If conversion fails,
*fallback* will be returned.
Example
set req.http.real = std.time2real(now);
set req.http.real = std.time2real(now, 1.0);
$Function BOOL healthy(BACKEND be)
......@@ -241,7 +252,7 @@ Example
$Function TIME time(STRING s, TIME fallback)
Description
Converts the string *s* to a time. If conversion fails,
Converts the string *s* to a time. If conversion fails,
*fallback* will be returned.
Supported formats:
......
......@@ -187,27 +187,51 @@ vmod_real(VRT_CTX, VCL_STRING p, VCL_REAL d)
return (r);
}
VCL_INT __match_proto__(td_std_real2integer)
vmod_real2integer(VRT_CTX, VCL_REAL r, VCL_INT i)
{
CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
if (!isfinite(r))
return (i);
r = round(r);
if (r > LONG_MAX || r < LONG_MIN)
return(i);
return ((long)r);
}
VCL_TIME __match_proto__(td_std_real2time)
vmod_real2time(VRT_CTX, VCL_REAL r)
vmod_real2time(VRT_CTX, VCL_REAL r, VCL_TIME t)
{
CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
if (!isfinite(r))
return (t);
return (r);
}
VCL_INT __match_proto__(td_std_time2integer)
vmod_time2integer(VRT_CTX, VCL_TIME t)
vmod_time2integer(VRT_CTX, VCL_TIME t, VCL_INT i)
{
CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
return ((long)floor(t));
if (!isfinite(t))
return (i);
t = round(t);
if (t > LONG_MAX || t < LONG_MIN)
return(i);
return ((long)t);
}
VCL_REAL __match_proto__(td_std_time2real)
vmod_time2real(VRT_CTX, VCL_TIME t)
vmod_time2real(VRT_CTX, VCL_TIME t, VCL_REAL r)
{
CHECK_OBJ_NOTNULL(ctx, VRT_CTX_MAGIC);
if (!isfinite(t))
return (r);
return (t);
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment