It defines two virtual hosts with nearly identical configuration; the only difference is that the second one has SSL enabled. To prevent this duplication, we can use a <literal>let</literal>:
The <literal>let exampleOrgCommon = <replaceable>...</replaceable></literal> defines a variable named <literal>exampleOrgCommon</literal>. The <literal>//</literal> operator merges two attribute sets, so the configuration of the second virtual host is the set <literal>exampleOrgCommon</literal> extended with the SSL options.
but not <literal>{ let exampleOrgCommon = <replaceable>...</replaceable>; in <replaceable>...</replaceable>; }</literal> since attributes (as opposed to attribute values) are not expressions.
<emphasis>Functions</emphasis> provide another method of abstraction. For instance, suppose that we want to generate lots of different virtual hosts, all with identical configuration except for the host name. This can be done as follows:
Here, <varname>makeVirtualHost</varname> is a function that takes a single argument <literal>name</literal> and returns the configuration for a virtual host. That function is then called for several names to produce the list of virtual host configurations.
What if you need more than one argument, for instance, if we want to use a different <literal>documentRoot</literal> for each virtual host? Then we can make <varname>makeVirtualHost</varname> a function that takes a <emphasis>set</emphasis> as its argument, like this:
But in this case (where every root is a subdirectory of <filename>/sites</filename> named after the virtual host), it would have been shorter to define <varname>makeVirtualHost</varname> as