2016-01-21 30 views
0

我有一个外壳脚本 的MySQL --local-infile的= 1 -h为myhost -P MyPort上-u我< ./loader_file.sql阶系统调用到MySQL失败

当我直接在命令行运行这,它的效果很好。数据被加载到数据库中。

但Scala代码

val myScript = "mysql --local-infile=1 -h myhost -P myport -u me" #< "loader_file.sql" 
myScript ! 

我得到一个错误信息说我在外壳MySQL的命令,如“使用”和“负荷”里面都没有找到。显然,shell将loader_file.sql解释为bash命令,而不是mysql命令。

但如果我纳入整个字符串作为一个命令

val myScript = "mysql --local-infile=1 -h myhost -P myport -u me < loader_file.sql" 

然后我得到一个MySQL转储其所有的有效选项。显然,mysql认为我喂它非法的输入参数。

任何人都知道如何解决这个问题?

+0

我知道了将整个myScript字符串封装到一个shell脚本myscript.sh中,然后调用myscript.sh!我很好奇,但如果有一种方法可以直接调用它。所以我会把这个开放给任何知道这一点的人。 – bhomass

+0

必须是在这个问题相同的问题:http://stackoverflow.com/questions/21247653/using-scala-sys-process-with-curl-single-quotes-and-white-space(见我的答案)。此外,所有这些特殊的管道符号都是特定于外壳的,可能无法正确扩展。 –

回答

1

下面是你需要从Scala代码做什么:

import scala.sys.process._ 

val cmd = Seq("bash","-c","mysql --local-infile=1 -h myhost -P myport -u me < loader_file.sql") 

for(line <- cmd.lineStream_!){ 
    printf("%s\n",line) 
} 

这应该在linux下工作,OSX,Cygwin的或类似的(听起来像是你有这些环境之一,因为bash的存在)。

有很多在这个特定主题的变化,使您可以设置默认工作目录,指定的环境变量,分别处理STDOUT和STDERR流,并获取返回值等

这里有一个版本,除了指定环境变量之外,什么都不做:

import scala.sys.process._ 

val cmd = Seq("bash","-c","command with args, blah, blah, blah") 
val proc = Process(cmd, new java.io.File(".")) 
val exitValue = proc ! ProcessLogger (
    (out) => System.out.printf("stdout:%s\n",out) 
    , 
    (err) => System.err.printf("stderr:%s\n",err) 
) 
printf("exit value: %d\n",exitValue) 

scala.sys.process的文档很不错,尽管它假设了一个linux类型的环境。一个shell命令行有时不会被Seq(“bash”,“ - c”,...)包装,但它不是可移植的(例如,Windows不会将命令行传递给bash) 。