echoe 2.1 → 2.3

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.
Files changed (8) hide show
  1. data/CHANGELOG +5 -1
  2. data/Manifest +1 -0
  3. data/README +1 -1
  4. data/Rakefile +5 -1
  5. data/TODO +3 -0
  6. data/lib/echoe.rb +130 -34
  7. data/test/test_echoe.rb +3 -5
  8. metadata +4 -6
data/CHANGELOG CHANGED
@@ -1,7 +1,11 @@
1
1
 
2
+ v2.3. Work around metadependencies issue by including gemspecs instead of Rakefiles by default; include_gemspec and include_rakefile accessors.
3
+
4
+ v2.2. Need_gem option; announce task.
5
+
2
6
  v2.1. Adjust default RDoc include pattern; extra_deps now dependencies; rubyforge_name now project; support install messages; manifest instead of build_manifest.
3
7
 
4
- v2. Support documentation hosts other than rubyforge; switch to Snax-style gem versioning; auto-load CHANGELOG contents; remove bin/echoe which doesn't work anyway. Incompatible changes.
8
+ v2. Support documentation hosts other than rubyforge; auto-load CHANGELOG contents; remove bin/echoe which doesn't work anyway. Incompatible changes.
5
9
 
6
10
  v1.4. Auto-detect readme file; make rdoc default pattern compatible with manifest generator; fix publish_docs task.
7
11
 
data/Manifest CHANGED
@@ -1,5 +1,6 @@
1
1
  test/test_echoe.rb
2
2
  lib/echoe.rb
3
+ TODO
3
4
  Rakefile
4
5
  README
5
6
  Manifest
data/README CHANGED
@@ -5,7 +5,7 @@ Echoe is a simple tool for working with Rubygems. It generates Rake tasks for do
5
5
 
6
6
  == License
7
7
 
8
- Copyright 2007 Cloudburst, LLC. See included LICENSE file. Portions copyright 2006 Ryan Davis, Zen Spider Software, and used with permission. See included MIT-LICENSE file.
8
+ Copyright 2007 Cloudburst, LLC. See the included LICENSE file. Portions copyright 2006 Ryan Davis/Zen Spider Software and used with permission. See the included MIT-LICENSE file.
9
9
 
10
10
  == Features
11
11
 
data/Rakefile CHANGED
@@ -7,6 +7,10 @@ Echoe.new('echoe') do |p|
7
7
  p.summary = 'A tool for packaging Ruby gems.'
8
8
  p.url = 'http://blog.evanweaver.com/pages/code#echoe'
9
9
  p.docs_host = 'blog.evanweaver.com:~/www/snax/public/files/doc/'
10
- p.dependencies = ['rake', 'rubyforge >= 0.4.0', 'highline']
10
+ p.dependencies = ['rake', 'rubyforge >=0.4.3', 'highline']
11
+
12
+ # Echoe is self-dependent
13
+ p.include_gemspec = false
14
+ p.include_rakefile = true
11
15
  end
12
16
 
data/TODO ADDED
@@ -0,0 +1,3 @@
1
+
2
+ * Figure out why need_gem = false caused releasing to fail
3
+ * Add support for Rubyforge release announcements
data/lib/echoe.rb CHANGED
@@ -7,24 +7,30 @@ require 'rake/gempackagetask'
7
7
  require 'rake/rdoctask'
8
8
  require 'rake/testtask'
9
9
  require 'rbconfig'
10
+ require 'open-uri'
10
11
  require 'highline/import'
11
- gem 'rubyforge', '>= 0.4.0'
12
+ gem 'rubyforge', '>=0.4.0'
12
13
  require 'rubyforge'
13
14
 
14
15
  =begin rdoc
15
16
 
16
17
  Echoe includes some optional accessors for more advanced gem configuration.
17
18
 
18
- For example, Echoe's own <tt>Rakefile</tt> looks like this:
19
+ For example, a simple <tt>Rakefile</tt> might look like this:
19
20
 
20
- Echoe.new('echoe') do |p|
21
- p.project = 'fauna'
22
- p.author = 'Evan Weaver'
23
- p.summary = 'A tool for packaging Ruby gems.'
24
- p.url = 'http://blog.evanweaver.com/pages/code#echoe'
25
- p.docs_host = 'blog.evanweaver.com:~/www/snax/public/files/doc/'
26
- p.dependencies = ['rake', 'rubyforge >= 0.4.0', 'highline']
21
+ Echoe.new("uncapitalizer") do |p|
22
+ p.author = "Evan Weaver"
23
+ p.summary = "A library that uncapitalizes strings. It's awesome."
24
+ p.url = "http://www.uncapitalizer.com"
25
+ p.docs_host = "uncapitalizer.com:~/www/files/doc/"
26
+ p.dependencies = ["string_tools >=1.4.0"]
27
27
  end
28
+
29
+ == Metadependencies
30
+
31
+ Echoe does not force packages to depend on Echoe itself. Instead, it generates a <tt>gemspec</tt> from your <tt>Rakefile</tt> and includes that, along with a comment containing the original <tt>Rakefile</tt> source. Downstream repackagers can use the <tt>gemspec</tt> as-is to build new versions of your gem. This way no dependencies are added, but no contents are lost.
32
+
33
+ If you do want metadependencies, add <tt>'echoe'</tt> to the <tt>p.dependencies</tt> array, and set <tt>p.include_rakefile = true</tt> and <tt>p.include_gemspec = false</tt>.
28
34
 
29
35
  == Accessor options
30
36
 
@@ -46,14 +52,19 @@ Packaging options:
46
52
 
47
53
  * <tt>dependencies</tt> - An array of dependencies for this gem, in 'gem_name [= version]' format.
48
54
  * <tt>manifest_name</tt> - The name of the manifest file (defaults to <tt>Manifest</tt>).
49
- * <tt>need_tar</tt> - Whether to generate a <tt>.tgz</tt> package (default <tt>false</tt>).
55
+ * <tt>need_gem</tt> - Whether to generate a gem package (default <tt>true</tt>).
50
56
  * <tt>need_tar_gz</tt> - Whether to generate a <tt>.tar.gz</tt> package (default <tt>true</tt>).
57
+ * <tt>need_tgz</tt> - Whether to generate a <tt>.tgz</tt> package (default <tt>false</tt>).
51
58
  * <tt>need_zip</tt> - Whether to generate a <tt>.zip</tt> package (default <tt>false</tt>).
59
+ * <tt>extensions</tt> - Any extension files that need to be executed (defaults to <tt>"ext/extconf.rb"</tt> if it exists).
60
+ * <tt>include_gemspec</tt> - Include the generated gemspec file within the package. Default <tt>true</tt>.
61
+ * <tt>include_rakefile</tt> - Include the Rakefile within the package. Default <tt>false</tt>.
52
62
 
53
63
  Publishing options:
54
64
 
55
65
  * <tt>project</tt> - The name of the Rubyforge project to upload to (defaults to the name of the gem).
56
- * <tt>docs_host</tt> - A host and path to publish the documentation to (defaults to the Rubyforge project).
66
+ * <tt>docs_host</tt> - A host and filesystem path to publish the documentation to (defaults to the Rubyforge project).
67
+ * <tt>announce</tt> - Generate a release announcement, edit it, and post it to Rubyforge.
57
68
 
58
69
  Documentation options:
59
70
 
@@ -80,10 +91,10 @@ class Echoe
80
91
  FILTER = ENV['FILTER'] # for tests (eg FILTER="-n test_blah")
81
92
 
82
93
  # user-configurable
83
- attr_accessor :author, :changes, :clean_pattern, :description, :email, :dependencies, :need_tar, :need_tar_gz, :need_zip, :rdoc_pattern, :project, :summary, :test_pattern, :url, :version, :docs_host, :rdoc_template, :manifest_name, :install_message
94
+ attr_accessor :author, :changes, :clean_pattern, :description, :email, :dependencies, :need_tgz, :need_tar_gz, :need_gem, :need_zip, :rdoc_pattern, :project, :summary, :test_pattern, :url, :version, :docs_host, :rdoc_template, :manifest_name, :install_message, :extensions
84
95
 
85
96
  # best left alone
86
- attr_accessor :name, :lib_files, :test_files, :bin_files, :spec, :rdoc_options, :rubyforge_name
97
+ attr_accessor :name, :lib_files, :test_files, :bin_files, :spec, :rdoc_options, :rubyforge_name, :has_rdoc, :include_gemspec, :include_rakefile, :gemspec_name
87
98
 
88
99
  # legacy
89
100
  attr_accessor :extra_deps
@@ -116,15 +127,22 @@ class Echoe
116
127
  self.description = ""
117
128
  self.summary = ""
118
129
  self.install_message = nil
130
+ self.has_rdoc = true
119
131
  self.rdoc_pattern = /^(lib|bin|tasks)|^README|^CHANGELOG|^TODO|^LICENSE$/
120
132
  self.rdoc_options = ['--line-numbers', '--inline-source']
121
133
  self.dependencies = []
122
134
  self.manifest_name = "Manifest"
135
+ self.extensions = ["ext/extconf.rb"] if File.exist?("ext/extconf.rb")
123
136
 
124
- self.need_tar = false
137
+ self.need_gem = true
125
138
  self.need_tar_gz = true
139
+ self.need_tgz = false
126
140
  self.need_zip = false
127
141
 
142
+ self.include_rakefile = false
143
+ self.include_gemspec = true
144
+ self.gemspec_name = "#{name}.gemspec"
145
+
128
146
  yield self if block_given?
129
147
 
130
148
  # set some post-defaults
@@ -161,33 +179,68 @@ class Echoe
161
179
 
162
180
  begin
163
181
  s.files = File.read(manifest_name).split
182
+ s.files += [gemspec_name] if include_gemspec
183
+ s.files += ["Rakefile"] if include_rakefile
184
+ s.files.uniq! # not really necessary
164
185
  rescue Errno::ENOENT
165
- $stderr.puts "Missing Manifest. You can build one with\n$ rake build_manifest."
186
+ puts "Missing manifest. You can build one with 'rake manifest'."
187
+ exit
166
188
  end
167
189
  s.executables = s.files.grep(/bin/) { |f| File.basename(f) }
168
190
 
169
191
  s.bindir = "bin"
170
192
  dirs = Dir['{lib,ext}']
193
+ s.extensions = Array(extensions) if extensions
171
194
  s.require_paths = dirs unless dirs.empty?
172
- s.has_rdoc = true
195
+ s.has_rdoc = has_rdoc
173
196
 
174
197
  if File.exist? "test/test_all.rb"
175
198
  s.test_file = "test/test_all.rb"
176
199
  else
177
200
  s.test_files = Dir[*test_pattern]
178
201
  end
179
-
180
202
  end
181
203
 
182
204
  self.lib_files = spec.files.grep(/^lib/)
183
205
  self.bin_files = spec.files.grep(/^bin/)
184
206
  self.test_files = spec.files.grep(/^test/)
185
207
 
186
- Rake::GemPackageTask.new spec do |pkg|
187
- pkg.need_tar = @need_tar
208
+ Rake::GemPackageTask.new(spec) do |pkg|
209
+ pkg.need_tar = @need_tgz
188
210
  pkg.need_tar_gz = @need_tar_gz
189
211
  pkg.need_zip = @need_zip
190
212
  end
213
+
214
+ task :build_gemspec do
215
+ # Construct the gemspec file, if needed.
216
+ if include_gemspec
217
+ File.open(gemspec_name, 'w') do |f|
218
+ f.puts "\n# Gem::Specification for #{name.capitalize}-#{version}\n# Originally generated by Echoe\n\n"
219
+ f.puts spec.to_ruby
220
+
221
+ f.puts "\n\n# # Original Rakefile source (requires the Echoe gem):\n# \n"
222
+ File.open("Rakefile").readlines.each do |line|
223
+ f.write "# #{line}"
224
+ end
225
+ end
226
+ end
227
+ end
228
+
229
+ # Chain it to the gemspec task prerequisite
230
+ task gemspec_name.to_sym => [:build_gemspec]
231
+
232
+ task :package do
233
+ # Chain some cleanup tasks to the default :package task.
234
+ # Remove the gemfile if it wasn't actually requested.
235
+ unless @need_gem
236
+ puts " Gem file not requested. Removed."
237
+ system "rm pkg/*.gem"
238
+ end
239
+ # Remove the generated gemspec once the packaging is done, to discourage people from modifying it by hand.
240
+ if include_gemspec and File.exist? gemspec_name
241
+ File.delete gemspec_name
242
+ end
243
+ end
191
244
 
192
245
  desc 'Install the gem'
193
246
  task :install => [:clean, :package] do
@@ -219,23 +272,20 @@ class Echoe
219
272
  c["release_changes"] = changes if changes
220
273
  c["preformatted"] = false
221
274
 
222
- files = [(@need_tar ? pkg_tar : nil),
275
+ files = [(@need_tgz ? pkg_tar : nil),
223
276
  (@need_tar_gz ? pkg_tar_gz : nil),
224
- (@need_zip ? pkg_zip : nil),
225
- pkg_gem].compact
277
+ (@need_zip ? pkg_zip : nil),
278
+ (@need_gem ? pkg_gem : nil)].compact
226
279
 
227
280
  puts "Releasing #{name} v. #{version}"
228
281
  self.version = self.version.ljust(3)
229
-
230
- begin
231
- rf.add_release project, name, version, *files
232
- rescue NoMethodError
233
- end
282
+
283
+ rf.add_release project, name, version, *files
234
284
  end
235
285
 
236
286
  end
237
287
 
238
- ### RDoc
288
+ ### Documentation
239
289
 
240
290
  Rake::RDocTask.new(:docs) do |rd|
241
291
  rd.main = Dir['*'].detect {|f| f =~ /^readme/i}
@@ -289,6 +339,39 @@ class Echoe
289
339
  sh("scp -qr #{local_dir} #{host}:#{dir}/#{remote_dir_name}")
290
340
  end
291
341
  end
342
+
343
+ desc 'Generate a release announcement, edit it, and post it to Rubyforge.'
344
+ task :announce do
345
+
346
+ filename = "/tmp/#{name}_#{version}_announcement.txt"
347
+
348
+ if !File.exist?(filename) or agree "Overwrite existing announcement file? "
349
+ File.open(filename, 'w') do |f|
350
+ f.write "Subject: #{name.capitalize} #{version}\n\n"
351
+ f.write "#{name.capitalize} has been updated to #{version}. #{name.capitalize} is #{summary.uncapitalize}\n\n"
352
+ f.write "Changes in this version: #{changes.sub(/^\s*[\w\d\.]+\s+/, '').uncapitalize}\n\n" unless changes.empty?
353
+ f.write "More information is available at #{url} .\n\n" unless url.empty?
354
+ end
355
+ end
356
+
357
+ begin
358
+ system("nano #{filename}") or raise "Editor returned an error"
359
+ puts File.open(filename).read
360
+ end while !agree "Done editing? "
361
+
362
+ if agree "Publish announcement to Rubyforge? "
363
+ File.open(filename).readlines.detect { |line| line =~ /Subject: (.*)/ }
364
+ subject = $1 or raise "Subject line seems to have disappeared"
365
+
366
+ body = File.open(filename).readlines.reject { |line| line =~ /Subject: / }.join.gsub("\n\n\n", "\n\n")
367
+
368
+ rf = RubyForge.new
369
+ rf.login
370
+ rf.post_news(project, subject, body)
371
+ puts "Published."
372
+ File.delete filename
373
+ end
374
+ end
292
375
 
293
376
  ### Clean
294
377
 
@@ -307,13 +390,19 @@ class Echoe
307
390
  files = []
308
391
  Find.find '.' do |file|
309
392
  file = file[2..-1]
310
- unless !file or file =~ /^(pkg|doc)|\.svn|CVS|\.bzr|\.DS/ or File.directory? file
311
- files << file
312
- end
393
+ next unless file
394
+ next if file =~ /^(pkg|doc)|\.svn|CVS|\.bzr|\.DS/
395
+ next if File.directory?(file)
396
+ next if !include_rakefile and file == "Rakefile"
397
+ files << file
313
398
  end
314
- files = (files << manifest_name).uniq
315
- File.open(manifest_name, 'w').puts files
316
- puts files
399
+
400
+ files << "Rakefile" if include_rakefile
401
+ files << manifest_name
402
+ files.uniq!
403
+
404
+ File.open(manifest_name, 'w').puts(files)
405
+ puts(files)
317
406
  end
318
407
 
319
408
  task :build_manifest => [:manifest]
@@ -340,3 +429,10 @@ end
340
429
  class ::Rake::SshDirPublisher # :nodoc:
341
430
  attr_reader :host, :remote_dir, :local_dir
342
431
  end
432
+
433
+ class String #:nodoc:
434
+ def uncapitalize #:nodoc:
435
+ "#{self[0..0].downcase}#{self[1..-1]}"
436
+ end
437
+ end
438
+
data/test/test_echoe.rb CHANGED
@@ -2,7 +2,7 @@
2
2
  require 'test/unit/testcase'
3
3
  require 'echoe'
4
4
 
5
- $rakefile = nil # shuts up a warning in rdoctask.rb
5
+ $rakefile = nil # Avoids a warning in rdoctask.rb
6
6
 
7
7
  class TestEchoe < Test::Unit::TestCase
8
8
  def setup
@@ -10,10 +10,8 @@ class TestEchoe < Test::Unit::TestCase
10
10
  end
11
11
 
12
12
  def test_basics
13
- boring = %w(clobber clobber_docs clobber_package doc doc/index.html pkg pkg/blah-1.0.0 pkg/blah-1.0.0.gem pkg/blah-1.0.0.tar.gz redocs repackage default)
14
- expected = %w(clean clobber clobber_docs clobber_package docs gem install manifest package publish_docs redocs release repackage test uninstall build_manifest)
15
- expected += boring
16
-
13
+ expected = ["announce", "blah.gemspec", "build_gemspec", "build_manifest", "clean", "clobber", "clobber_docs", "clobber_package", "default", "doc", "doc/index.html", "docs", "gem", "install", "manifest", "package", "pkg", "pkg/blah-1.0.0", "pkg/blah-1.0.0.gem", "pkg/blah-1.0.0.tar.gz", "publish_docs", "redocs", "release", "repackage", "test", "uninstall"]
14
+
17
15
  Echoe.new('blah', '1.0.0')
18
16
  tasks = Rake.application.tasks.map { |t| t.name }
19
17
  assert((expected - tasks).empty?)
metadata CHANGED
@@ -3,8 +3,8 @@ rubygems_version: 0.9.4
3
3
  specification_version: 1
4
4
  name: echoe
5
5
  version: !ruby/object:Gem::Version
6
- version: "2.1"
7
- date: 2007-08-06 00:00:00 -04:00
6
+ version: "2.3"
7
+ date: 2007-08-13 00:00:00 -04:00
8
8
  summary: A tool for packaging Ruby gems.
9
9
  require_paths:
10
10
  - lib
@@ -31,6 +31,7 @@ authors:
31
31
  files:
32
32
  - test/test_echoe.rb
33
33
  - lib/echoe.rb
34
+ - TODO
34
35
  - Rakefile
35
36
  - README
36
37
  - Manifest
@@ -66,10 +67,7 @@ dependencies:
66
67
  requirements:
67
68
  - - ">="
68
69
  - !ruby/object:Gem::Version
69
- version: "0"
70
- - - "="
71
- - !ruby/object:Gem::Version
72
- version: 0.4.0
70
+ version: 0.4.3
73
71
  version:
74
72
  - !ruby/object:Gem::Dependency
75
73
  name: highline