lsl 0.0.1 → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.1
1
+ 0.1.0
data/lib/lsl.rb CHANGED
@@ -6,55 +6,52 @@ require 'mharris_ext'
6
6
  require File.dirname(__FILE__) + "/lsl/grammars/#{g}"
7
7
  end
8
8
 
9
- class Object
10
- def blank?
11
- to_s.strip == ''
12
- end
13
- def present?
14
- !blank?
15
- end
16
- def unquoted
17
- ((self[0..0]+self[-1..-1]) == '""') ? self[1..-2] : self
18
- end
9
+ %w(single compound execution).each do |f|
10
+ require File.dirname(__FILE__) + "/lsl/command/#{f}"
19
11
  end
20
12
 
21
- class Object
22
- def list_values
23
- elements.map { |x| x.text_value.strip }.select { |x| x.present? }.map { |x| x.unquoted }
24
- end
25
- def find_child_node(node)
26
-
27
- elements.each do |e|
28
- return e.send(node) if e.respond_to?(node)
13
+ %w(ext).each do |f|
14
+ require File.dirname(__FILE__) + "/lsl/ext/#{f}"
15
+ end
16
+
17
+ %w(mapping).each do |f|
18
+ require File.dirname(__FILE__) + "/lsl/mapping/#{f}"
19
+ end
20
+
21
+ %w(shell).each do |f|
22
+ require File.dirname(__FILE__) + "/lsl/#{f}"
23
+ end
24
+
25
+ module LSL
26
+ module ExecutionStrategy
27
+ class Base
29
28
  end
30
- #return send(node) if respond_to?(node)
31
- nil
32
- end
33
- def find_child_node2(node)
34
-
35
- elements.each do |e|
36
- return e.send(node) if e.respond_to?(node)
29
+ class Shell < Base
30
+ def call(cmd)
31
+ str = "#{cmd.ex} " + cmd.args.join(" ")
32
+ `#{str}`
33
+ end
37
34
  end
38
- #return send(node) if respond_to?(node)
39
- nil
35
+ class Eval < Base
36
+ def str(cmd)
37
+ "#{cmd.ex} " + cmd.args.map { |x| x.quoted }.join(" ")
38
+ end
39
+ def call(cmd)
40
+ eval(str(cmd))
41
+ end
42
+ end
43
+
44
+
40
45
  end
41
-
42
46
  end
43
47
 
44
- class SingleCommandObj
45
- attr_accessor :ex, :args, :options
46
- include FromHash
47
- def to_h
48
- {:ex => ex, :args => args, :options => options}
49
- end
50
- def url
51
- "http://localhost:4567/#{ex}" + args.map { |x| "/#{x}" }.join
52
- end
53
- def method
54
- ex.split(".").last
55
- end
56
- def obj
57
- a = ex.split(".")
58
- (a.size > 1) ? eval(a.first) : nil
59
- end
60
- end
48
+ def with_debug
49
+ $debug = true
50
+ yield
51
+ ensure
52
+ $debug = false
53
+ end
54
+
55
+
56
+
57
+
@@ -0,0 +1,16 @@
1
+ module LSL
2
+ module Command
3
+ class Compound
4
+ fattr(:commands) { [] }
5
+ attr_accessor :output_filename
6
+ include FromHash
7
+ def each_command
8
+ args = []
9
+ commands.each do |c|
10
+ args = yield(c,args)
11
+ end
12
+ args
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,111 @@
1
+ class Array
2
+ def each_with_expansion(&b)
3
+ return if empty?
4
+ first.array_aware_each do |x|
5
+ if size == 1
6
+ yield([x])
7
+ else
8
+ self[1..-1].each_with_expansion do |args|
9
+ yield([x] + args)
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
15
+
16
+ class Object
17
+ def array_aware_each(&b)
18
+ if kind_of?(Array)
19
+ each(&b)
20
+ else
21
+ yield(self)
22
+ end
23
+ end
24
+ def send_with_expansion(sym,*args,&b)
25
+ return send(sym,&b) if args.empty?
26
+ res = []
27
+ args.each_with_expansion do |a|
28
+ res << send(sym,*a,&b)
29
+ end
30
+ res = res.select { |x| x.present? }
31
+ if res.size == 1
32
+ res = res.first
33
+ elsif res.empty?
34
+ res = nil
35
+ end
36
+ res
37
+ end
38
+ end
39
+
40
+ module LSL
41
+ module CommandExecution
42
+ #a CommandExecution is method independant
43
+ class Base
44
+ attr_accessor :command_str, :shell
45
+ include FromHash
46
+ end
47
+ class Single < Base
48
+ attr_accessor :command, :input_args
49
+ fattr(:simple_obj) { command.obj || shell.env }
50
+ fattr(:obj) do
51
+ m = LSL::Mapping.new
52
+ m.method(command) || simple_obj
53
+ end
54
+ fattr(:command_args) do
55
+ res = command.args
56
+ res << [command.options] unless command.options.empty?
57
+ res
58
+ end
59
+ def fixed_input_args
60
+ return [] unless input_args
61
+ return [] if input_args.respond_to?("empty?") && input_args.empty?
62
+ res = input_args
63
+ res = [res] unless res.kind_of?(Array)
64
+ #puts "ia #{res.inspect}"
65
+ res
66
+ [res]
67
+ end
68
+ fattr(:args) do
69
+ command_args + fixed_input_args
70
+ end
71
+ fattr(:result) do
72
+ if obj.respond_to?(command.method)
73
+ res = obj.send_with_expansion(command.method,*args)
74
+ #puts "RES #{res.inspect}" if res
75
+ res
76
+ else
77
+ `#{command.raw}`.output_to_array
78
+ end
79
+ end
80
+ def run!
81
+ result
82
+ rescue => exp
83
+ puts "command failed #{exp.message}"
84
+ end
85
+ end
86
+ class Compound < Base
87
+ fattr(:command) { shell.parser.parse(command_str).command_hash }
88
+ fattr(:command_executions) do
89
+ exes = []
90
+ input_args = lambda { exes.last.andand.result || [] }
91
+ command.each_command do |c,args|
92
+ c = LSL::CommandExecution::Single.new(:shell => shell, :command => c, :input_args => input_args[])
93
+ c.run!
94
+ exes << c
95
+ end
96
+ exes
97
+ end
98
+ def run!
99
+ command_executions
100
+ if command.output_filename
101
+ ::File.create(command.output_filename,result.join("\n"))
102
+ else
103
+ puts result.join("\n") if result
104
+ end
105
+ end
106
+ def result
107
+ command_executions.last.result
108
+ end
109
+ end
110
+ end
111
+ end
@@ -0,0 +1,21 @@
1
+ module LSL
2
+ module Command
3
+ class Single
4
+ attr_accessor :ex, :args, :options, :raw
5
+ include FromHash
6
+ def to_h
7
+ {:ex => ex, :args => args, :options => options}
8
+ end
9
+ def url
10
+ "http://localhost:4567/#{ex}" + args.map { |x| "/#{x}" }.join
11
+ end
12
+ def method
13
+ ex.split(".").last
14
+ end
15
+ def obj
16
+ a = ex.split(".")
17
+ (a.size > 1) ? eval(a.first) : nil
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,43 @@
1
+ class Object
2
+ def blank?
3
+ to_s.strip == ''
4
+ end
5
+ def present?
6
+ !blank?
7
+ end
8
+ def quoted?
9
+ ((self[0..0]+self[-1..-1]) == '""')
10
+ end
11
+ def unquoted
12
+ quoted? ? self[1..-2] : self
13
+ end
14
+ def quoted
15
+ quoted? ? self : "\"#{self}\""
16
+ end
17
+ end
18
+
19
+ class Object
20
+ def list_values
21
+ elements.map { |x| x.text_value.strip }.map { |x| x.split(" ") }.flatten.map { |x| x.strip }.select { |x| x.present? }.map { |x| x.unquoted }
22
+ end
23
+ def find_child_node(node)
24
+ find_child_nodes(node).first
25
+ end
26
+ def find_child_nodes(node)
27
+ return [] unless elements
28
+ res = []
29
+ elements.each do |e|
30
+ #puts e.inspect if $debug and node.to_s == 'single_command'
31
+ if e.respond_to?(node)
32
+ res << e.send(node)
33
+ else
34
+ res += e.find_child_nodes(node)
35
+ end
36
+ end
37
+ #return send(node) if respond_to?(node)
38
+ res
39
+ end
40
+ def find_child_node2(node)
41
+ find_child_node(node)
42
+ end
43
+ end
@@ -1,7 +1,7 @@
1
1
  module LSL
2
2
  grammar Base
3
3
  rule word
4
- [a-zA-Z\.\/\\]+
4
+ [0-9a-zA-Z\.\/\\:\*_]+
5
5
  end
6
6
  rule ws1
7
7
  ' '
@@ -3,7 +3,23 @@ module LSL
3
3
  include LSL::SingleCommand
4
4
  include LSL::File
5
5
  rule full_command
6
- single_command (ows ">" ows filename)?
6
+ single_command (ows "|" ows single_command)* (ows ">" ows filename)? {
7
+ def filename
8
+ find_child_node(:filename)
9
+ end
10
+ def single_commands
11
+
12
+ res = [single_command.command_hash]
13
+ rest = find_child_nodes(:single_command).map { |x| x.command_hash }
14
+ #puts "rest #{rest.size}"
15
+ res + rest
16
+ end
17
+ def command_hash
18
+ res = LSL::Command::Compound.new(:commands => single_commands)
19
+ res.output_filename = filename.text_value if filename
20
+ res
21
+ end
22
+ }
7
23
  end
8
24
  end
9
25
  end
@@ -11,7 +11,8 @@ module LSL
11
11
  find_child_node(:options)
12
12
  end
13
13
  def command_hash
14
- SingleCommandObj.new(:ex => ex.text_value, :args => args.andand.list_values || [], :options => options.andand.hash_values || {})
14
+ LSL::Command::Single.new(:raw => text_value, :ex => ex.text_value,
15
+ :args => args.andand.list_values || [], :options => options.andand.hash_values || {})
15
16
  end
16
17
  }
17
18
  end
@@ -0,0 +1,32 @@
1
+ require 'rake'
2
+ task :abc do
3
+ puts "task abc"
4
+ end
5
+
6
+ class RemoteCall
7
+ def remote_call(*args)
8
+ require 'open-uri'
9
+ open("http://localhost:4567/remote_call").read
10
+ end
11
+ end
12
+
13
+ class RakeRunner
14
+ def method_missing(sym,*args,&b)
15
+ Rake::Task[sym].invoke
16
+ "ran"
17
+ end
18
+ end
19
+
20
+ module LSL
21
+ class Mapping
22
+ def method(cmd)
23
+ if cmd.ex == 'remote_call'
24
+ RemoteCall.new
25
+ elsif cmd.ex == 'abc'
26
+ RakeRunner.new
27
+ else
28
+ nil
29
+ end
30
+ end
31
+ end
32
+ end
@@ -1,43 +1,5 @@
1
1
  require File.dirname(__FILE__) + "/../lsl"
2
- require 'open-uri'
3
- require 'fileutils'
2
+ #require 'open-uri'
4
3
 
5
- class CommandEnv
6
- def echo(str)
7
- puts "ECHOING #{str}"
8
- end
9
- def cp(a,b)
10
- puts "gonna copy #{a} to #{b}"
11
- end
12
- def del(a)
13
- puts "deleting #{a}"
14
- end
15
- end
16
4
 
17
- class Foo
18
- def self.bar(*args)
19
- puts "bar #{args.inspect}"
20
- end
21
- end
22
-
23
- class Shell
24
- fattr(:env) { CommandEnv.new }
25
- fattr(:parser) { LSL::SingleCommandParser.new }
26
- def run(str)
27
- command = parser.parse(str).command_hash
28
- obj = command.obj || env
29
- obj.send(command.method,*command.args)
30
- #open(command.url)
31
- rescue => exp
32
- puts "command failed #{exp.message}"
33
- end
34
- def run_loop
35
- loop do
36
- str = STDIN.gets.strip
37
- run(str)
38
- end
39
- end
40
- end
41
-
42
- s = Shell.new
43
- s.run_loop
5
+ run_shell!
@@ -3,4 +3,8 @@ require 'mharris_ext'
3
3
 
4
4
  get "/echo/:str" do
5
5
  puts params[:str]
6
+ end
7
+
8
+ get "/remote_call" do
9
+ "rc"
6
10
  end
@@ -0,0 +1,88 @@
1
+ require 'fileutils'
2
+
3
+ class String
4
+ def output_to_array
5
+ split("\n").select { |x| x.present? }.map { |x| x.strip }
6
+ end
7
+ end
8
+
9
+ def ec_array(cmd)
10
+ `#{cmd}`.output_to_array
11
+ end
12
+
13
+
14
+ $printed ||= []
15
+ module LSL
16
+ module ShellLike
17
+ module Inner
18
+ def echo(*args)
19
+ #puts args.inspect
20
+ puts args.join(" ")
21
+ nil
22
+ end
23
+ def ls(d=".")
24
+ ec_array "ls #{d}"
25
+ end
26
+ def pf(f)
27
+ str = ::File.read(f)
28
+ $printed << str
29
+ puts str
30
+ end
31
+ def foo
32
+ ["foo"]
33
+ end
34
+ def longest(*args)
35
+ res = args.sort_by { |x| x.size }.last
36
+ #puts "Longest: #{res}"
37
+ res
38
+ end
39
+ def pm(a,b)
40
+ puts a.length * b.length
41
+ end
42
+ def cc(*args)
43
+ args.reverse.join("")
44
+ end
45
+ def la(*args)
46
+ ::File.append("spec/mock_dir/log.txt","LOG #{Time.now} " + args.join(",") + "\n")
47
+ end
48
+ def cd(d)
49
+ Dir.chdir(d)
50
+ end
51
+ def exit(*args)
52
+ puts "Exiting"
53
+ Kernel.exit(*args)
54
+ end
55
+ end
56
+ include FileUtils
57
+ include Inner
58
+ end
59
+
60
+
61
+ class CommandEnv
62
+ include LSL::ShellLike
63
+ end
64
+
65
+ class Shell
66
+ fattr(:env) { LSL::CommandEnv.new }
67
+ fattr(:parser) { LSL::CompoundCommandParser.new }
68
+ def run(str)
69
+ LSL::CommandExecution::Compound.new(:command_str => str, :shell => self).tap { |x| x.run! }
70
+ end
71
+ def get_input
72
+ STDIN.gets.strip
73
+ end
74
+ def run_loop
75
+ loop do
76
+ print "#{Dir.getwd}> "
77
+ str = get_input
78
+ run(str)
79
+ end
80
+ end
81
+ end
82
+ end
83
+
84
+ def run_shell!(obj=nil)
85
+ s = LSL::Shell.new
86
+ s.env = obj if obj
87
+ s.run_loop
88
+ end
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{lsl}
8
- s.version = "0.0.1"
8
+ s.version = "0.1.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["mharris717"]
12
- s.date = %q{2010-12-27}
12
+ s.date = %q{2010-12-31}
13
13
  s.default_executable = %q{lsl}
14
14
  s.description = %q{little shell language}
15
15
  s.email = %q{mharris717@gmail.com}
@@ -29,20 +29,32 @@ Gem::Specification.new do |s|
29
29
  "VERSION",
30
30
  "bin/lsl",
31
31
  "lib/lsl.rb",
32
+ "lib/lsl/command/compound.rb",
33
+ "lib/lsl/command/execution.rb",
34
+ "lib/lsl/command/single.rb",
35
+ "lib/lsl/ext/ext.rb",
32
36
  "lib/lsl/grammars/base.treetop",
33
37
  "lib/lsl/grammars/compound_command.treetop",
34
38
  "lib/lsl/grammars/file.treetop",
35
39
  "lib/lsl/grammars/list.treetop",
36
40
  "lib/lsl/grammars/quoting.treetop",
37
41
  "lib/lsl/grammars/single_command.treetop",
42
+ "lib/lsl/mapping/mapping.rb",
38
43
  "lib/lsl/sandbox.rb",
39
44
  "lib/lsl/server.rb",
45
+ "lib/lsl/shell.rb",
40
46
  "lsl.gemspec",
41
47
  "spec/compound_command_spec.rb",
42
48
  "spec/lsl_spec.rb",
49
+ "spec/mock_dir/a.txt",
50
+ "spec/mock_dir/b.txt",
51
+ "spec/mock_dir/log.txt",
52
+ "spec/mock_dir/output.txt",
43
53
  "spec/quoting_spec.rb",
54
+ "spec/shell_spec.rb",
44
55
  "spec/single_command_spec.rb",
45
- "spec/spec_helper.rb"
56
+ "spec/spec_helper.rb",
57
+ "to"
46
58
  ]
47
59
  s.homepage = %q{http://github.com/mharris717/lsl}
48
60
  s.licenses = ["MIT"]
@@ -53,6 +65,7 @@ Gem::Specification.new do |s|
53
65
  "spec/compound_command_spec.rb",
54
66
  "spec/lsl_spec.rb",
55
67
  "spec/quoting_spec.rb",
68
+ "spec/shell_spec.rb",
56
69
  "spec/single_command_spec.rb",
57
70
  "spec/spec_helper.rb"
58
71
  ]
@@ -5,11 +5,46 @@ describe "CompoundCommand" do
5
5
  @parser = LSL::CompoundCommandParser.new
6
6
  end
7
7
  def parser; @parser; end
8
+ def parse(*args); parser.parse(*args); end
9
+ def parse_obj(*args); parse(*args).command_hash; end
8
10
  it 'single_command' do
9
11
  parser.should be_parsed("cp a b -v a")
10
12
  end
11
13
  it 'command with output redirection' do
12
14
  parser.should be_parsed("cp a b > foo.txt")
13
15
  end
16
+ it 'command with output redirection 2' do
17
+ parser.parse("cp a b > foo.txt").command_hash.output_filename.should == 'foo.txt'
18
+ end
19
+ it 'makes command obj without output filename' do
20
+ parser.parse("cp a b").command_hash.output_filename.should be_nil
21
+ end
22
+ it 'pipes' do
23
+ parser.should be_parsed("cp a b | cp a b > foo.txt")
24
+ end
25
+ it 'has one command' do
26
+ parser.parse("cp a b").command_hash.commands.size.should == 1
27
+ end
28
+ it 'has multiple commands' do
29
+ parser.parse("cp a b | ls c d").command_hash.commands.size.should == 2
30
+ end
31
+ it 'has 1st command' do
32
+ parse_obj("cp a b | ls c d").commands.first.ex.should == 'cp'
33
+ end
34
+ it 'has 2nd command' do
35
+ c = parse_obj("cp a b | ls c d").commands.last
36
+ c.ex.should == 'ls'
37
+ c.args.should == ['c','d']
38
+ end
39
+ describe "execution" do
40
+ it "each_command args" do
41
+ res = []
42
+ parse_obj("cp a b | ls c d").each_command do |c,args|
43
+ res << args
44
+ 14
45
+ end
46
+ res.should == [[],14]
47
+ end
48
+ end
14
49
 
15
50
  end
@@ -4,8 +4,3 @@ describe "Lsl" do
4
4
 
5
5
 
6
6
  end
7
-
8
- a = <<EOF
9
- output redirection
10
- quoting
11
- EOF
File without changes
File without changes
@@ -0,0 +1,5 @@
1
+ LOG Fri Dec 31 14:21:26 -0500 2010
2
+ LOG Fri Dec 31 14:21:31 -0500 2010
3
+ LOG Fri Dec 31 14:21:36 -0500 2010 Gemfile
4
+ LOG Fri Dec 31 14:21:36 -0500 2010 Gemfile.lock
5
+ LOG Fri Dec 31 14:22:47 -0500 2010
@@ -0,0 +1 @@
1
+ VERSION
@@ -0,0 +1,48 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "Shell" do
4
+ before do
5
+ @shell = LSL::Shell.new
6
+ end
7
+ def run(*args); @shell.run(*args); end
8
+ it 'smoke' do
9
+ 2.should == 2
10
+ end
11
+ it 'simple' do
12
+ @shell.run("ls VERSION").result.should == ['VERSION']
13
+ @shell.run("ls VERSIONX").result.should == []
14
+ end
15
+ it 'piping' do
16
+ @shell.run('ls VERSION | pf')
17
+ $printed.should == ['0.0.1']
18
+ end
19
+ it 'foo' do
20
+ #30.times do
21
+ #@shell.run("foo | echo")
22
+ #end
23
+ run("ls VERSION | longest").result.should == 'VERSION'
24
+ run("ls VERSION | longest abc").result.should == 'VERSION'
25
+ run("ls VERSION | longest abc abcdefgh").result.should == 'abcdefgh'
26
+ end
27
+ it 'star arg' do
28
+ run("ls Gemfile*").result.should == ['Gemfile','Gemfile.lock']
29
+ end
30
+ it 'remote call' do
31
+ run("remote_call foo").result.should == 'rc'
32
+ run("remote_call foo | echo")
33
+ end
34
+ it 'rake' do
35
+ run("abc").result.should == "ran"
36
+ end
37
+ describe 'output redirection' do
38
+ before do
39
+ @file = "spec/mock_dir/output.txt"
40
+ eat_exceptions { FileUtils.rm @file }
41
+ end
42
+ it "foo" do
43
+ run("ls VERSION > #{@file}")
44
+ File.read(@file).should == "VERSION"
45
+ end
46
+ end
47
+
48
+ end
@@ -55,6 +55,12 @@ describe "Command" do
55
55
  it "ex and args" do
56
56
  parse("cp a b").command_hash.to_h.should == {:ex => "cp", :args => ['a','b'], :options => {}}
57
57
  end
58
+ it "ex and args 2" do
59
+ parse("cp a b").command_hash.ex.should == 'cp'
60
+ end
61
+ it "ex and 3 args" do
62
+ parse("cp a b c").command_hash.to_h.should == {:ex => "cp", :args => ['a','b','c'], :options => {}}
63
+ end
58
64
  it 'quoted arg' do
59
65
  parse('cp "abc"').command_hash.args.should == ['abc']
60
66
  end
@@ -67,6 +73,9 @@ describe "Command" do
67
73
  it "ex and option value" do
68
74
  parse("cp -v a").command_hash.to_h.should == {:ex => "cp", :args => [], :options => {"v" => 'a'}}
69
75
  end
76
+ it 'raw string' do
77
+ parse("cp a b").command_hash.raw.should == 'cp a b'
78
+ end
70
79
  end
71
80
 
72
81
  end
@@ -78,4 +87,8 @@ quoting
78
87
  going to ignore list arguments for now
79
88
  how to i break out into raw code
80
89
  ability to bring code directly into the shell
90
+ easy extensibility by anyone using the library
91
+ pipes
92
+ need a lesson on bash syntax
93
+ piping inut, communicating in json. what's diff between array and array of args
81
94
  EOF
data/to ADDED
@@ -0,0 +1,4 @@
1
+ #! /usr/bin/ruby
2
+
3
+ puts "a"
4
+ puts "b"
metadata CHANGED
@@ -4,9 +4,9 @@ version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
6
  - 0
7
- - 0
8
7
  - 1
9
- version: 0.0.1
8
+ - 0
9
+ version: 0.1.0
10
10
  platform: ruby
11
11
  authors:
12
12
  - mharris717
@@ -14,7 +14,7 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-12-27 00:00:00 -05:00
17
+ date: 2010-12-31 00:00:00 -05:00
18
18
  default_executable: lsl
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
@@ -127,20 +127,32 @@ files:
127
127
  - VERSION
128
128
  - bin/lsl
129
129
  - lib/lsl.rb
130
+ - lib/lsl/command/compound.rb
131
+ - lib/lsl/command/execution.rb
132
+ - lib/lsl/command/single.rb
133
+ - lib/lsl/ext/ext.rb
130
134
  - lib/lsl/grammars/base.treetop
131
135
  - lib/lsl/grammars/compound_command.treetop
132
136
  - lib/lsl/grammars/file.treetop
133
137
  - lib/lsl/grammars/list.treetop
134
138
  - lib/lsl/grammars/quoting.treetop
135
139
  - lib/lsl/grammars/single_command.treetop
140
+ - lib/lsl/mapping/mapping.rb
136
141
  - lib/lsl/sandbox.rb
137
142
  - lib/lsl/server.rb
143
+ - lib/lsl/shell.rb
138
144
  - lsl.gemspec
139
145
  - spec/compound_command_spec.rb
140
146
  - spec/lsl_spec.rb
147
+ - spec/mock_dir/a.txt
148
+ - spec/mock_dir/b.txt
149
+ - spec/mock_dir/log.txt
150
+ - spec/mock_dir/output.txt
141
151
  - spec/quoting_spec.rb
152
+ - spec/shell_spec.rb
142
153
  - spec/single_command_spec.rb
143
154
  - spec/spec_helper.rb
155
+ - to
144
156
  has_rdoc: true
145
157
  homepage: http://github.com/mharris717/lsl
146
158
  licenses:
@@ -175,5 +187,6 @@ test_files:
175
187
  - spec/compound_command_spec.rb
176
188
  - spec/lsl_spec.rb
177
189
  - spec/quoting_spec.rb
190
+ - spec/shell_spec.rb
178
191
  - spec/single_command_spec.rb
179
192
  - spec/spec_helper.rb