When the shell parses a command line,
it removes quotes but remembers the text structure that they imply.
(That is a gross oversimplification;
see bash(1) or Shell Command Language for more details.)
For example, the command-line input
-blah apple -secondfruit "green banana" -some more
causes the shell to identify six words, or tokens:
-blah
apple
-secondfruit
green banana
-some
more
which will be stored in memory as
-blahⓧappleⓧ-secondfruitⓧgreen bananaⓧ-someⓧmoreⓧ
where ⓧ
represents a null byte.
This will then sometimes be displayed or reported as
-blah apple -secondfruit green banana -some more
so you might believe that the quotes are just being ignored,
and you have seven words, while, in fact, you have what you want.
Note:
In the above, ⓧ
represents a null byte.
What I'm describing here is standard shell argument-parsing processing.
If you type
ls -l fruit.sh "I came here for an argument" startScheduledTask.sh
the /bin/ls
program gets invoked with the string
lsⓧ-lⓧfruit.shⓧI came here for an argumentⓧstartScheduledTask.shⓧ
in memory, and this gets interpreted as
- argv[0] =
ls
- argv[1] =
-l
- argv[2] =
fruit.sh
- argv[3] =
I came here for an argument
- argv[4] =
startScheduledTask.sh
This exact same process happens if you are
- typing a
java
command directly into your primary, interactive shell,
- executing a
java
command that is in a shell script, or
- running a shell script by typing a command like
./startScheduledTask.sh
directly into your primary, interactive shell,
so this is not the problem.
Any program that cannot handle having its arguments separated by null characters
cannot work in Unix & Linux.
TL;DR
Your first command is correct. "$@"
gives you what you want;
it is the correct way for a shell script to pass its arguments
to a program that it calls. If you add debug code to your program
to loop through its arguments, printing each one on a new line,
and/or in brackets (but not all on one line, separated only by spaces),
you will see that the "$@"
is passing six arguments to the program.
OK, even more:
Your class path has asterisks (*
s) in it? Really?
I’m a little out of practice with Java, but that seems odd to me.
Please double-check that you’re doing that correctly for your system.
But, if it works correctly when you type the classpath with asterisks “directly”
(i.e., directly into your main shell; your primary, interactive shell;
your login shell), then that’s probably not the problem.
But please humor me and put that string into quotes, anyway.
Your problem is too complicated. When you’re building an airplane,
you don’t build the entire plane and then try to fly it.
And then, when it doesn’t fly, you don’t step back and ask,
“What’s wrong with the plane?”
No, you test it in pieces. You need to simplify.
- Stop running it in the background.
- Stop saying
nohup
.
- Stop redirecting the output.
- Don’t show your 42-character long shell prompt in your question.
- Your question is about an argument with spaces in it,
so don’t take that out,
but it doesn’t have to be 60 characters long with eight spaces.
green banana
is a great test value.
- Try it with arguments to your program not beginning with
-
(dash).
- Maybe even comment out the
new TaskRunner().run(args)
part
of your program, leaving only the DEBUG and System.exit(0);
.
None of these should make a difference.
But they are distractions that make it hard to see what’s important.
If you can demonstrate the problem in a minimal test configuration,
we can rule out all those other things as being related to the problem.
But, if the problem goes away when you remove the irrelevant things,
then one of them was probably causing the problem.
Also, please stop mixing fake/test data and real data
(i.e., fruits and tasks) in the question.
Please write this script (call it fruity.sh
):
#!/bin/sh
# classpath
CP="/opt/fxudply/fxcal-client-jar/current/lib:/opt/fxudply/fxcal-client-jar/current/lib/*:/opt/fxudply/fxcal-config/current/wib-config:/opt/fxudply/fxcal-config/current/wib-config/*"
# package.name.classname
PC=wib.runner.TaskRunner
"$JAVA_HOME"/bin/java -cp "$CP" "$PC" "$@"
and run
./fruity.sh taskExtRef "green banana"
If the debug says
…[taskExtRef, green banana]
then the "$@"
is working correctly,
and the problem lies elsewhere in your script. Try to find it.
Make one change at a time and see how the behavior changes.
If you can’t figure it out, we may be able to help you,
but only if you show us the part of the script that’s causing the problem.
But if the debug says
…[taskExtRef, green, banana]
then let us know.
DEBUG: : arguments
when your debug code saysDEBUG: arguments
? … … … … … … … … P.S. I updated my answer; please see it. – Scott Aug 31 at 3:17