nscript 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 7d487c1f30024a94c47f95fe6241322741e10c9df7a96655492bcb5a93e9c9ad
4
+ data.tar.gz: 522f48639a5bcffbdecc19767c85e4c352b7ca72b722fd8bf915802ea2543b91
5
+ SHA512:
6
+ metadata.gz: 51625e11380e44d92064ae1f7b8797edc56ccd82d7163cf66e59214a5e98377b127804388862ae18c5027ee7142f245f594191efe6a40bc3505c6d6c29610c9c
7
+ data.tar.gz: 6f19c41ef4ffa3fad5205e3c6bf03c289163768e0f194c43e7df241b99af658af112b9aea66196bd8cc6fd1e68301a131be020e78958f10ee73e48ed3532b0a6
data/.gitignore ADDED
@@ -0,0 +1,11 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /_yardoc/
4
+ /coverage/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
9
+
10
+ # rspec failure tracking
11
+ .rspec_status
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --format documentation
2
+ --color
3
+ --require spec_helper
data/.travis.yml ADDED
@@ -0,0 +1,5 @@
1
+ sudo: false
2
+ language: ruby
3
+ rvm:
4
+ - 2.5.1
5
+ before_install: gem install bundler -v 1.16.1
@@ -0,0 +1,74 @@
1
+ # Contributor Covenant Code of Conduct
2
+
3
+ ## Our Pledge
4
+
5
+ In the interest of fostering an open and welcoming environment, we as
6
+ contributors and maintainers pledge to making participation in our project and
7
+ our community a harassment-free experience for everyone, regardless of age, body
8
+ size, disability, ethnicity, gender identity and expression, level of experience,
9
+ nationality, personal appearance, race, religion, or sexual identity and
10
+ orientation.
11
+
12
+ ## Our Standards
13
+
14
+ Examples of behavior that contributes to creating a positive environment
15
+ include:
16
+
17
+ * Using welcoming and inclusive language
18
+ * Being respectful of differing viewpoints and experiences
19
+ * Gracefully accepting constructive criticism
20
+ * Focusing on what is best for the community
21
+ * Showing empathy towards other community members
22
+
23
+ Examples of unacceptable behavior by participants include:
24
+
25
+ * The use of sexualized language or imagery and unwelcome sexual attention or
26
+ advances
27
+ * Trolling, insulting/derogatory comments, and personal or political attacks
28
+ * Public or private harassment
29
+ * Publishing others' private information, such as a physical or electronic
30
+ address, without explicit permission
31
+ * Other conduct which could reasonably be considered inappropriate in a
32
+ professional setting
33
+
34
+ ## Our Responsibilities
35
+
36
+ Project maintainers are responsible for clarifying the standards of acceptable
37
+ behavior and are expected to take appropriate and fair corrective action in
38
+ response to any instances of unacceptable behavior.
39
+
40
+ Project maintainers have the right and responsibility to remove, edit, or
41
+ reject comments, commits, code, wiki edits, issues, and other contributions
42
+ that are not aligned to this Code of Conduct, or to ban temporarily or
43
+ permanently any contributor for other behaviors that they deem inappropriate,
44
+ threatening, offensive, or harmful.
45
+
46
+ ## Scope
47
+
48
+ This Code of Conduct applies both within project spaces and in public spaces
49
+ when an individual is representing the project or its community. Examples of
50
+ representing a project or community include using an official project e-mail
51
+ address, posting via an official social media account, or acting as an appointed
52
+ representative at an online or offline event. Representation of a project may be
53
+ further defined and clarified by project maintainers.
54
+
55
+ ## Enforcement
56
+
57
+ Instances of abusive, harassing, or otherwise unacceptable behavior may be
58
+ reported by contacting the project team at stormburpee@gmail.com. All
59
+ complaints will be reviewed and investigated and will result in a response that
60
+ is deemed necessary and appropriate to the circumstances. The project team is
61
+ obligated to maintain confidentiality with regard to the reporter of an incident.
62
+ Further details of specific enforcement policies may be posted separately.
63
+
64
+ Project maintainers who do not follow or enforce the Code of Conduct in good
65
+ faith may face temporary or permanent repercussions as determined by other
66
+ members of the project's leadership.
67
+
68
+ ## Attribution
69
+
70
+ This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
71
+ available at [http://contributor-covenant.org/version/1/4][version]
72
+
73
+ [homepage]: http://contributor-covenant.org
74
+ [version]: http://contributor-covenant.org/version/1/4/
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ source "https://rubygems.org"
2
+
3
+ git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
4
+
5
+ # Specify your gem's dependencies in nscript.gemspec
6
+ gemspec
data/Gemfile.lock ADDED
@@ -0,0 +1,35 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ nscript (0.1.0)
5
+
6
+ GEM
7
+ remote: https://rubygems.org/
8
+ specs:
9
+ diff-lcs (1.3)
10
+ rake (10.5.0)
11
+ rspec (3.7.0)
12
+ rspec-core (~> 3.7.0)
13
+ rspec-expectations (~> 3.7.0)
14
+ rspec-mocks (~> 3.7.0)
15
+ rspec-core (3.7.1)
16
+ rspec-support (~> 3.7.0)
17
+ rspec-expectations (3.7.0)
18
+ diff-lcs (>= 1.2.0, < 2.0)
19
+ rspec-support (~> 3.7.0)
20
+ rspec-mocks (3.7.0)
21
+ diff-lcs (>= 1.2.0, < 2.0)
22
+ rspec-support (~> 3.7.0)
23
+ rspec-support (3.7.1)
24
+
25
+ PLATFORMS
26
+ ruby
27
+
28
+ DEPENDENCIES
29
+ bundler (~> 1.16)
30
+ nscript!
31
+ rake (~> 10.0)
32
+ rspec (~> 3.0)
33
+
34
+ BUNDLED WITH
35
+ 1.16.1
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2018 Storm Burpee
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,43 @@
1
+ # Nscript
2
+
3
+ Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/nscript`. To experiment with that code, run `bin/console` for an interactive prompt.
4
+
5
+ TODO: Delete this and the text above, and describe your gem
6
+
7
+ ## Installation
8
+
9
+ Add this line to your application's Gemfile:
10
+
11
+ ```ruby
12
+ gem 'nscript'
13
+ ```
14
+
15
+ And then execute:
16
+
17
+ $ bundle
18
+
19
+ Or install it yourself as:
20
+
21
+ $ gem install nscript
22
+
23
+ ## Usage
24
+
25
+ TODO: Write usage instructions here
26
+
27
+ ## Development
28
+
29
+ After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
30
+
31
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
32
+
33
+ ## Contributing
34
+
35
+ Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/nscript. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the [Contributor Covenant](http://contributor-covenant.org) code of conduct.
36
+
37
+ ## License
38
+
39
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
40
+
41
+ ## Code of Conduct
42
+
43
+ Everyone interacting in the Nscript project’s codebases, issue trackers, chat rooms and mailing lists is expected to follow the [code of conduct](https://github.com/[USERNAME]/nscript/blob/master/CODE_OF_CONDUCT.md).
data/Rakefile ADDED
@@ -0,0 +1,6 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+
6
+ task :default => :spec
data/bin/nscript ADDED
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "#{File.dirname(__FILE__)}/../lib/nscript/command_line.rb"
4
+
5
+ NScript::CommandLine.new
data/examples/code.ns ADDED
@@ -0,0 +1,173 @@
1
+ # Functions:
2
+ square: (x) -> x * x
3
+
4
+ sum: (x, y) -> x + y
5
+
6
+ odd: (x) -> x % 2 isnt 0
7
+
8
+ even: (x) -> x % 2 is 0
9
+
10
+ run_loop: ->
11
+ fire_events((e) -> e.stopPropagation())
12
+ listen()
13
+ wait()
14
+
15
+ # Objects:
16
+ dense_object_literal: {one: 1, two: 2, three: 3}
17
+
18
+ spaced_out_multiline_object: {
19
+ pi: 3.14159
20
+ list: [1, 2, 3, 4]
21
+ regex: /match[ing](every|thing|\/)/gi
22
+ three: new Idea()
23
+
24
+ inner_obj: {
25
+ freedom: -> _.freedom()
26
+ }
27
+ }
28
+
29
+ # Arrays:
30
+ stooges: [{moe: 45}, {curly: 43}, {larry: 46}]
31
+
32
+ exponents: [(x) -> x, (x) -> x * x, (x) -> x * x * x]
33
+
34
+ empty: []
35
+
36
+ multiline: [
37
+ 'line one'
38
+ 'line two'
39
+ ]
40
+
41
+ # Conditionals and ternaries.
42
+ if submarine.shields_up
43
+ full_speed_ahead()
44
+ fire_torpedos()
45
+ else if submarine.sinking
46
+ abandon_ship()
47
+ else
48
+ run_away()
49
+
50
+ eldest: if 25 > 21 then liz else marge
51
+
52
+ decoration: medal_of_honor if war_hero
53
+
54
+ go_to_sleep() unless coffee
55
+
56
+ # Returning early:
57
+ race: ->
58
+ run()
59
+ walk()
60
+ crawl()
61
+ if tired then return sleep()
62
+ race()
63
+
64
+ # Conditional assignment:
65
+ good ||= evil
66
+ wine &&= cheese
67
+
68
+ # Nested property access and calls.
69
+ ((moon.turn(360))).shapes[3].move({x: 45, y: 30}).position['top'].offset('x')
70
+
71
+ a: b: c: 5
72
+
73
+ # Embedded JavaScript.
74
+ callback(
75
+ `function(e) { e.stop(); }`
76
+ )
77
+
78
+ # Try/Catch/Finally/Throw.
79
+ try
80
+ all_hell_breaks_loose()
81
+ dogs_and_cats_living_together()
82
+ throw "up"
83
+ catch error
84
+ print(error)
85
+ finally
86
+ clean_up()
87
+
88
+ try all_hell_breaks_loose() catch error then print(error) finally clean_up()
89
+
90
+ # While loops, break and continue.
91
+ while demand > supply
92
+ sell()
93
+ restock()
94
+
95
+ while supply > demand then buy()
96
+
97
+ while true
98
+ break if broken
99
+ continue if continuing
100
+
101
+ # Unary operators.
102
+ !!true
103
+
104
+ # Lexical scoping.
105
+ v_1: 5
106
+ change_a_and_set_b: ->
107
+ v_1: 10
108
+ v_2: 15
109
+ v_2: 20
110
+
111
+ # Array comprehensions.
112
+ supper: food.capitalize() for food in ['toast', 'cheese', 'wine']
113
+
114
+ drink(bottle) for bottle, i in ['soda', 'wine', 'lemonade'] when even(i)
115
+
116
+ # Switch statements ("else" serves as a default).
117
+ activity: switch day
118
+ when "Tuesday" then eat_breakfast()
119
+ when "Sunday" then go_to_church()
120
+ when "Saturday" then go_to_the_park()
121
+ when "Wednesday"
122
+ if day is bingo_day
123
+ go_to_bingo()
124
+ else
125
+ eat_breakfast()
126
+ go_to_work()
127
+ eat_dinner()
128
+ else go_to_work()
129
+
130
+ # Semicolons can optionally be used instead of newlines.
131
+ wednesday: -> eat_breakfast(); go_to_work(); eat_dinner()
132
+
133
+ # Array slice literals.
134
+ zero_to_nine: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
135
+ three_to_six: zero_to_nine[3..6]
136
+
137
+ # Multiline strings with inner quotes.
138
+ story: "Lorem ipsum dolor \"sit\" amet, consectetuer adipiscing elit,
139
+ sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna
140
+ aliquam erat volutpat. Ut wisi enim ad."
141
+
142
+ # Inheritance and calling super.
143
+ Animal: ->
144
+ Animal::move: (meters) ->
145
+ alert(this.name + " moved " + meters + "m.")
146
+
147
+ Snake: (name) -> this.name: name
148
+ Snake extends Animal
149
+ Snake::move: ->
150
+ alert('Slithering...')
151
+ super(5)
152
+
153
+ Horse: (name) -> this.name: name
154
+ Horse extends Animal
155
+ Horse::move: ->
156
+ alert('Galloping...')
157
+ super(45)
158
+
159
+ sam: new Snake("Sammy the Snake")
160
+ tom: new Horse("Tommy the Horse")
161
+
162
+ sam.move()
163
+ tom.move()
164
+
165
+ # Numbers.
166
+ a_googol: 1e100
167
+ hex: 0xff0000
168
+ negative: -1.0
169
+ infinity: Infinity
170
+ nan: NaN
171
+
172
+ # Deleting.
173
+ delete secret.identity
@@ -0,0 +1,6 @@
1
+ Hello: ->
2
+ Hello::world: ->
3
+ console.log("Hello, World!")
4
+
5
+ hello: new Hello()
6
+ hello.world()
@@ -0,0 +1,235 @@
1
+ require 'optparse'
2
+ require 'fileutils'
3
+ require 'open3'
4
+ begin
5
+ require File.expand_path(File.dirname(__FILE__) + '/../nscript')
6
+ rescue LoadError => e
7
+ puts(e.message)
8
+ puts("use \"rake build:parser\" to regenerate parser.rb")
9
+ exit(1)
10
+ end
11
+
12
+ module NScript
13
+
14
+ # The CommandLine handles all of the functionality of the `nscript`
15
+ # utility.
16
+ class CommandLine
17
+
18
+ BANNER = <<-EOS
19
+ nscript compiles NScript source files into JavaScript.
20
+
21
+ Usage:
22
+ nscript path/to/script.ns
23
+ EOS
24
+
25
+ # Seconds to pause between checks for changed source files.
26
+ WATCH_INTERVAL = 0.5
27
+
28
+ # Path to the root of the NScript install.
29
+ ROOT = File.expand_path(File.dirname(__FILE__) + '/../..')
30
+
31
+ # Commands to execute NScripts.
32
+ RUNNERS = {
33
+ :node => "node #{ROOT}/lib/nscript/runner.js",
34
+ :narwhal => "narwhal -p #{ROOT} -e 'require(\"nscript\").run(system.args);'"
35
+ }
36
+
37
+ # Run the CommandLine off the contents of ARGV.
38
+ def initialize
39
+ @mtimes = {}
40
+ parse_options
41
+ return launch_repl if @options[:interactive]
42
+ return eval_scriptlet if @options[:eval]
43
+ check_sources
44
+ return run_scripts if @options[:run]
45
+ @sources.each {|source| compile_javascript(source) }
46
+ watch_nscript_scripts if @options[:watch]
47
+ end
48
+
49
+ # The "--help" usage message.
50
+ def usage
51
+ puts "\n#{@option_parser}\n"
52
+ exit
53
+ end
54
+
55
+
56
+ private
57
+
58
+ # Compiles (or partially compiles) the source NScript file, returning
59
+ # the desired JS, tokens, or lint results.
60
+ def compile_javascript(source)
61
+ script = File.read(source)
62
+ return tokens(script) if @options[:tokens]
63
+ js = compile(script, source)
64
+ return unless js
65
+ return puts(js) if @options[:print]
66
+ return lint(js) if @options[:lint]
67
+ File.open(path_for(source), 'w+') {|f| f.write(js) }
68
+ end
69
+
70
+ # Spins up a watcher thread to keep track of the modification times of the
71
+ # source files, recompiling them whenever they're saved.
72
+ def watch_nscript_scripts
73
+ watch_thread = Thread.start do
74
+ loop do
75
+ @sources.each do |source|
76
+ mtime = File.stat(source).mtime
77
+ @mtimes[source] ||= mtime
78
+ if mtime > @mtimes[source]
79
+ @mtimes[source] = mtime
80
+ compile_javascript(source)
81
+ end
82
+ end
83
+ sleep WATCH_INTERVAL
84
+ end
85
+ end
86
+ Signal.trap("INT") { watch_thread.kill }
87
+ watch_thread.join
88
+ end
89
+
90
+ # Ensure that all of the source files exist.
91
+ def check_sources
92
+ usage if @sources.empty?
93
+ missing = @sources.detect {|s| !File.exists?(s) }
94
+ if missing
95
+ STDERR.puts("File not found: '#{missing}'")
96
+ exit(1)
97
+ end
98
+ end
99
+
100
+ # Pipe compiled JS through JSLint (requires a working 'jsl' command).
101
+ def lint(js)
102
+ stdin, stdout, stderr = Open3.popen3('jsl -nologo -stdin')
103
+ stdin.write(js)
104
+ stdin.close
105
+ puts stdout.read.tr("\n", '')
106
+ errs = stderr.read.chomp
107
+ puts errs unless errs.empty?
108
+ stdout.close and stderr.close
109
+ end
110
+
111
+ # Eval a little piece of NScript directly from the command line.
112
+ def eval_scriptlet
113
+ script = STDIN.tty? ? @sources.join(' ') : STDIN.read
114
+ return tokens(script) if @options[:tokens]
115
+ js = compile(script)
116
+ return lint(js) if @options[:lint]
117
+ puts js
118
+ end
119
+
120
+ # Use Node.js or Narwhal to run an interactive NScript session.
121
+ def launch_repl
122
+ exec "#{RUNNERS[@options[:runner]]}"
123
+ rescue Errno::ENOENT
124
+ puts "Error: #{@options[:runner]} must be installed to use the interactive REPL."
125
+ exit(1)
126
+ end
127
+
128
+ # Use Node.js or Narwhal to compile and execute NScripts.
129
+ def run_scripts
130
+ sources = @sources.join(' ')
131
+ exec "#{RUNNERS[@options[:runner]]} #{sources}"
132
+ rescue Errno::ENOENT
133
+ puts "Error: #{@options[:runner]} must be installed in order to execute scripts."
134
+ exit(1)
135
+ end
136
+
137
+ # Print the tokens that the lexer generates from a source script.
138
+ def tokens(script)
139
+ puts Lexer.new.tokenize(script).inspect
140
+ end
141
+
142
+ # Compile a single source file to JavaScript.
143
+ def compile(script, source='error')
144
+ begin
145
+ options = {}
146
+ options[:no_wrap] = true if @options[:no_wrap]
147
+ options[:globals] = true if @options[:globals]
148
+ NScript.compile(script, options)
149
+ rescue NScript::ParseError => e
150
+ STDERR.puts "#{source}: #{e.message}"
151
+ exit(1) unless @options[:watch]
152
+ nil
153
+ end
154
+ end
155
+
156
+ # Write out JavaScript alongside NScript unless an output directory
157
+ # is specified.
158
+ def path_for(source)
159
+ filename = File.basename(source, File.extname(source)) + '.js'
160
+ dir = @options[:output] || File.dirname(source)
161
+ File.join(dir, filename)
162
+ end
163
+
164
+ # Install the NScript TextMate bundle to ~/Library.
165
+ def install_bundle
166
+ bundle_dir = File.expand_path('~/Library/Application Support/TextMate/Bundles/')
167
+ FileUtils.cp_r("#{ROOT}/extras/NScript.tmbundle", bundle_dir)
168
+ end
169
+
170
+ # Use OptionParser for all the options.
171
+ def parse_options
172
+ @options = {:runner => :node}
173
+ @option_parser = OptionParser.new do |opts|
174
+ opts.on('-i', '--interactive', 'run an interactive NScript REPL') do |i|
175
+ @options[:interactive] = true
176
+ end
177
+ opts.on('-r', '--run', 'compile and run a NScript') do |r|
178
+ @options[:run] = true
179
+ end
180
+ opts.on('-o', '--output [DIR]', 'set the directory for compiled JavaScript') do |d|
181
+ @options[:output] = d
182
+ FileUtils.mkdir_p(d) unless File.exists?(d)
183
+ end
184
+ opts.on('-w', '--watch', 'watch scripts for changes, and recompile') do |w|
185
+ @options[:watch] = true
186
+ end
187
+ opts.on('-p', '--print', 'print the compiled JavaScript to stdout') do |d|
188
+ @options[:print] = true
189
+ end
190
+ opts.on('-l', '--lint', 'pipe the compiled JavaScript through JSLint') do |l|
191
+ @options[:lint] = true
192
+ end
193
+ opts.on('-e', '--eval', 'compile a cli scriptlet or read from stdin') do |e|
194
+ @options[:eval] = true
195
+ end
196
+ opts.on('-t', '--tokens', 'print the tokens that the lexer produces') do |t|
197
+ @options[:tokens] = true
198
+ end
199
+ opts.on('-v', '--verbose', 'print at every step of code generation') do |v|
200
+ ENV['VERBOSE'] = 'true'
201
+ end
202
+ opts.on('-n', '--no-wrap', 'raw output, no function safety wrapper') do |n|
203
+ @options[:no_wrap] = true
204
+ end
205
+ opts.on('-g', '--globals', 'attach all top-level variable as globals') do |n|
206
+ @options[:globals] = true
207
+ end
208
+ opts.on_tail('--narwhal', 'use Narwhal instead of Node.js') do |n|
209
+ @options[:runner] = :narwhal
210
+ end
211
+ opts.on_tail('--install-bundle', 'install the NScript TextMate bundle') do |i|
212
+ install_bundle
213
+ exit
214
+ end
215
+ opts.on_tail('--version', 'display NScript version') do
216
+ puts "NScript version #{NScript::VERSION}"
217
+ exit
218
+ end
219
+ opts.on_tail('-h', '--help', 'display this help message') do
220
+ usage
221
+ end
222
+ end
223
+ @option_parser.banner = BANNER
224
+ begin
225
+ @option_parser.parse!(ARGV)
226
+ rescue OptionParser::InvalidOption => e
227
+ puts e.message
228
+ exit(1)
229
+ end
230
+ @sources = ARGV
231
+ end
232
+
233
+ end
234
+
235
+ end