What is the right formula for this Enum.reduce and String.replace combination?

In the code below structList is a list of structs with each key being a string in a template and the value being the replacement.

%ParamStruct{default: "Greater London", description: "Region",
 key: "ca_cert_subj_state", label: "State/County", order: 99, required: false,
 value: "Greater London"}

So in the one above the key is ca_cert_subj_state and value is Greater London

This is the string in which the replacements are made:

sslCmd = """
openssl req -x509 -new -nodes -sha256 \
 -key {{key-file-pass}}.key \
 -days 3650 \
 -out {{key-file-pass}}.pem \
 -subj ""\
/C={{ca_cert_subj_country}}\
/ST={{ca_cert_subj_state}}\
/L={{ca_cert_subj_location}}\
/O={{ca_cert_subj_organization}}\
/OU={{ca_cert_subj_org_unit}}\
/CN={{ca_cert_subj_common_name}}\
/emailAddress={{ca_cert_email}}\
"""

The following code is supposed to accumulate the result of changing the strings in sslCmd but clearly doesn’t work. I am not sure how it should recurse or iterate. Any ideas?

Enum.reduce(structList, sslCmd, fn(x, sslCmd) -> 
     sslCmd = String.replace(sslCmd, "{{#{x.key}}}", x.value)
  end
)

Try

Enum.reduce(structList, sslCmd, fn(x, sslCmd) -> 
   String.replace(sslCmd, "{{#{x.key}}}", x.value)
end)

EDIT: = operator returns the value anyway, so just ignore my post, sorry.

Do you assign or return the return value of got snippet of are you relying on mutation of sslCmd? If the later, remember that there is no such thing in elixir

The assignment to sslCmd does not belong in the reduce function. It doesn’t change on account immutability. When assigned to the outcome of the Enum it works.

I have the Enum.reduce method working. This time I want to make make recursive calls over the list with this replace_string function. Is it all okay or are there some cases I have missed?

  def replace_string(subject, []), do: subject
      
  def replace_string(subject, [head | tail]) do
    replace_string(String.replace(subject, "{{#{head.key}}}", head.value),tail)
  end                                                                                                                              

I access this via

IO.puts "called via replace_string" <> " - " <> ProcessList.replace_string(sslCmd, structList)

I have a feeling it is not as complete as it should be. Any critiques?