Выполнение команд оболочки из Scala REPL

Интересной особенностью Scala REPL является то, что если вы удаляете любую банку в своем каталоге %SCALA_HOME%\lib, она доступна для импорта из REPL. У меня там несколько банок, и мне часто нужно выяснить, какие из них доступны для включения. Поэтому мне всегда нужно открыть другое окно команд и выяснить, какие банки существуют в этом каталоге. Было бы замечательно, если бы REPL разрешил мне выполнять системные команды, такие как dir или ls, или, по крайней мере, перечислить все банки в приведенном выше каталоге lib. Какой самый простой способ (если есть) вызвать команды оболочки в REPL?

Ответы

Ответ 1

В REPL команда :sh позволяет ввести команду оболочки:

Версия для Windows:

scala> :sh cmd /C dir
  res0: scala.tools.nsc.interpreter.ProcessResult = `cmd /C dir` (28 lines, exit 0)
scala> res0 foreach println

(к сожалению, нет способа избежать вызова cmd \C перед командой оболочки)

Unix-подобная версия:

scala> :sh ls
  res0: scala.tools.nsc.interpreter.ProcessResult = `cmd /C dir` (28 lines, exit 0)
scala> res0 foreach println

Обновление: Вдохновленный Даниэль ответ, небольшой трюк для пользователей Windows:

scala> implicit def stringToDosProcess(s: String) =
  scala.sys.process.stringToProcess("cmd /C "+ s)
stringToDosProcess: (s: String)scala.sys.process.ProcessBuilder

scala> "dir".!

Ответ 2

Альтернатива: используйте библиотеку Scala sys.process:

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

scala> "ls /home/dcs/scala-2.9.1.final".!
bin
doc
lib
man
meta
misc
src
res1: Int = 0

Ответ 3

UPDATE

Средство для извлечения вывода :sh изменилось за эти годы.

Welcome to Scala 2.11.8 (OpenJDK 64-Bit Server VM, Java 1.8.0_91).
Type in expressions for evaluation. Or try :help.

scala> :sh date
res0: scala.tools.nsc.interpreter.ProcessResult = `date` (1 lines, exit 0)

scala> res0 foreach println
<console>:13: error: value foreach is not a member of scala.tools.nsc.interpreter.ProcessResult
       res0 foreach println
            ^

scala> res0.show
<console>:13: error: value show is not a member of scala.tools.nsc.interpreter.ProcessResult
       res0.show
            ^

scala> res0.lines
res3: List[String] = List(Sat Sep 17 19:29:26 PDT 2016)

Ответ 4

Малоизвестный трюк REPL:

Добро пожаловать в Scala версию 2.10.0-20120323-101508-45eebcf98d (Java-сервер HotSpot (TM), 64-разрядный сервер VM, Java 1.6.0_26). Введите выражения, чтобы они были оценены. Тип: помощь для получения дополнительной информации.

scala> /home/dcs/scala-2.9.1.final/<TAB>
/home/dcs/scala-2.9.1.final/misc   /home/dcs/scala-2.9.1.final/bin    /home/dcs/scala-2.9.1.final/man    /home/dcs/scala-2.9.1.final/src    /home/dcs/scala-2.9.1.final/lib    
/home/dcs/scala-2.9.1.final/meta   /home/dcs/scala-2.9.1.final/doc    

scala> /home/dcs/scala-2.9.1.final/lib/<TAB>
/home/dcs/scala-2.9.1.final/lib/scala-dbc.jar        /home/dcs/scala-2.9.1.final/lib/scala-swing.jar      /home/dcs/scala-2.9.1.final/lib/jline.jar            
/home/dcs/scala-2.9.1.final/lib/scala-library.jar    /home/dcs/scala-2.9.1.final/lib/scala-compiler.jar   /home/dcs/scala-2.9.1.final/lib/scalap.jar           

scala> /home/dcs/scala-2.9.1.final/lib/scala-library.jar
res0: scala.tools.nsc.io.File = /home/dcs/scala-2.9.1.final/lib/scala-library.jar

Где <TAB> я нажимаю tab.

Ответ 5

ОБНОВЛЕНИЕ 2018/01/15

Пример: вам нравится видеть файлы в текущем рабочем каталоге:

scala> :sh ls -l
res3: scala.tools.nsc.interpreter.ProcessResult = `ls -l` (13 lines, exit 0)

Но вы не можете этого сделать:

scala> res3.foreach {println}
<console>:40: error: value foreach is not a member of scala.tools.nsc.interpreter.ProcessResult
       res3.foreach {println}
            ^

Сначала вам нужно назначить строки другому типу, который поддерживает итерацию:

scala> res3.lines
res7: List[String] = List(total 960, [email protected]  1 dave  staff   11325 Jan  3 15:01 LICENSE, [email protected]  1 dave  staff    8859 Jan  3 15:01 README.rst, [email protected]  3 dave  staff      96 Jan  3 15:03 assembly, [email protected] 20 dave  staff     640 Jan  3 15:01 bin, [email protected] 13 dave  staff     416 Jan  3 15:01 doc, [email protected]  7 dave  staff     224 Jan  3 15:01 docker, [email protected]  6 dave  staff     192 Jan  3 15:03 examples, [email protected]  1 dave  staff     826 Jan  3 15:01 gradle.properties, [email protected]  1 dave  staff     128 Jan  3 15:04 h2o_drivers.txt, drwxr-xr-x   3 dave  staff      96 Jan 16 00:54 h2ologs, [email protected]  5 dave  staff     160 Jan  3 15:04 py, [email protected]  1 dave  staff  455890 Sep 19 04:18 rsparkling.tar.gz)

Затем итерация и вуаля!

scala> res7.foreach {println}
total 960
[email protected]  1 dave  staff   11325 Jan  3 15:01 LICENSE
[email protected]  1 dave  staff    8859 Jan  3 15:01 README.rst
[email protected]  3 dave  staff      96 Jan  3 15:03 assembly
[email protected] 20 dave  staff     640 Jan  3 15:01 bin
[email protected] 13 dave  staff     416 Jan  3 15:01 doc
[email protected]  7 dave  staff     224 Jan  3 15:01 docker
[email protected]  6 dave  staff     192 Jan  3 15:03 examples
[email protected]  1 dave  staff     826 Jan  3 15:01 gradle.properties
[email protected]  1 dave  staff     128 Jan  3 15:04 h2o_drivers.txt
drwxr-xr-x   3 dave  staff      96 Jan 16 00:54 h2ologs
[email protected]  5 dave  staff     160 Jan  3 15:04 py
[email protected]  1 dave  staff  455890 Sep 19 04:18 rsparkling.tar.gz