Search code examples
shellshcodefresh

Shell command syntax error in for loop in Codefresh


I have below step to go through for loop. However I'm getting below synatx error.

Code:

steps:
  arti_lib_deploy:
    stage: build image
    type: freestyle
    title: "Deploy Libs to Artifactory"
    image: 'hub.artifactory.gcp.xxxx/curlimages/curl:latest'
    commands:
      - LIB_FOLDERS=["lib1","lib2"]
      - >
        for LIB_FOLDER in "${LIB_FOLDERS[@]}"; do
         echo "FolderName- ${LIB_FOLDER}"
         curl -X GET -kv https://xxxx.service.test/entitlements/effPermissions?permissionId= "${LIB_FOLDER}"
        done

Error:

Executing command: LIB_FOLDERS=["lib1","lib2"]
[2023-08-06T10:54:14.700Z] ------------------------------
Executing command: for LIB_FOLDER in "${LIB_FOLDERS[@]}"; do
echo "FolderName-${LIB_FOLDER }"
done

[2023-08-06T10:54:14.701Z] /bin/sh: syntax error: bad substitution
[2023-08-06T10:54:15.036Z] Reading environment variable exporting file contents.[2023-08-06T10:54:15.052Z] Reading environment variable exporting file contents.[2023-08-06T10:54:16.224Z] [SYSTEM]
Message
Failed to run freestyle step: Deploy Libs to Artifactory
Caused by
Container for step title: Deploy Libs to Artifactory, step type: freestyle, operation: Freestylestep. 
Failed with exit code: 2
Documentation Link https://codefresh.io/docs/docs/codefresh-yaml/steps/freestyle/
Exit code
2
Name
NonZeroExitCodeError

Sh command:

 commands:
   - LIB_FOLDERS="lib1 lib2"
   - for LIB_FOLDER in $LIB_FOLDERS;
     do
      echo "FolderName- $LIB_FOLDER"
     done

Error:

Executing command: LIB_FOLDERS="lib1 lib2"
------------------------------
/bin/sh: syntax error: unexpected end of file (expecting "done")
[2023-08-06T23:48:22.532Z] Reading environment variable exporting file contents.
[2023-08-06T23:48:22.543Z] Reading environment variable exporting file contents.

Solution

  • I'm not familiar with Codefresh, but your question gives me some vague ideas about how it interacts with the shell.

    Your original code has "${LIB_FOLDERS[@]}" in one of the commands. That's bash-specific syntax (it expands to all the elements of the LIB_FOLDERS array), but the error message indicates that Codefresh uses /bin/sh. Apparently /bin/sh is not bash on your system (it typically isn't); perhaps it's ash or dash.

    One solution would be to avoid bash-specific commands. Another would be to figure out how to persuade Codefresh to use bash rather than /bin/sh. Or you could probably write an external bash script that's invoked as a command.

    Your second attempt, after some comments was this:

     commands:
       - LIB_FOLDERS="lib1 lib2"
       - for LIB_FOLDER in $LIB_FOLDERS;
         do
          echo "FolderName- $LIB_FOLDER"
         done
    

    which gave:

    /bin/sh: syntax error: unexpected end of file (expecting "done")
    

    This suggests that each command preceded by - is passed to /bin/sh separately. One solution is to write the loop in a single line, for example:

     commands:
       - LIB_FOLDERS="lib1 lib2"
       - for LIB_FOLDER in $LIB_FOLDERS ; do echo "FolderName- $LIB_FOLDER" ; done
    

    And again, if this gets too complicated, it might be best to put the commands in an external script. Note in particular that lib1 and lib2 happen to be single words, so combining them into a string that you then split works. If there were spaces in those folder names, you'd have to do something more complicated.