Mike Slinn

Scala and Shell Scripts

— Draft —

Published 2013-12-28. Last modified 2024-07-20.
Time to read: 2 minutes.

There are two ways to execute Scala code as a script:

  1. As a text file that only contains Scala code, with a .scala file type.
  2. As a shell script with any or no file type.

Scala File

This method of writing a Scala script requires that your Scala code be stored into a text file with the scala file type. ou can then execute that code by typing scala filename.scala. Let’s try this by creating a file called hello.scala with the following inside. You can use your favorite text editor to create this file.

  1. Using the Linux gedit editor to edit a new file in the current directory:
    Shell
    $ gedit hello.scala &
  2. Using vi, commonly available on Linux:
    Shell
    $ vi hello.scala

The entire file should contain only this one line:

hello.scala
println("Hello, world!")

To execute this file simply specify the full filename as a parameter to the Scala compiler driver.

Shell
$ scala hello.scala
Hello world! 

Remember, if your Mac laptop has a problem running the file, use -nocompdaemon:

Shell
$ scala -nocompdaemon hello.scala

Note that only Scala code was placed into the source file, and the source file was not made executable. Also note that the script was not defined as a program, it is just a collection of Scala source lines.

Exercise – Scala script

Write a Scala script file that prints out the current directory each time it is run. You can obtain the current directory from the returned value of this incantation:

Turn this incantation into a Scala program
new java.io.File("").getAbsolutePath.toString

Try running the script from various directories.

Shell Scripts

Scala scripts can be used with *nix shells such as bash, sh, zsh and csh. They do not work from a Windows command prompt, however they do work from Linux and Mac shells. Scala scripts can have any file type, or no file type. All you need to to is to put the following three lines at the top of the file, and to make the file executable; the remainder of the file contents will be interpreted as Scala code.

Shell script
#!/bin/sh
exec scala "$0" "$@"
!#

// Your Scala code goes here

Here is a simple example. Please make a file called script2 somewhere on your computer and copy the following into it:

script2
#!/bin/sh
exec scala "$0" "$@"
!#

println("Hello, world!")

Now make the file executable by typing the following at a shell prompt:

Shell
$ chmod a+x script2

Run the script like this:

Shell
$ ./script2
hello, world! 

Exercise – Shell Script

Write a shell script that prints out the number of days to your birthday. If you had a birthday earlier this year, it is fine to print out the number of days since your birthday instead. As a hint, here is some code that computes the number of seconds to/since Christmas:

Scala code
import java.util.Calendar

val xmas = Calendar.getInstance()
xmas.set(Calendar.MONTH, Calendar.DECEMBER)
xmas.set(Calendar.DAY_OF_MONTH, 25)

def secsUntilXmas: Long = (xmas.getTimeInMillis - System.currentTimeMillis) / 1000

Experiment in the REPL, then move your code into a shell script.

Here is a more complex example, stored in a file called script3. Note that the bash script is longer than the previous bash scripts: this one defines two environment variables called SCRIPT, which contains the fully qualified name of the script file, and DIR, which contains the directory of the script file. The environment variables are then used to invoke the Scala program that follows. The Scala program accepts the arguments passed to it and prints them out as part of a message.

script3
#!/bin/sh
SCRIPT="$(cd "${0%/*}" 2>/dev/null; echo "$PWD"/"${0##*/}")"
DIR="$( dirname "${SCRIPT}"} )"
exec scala "$0" "$DIR" "$SCRIPT"
::!#

import java.io.File

object App {
  def main(args: Array[String]): Unit = {
    val Array(directory,script) = args.map(new File(_).getAbsolutePath)
    println("Executing ’%s’ in directory ’%s’".format(script, directory))
  }
}

Save the above into a file called script3. Make it executable and run it as follows:

Shell
$ chmod a+x script3
$ ./script3 Executing ’/var/work/course_scala_intro_code/scripts/script3’ in directory ’/var/work/course_scala_intro_code/scripts’

* indicates a required field.

Please select the following to receive Mike Slinn’s newsletter:

You can unsubscribe at any time by clicking the link in the footer of emails.

Mike Slinn uses Mailchimp as his marketing platform. By clicking below to subscribe, you acknowledge that your information will be transferred to Mailchimp for processing. Learn more about Mailchimp’s privacy practices.