Available in all subroutines.

Invokes a user-defined subroutine. You may define subroutines in the same way as built-in subroutines, but they are only executed when invoked from a call statement. Control passes to the custom subroutine and returns to the calling point when the subroutine ends, unless the subroutine includes a statement that would terminate the current lifecycle state.

Custom subroutines do not accept parameters and do not return a value, but may apply side effects to a request, such as modifying request state. Custom subroutines have access to the same request-level state that the calling subroutine does (so, for example, a custom subroutine called from vcl_fetch would be able to set beresp.ttl), but do not have access to local variables defined in the parent subroutine. Likewise, local variables defined in a custom subroutine are not accessible outside it.

Custom subroutines may include the terminating statements restart, return or error. In the case of return without an argument, control passes back to the line after the call statement (which is also the default behavior if the custom subroutine does not contain any terminating statements). However, in the case of a return with an argument, a restart or an error from inside a custom subroutine, the parent subroutine will be terminated as well, with the specified exit state.

A custom subroutine may call another custom subroutine. It is not possible to call a built-in VCL subroutine.

User contributed notes

We welcome comments that add use cases, ideas, tips, and caveats. All comments will be moderated before publication. To post support questions, visit our support center and we'll find you the help you need.