What does HackerNews think of swift-sh?

Easily script with third-party Swift dependencies.

Language: Swift

#10 in JavaScript
#19 in Swift
Beyond the basics, the shell features with the biggest ROI beyond the basics are to quote properly and use namerefs and arrays (esp. to return values from functions), e.g.,

  # find2ra arrayName {find arguments...}
  # Run find command and put results in array arrayName.
  find2ra() {
    # (error checking removed)

    local -r f2raVar="${1}"
    shift
    # map find entries to ra, using char=0 as delimiter
    mapfile -d $'\0' -t "$f2raVar" < <(find -dsx "${@}" -print0)
    # -print0: handle paths with spaces, etc.
    # -ds: For consistency, use depth-first, lexigraphic order
    # -x: Avoid traversing other devices
  }

  # sample usage
  ra=()
  find2ra ra . -type f -name \*.sh
  for shFile in "${ra[@]}"; do ... ; done
There are many resources for shell scripts already. A good starting-point might be to list the awesome shell-script sample sites already available.

The effort to document shell is also somewhat Pyrrhic. The benefit would be... more shell? A more modern shell?

Another goal might be to switch to a real language sooner. Go and Python are the obvious choices, but Swift and Java also support shebang's:

   #!/usr/bin/env swift

   #!/usr/bin/env java --source 17
Dependencies are always tricky. swift-sh allows you to declare dependencies as comments after the import:

  import PromiseKit  // @mxcl ~> 6.5
https://github.com/mxcl/swift-sh
Yes, swift CLI will compile and run your swift file.

But many people also want to use libraries. For Python, they use the system libraries or work within an environment with installed libraries (i.e., the library-install process happens at environment-configuration time).

In Swift, the easiest way to consume libraries is using packages, but that requires a Package.swift declaring the project scope for the script file (which must comply with top-level and main-entrypoint code requirements).

The easiest way to do that when scripting is a swift tool that manages the process of gathering your library dependencies, auto-generating a project, building the tool, and caching it all so there's no overhead the next time.

The best available tool now is https://github.com/mxcl/swift-sh. It reads dependency information off import comments.

It can also generate the project for you, if/when you want to build in XCode (e.g., move into a more complex application, perhaps requiring sandbox declarations).

Working scripts are not always updated, so any script-build tool has to maintain backwards compatibility, but the swift package manager has changed a lot in recent versions. swift-sh seems to err on the side of backwards compatibility, and does not support e.g., the most recent dependency versioning styles.

Swift-forum discussions about better support for scripting haven't resulted in any official tooling.

Interesting.

I've resisted the pull of the Nix side so far...

There's a similar package that auto-pulls dependencies for Swift scripts, but it requires you to explicitly state the external dependencies as comment annotations. The example given is:

    #!/usr/bin/swift sh
    
    import Foundation
    import PromiseKit  // @mxcl ~> 6.5
    
    firstly {
        after(.seconds(2))
    }.then {
        after(.milliseconds(500))
    }.done {
        print("notice: two and a half seconds elapsed")
        exit(0)
    }
    
    RunLoop.main.run()


https://github.com/mxcl/swift-sh
The tricky part is that it is impossible to import any libraries in a script except:

- The official libraries that ship with Swift

- If you create a full-blown Swift package manager project and compile an executable. But this doesn't sound like a script anymore

- If you use John Sundell's Marathon [https://github.com/JohnSundell/Marathon] however it adds additional complexity around the writing of scripts

I.e. none of the solutions are as simple as writing a bash script

Edit: Just saw that Max Howell (creator of Homebrew) released this today https://github.com/mxcl/swift-sh This absolutely solves the issues. Fantastic.