ore 0.1.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (107) hide show
  1. data/.document +4 -0
  2. data/.rspec +1 -0
  3. data/.yardopts +1 -0
  4. data/ChangeLog.md +31 -0
  5. data/GemspecYML.md +252 -0
  6. data/LICENSE.txt +21 -0
  7. data/README.md +104 -0
  8. data/Rakefile +9 -0
  9. data/bin/mine +12 -0
  10. data/bin/ore +12 -0
  11. data/data/ore/templates/base/.document +3 -0
  12. data/data/ore/templates/base/.gitignore.erb +3 -0
  13. data/data/ore/templates/base/:name:.gemspec.erb +10 -0
  14. data/data/ore/templates/base/ChangeLog.md.erb +4 -0
  15. data/data/ore/templates/base/ChangeLog.rdoc.erb +4 -0
  16. data/data/ore/templates/base/ChangeLog.tt.erb +4 -0
  17. data/data/ore/templates/base/LICENSE.txt.erb +20 -0
  18. data/data/ore/templates/base/README.md.erb +42 -0
  19. data/data/ore/templates/base/README.rdoc.erb +38 -0
  20. data/data/ore/templates/base/README.tt.erb +44 -0
  21. data/data/ore/templates/base/Rakefile.erb +23 -0
  22. data/data/ore/templates/base/gemspec.yml.erb +23 -0
  23. data/data/ore/templates/base/lib/:namespace_dir:.rb.erb +1 -0
  24. data/data/ore/templates/base/lib/:namespace_dir:/version.rb.erb +8 -0
  25. data/data/ore/templates/bundler/Gemfile.erb +20 -0
  26. data/data/ore/templates/bundler/_dependencies.erb +1 -0
  27. data/data/ore/templates/jeweler_tasks/_dependencies.erb +3 -0
  28. data/data/ore/templates/jeweler_tasks/_tasks.erb +17 -0
  29. data/data/ore/templates/ore_tasks/_dependencies.erb +1 -0
  30. data/data/ore/templates/ore_tasks/_tasks.erb +12 -0
  31. data/data/ore/templates/rdoc/_tasks.erb +6 -0
  32. data/data/ore/templates/rspec/.rspec +1 -0
  33. data/data/ore/templates/rspec/_dependencies.erb +3 -0
  34. data/data/ore/templates/rspec/_tasks.erb +14 -0
  35. data/data/ore/templates/rspec/spec/:namespace_dir:_spec.rb.erb +8 -0
  36. data/data/ore/templates/rspec/spec/spec_helper.rb.erb +7 -0
  37. data/data/ore/templates/test_unit/test/helper.rb.erb +24 -0
  38. data/data/ore/templates/test_unit/test/test_:name:.rb.erb +5 -0
  39. data/data/ore/templates/yard/.yardopts.erb +1 -0
  40. data/data/ore/templates/yard/_dependencies.erb +1 -0
  41. data/data/ore/templates/yard/_gem.erb +1 -0
  42. data/data/ore/templates/yard/_tasks.erb +13 -0
  43. data/gemspec.yml +21 -0
  44. data/lib/ore.rb +3 -0
  45. data/lib/ore/checks.rb +85 -0
  46. data/lib/ore/cli.rb +120 -0
  47. data/lib/ore/config.rb +52 -0
  48. data/lib/ore/defaults.rb +137 -0
  49. data/lib/ore/dependency.rb +62 -0
  50. data/lib/ore/document_file.rb +118 -0
  51. data/lib/ore/exceptions.rb +3 -0
  52. data/lib/ore/exceptions/exception.rb +4 -0
  53. data/lib/ore/exceptions/invalid_metadata.rb +6 -0
  54. data/lib/ore/exceptions/project_not_found.rb +6 -0
  55. data/lib/ore/generator.rb +247 -0
  56. data/lib/ore/naming.rb +95 -0
  57. data/lib/ore/paths.rb +143 -0
  58. data/lib/ore/project.rb +568 -0
  59. data/lib/ore/settings.rb +236 -0
  60. data/lib/ore/specification.rb +29 -0
  61. data/lib/ore/template.rb +3 -0
  62. data/lib/ore/template/directory.rb +179 -0
  63. data/lib/ore/template/helpers.rb +144 -0
  64. data/lib/ore/template/interpolations.rb +31 -0
  65. data/lib/ore/versions.rb +3 -0
  66. data/lib/ore/versions/exceptions.rb +1 -0
  67. data/lib/ore/versions/exceptions/invalid_version.rb +8 -0
  68. data/lib/ore/versions/version.rb +75 -0
  69. data/lib/ore/versions/version_constant.rb +126 -0
  70. data/lib/ore/versions/version_file.rb +66 -0
  71. data/lib/rubygems_plugin.rb +40 -0
  72. data/ore.gemspec +6 -0
  73. data/spec/dependency_spec.rb +36 -0
  74. data/spec/document_file_spec.rb +29 -0
  75. data/spec/helpers/files.rb +7 -0
  76. data/spec/helpers/files/.document +5 -0
  77. data/spec/helpers/files/VERSION +1 -0
  78. data/spec/helpers/files/VERSION.yml +5 -0
  79. data/spec/helpers/projects.rb +13 -0
  80. data/spec/helpers/projects/dm-plugin/Gemfile +3 -0
  81. data/spec/helpers/projects/dm-plugin/VERSION +1 -0
  82. data/spec/helpers/projects/dm-plugin/dm-plugin.gemspec +10 -0
  83. data/spec/helpers/projects/dm-plugin/gemspec.yml +7 -0
  84. data/spec/helpers/projects/dm-plugin/lib/dm-plugin.rb +1 -0
  85. data/spec/helpers/projects/explicit/gemspec.yml +10 -0
  86. data/spec/helpers/projects/explicit/lib/explicit/version.rb +15 -0
  87. data/spec/helpers/projects/ffi-binding/gemspec.yml +7 -0
  88. data/spec/helpers/projects/ffi-binding/lib/ffi/binding/version.rb +5 -0
  89. data/spec/helpers/projects/jewelery/VERSION +1 -0
  90. data/spec/helpers/projects/jewelery/bin/jewelery +3 -0
  91. data/spec/helpers/projects/jewelery/gemspec.yml +4 -0
  92. data/spec/helpers/projects/jewelery/jewelery.gemspec +10 -0
  93. data/spec/helpers/projects/jewelery/lib/jewelery.rb +4 -0
  94. data/spec/helpers/projects/jewelery/lib/jewelery/rubies.rb +4 -0
  95. data/spec/helpers/projects/minimal/gemspec.yml +4 -0
  96. data/spec/helpers/projects/minimal/lib/minimal.rb +2 -0
  97. data/spec/naming_spec.rb +48 -0
  98. data/spec/projects/dm_plugin_project_spec.rb +29 -0
  99. data/spec/projects/explicit_project_spec.rb +33 -0
  100. data/spec/projects/ffi_binding_project_spec.rb +21 -0
  101. data/spec/projects/jeweler_project_spec.rb +17 -0
  102. data/spec/projects/minimal_project_spec.rb +17 -0
  103. data/spec/projects/project_examples.rb +34 -0
  104. data/spec/spec_helper.rb +4 -0
  105. data/spec/versions/version_file_spec.rb +28 -0
  106. data/spec/versions/version_spec.rb +53 -0
  107. metadata +226 -0
@@ -0,0 +1,118 @@
1
+ require 'set'
2
+
3
+ module Ore
4
+ #
5
+ # Parses the contents of a `.document`.
6
+ #
7
+ class DocumentFile
8
+
9
+ # The path to the `.document` file.
10
+ attr_reader :path
11
+
12
+ # The glob-patterns to find all code-files.
13
+ attr_reader :file_globs
14
+
15
+ # The glob-patterns to find all extra-files.
16
+ attr_reader :extra_file_globs
17
+
18
+ #
19
+ # Creates a new {DocumentFile}.
20
+ #
21
+ # @param [String] path
22
+ # The path of the `.document` file.
23
+ #
24
+ def initialize(path)
25
+ @path = File.expand_path(path)
26
+
27
+ @file_globs = Set[]
28
+ @extra_file_globs = Set[]
29
+
30
+ parse!
31
+ end
32
+
33
+ @@file = '.document'
34
+
35
+ #
36
+ # Finds the document file in a project.
37
+ #
38
+ # @param [Project] project
39
+ # The project to search within.
40
+ #
41
+ # @return [DocumentFile, nil]
42
+ # The found document file.
43
+ #
44
+ def self.find(project)
45
+ self.new(project.path(@@file)) if project.file?(@@file)
46
+ end
47
+
48
+ #
49
+ # All files described in the `.document` file.
50
+ #
51
+ # @yield [path]
52
+ # The given block will be passed every path that matches the file
53
+ # globs in the `.document` file.
54
+ #
55
+ # @yieldparam [String] path
56
+ # A match that matches the `.document` file patterns.
57
+ #
58
+ # @return [Enumerator]
59
+ # If no block was given, an enumerator object will be returned.
60
+ #
61
+ def each_file(&block)
62
+ return enum_for(:each_file) unless block
63
+
64
+ @file_globs.each do |pattern|
65
+ Dir.glob(pattern,&block)
66
+ end
67
+ end
68
+
69
+ #
70
+ # All extra-files described in the `.document` file.
71
+ #
72
+ # @yield [path]
73
+ # The given block will be passed every path that matches the
74
+ # extra-file globs in the `.document` file.
75
+ #
76
+ # @yieldparam [String] path
77
+ # A match that matches the `.document` extra-file patterns.
78
+ #
79
+ # @return [Enumerator]
80
+ # If no block was given, an enumerator object will be returned.
81
+ #
82
+ def each_extra_file(&block)
83
+ return enum_for(:each_extra_file) unless block
84
+
85
+ @extra_file_globs.each do |pattern|
86
+ Dir.glob(pattern,&block)
87
+ end
88
+ end
89
+
90
+ protected
91
+
92
+ #
93
+ # Parses the contents of a `.document` file.
94
+ #
95
+ def parse!
96
+ separator = false
97
+
98
+ File.open(@path) do |file|
99
+ file.each_line do |line|
100
+ line = line.chomp.strip
101
+
102
+ next if line.empty?
103
+
104
+ unless separator
105
+ if line == '-'
106
+ separator = true
107
+ else
108
+ @file_globs << line
109
+ end
110
+ else
111
+ @extra_file_globs << line
112
+ end
113
+ end
114
+ end
115
+ end
116
+
117
+ end
118
+ end
@@ -0,0 +1,3 @@
1
+ require 'ore/exceptions/exception'
2
+ require 'ore/exceptions/project_not_found'
3
+ require 'ore/exceptions/invalid_metadata'
@@ -0,0 +1,4 @@
1
+ module Ore
2
+ class Exception < RuntimeError
3
+ end
4
+ end
@@ -0,0 +1,6 @@
1
+ require 'ore/exceptions/exception'
2
+
3
+ module Ore
4
+ class InvalidMetadata < Exception
5
+ end
6
+ end
@@ -0,0 +1,6 @@
1
+ require 'ore/exceptions/exception'
2
+
3
+ module Ore
4
+ class ProjectNotFound < Exception
5
+ end
6
+ end
@@ -0,0 +1,247 @@
1
+ require 'ore/template/directory'
2
+ require 'ore/template/interpolations'
3
+ require 'ore/template/helpers'
4
+ require 'ore/naming'
5
+ require 'ore/config'
6
+
7
+ require 'thor/group'
8
+ require 'date'
9
+ require 'set'
10
+
11
+ module Ore
12
+ class Generator < Thor::Group
13
+
14
+ include Thor::Actions
15
+ include Naming
16
+ include Template::Interpolations
17
+ include Template::Helpers
18
+
19
+ # The base template for all RubyGems
20
+ @@base_template = :base
21
+
22
+ #
23
+ # The templates registered with the generator.
24
+ #
25
+ def Generator.templates
26
+ @templates ||= {}
27
+ end
28
+
29
+ #
30
+ # Registers a template with the generator.
31
+ #
32
+ # @param [String] path
33
+ # The path to the template.
34
+ #
35
+ # @raise [StandardError]
36
+ # The given path was not a directory.
37
+ #
38
+ def Generator.register_template(path)
39
+ unless File.directory?(path)
40
+ raise(StandardError,"#{path.dump} is must be a directory")
41
+ end
42
+
43
+ name = File.basename(path).to_sym
44
+ Generator.templates[name] = path
45
+ end
46
+
47
+ Config.builtin_templates { |path| Generator.register_template(path) }
48
+ Config.installed_templates { |path| Generator.register_template(path) }
49
+
50
+ namespace ''
51
+
52
+ class_option :markdown, :type => :boolean, :default => false
53
+ class_option :textile, :type => :boolean, :default => false
54
+ class_option :templates, :type => :array,
55
+ :default => [],
56
+ :aliases => '-T'
57
+ class_option :name, :type => :string, :aliases => '-n'
58
+ class_option :version, :type => :string,
59
+ :default => '0.1.0',
60
+ :aliases => '-V'
61
+ class_option :summary, :default => 'TODO: Summary',
62
+ :aliases => '-s'
63
+ class_option :description, :default => 'TODO: Description',
64
+ :aliases => '-D'
65
+ class_option :license, :default => 'MIT', :aliases => '-L'
66
+ class_option :homepage, :type => :string, :aliases => '-U'
67
+ class_option :email, :type => :string, :aliases => '-e'
68
+ class_option :authors, :type => :array,
69
+ :default => [ENV['USER']], :aliases => '-a'
70
+ class_option :rdoc, :type => :boolean, :default => true
71
+ class_option :yard, :type => :boolean, :default => false
72
+ class_option :test_unit, :type => :boolean, :default => false
73
+ class_option :rspec, :type => :boolean, :default => true
74
+ class_option :bundler, :type => :boolean, :default => false
75
+ class_option :jeweler_tasks, :type => :boolean, :default => false
76
+ class_option :ore_tasks, :type => :boolean, :default => false
77
+ class_option :git, :type => :boolean, :default => true
78
+ argument :path, :required => true
79
+
80
+ def generate
81
+ self.destination_root = path
82
+
83
+ enable_templates!
84
+ load_templates!
85
+ initialize_variables!
86
+
87
+ say "Generating #{self.destination_root}", :green
88
+
89
+ generate_directories!
90
+ generate_files!
91
+
92
+ if options.git?
93
+ in_root do
94
+ unless File.directory?('.git')
95
+ run 'git init'
96
+ run 'git add .'
97
+ run 'git commit -m "Initial commit."'
98
+ end
99
+ end
100
+ end
101
+ end
102
+
103
+ protected
104
+
105
+ #
106
+ # Enables templates.
107
+ #
108
+ def enable_templates!
109
+ @enabled_templates = [@@base_template]
110
+
111
+ @enabled_templates << :bundler if options.bundler?
112
+ @enabled_templates << :jeweler_tasks if options.jeweler_tasks?
113
+ @enabled_templates << :ore_tasks if options.ore_tasks?
114
+
115
+ if options.rspec?
116
+ @enabled_templates << :rspec
117
+ elsif options.test_unit?
118
+ @enabled_templates << :test_unit
119
+ end
120
+
121
+ if options.yard?
122
+ @enabled_templates << :yard
123
+ elsif options.rdoc?
124
+ @enabled_templates << :rdoc
125
+ end
126
+
127
+ options.templates.each do |name|
128
+ name = name.to_sym
129
+
130
+ unless @enabled_templates.include?(name)
131
+ @enabled_templates << name
132
+ end
133
+ end
134
+ end
135
+
136
+ #
137
+ # Loads the given templates.
138
+ #
139
+ def load_templates!
140
+ @templates = []
141
+
142
+ @enabled_templates.each do |name|
143
+ unless (template_dir = Generator.templates[name])
144
+ say "Unknown template #{name.dump}", :red
145
+ exit -1
146
+ end
147
+
148
+ self.source_paths << template_dir
149
+ @templates << Template::Directory.new(template_dir)
150
+ end
151
+ end
152
+
153
+ #
154
+ # Initializes variables for the templates.
155
+ #
156
+ def initialize_variables!
157
+ @ore_version = '0.1.0'
158
+
159
+ @project_dir = File.basename(destination_root)
160
+ @name = (options.name || @project_dir)
161
+
162
+ @modules = modules_of(@name)
163
+ @module_depth = @modules.length
164
+ @module = @modules.last
165
+
166
+ @namespace = namespace_of(@name)
167
+ @namespace_dirs = namespace_dirs_of(@name)
168
+ @namespace_dir = namespace_path_of(@name)
169
+
170
+ @version = options.version
171
+ @summary = options.summary
172
+ @description = options.description
173
+ @license = options.license
174
+ @email = options.email
175
+ @safe_email = @email.sub('@',' at ') if @email
176
+ @homepage = (options.homepage || "http://rubygems.org/gems/#{@name}")
177
+ @authors = options.authors
178
+ @author = options.authors.first
179
+
180
+ @markup = if options.yard?
181
+ if options.markdown?
182
+ :markdown
183
+ elsif options.textile?
184
+ :textile
185
+ else
186
+ :rdoc
187
+ end
188
+ else
189
+ :rdoc
190
+ end
191
+
192
+ @date = Date.today
193
+ @year = @date.year
194
+ @month = @date.month
195
+ @day = @date.day
196
+ end
197
+
198
+ #
199
+ # Creates directories listed in the template directories.
200
+ #
201
+ def generate_directories!
202
+ generated = Set[]
203
+
204
+ @templates.each do |template|
205
+ template.each_directory do |dir|
206
+ unless generated.include?(dir)
207
+ path = interpolate(dir)
208
+ empty_directory path
209
+
210
+ generated << dir
211
+ end
212
+ end
213
+ end
214
+ end
215
+
216
+ #
217
+ # Copies static files and renders templates in the template directories.
218
+ #
219
+ def generate_files!
220
+ generated = Set[]
221
+
222
+ @templates.reverse_each do |template|
223
+ template.each_file(@markup) do |dest,file|
224
+ unless generated.include?(dest)
225
+ path = interpolate(dest)
226
+ copy_file file, path
227
+
228
+ generated << dest
229
+ end
230
+ end
231
+
232
+ template.each_template(@markup) do |dest,file|
233
+ unless generated.include?(dest)
234
+ path = interpolate(dest)
235
+
236
+ @current_template_dir = File.dirname(dest)
237
+ template file, path
238
+ @current_template_dir = nil
239
+
240
+ generated << dest
241
+ end
242
+ end
243
+ end
244
+ end
245
+
246
+ end
247
+ end
data/lib/ore/naming.rb ADDED
@@ -0,0 +1,95 @@
1
+ module Ore
2
+ #
3
+ # Provides methods for guessing the namespaces and directories
4
+ # of projects. {Naming} uses the naming conventions of project names
5
+ # defined by the
6
+ # [Ruby Packaging Standard (RPS)](http://chneukirchen.github.com/rps/).
7
+ #
8
+ module Naming
9
+ # The directory which contains executables for a project
10
+ @@bin_dir = 'bin'
11
+
12
+ # The directory which contains the code for a project
13
+ @@lib_dir = 'lib'
14
+
15
+ # The directory which contains C extension code for a project
16
+ @@ext_dir = 'ext'
17
+
18
+ # The directory which contains data files for a project
19
+ @@data_dir = 'data'
20
+
21
+ # The directory which contains unit-tests for a project
22
+ @@test_dir = 'test'
23
+
24
+ # The directory which contains spec-tests for a project
25
+ @@spec_dir = 'spec'
26
+
27
+ # The directory which contains built packages
28
+ @@pkg_dir = 'pkg'
29
+
30
+ # Common project prefixes and namespaces
31
+ @@common_namespaces = {
32
+ 'ffi' => 'FFI',
33
+ 'dm' => 'DataMapper'
34
+ }
35
+
36
+ #
37
+ # Guesses the module names from a project name.
38
+ #
39
+ # @return [Array<String>]
40
+ # The module names for a project.
41
+ #
42
+ def modules_of(name)
43
+ name.split('-').map do |words|
44
+ words.split('_').map { |word|
45
+ @@common_namespaces[word] || word.capitalize
46
+ }.join
47
+ end
48
+ end
49
+
50
+ #
51
+ # Guesses the full namespace for a project.
52
+ #
53
+ # @return [String]
54
+ # The full module namespace for a project.
55
+ #
56
+ def namespace_of(name)
57
+ modules_of(name).join('::')
58
+ end
59
+
60
+ #
61
+ # Converts a camel-case name to an underscored file name.
62
+ #
63
+ # @param [String] name
64
+ # The name to underscore.
65
+ #
66
+ # @return [String]
67
+ # The underscored version of the name.
68
+ #
69
+ def underscore(name)
70
+ name.gsub(/[^A-Z_][A-Z][^A-Z_]/) { |cap|
71
+ cap[0,1] + '_' + cap[1..-1]
72
+ }.downcase
73
+ end
74
+
75
+ #
76
+ # Guesses the namespace directories within `lib/` for a project.
77
+ #
78
+ # @return [Array<String>]
79
+ # The namespace directories for the project.
80
+ #
81
+ def namespace_dirs_of(name)
82
+ name.split('-').map { |word| underscore(word) }
83
+ end
84
+
85
+ #
86
+ # Guesses the namespace directory within `lib/` for a project.
87
+ #
88
+ # @return [String]
89
+ # The namespace directory for the project.
90
+ #
91
+ def namespace_path_of(name)
92
+ File.join(namespace_dirs_of(name))
93
+ end
94
+ end
95
+ end