shell_shock 0.0.3 → 0.0.4

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,11 @@
1
+ module ShellShock
2
+ module CommandSpec
3
+ def with_usage text
4
+ it('should display usage') { @command.usage.should == text }
5
+ end
6
+
7
+ def with_help text
8
+ it('should display help') { @command.help.should == text }
9
+ end
10
+ end
11
+ end
@@ -1,84 +1,83 @@
1
1
  require 'rubygems'
2
2
  require 'readline'
3
+ require 'shell_shock/exit_command'
4
+ require 'shell_shock/help_command'
5
+ require 'shell_shock/logger'
3
6
 
4
7
  module ShellShock
5
8
  module Context
9
+ include Logger
10
+
11
+ def head_tail string
12
+ if string
13
+ m = /[^ ]+/.match(string.strip)
14
+ return m[0], m.post_match.strip if m
15
+ end
16
+ return '', ''
17
+ end
18
+
6
19
  def refresh
7
20
  refresh_commands if respond_to?(:refresh_commands)
8
21
  Readline.completer_word_break_characters = ''
9
- Readline.completion_proc = lambda do |word|
10
- name, *words = word.scan(/[\w?]+/)
11
- if name
12
- command = @commands[name]
22
+ Readline.completion_proc = lambda do |string|
23
+ log "trying completion for \"#{string}\""
24
+ first, rest = head_tail(string)
25
+ log "split \"#{first}\" from \"#{rest}\""
26
+ if first
27
+ command = @commands[first]
13
28
  if command
29
+ log "matched #{first} command"
14
30
  if command.respond_to?(:completion)
15
- rest = words || []
16
- completions = command.completion(rest.join(' ')).map {|c| "#{name} #{c}" }
17
- return completions
31
+ completions = command.completion(rest).map {|c| "#{first} #{c}" }
18
32
  else
19
- return []
33
+ log "#{first} has no completion proc"
34
+ completions = []
20
35
  end
21
36
  end
22
37
  end
23
38
 
24
- @commands.keys.grep( /^#{Regexp.escape(word)}/ ).sort
39
+ completions ||= @commands.keys.grep( /^#{Regexp.escape(first)}/ ).sort
40
+ log "returning #{completions.inspect} completions"
41
+ completions
25
42
  end
26
43
  end
27
44
 
28
- def push
29
- refresh
30
- begin
31
- while line = Readline.readline(@prompt_text, true)
32
- line.strip!
33
- case line
34
- when /^([\w?]+) (.*)/
35
- return if ['quit', 'exit'].include?($1)
36
- process_command $1, $2
37
- when /^([\w?]+)/
38
- return if ['quit', 'exit'].include?($1)
39
- process_command $1
40
- else
41
- @io.say "can not process line \"#{line}\""
42
- end
43
- @io.say
44
- refresh
45
- end
46
- rescue Interrupt => e
47
- return
48
- end
49
- @io.say
45
+ def abort!
46
+ @abort = true
50
47
  end
51
48
 
52
- def display_help_for_command command_name
53
- command = @commands[command_name]
54
- if command
55
- @io.say "Command \"#{command_name}\""
56
- @io.say "Usage: #{command_name} #{command.usage}" if command.respond_to?(:usage)
57
- @io.say "Help:\n #{command.help}" if command.respond_to?(:help)
58
- else
59
- @io.say "no help available for command \"#{command_name}\""
60
- end
49
+ def abort?
50
+ @abort
61
51
  end
62
52
 
63
- def process_help command=nil
64
- if command
65
- display_help_for_command command
66
- else
67
- @io.say "Available commands:"
68
- @commands.keys.sort.each { |command| @io.say command }
69
- @io.say
70
- end
53
+ def add_command command, *aliases
54
+ @commands ||= {}
55
+ aliases.each {|a| @commands[a] = command}
71
56
  end
72
57
 
73
- def process_command name, parameter=nil
74
- if ['?', 'help'].include?(name)
75
- process_help parameter
76
- return
77
- end
78
- if @commands[name]
79
- @commands[name].execute parameter
80
- else
81
- @io.say "unknown command \"#{name}\""
58
+ def push
59
+ @prompt ||= ' > '
60
+ add_command HelpCommand.new(@commands), '?', 'help'
61
+ add_command ExitCommand.new(self), 'exit', 'quit'
62
+ begin
63
+ until abort?
64
+ refresh
65
+ line = Readline.readline(@prompt, true)
66
+ if line
67
+ first, rest = head_tail(line)
68
+ log "looking for command \"#{first}\" with parameter \"#{rest}\""
69
+ if @commands[first]
70
+ @commands[first].execute rest
71
+ else
72
+ puts "unknown command \"#{first}\""
73
+ end
74
+ else
75
+ abort!
76
+ end
77
+ puts
78
+ end
79
+ rescue Interrupt => e
80
+ puts
82
81
  end
83
82
  end
84
83
  end
@@ -0,0 +1,15 @@
1
+ module ShellShock
2
+ class ExitCommand
3
+ attr_reader :help, :usage
4
+
5
+ def initialize context
6
+ @context = context
7
+ @usage = ''
8
+ @help = 'exits the current context'
9
+ end
10
+
11
+ def execute ignore
12
+ @context.abort!
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,36 @@
1
+ module ShellShock
2
+ class HelpCommand
3
+ attr_reader :help, :usage
4
+
5
+ def initialize commands
6
+ @commands = commands
7
+ @usage = '<command name>'
8
+ @help = 'displays the help information for a command'
9
+ end
10
+
11
+ def completion text
12
+ @commands.keys.grep(/^#{Regexp.escape(text)}/).sort
13
+ end
14
+
15
+ def execute command
16
+ command.empty? ? display_help_for_commands : display_help_for_command(command)
17
+ end
18
+
19
+ def display_help_for_commands
20
+ return if @commands.keys.empty?
21
+ puts 'Available commands:'
22
+ @commands.keys.sort.each { |command| puts command }
23
+ end
24
+
25
+ def display_help_for_command command_name
26
+ command = @commands[command_name]
27
+ if command
28
+ puts "Command \"#{command_name}\""
29
+ puts "Usage: #{command_name} #{command.usage}" if command.respond_to?(:usage)
30
+ puts "Help:\n #{command.help}" if command.respond_to?(:help)
31
+ else
32
+ puts "unknown command \"#{command_name}\""
33
+ end
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,10 @@
1
+ module ShellShock
2
+ module Logger
3
+ def log message
4
+ return unless ENV['LOG_PATH']
5
+ File.open(ENV['LOG_PATH'], 'a') do |file|
6
+ file.puts message
7
+ end
8
+ end
9
+ end
10
+ end
metadata CHANGED
@@ -1,12 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: shell_shock
3
3
  version: !ruby/object:Gem::Version
4
+ hash: 23
4
5
  prerelease: false
5
6
  segments:
6
7
  - 0
7
8
  - 0
8
- - 3
9
- version: 0.0.3
9
+ - 4
10
+ version: 0.0.4
10
11
  platform: ruby
11
12
  authors:
12
13
  - Mark Ryall
@@ -14,16 +15,18 @@ autorequire:
14
15
  bindir: bin
15
16
  cert_chain: []
16
17
 
17
- date: 2010-06-15 00:00:00 +10:00
18
+ date: 2010-10-24 00:00:00 +10:00
18
19
  default_executable:
19
20
  dependencies:
20
21
  - !ruby/object:Gem::Dependency
21
22
  name: rake
22
23
  prerelease: false
23
24
  requirement: &id001 !ruby/object:Gem::Requirement
25
+ none: false
24
26
  requirements:
25
27
  - - ~>
26
28
  - !ruby/object:Gem::Version
29
+ hash: 49
27
30
  segments:
28
31
  - 0
29
32
  - 8
@@ -35,16 +38,34 @@ dependencies:
35
38
  name: gemesis
36
39
  prerelease: false
37
40
  requirement: &id002 !ruby/object:Gem::Requirement
41
+ none: false
38
42
  requirements:
39
43
  - - ~>
40
44
  - !ruby/object:Gem::Version
45
+ hash: 23
41
46
  segments:
42
47
  - 0
43
48
  - 0
44
- - 3
45
- version: 0.0.3
49
+ - 4
50
+ version: 0.0.4
46
51
  type: :development
47
52
  version_requirements: *id002
53
+ - !ruby/object:Gem::Dependency
54
+ name: rspec
55
+ prerelease: false
56
+ requirement: &id003 !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ~>
60
+ - !ruby/object:Gem::Version
61
+ hash: 13
62
+ segments:
63
+ - 2
64
+ - 0
65
+ - 1
66
+ version: 2.0.1
67
+ type: :development
68
+ version_requirements: *id003
48
69
  description: |
49
70
  This is just some code extracted from a few command line gems i've created (shh and cardigan).
50
71
 
@@ -58,7 +79,11 @@ extensions: []
58
79
  extra_rdoc_files: []
59
80
 
60
81
  files:
82
+ - lib/shell_shock/logger.rb
83
+ - lib/shell_shock/exit_command.rb
84
+ - lib/shell_shock/help_command.rb
61
85
  - lib/shell_shock/context.rb
86
+ - lib/shell_shock/command_spec.rb
62
87
  - README.rdoc
63
88
  - MIT-LICENSE
64
89
  has_rdoc: true
@@ -71,23 +96,27 @@ rdoc_options: []
71
96
  require_paths:
72
97
  - lib
73
98
  required_ruby_version: !ruby/object:Gem::Requirement
99
+ none: false
74
100
  requirements:
75
101
  - - ">="
76
102
  - !ruby/object:Gem::Version
103
+ hash: 3
77
104
  segments:
78
105
  - 0
79
106
  version: "0"
80
107
  required_rubygems_version: !ruby/object:Gem::Requirement
108
+ none: false
81
109
  requirements:
82
110
  - - ">="
83
111
  - !ruby/object:Gem::Version
112
+ hash: 3
84
113
  segments:
85
114
  - 0
86
115
  version: "0"
87
116
  requirements: []
88
117
 
89
118
  rubyforge_project:
90
- rubygems_version: 1.3.6
119
+ rubygems_version: 1.3.7
91
120
  signing_key:
92
121
  specification_version: 3
93
122
  summary: library for creating simple shell applications using readline