Commit 5407a1ad authored by Pierre Smeyers's avatar Pierre Smeyers
Browse files

Merge branch 'fix/envsubst-enhancements' into 'master'

fix: homogenize new TBC envsubst mechanism

See merge request to-be-continuous/openshift!62
parents 45fa9f1c 2076fb73
Loading
Loading
Loading
Loading
+4 −4
Original line number Diff line number Diff line
@@ -173,7 +173,7 @@ The template processes the following steps:
3. _optionally_ executes the `os-post-apply.sh` script in your project to perform specific environment post-initialization stuff,
4. _optionally_ executes the `os-readiness-check` to wait & check for the application to be ready (if not found, the template assumes the application was successfully started).

Deployment jobs process the selected template with the following [labels](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#writing-labels):
Deployment jobs process the selected template with the following [labels](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#templates-writing-labels_using-templates):

* `app`: the application target name to use in this environment (i.e. `$environment_name`)<br/>
   _Can be overridden with `$OS_APP_LABEL`._
@@ -252,7 +252,7 @@ by using available environment variables:
    (ex: `${SECRET_TOKEN}` that you have set in your project CI/CD variables)

While your scripts may simply use any of those variables, your [OpenShift templates](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html)
shall be variabilized using [parameters](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#writing-parameters).
shall be variabilized using [parameters](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#templates-writing-parameters_using-templates).

Parameters are evaluated in the following order:

@@ -404,8 +404,8 @@ The OpenShift template uses some global configuration used throughout all jobs.
| `environment-url` / `OS_ENVIRONMENT_URL`    | Default environments url _(only define for static environment URLs declaration)_<br/>_supports late variable expansion (ex: `https://%{environment_name}.openshift.acme.com`)_ | _none_ |
| `scripts-dir` / `OS_SCRIPTS_DIR` | directory where OpenShift scripts (templates, hook scripts) are located | `.` _(root project dir)_ |
| `base-template-name` / `OS_BASE_TEMPLATE_NAME`  | Base OpenShift template name           | `openshift` |
| `app-label` / `OS_APP_LABEL` | The OpenShift [label](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#writing-labels) set with the `$environment_name` [dynamic variable](#using-variables) value. _Advanced usage_ | `app` |
| `env-label` / `OS_ENV_LABEL` | The OpenShift [label](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#writing-labels) set with the `$environment_type` [dynamic variable](#using-variables) value (`review`, `integration`, `staging` or `prod`). _Advanced usage_ | `env` |
| `app-label` / `OS_APP_LABEL` | The OpenShift [label](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#templates-writing-labels_using-templates) set with the `$environment_name` [dynamic variable](#using-variables) value. _Advanced usage_ | `app` |
| `env-label` / `OS_ENV_LABEL` | The OpenShift [label](https://docs.openshift.com/container-platform/latest/applications/creating_applications/using-templates.html#templates-writing-labels_using-templates) set with the `$environment_type` [dynamic variable](#using-variables) value (`review`, `integration`, `staging` or `prod`). _Advanced usage_ | `env` |

### Review environments configuration

+73 −4
Original line number Diff line number Diff line
@@ -389,9 +389,78 @@ stages:
    echo "$1" | tr '[:lower:]' '[:upper:]' | tr '[:punct:]' '_'
  }

  function awkenvsubst() {
    # escapes '&' char in variables for gsub
    awk '!/# *nosubst/{while(match($0,"[$%]{[^}]*}")) {var=substr($0,RSTART+2,RLENGTH-3);val=ENVIRON[var];gsub("&","\\\\&",val);gsub("[$%]{"var"}",val)}}1'
  function tbc_envsubst() {
    awk '
      BEGIN {
        count_replaced_lines = 0
        # ASCII codes
        for (i=0; i<=255; i++)
          char2code[sprintf("%c", i)] = i
      }
      # determine encoding (from env or from file extension)
      function encoding() {
        enc = ENVIRON["TBC_ENVSUBST_ENCODING"]
        if (enc != "")
          return enc
        if (match(FILENAME, /\.(json|yaml|yml)$/))
          return "jsonstr"
        return "raw"
      }
      # see: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent
      function uriencode(str) {
        len = length(str)
        enc = ""
        for (i=1; i<=len; i++) {
          c = substr(str, i, 1);
          if (index("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-_.!~*'\''()", c))
            enc = enc c
          else
            enc = enc "%" sprintf("%02X", char2code[c])
        }
        return enc
      }
      !/# *nosubst/ {
        orig_line = $0
        line = $0
        count_repl_in_line = 0
        # /!\ 3rd arg (match) not supported in BusyBox awk
        while (match(line, /[$%]\{([[:alnum:]_]+)\}/)) {
          expr_start = RSTART
          expr_len = RLENGTH
          # get var name
          var = substr(line, expr_start+2, expr_len-3)
          # get var value (from env)
          val = ENVIRON[var]
          # check variable is set
          if (val == "") {
            printf("[\033[1;93mWARN\033[0m] Environment variable \033[33;1m%s\033[0m is not set or empty\n", var) > "/dev/stderr"
          } else {
            enc = encoding()
            if (enc == "jsonstr") {
              gsub(/["\\]/, "\\\\&", val)
              gsub("\n", "\\n", val)
              gsub("\r", "\\r", val)
              gsub("\t", "\\t", val)
            } else if (enc == "uricomp") {
              val = uriencode(val)
            } else if (enc == "raw") {
            } else {
              printf("[\033[1;93mWARN\033[0m] Unsupported encoding \033[33;1m%s\033[0m: ignored\n", enc) > "/dev/stderr"
            }
          }
          # replace expression in line
          line = substr(line, 1, expr_start - 1) val substr(line, expr_start + expr_len)
          count_repl_in_line++
        }
        if (count_repl_in_line) {
          if (count_replaced_lines == 0)
            printf("[\033[1;94mINFO\033[0m] Variable expansion occurred in file \033[33;1m%s\033[0m:\n", FILENAME) > "/dev/stderr"
          count_replaced_lines++
          printf("> line %s: %s\n", NR, orig_line) > "/dev/stderr"
        }
        print line
      }
    ' "$@"
  }

  function pre_apply() {
@@ -499,7 +568,7 @@ stages:
    export appname_scc=$environment_name_ssc

    # variables expansion in $environment_url
    environment_url=$(echo "$environment_url" | awkenvsubst)
    environment_url=$(echo "$environment_url" | TBC_ENVSUBST_ENCODING=uricomp tbc_envsubst -)
    export environment_url
    # extract hostname from $environment_url
    hostname=$(echo "$environment_url" | awk -F[/:] '{print $4}')