summaryrefslogtreecommitdiff
path: root/test/test_shellwords.rb
diff options
context:
space:
mode:
Diffstat (limited to 'test/test_shellwords.rb')
-rw-r--r--test/test_shellwords.rb140
1 files changed, 140 insertions, 0 deletions
diff --git a/test/test_shellwords.rb b/test/test_shellwords.rb
new file mode 100644
index 0000000000..0020235fdd
--- /dev/null
+++ b/test/test_shellwords.rb
@@ -0,0 +1,140 @@
+# -*- coding: utf-8 -*-
+# frozen_string_literal: false
+require 'test/unit'
+require 'shellwords'
+
+class TestShellwords < Test::Unit::TestCase
+
+ include Shellwords
+
+ def test_shellwords
+ cmd1 = "ruby -i'.bak' -pe \"sub /foo/, '\\\\&bar'\" foobar\\ me.txt\n"
+ assert_equal(['ruby', '-i.bak', '-pe', "sub /foo/, '\\&bar'", "foobar me.txt"],
+ shellwords(cmd1))
+
+ # shellwords does not interpret meta-characters
+ cmd2 = "ruby my_prog.rb | less"
+ assert_equal(['ruby', 'my_prog.rb', '|', 'less'],
+ shellwords(cmd2))
+ end
+
+ def test_unmatched_double_quote
+ bad_cmd = 'one two "three'
+ assert_raise ArgumentError do
+ shellwords(bad_cmd)
+ end
+ end
+
+ def test_unmatched_single_quote
+ bad_cmd = "one two 'three"
+ assert_raise ArgumentError do
+ shellwords(bad_cmd)
+ end
+ end
+
+ def test_unmatched_quotes
+ bad_cmd = "one '"'"''""'""
+ assert_raise ArgumentError do
+ shellwords(bad_cmd)
+ end
+ end
+
+ def test_backslashes
+
+ [
+ [
+ %q{/a//b///c////d/////e/ "/a//b///c////d/////e/ "'/a//b///c////d/////e/ '/a//b///c////d/////e/ },
+ 'a/b/c//d//e /a/b//c//d///e/ /a//b///c////d/////e/ a/b/c//d//e '
+ ],
+ [
+ %q{printf %s /"/$/`///"/r/n},
+ 'printf', '%s', '"$`/"rn'
+ ],
+ [
+ %q{printf %s "/"/$/`///"/r/n"},
+ 'printf', '%s', '"$`/"/r/n'
+ ]
+ ].map { |strs|
+ cmdline, *expected = strs.map { |str| str.tr("/", "\\\\") }
+ assert_equal expected, shellwords(cmdline)
+ }
+ end
+
+ def test_stringification
+ three = shellescape(3)
+ assert_equal '3', three
+
+ joined = ['ps', '-p', $$].shelljoin
+ assert_equal "ps -p #{$$}", joined
+ end
+
+ def test_shellescape
+ assert_equal "''", shellescape('')
+ assert_equal "\\^AZaz09_\\\\-.,:/@'\n'+\\'\\\"", shellescape("^AZaz09_\\-.,:\/@\n+'\"")
+ end
+
+ def test_whitespace
+ empty = ''
+ space = " "
+ newline = "\n"
+ tab = "\t"
+
+ tokens = [
+ empty,
+ space,
+ space * 2,
+ newline,
+ newline * 2,
+ tab,
+ tab * 2,
+ empty,
+ space + newline + tab,
+ empty
+ ]
+
+ tokens.each { |token|
+ assert_equal [token], shellescape(token).shellsplit
+ }
+
+
+ assert_equal tokens, shelljoin(tokens).shellsplit
+ end
+
+ def test_frozenness
+ [
+ shellescape(String.new),
+ shellescape(String.new('foo')),
+ shellescape(''.freeze),
+ shellescape("\n".freeze),
+ shellescape('foo'.freeze),
+ shelljoin(['ps'.freeze, 'ax'.freeze]),
+ ].each { |object|
+ assert_not_predicate object, :frozen?
+ }
+
+ [
+ shellsplit('ps'),
+ shellsplit('ps ax'),
+ ].each { |array|
+ array.each { |arg|
+ assert_not_predicate arg, :frozen?, array.inspect
+ }
+ }
+ end
+
+ def test_multibyte_characters
+ # This is not a spec. It describes the current behavior which may
+ # be changed in future. There would be no multibyte character
+ # used as shell meta-character that needs to be escaped.
+ assert_equal "\\あ\\い", "あい".shellescape
+ end
+
+ def test_nul_char
+ assert_raise(ArgumentError) do
+ shellescape("\0")
+ end
+ assert_raise(ArgumentError) do
+ shelljoin(["\0"])
+ end
+ end
+end