How to add RECV snippet after backend condition

Hello,

I try to add a RECV VCL snippet after req.backend is defined.
But it looks like snippets are inserted before the backend condition.

I try to change the priority (I tried 1000, 10000 and 100000) but it didn’t work.

Is it possible to do something like that ?


What I’m trying to do:

sub vcl_recv {
#--FASTLY RECV BEGIN

#### WHERE SNIPPET USUALLY GOES

  # default conditions
    # end default conditions
  # Request Condition: be1_condition Prio: 0
  if(
# A very long condition
   ) {
    set req.backend = F_be1;
      }
  #end condition
  # Request Condition: be2_condition Prio: 0
  if(
# Another very long condition
   ) {
    set req.backend = F_be2;
      }

#### HERE WHAT I WANT TO DO
  if (req.backend == F_be1) {
# Do something usefull
  }

#--FASTLY RECV END
}

Hi @Florent, welcome to the Fastly community forum :slight_smile:

It is possible to add VCL to this section, but not with the VCL Snippets feature. Instead you should use a custom VCL file which gives you the flexibility to place logic anywhere in the file and, by extension, the subroutine.

I would recommend that you take a look at our Using VCL guide, specifically the Custom VCL section, which gives you some boilerplate code that you can start from when adding the VCL file in the dashboard.

Let me know if you run into any issues here!

I was hoping that I don’t have to rely on a custom VCL.

I guess I will try to found another way to fulfil my need or migrate to a Custom VCL

Hi @Florent - I can think of two ways of doing this.

One way is to assign a “condition” of false to both your backends. That way those backends will never be selected by the autogenerated code. You will have to manually assign the backends in a VCL snippet.

The code will look something like this in vcl_recv:

if (condition1) {
  set req.backend = F_be1;
} else if (condition2) {
  set req.backend = F_be2;
}

if (req.backend == F_be1) {
  // Do something
}

Below that would be the auto-generated code but it would be wrapped in a false statement so would never execute.

if (false) {
  # auto-generated backend assignment that doesn't run.
}

The other way of doing this is to leave everything as is and to simply reuse the condition you have attached to backend1 (F_be1). So simply do

if (condition that you applied to F_be1) {
  # Do something
}

Let me know if this answers your question!

My solution for now is the following:
Keep using Fastly backend declaration as is

if (
# A very long condition
) {
# Do something usefull
}

### Native backend condition / selection
if(
# A very long condition
) {
  set req.backend = F_be1;
}

I have control over the content of the condition, so I can easily duplicate it somewhere else.
Not as neat as req.backend == F_be1 but it does the tricks, and avoid unusual backend setup

But I keep in mind the solution of the condition set to false: it can be useful in case of a condition that have more than 512 chars


Maybe if there is a function like backend.is_condition_true (signature BOOL backend.is_condition_true ( ID condition_name )) that would reduce code duplication and the risk of code desynchronization.
(Backend condition are stored separately from the backend, so make them reusable would be somewhat logical)