12.16. Handling Wildcard Characters in External Commands

Problem

You want to use a Unix shell wildcard character, such as *, in an external command.

Solution

In general, the best thing you can do when using a wildcard character like * is to run your command while invoking a Unix shell. For instance, if you have .scala files in the current directory and try to list them with the following command, the command will fail:

scala> import scala.sys.process._
import scala.sys.process._

scala> "ls *.scala".!
ls: *.scala: No such file or directory
res0: Int = 1

But by running the same command inside a Bourne shell, the command now correctly shows the .scala files (and returns the exit status of the command):

scala> val status = Seq("/bin/sh", "-c", "ls *.scala").!
AndOrTest.scala
Console.scala
status: Int = 0

Discussion

Putting a shell wildcard character like * into a command doesn’t work because the * needs to be interpreted and expanded by a shell, like the Bourne or Bash shells. In this example, even though there are files in the current directory named AndOrTest.scala and Console.scala, the first attempt doesn’t work. These other attempts will also fail as a result of the same problem:

scala> "echo *".!
*
res0: Int = 0

scala> Seq("grep", "-i", "foo", "*.scala").!
grep: *.scala: No such file or directory
res1: Int = 2

scala> Seq("ls", "*.scala").!
ls: *.scala: No such file or directory
res2: Int = 1

In each example, you can make these commands work by invoking a shell in the first two parameters ...

Get Scala Cookbook now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.