зеркало из https://github.com/github/ruby.git
* lib/rake: updated to rake code to rake-0.8.7 source code base.
* lib/rake/loaders/makefile.rb (Rake::MakefileLoader#process_line): respace dependencies too. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25199 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
Родитель
a0f667c33e
Коммит
719b0f8e30
|
@ -1,3 +1,10 @@
|
|||
Sat Oct 3 04:07:52 2009 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||
|
||||
* lib/rake: updated to rake code to rake-0.8.7 source code base.
|
||||
|
||||
* lib/rake/loaders/makefile.rb (Rake::MakefileLoader#process_line):
|
||||
respace dependencies too.
|
||||
|
||||
Sat Oct 3 02:59:21 2009 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||
|
||||
* parse.y (assignable_gen): get rid of macro collision.
|
||||
|
|
|
@ -0,0 +1,440 @@
|
|||
|
||||
= Rake Changelog
|
||||
|
||||
== Version 0.8.7
|
||||
|
||||
* Fixed EXEEXT for JRuby on windows.
|
||||
|
||||
== Version 0.8.6
|
||||
|
||||
* Minor fixes to the RDoc generation (removed dependency on darkfish
|
||||
and removed inline source option).
|
||||
|
||||
== Version 0.8.5
|
||||
|
||||
* Better support for the system command on Windows.
|
||||
|
||||
== Version 0.8.4
|
||||
|
||||
* Preserve case when locating rakefiles (patch from James
|
||||
M. Lawrence/quix)
|
||||
|
||||
* Better support for windows paths in the test task (patch from Simon
|
||||
Chiang/bahuvrihi)
|
||||
|
||||
* Windows system dir search order is now: HOME, HOMEDRIVE + HOMEPATH,
|
||||
APPDATA, USERPROFILE (patch from Luis Lavena)
|
||||
|
||||
* MingGW is now recognized as a windows platform. (patch from Luis
|
||||
Lavena)
|
||||
|
||||
* Numerous fixes to the windows test suite (patch from Luis Lavena).
|
||||
|
||||
* Improved Rakefile case insensitivity testing (patch from Luis
|
||||
Lavena).
|
||||
|
||||
* Fixed stray ARGV option problem that was interfering with
|
||||
Test::Unit::Runner.
|
||||
|
||||
* Fixed default verbose mode (was accidently changed to false).
|
||||
|
||||
* Removed reference to manage_gem to fix the warning produced by the
|
||||
gem package task.
|
||||
|
||||
== Version 0.8.3
|
||||
|
||||
* Enhanced the system directory detection in windows. We now check
|
||||
HOMEDRIVE/HOMEPATH and USERPROFILE if APPDATA isn't found. (Patch
|
||||
supplied by James Tucker). Rake no long aborts if it can't find the
|
||||
directory.
|
||||
|
||||
* Added fix to handle ruby installations in directories with spaces in
|
||||
their name.
|
||||
|
||||
== Version 0.8.2
|
||||
|
||||
* Fixed bug in package task so that it will include the subdir
|
||||
directory in the package for testing. (Bug found by Adam Majer)
|
||||
|
||||
* Added ENV var to rakefile to prevent OS X from including extended
|
||||
attribute junk in a tar file. (Bug found by Adam Majer)
|
||||
|
||||
* Fixed filename dependency order bug in test_inspect_pending and
|
||||
test_to_s_pending. (Bug found by Adam Majer)
|
||||
|
||||
* Fixed check for file utils options to make them immune to the
|
||||
symbol/string differences. (Patch supplied by Edwin Pratomo)
|
||||
|
||||
* Fixed bug with rules involving multiple source (Patch supplied by
|
||||
Emanuel Indermühle)
|
||||
|
||||
* Switched from getoptlong to optparse (patches supplied by Edwin
|
||||
Pratomo)
|
||||
|
||||
* The -T option will now attempt to dynamically sense the size of the
|
||||
terminal. RAKE_COLUMNS will override any dynamic sensing.
|
||||
|
||||
* FileList#clone and FileList#dup have better sematics w.r.t. taint
|
||||
and freeze.
|
||||
|
||||
* Added ability clear prerequisites, and/or actions from an existing
|
||||
task.
|
||||
|
||||
* Added the ability to reenable a task to be invoked a second time.
|
||||
|
||||
* Changed RDoc test task to have no default template. This makes it
|
||||
easier for the tempate to pick up the template from the environment.
|
||||
|
||||
* Changed from using Mutex to Monitor. Evidently Mutex causes thread
|
||||
join errors when Ruby is compiled with -disable-pthreads. (Patch
|
||||
supplied by Ittay Dror)
|
||||
|
||||
* Fixed bug in makefile parser that had problems with extra spaces in
|
||||
file task names. (Patch supplied by Ittay Dror)
|
||||
|
||||
* Added a performance patch for reading large makefile dependency
|
||||
files. (Patch supplied by Ittay Dror)
|
||||
|
||||
* Default values for task arguments can easily be specified with the
|
||||
:with_defaults method. (Idea for default argument merging supplied
|
||||
by (Adam Q. Salter)
|
||||
|
||||
* The -T output will only self-truncate if the output is a tty.
|
||||
However, if RAKE_COLUMNS is explicitly set, it will be honored in
|
||||
any case. (Patch provided by Gavin Stark).
|
||||
|
||||
* Numerous fixes for running under windows. A big thanks to Bheeshmar
|
||||
Redheendran for spending a good part of the afternoon at the
|
||||
Lonestar Ruby Conference to help me work out these issues.
|
||||
|
||||
== Version 0.8.1
|
||||
|
||||
* Removed requires on parsedate.rb (in Ftptools)
|
||||
* Removed ftools from rake.rb. Made it options in sys.rb
|
||||
|
||||
== Version 0.8.0
|
||||
|
||||
* Added task parameters (e.g. "rake build[version7]")
|
||||
* Made task parameters passable to prerequisites.
|
||||
* Comments are limited to 80 columns or so (suggested by Jamis Buck).
|
||||
* Added -D to display full comments (suggested by Jamis Buck).
|
||||
* The rake program will set the status value used in any explicit
|
||||
exit(n) calls. (patch provided by Stephen Touset)
|
||||
* Fixed error in functional tests that were not including session (and
|
||||
silently skipping the functionl tests.
|
||||
* Removed --usage and make -h the same as -H.
|
||||
* Make a prettier inspect for tasks.
|
||||
|
||||
== Version 0.7.3
|
||||
|
||||
* Added existing and existing! methods to FileList
|
||||
* FileLists now claim to be Arrays (via is_a?) to get better support
|
||||
from the FileUtil module.
|
||||
* Added init and top_level for custom rake applications.
|
||||
|
||||
== Version 0.7.2
|
||||
|
||||
* Error messages are now send to stderr rather than stdout (from
|
||||
Payton Quackenbush).
|
||||
* Better error handling on invalid command line arguments (from Payton
|
||||
Quackenbush).
|
||||
* Added rcov task and updated unit testing for better code coverage.
|
||||
* Fixed some bugs where the application object was going to the global
|
||||
appliation instead of using its own data.
|
||||
* Added square and curly bracket patterns to FileList#include (Tilman
|
||||
Sauerbeck).
|
||||
* Added plain filename support to rule dependents (suggested by Nobu
|
||||
Nakada).
|
||||
* Added pathmap support to rule dependents.
|
||||
* Added a 'tasks' method to a namespace to get a list of tasks
|
||||
associated with the namespace.
|
||||
* Fixed the method name leak from FileUtils (bug found by Glenn
|
||||
Vanderburg).
|
||||
* Added rake_extension to handle detection of extension collisions.
|
||||
* Added test for noop, bad_option and verbose flags to sh command.
|
||||
* Removed dependency on internal fu_xxx functions from FileUtils.
|
||||
* Added a 'shame' task to the Rakefile.
|
||||
* Added tar_command and zip_command options to the Package task.
|
||||
* Added a description to the gem task in GemPackageTask.
|
||||
* Fixed a bug when rules have multiple prerequisites (patch by Joel
|
||||
VanderWerf)
|
||||
* Added a protected 'require "rubygems"' to test/test_application to
|
||||
unbreak cruisecontrol.rb.
|
||||
* Added the handful of RakeFileUtils to the private method as well.
|
||||
* Added block based exclusion.
|
||||
* The clean task will no longer delete 'core' if it is a directory.
|
||||
* Removed rake_dup. Now we just simply rescue a bad dup.
|
||||
* Refactored the FileList reject logic to remove duplication.
|
||||
* Removed if __FILE__ at the end of the rake.rb file.
|
||||
|
||||
== Version 0.7.1
|
||||
|
||||
* Added optional filter parameter to the --tasks command line option.
|
||||
* Added flatten to allow rule transform procs to return lists of
|
||||
prereqs (Joel VanderWerf provided patch).
|
||||
* Added pathmap to String and FileList.
|
||||
* The -r option will now load .rake files (but a straight require
|
||||
doesn't yet). NOTE: This is experimental ... it may be
|
||||
discontinued.
|
||||
* The -f option without a value will disable the search for a
|
||||
Rakefile. The assumption is that the -r files are adequate.
|
||||
* Fixed the safe_ln function to fall back to cp in more error
|
||||
scenarios.
|
||||
|
||||
== Version 0.7.0
|
||||
|
||||
* Added Rake.original_dir to return the original starting directory of
|
||||
the rake application.
|
||||
* Added safe_ln support for openAFS (from Ludvig Omholt).
|
||||
* Added --trace reminder on short exception messages (David Heinemeier
|
||||
Hansson suggestion).
|
||||
* Added multitask declaration that executes prerequisites in
|
||||
parallel. (Doug Young providied an initial implementation).
|
||||
* Fixed missing_const hack to be compatible with Rails. (Jamis Buck
|
||||
supplied test case).
|
||||
* Made the RDoc task default to internal (in-process) RDoc formatting.
|
||||
The old behavior is still available by setting the +external+ flag
|
||||
to true.
|
||||
* Rakefiles are now loaded with the expanded path to prevent
|
||||
accidental polution from the Ruby load path.
|
||||
* The +namespace+ command now returns a NameSpace object that can be
|
||||
used to lookup tasks defined in that namespace. This allows for
|
||||
better anonymous namespace behavior.
|
||||
* Task objects my now be used in prerequisite lists directly.
|
||||
|
||||
== Version 0.6.1
|
||||
|
||||
* Rebuilt 0.6.0 gem without signing.
|
||||
|
||||
== Version 0.6.0
|
||||
|
||||
* Fixed file creation bug in the unit tests (caused infinite loop on
|
||||
windows).
|
||||
* Fixed bug where session based functional tests were run under
|
||||
windows.
|
||||
* Fixed bug in directory tasks so that updating a directory will not
|
||||
retrigger file tasks depending on the directory (see
|
||||
FileCreationTask and EarlyTime).
|
||||
* Added egrep to FileList
|
||||
* ruby command now runs same ruby version as rake.
|
||||
* Added investigation to task object. (suggested by Martin Fowler)
|
||||
* Added ruby_opts to the test task to allow arbitrary ruby options to
|
||||
be passed to the test script. (Greg Fast)
|
||||
* Fixed the test loader to ignore options. (Greg Fast)
|
||||
* Moved Task, FileTask, FileCreationTask and RakeApp into the Rake
|
||||
module namespace. Old style namespace behavior can be invoked via
|
||||
the --classic-namespace option. (requested by Kelly Felkins).
|
||||
* GemTask is now sensitive to the gem platform (Masao Mutoh).
|
||||
* A non-existing file prerequisite will no longer cause an exception
|
||||
(Philipp Neubeck).
|
||||
* Multiple prerequisites on Rake rules now allowed (initial patch
|
||||
supplied by Stuart Jansen).
|
||||
|
||||
== Version 0.5.4
|
||||
|
||||
* Added double quotes to the test runner.
|
||||
* Added .svn to default ignore list.
|
||||
* Updated FileList#include to support nested arrays and filelists.
|
||||
|
||||
== Version 0.5.3
|
||||
|
||||
* Added support for importing Rakefile and other dependencies.
|
||||
* Fixed bug so that now rules can chain off of existing tasks as well
|
||||
as existing files.
|
||||
* Fixed verbose flag bug in the testing task. Shortened some failure
|
||||
messages.
|
||||
* Make FileUtils methods private at the top level module to avoid
|
||||
accidental method leaking into other objects.
|
||||
* Added test loader option to test task. "testrb" is no longer the
|
||||
default test loader. It is now eating syntax errors that should
|
||||
halt the unit tests.
|
||||
* Revamped FileList so that it works more like and array (addressed
|
||||
flatten bug). Added many tests around file list.
|
||||
* Added +ext+ method to both String and FileList.
|
||||
|
||||
== Version 0.5.0
|
||||
|
||||
* Fixed documentation that was lacking the Rake module name (Tilman
|
||||
Sauerbeck).
|
||||
* Added tar.gz and tar.bz2 support to package task (Tilman Sauerbeck).
|
||||
* Recursive rules are now supported (Tilman Sauerbeck).
|
||||
* Added warning option for the Test Task (requested by Eric Hodel).
|
||||
* The jamis rdoc template is only used if it exists.
|
||||
* Added fix for Ruby 1.8.2 test/unit and rails problem.
|
||||
* Added contributed rake man file (Jani Monoses).
|
||||
* Added Brian Candler's fix for problems in --trace and --dry-run
|
||||
mode.
|
||||
|
||||
== Version 0.4.15
|
||||
|
||||
* Fixed a bug that prevented the TESTOPTS flag from working with the
|
||||
revised for 1.8.2 test task.
|
||||
* Updated the docs on --trace to indicate that it also enables a full
|
||||
backtrace on errors.
|
||||
|
||||
== Version 0.4.14
|
||||
|
||||
* Modified the TestTask to workaround the Ruby 1.8.2 change in
|
||||
autoexecuting unit tests.
|
||||
|
||||
== Version 0.4.13
|
||||
|
||||
* Fixed the dry-run flag so it is operating again.
|
||||
* Multiple arguments to sh and ruby commands will not be interpreted
|
||||
by the shell (patch provided by Jonathan Paisley).
|
||||
|
||||
== Version 0.4.12
|
||||
|
||||
* Added --silent (-s) to suppress the (in directory) rake message.
|
||||
|
||||
== Version 0.4.11
|
||||
|
||||
* Changed the "don't know how to rake" message (finally)
|
||||
* Changes references to a literal "Rakefile" to reference the global
|
||||
variable $rakefile (which contains the actual name of the rakefile).
|
||||
|
||||
== Version 0.4.10
|
||||
|
||||
* Added block support to the "sh" command, allowing users to take
|
||||
special actions on the result of the system call. E.g.
|
||||
|
||||
sh "shell_command" do |ok, res|
|
||||
puts "Program returned #{res.exitstatus}" if ! ok
|
||||
end
|
||||
|
||||
== Version 0.4.9
|
||||
|
||||
* Switched to Jamis Buck's RDoc template.
|
||||
* Removed autorequire from Rake's gem spec. This prevents the Rake
|
||||
libraries from loading while using rails.
|
||||
|
||||
== Version 0.4.8
|
||||
|
||||
* Added support for .rb versions of Rakefile.
|
||||
* Removed \\\n's from test task.
|
||||
* Fixed Ruby 1.9 compatibility issue with FileList.
|
||||
|
||||
== Version 0.4.7
|
||||
|
||||
* Fixed problem in FileList that caused Ruby 1.9 to go into infinite
|
||||
recursion. Since to_a was removed from Object, it does not need to
|
||||
added back into the list of methods to rewrite in FileList. (Thanks
|
||||
to Kent Sibilev for pointing this out).
|
||||
|
||||
== Version 0.4.6
|
||||
* Removed test version of ln in FileUtils that prevented safe_ln from
|
||||
using ln.
|
||||
|
||||
== Version 0.4.5
|
||||
* Upgraded comments in TestTask.
|
||||
* FileList to_s and inspect now automatically resolve pending changes.
|
||||
* FileList#exclude properly returns the FileList.
|
||||
|
||||
== Version 0.4.4
|
||||
* Fixed initialization problem with @comment.
|
||||
* Now using multi -r technique in TestTask. Switch Rakefile back to
|
||||
using the built-in test task macros because the rake runtime is no
|
||||
longer needed.
|
||||
* Added 'TEST=filename' and 'TESTOPTS=options' to the Test Task
|
||||
macros.
|
||||
* Allow a +test_files+ attribute in test tasks. This allows more
|
||||
flexibility in specifying test files.
|
||||
|
||||
== Version 0.4.3
|
||||
* Fixed Comment leakage.
|
||||
|
||||
== Version 0.4.2
|
||||
* Added safe_ln that falls back to a copy if a file link is not supported.
|
||||
* Package builder now uses safe_ln.
|
||||
|
||||
== Version 0.4.1
|
||||
* Task comments are now additive, combined with "/".
|
||||
* Works with (soon to be released) rubygems 0.6.2 (or 0.7.0)
|
||||
|
||||
== Version 0.4.0
|
||||
* FileList now uses deferred loading. The file system is not searched
|
||||
until the first call that needs the file names.
|
||||
* VAR=VALUE options are now accepted on the command line and are
|
||||
treated like environment variables. The values may be tested in a
|
||||
Rakefile by referencing ENV['VAR'].
|
||||
* File.mtime is now used (instead of File.new().mtime).
|
||||
|
||||
== Version 0.3.2.x
|
||||
|
||||
* Removed some hidden dependencies on rubygems. Tests now will test
|
||||
gems only if they are installed.
|
||||
* Removed Sys from some example files. I believe that is that last
|
||||
reference to Sys outside of the contrib area.
|
||||
* Updated all copyright notices to include 2004.
|
||||
|
||||
== Version 0.3.2
|
||||
|
||||
* GEM Installation now works with the application stub.
|
||||
|
||||
== Version 0.3.1
|
||||
|
||||
* FileLists now automatically ignore CVS, .bak, !
|
||||
* GEM Installation now works.
|
||||
|
||||
== Version 0.3.0
|
||||
|
||||
Promoted 0.2.10.
|
||||
|
||||
== Version 0.2.10
|
||||
General
|
||||
|
||||
* Added title to Rake's rdocs
|
||||
* Contrib packages are no longer included in the documentation.
|
||||
|
||||
RDoc Issues
|
||||
|
||||
* Removed default for the '--main' option
|
||||
* Fixed rendering of the rdoc options
|
||||
* Fixed clean/clobber confusion with rerdoc
|
||||
* 'title' attribute added
|
||||
|
||||
Package Task Library Issues
|
||||
|
||||
* Version (or explicit :noversion) is required.
|
||||
* +package_file+ attribute is now writable
|
||||
|
||||
FileList Issues
|
||||
|
||||
* Dropped bang version of exclude. Now using ant-like include/exclude semantics.
|
||||
* Enabled the "yield self" idiom in FileList#initialize.
|
||||
|
||||
== Version 0.2.9
|
||||
|
||||
This version contains numerous changes as the RubyConf.new(2003)
|
||||
presentation was being prepared. The changes include:
|
||||
|
||||
* The monolithic rubyapp task library is in the process of being
|
||||
dropped in favor of lighter weight task libraries.
|
||||
|
||||
== Version 0.2.7
|
||||
|
||||
* Added "desc" for task descriptions.
|
||||
* -T will now display tasks with descriptions.
|
||||
* -P will display tasks and prerequisites.
|
||||
* Dropped the Sys module in favor of the 1.8.x FileUtils module. Sys
|
||||
is still supported in the contrib area.
|
||||
|
||||
== Version 0.2.6
|
||||
|
||||
* Moved to RubyForge
|
||||
|
||||
== Version 0.2.5
|
||||
|
||||
* Switched to standard ruby app builder.
|
||||
* Added no_match option to file matcher.
|
||||
|
||||
== Version 0.2.4
|
||||
|
||||
* Fixed indir, which neglected to actually change directories.
|
||||
|
||||
== Version 0.2.3
|
||||
|
||||
* Added rake module for a help target
|
||||
* Added 'for_files' to Sys
|
||||
* Added a $rakefile constant
|
||||
* Added test for selecting proper rule with multiple targets.
|
|
@ -0,0 +1,196 @@
|
|||
= RAKE -- Ruby Make
|
||||
|
||||
Supporting Rake version: 0.8.6
|
||||
|
||||
This package contains Rake, a simple ruby build program with
|
||||
capabilities similar to make.
|
||||
|
||||
Rake has the following features:
|
||||
|
||||
* Rakefiles (rake's version of Makefiles) are completely defined in
|
||||
standard Ruby syntax. No XML files to edit. No quirky Makefile
|
||||
syntax to worry about (is that a tab or a space?)
|
||||
|
||||
* Users can specify tasks with prerequisites.
|
||||
|
||||
* Rake supports rule patterns to synthesize implicit tasks.
|
||||
|
||||
* Flexible FileLists that act like arrays but know about manipulating
|
||||
file names and paths.
|
||||
|
||||
* A library of prepackaged tasks to make building rakefiles easier. For example,
|
||||
tasks for building tarballs, gems and RDoc output are provided.
|
||||
|
||||
* Supports parallel execution of tasks.
|
||||
|
||||
|
||||
== Installation
|
||||
|
||||
=== Gem Installation
|
||||
|
||||
Download and install rake with the following.
|
||||
|
||||
gem install rake
|
||||
|
||||
=== Normal Installation
|
||||
|
||||
You can download the source tarball of the latest version of Rake from
|
||||
|
||||
* http://rubyforge.org/project/showfiles.php?group_id=50
|
||||
|
||||
Extract the tarball and run
|
||||
|
||||
% ruby install.rb
|
||||
|
||||
from its distribution directory.
|
||||
|
||||
== Usage
|
||||
|
||||
=== Simple Example
|
||||
|
||||
First, you must write a "Rakefile" file which contains the build rules. Here's
|
||||
a simple example:
|
||||
|
||||
task :default => [:test]
|
||||
|
||||
task :test do
|
||||
ruby "test/unittest.rb"
|
||||
end
|
||||
|
||||
This Rakefile has two tasks:
|
||||
|
||||
* A task named "test", which - upon invocation - will run a unit test file in
|
||||
Ruby.
|
||||
* A task named "default". This task does nothing by itself, but it has exactly
|
||||
one dependency, namely the "test" task. Invoking the "default" task will
|
||||
cause Rake to invoke the "test" task as well.
|
||||
|
||||
Running the "rake" command without any options will cause it to run the
|
||||
"default" task in the Rakefile:
|
||||
|
||||
% ls
|
||||
Rakefile test/
|
||||
% rake
|
||||
(in /home/some_user/Projects/rake)
|
||||
ruby test/unittest.rb
|
||||
....unit test output here...
|
||||
|
||||
Type "rake --help" for all available options.
|
||||
|
||||
|
||||
=== More Information
|
||||
|
||||
* For details on Rake's command-line invocation, read
|
||||
doc/command_line_usage.rdoc[http://rake.rubyforge.org/files/doc/command_line_usage_rdoc.html]
|
||||
* For details on writing Rakefiles, see
|
||||
doc/rakefile.rdoc[http://rake.rubyforge.org/files/doc/rakefile_rdoc.html].
|
||||
* For the original announcement of Rake, see
|
||||
doc/rational.rdoc[http://rake.rubyforge.org/files/doc/rational_rdoc.html].
|
||||
* For a glossary of terms, see
|
||||
doc/glossary.rdoc[http://rake.rubyforge.org/files/doc/glossary_rdoc.html].
|
||||
|
||||
|
||||
== Development
|
||||
|
||||
=== Source Repository
|
||||
|
||||
Rake is currently hosted at github. The github web page is
|
||||
http://github.com/jimweirich/rake. The public git clone URL is
|
||||
|
||||
* git://github.com/jimweirich/rake.git
|
||||
|
||||
=== Running the Rake Test Suite
|
||||
|
||||
If you wish to run the unit and functional tests that come with Rake:
|
||||
|
||||
* Install the 'session' gem in order to run the functional tests.
|
||||
* CD into the top project directory of rake.
|
||||
* Type one of the following:
|
||||
|
||||
rake # If you have a version of rake installed
|
||||
ruby -Ilib bin/rake # If you do not have a version of rake installed.
|
||||
|
||||
=== Issues and Bug Reports
|
||||
|
||||
Bugs, features requests and other issues can be logged at
|
||||
|
||||
* http://onestepback.org/redmine/projects/show/rake
|
||||
|
||||
You will need an account to before you can post issues. Register at
|
||||
http://onestepback.org/redmine/account/register. Or you can send me
|
||||
an email (at jim dot weirich at gmail dot com)
|
||||
|
||||
|
||||
== Online Resources
|
||||
|
||||
=== Rake References
|
||||
|
||||
* Rake Documentation Home: http://docs.rubyrake.org
|
||||
* Rake Project Page: http://rubyforge.org/projects/rake
|
||||
* Rake API Documents: http://rake.rubyforge.org
|
||||
* Rake Source Code Repo: http://github.com/jimweirich/rake
|
||||
* Rake Git Repo Clone URL: git://github.com/jimweirich/rake.git
|
||||
|
||||
=== Presentations and Articles about Rake
|
||||
|
||||
* Jim Weirich's 2003 RubyConf presentation: http://onestepback.org/articles/buildingwithrake/
|
||||
* Martin Fowler's article on Rake: http://martinfowler.com/articles/rake.html
|
||||
|
||||
== Other Make Reinvisionings ...
|
||||
|
||||
Rake is a late entry in the make replacement field. Here are links to
|
||||
other projects with similar (and not so similar) goals.
|
||||
|
||||
* http://directory.fsf.org/bras.html -- Bras, one of earliest
|
||||
implementations of "make in a scripting language".
|
||||
* http://www.a-a-p.org -- Make in Python
|
||||
* http://www.aromatic.com/tools/jam.txt -- JAM, Java Automated Make
|
||||
* http://ant.apache.org -- The Ant project
|
||||
* http://ppt.perl.org/commands/make/index.html -- Make from the Perl
|
||||
Power Tools implementation.
|
||||
* http://search.cpan.org/search?query=PerlBuildSystem -- The Perl Build System
|
||||
* http://make.rubyforge.org -- Rant, another Ruby make tool.
|
||||
|
||||
== Credits
|
||||
|
||||
[<b>Ryan Dlugosz</b>] For the initial conversation that sparked Rake.
|
||||
|
||||
[<b>nobu.nokada@softhome.net</b>] For the initial patch for rule support.
|
||||
|
||||
[<b>Tilman Sauerbeck <tilman@code-monkey.de></b>] For the recursive rule patch.
|
||||
|
||||
== License
|
||||
|
||||
Rake is available under an MIT-style license.
|
||||
|
||||
:include: MIT-LICENSE
|
||||
|
||||
== Support
|
||||
|
||||
The Rake homepage is http://rake.rubyforge.org. You can find the Rake
|
||||
RubyForge page at http://rubyforge.org/projects/rake.
|
||||
|
||||
Feel free to submit commits or feature requests. If you send a patch,
|
||||
remember to update the corresponding unit tests. If fact, I prefer
|
||||
new feature to be submitted in the form of new unit tests.
|
||||
|
||||
For other information, feel free to ask on the ruby-talk mailing list
|
||||
(which is mirrored to comp.lang.ruby) or contact
|
||||
jim dot weirich at gmail.com.
|
||||
|
||||
---
|
||||
|
||||
= Other stuff
|
||||
|
||||
Author:: Jim Weirich <jim.weirich@gmail.com>
|
||||
Requires:: Ruby 1.8.0 or later
|
||||
License:: Copyright 2003-2008 by Jim Weirich.
|
||||
Released under an MIT-style license. See the LICENSE file
|
||||
included in the distribution.
|
||||
|
||||
== Warranty
|
||||
|
||||
This software is provided "as is" and without any express or
|
||||
implied warranties, including, without limitation, the implied
|
||||
warranties of merchantibility and fitness for a particular
|
||||
purpose.
|
|
@ -0,0 +1,102 @@
|
|||
= Rake Command Line Usage
|
||||
|
||||
Rake is invoked from the command line using:
|
||||
|
||||
% rake [<em>options</em> ...] [<em>VAR</em>=<em>VALUE</em>] [<em>targets</em> ...]
|
||||
|
||||
Options are:
|
||||
|
||||
[<tt><em>name</em>=<em>value</em></tt>]
|
||||
Set the environment variable <em>name</em> to <em>value</em>
|
||||
during the execution of the <b>rake</b> command. You can access
|
||||
the value by using ENV['<em>name</em>'].
|
||||
|
||||
[<tt>--classic-namespace</tt> (-n)]
|
||||
Import the Task, FileTask, and FileCreateTask into the top-level
|
||||
scope to be compatible with older versions of Rake. Alternatively
|
||||
you can include the line <code>require
|
||||
'rake/classic_namespace'</code> in your Rakefile to get the
|
||||
classic behavior.
|
||||
|
||||
[<tt>--describe</tt> _pattern_ (-D)]
|
||||
Describe the tasks (matching optional PATTERN), then exit.
|
||||
|
||||
[<tt>--dry-run</tt> (-n)]
|
||||
Do a dry run. Print the tasks invoked and executed, but do not
|
||||
actually execute any of the actions.
|
||||
|
||||
[<tt>--execute</tt> _code_ (-e)]
|
||||
Execute some Ruby code and exit.
|
||||
|
||||
[<tt>--execute-print</tt> _code_ (-p)]
|
||||
Execute some Ruby code, print the result, and exit.
|
||||
|
||||
[<tt>--execute-continue</tt> _code_ (-p)]
|
||||
Execute some Ruby code, then continue with normal task processing.
|
||||
|
||||
[<tt>--help</tt> (-H)]
|
||||
Display some help text and exit.
|
||||
|
||||
[<tt>--libdir</tt> _directory_ (-I)]
|
||||
Add _directory_ to the list of directories searched for require.
|
||||
|
||||
[<tt>--nosearch</tt> (-N)]
|
||||
Do not search for a Rakefile in parent directories.
|
||||
|
||||
[<tt>--prereqs</tt> (-P)]
|
||||
Display a list of all tasks and their immediate prerequisites.
|
||||
|
||||
[<tt>--quiet</tt> (-q)]
|
||||
Do not echo commands from FileUtils.
|
||||
|
||||
[<tt>--rakefile</tt> _filename_ (-f)]
|
||||
Use _filename_ as the name of the rakefile. The default rakefile
|
||||
names are +rakefile+ and +Rakefile+ (with +rakefile+ taking
|
||||
precedence). If the rakefile is not found in the current
|
||||
directory, +rake+ will search parent directories for a match. The
|
||||
directory where the Rakefile is found will become the current
|
||||
directory for the actions executed in the Rakefile.
|
||||
|
||||
[<tt>--rakelibdir</tt> _rakelibdir_ (-R)]
|
||||
Auto-import any .rake files in RAKELIBDIR. (default is 'rakelib')
|
||||
|
||||
[<tt>--require</tt> _name_ (-r)]
|
||||
Require _name_ before executing the Rakefile.
|
||||
|
||||
[<tt>--rules</tt>]
|
||||
Trace the rules resolution.
|
||||
|
||||
[<tt>--silent (-s)</tt>]
|
||||
Like --quiet, but also suppresses the 'in directory' announcement.
|
||||
|
||||
[<tt>--system</tt> (-g)]
|
||||
Use the system wide (global) rakefiles. The project Rakefile is
|
||||
ignored. By default, the system wide rakefiles are used only if no
|
||||
project Rakefile is found. On Unix-like system, the system wide
|
||||
rake files are located in $HOME/.rake. On a windows system they
|
||||
are stored in $APPDATA/Rake.
|
||||
|
||||
[<tt>--no-system</tt> (-G)]
|
||||
Use the project level Rakefile, ignoring the system-wide (global)
|
||||
rakefiles.
|
||||
|
||||
[<tt>--tasks</tt> (-T)]
|
||||
Display a list of the major tasks and their comments. Comments
|
||||
are defined using the "desc" command.
|
||||
|
||||
[<tt>--trace</tt> (-t)]
|
||||
Turn on invoke/execute tracing. Also enable full backtrace on
|
||||
errors.
|
||||
|
||||
[<tt>--usage</tt> (-h)]
|
||||
Display a usage message and exit.
|
||||
|
||||
[<tt>--verbose</tt> (-v)]
|
||||
Echo the Sys commands to standard output.
|
||||
|
||||
[<tt>--version</tt> (-V)]
|
||||
Display the program version and exit.
|
||||
|
||||
In addition, any command line option of the form
|
||||
<em>VAR</em>=<em>VALUE</em> will be added to the environment hash
|
||||
<tt>ENV</tt> and may be tested in the Rakefile.
|
|
@ -0,0 +1,38 @@
|
|||
# Example Rakefile -*- ruby -*-
|
||||
|
||||
task :default => [:main]
|
||||
|
||||
file "a.o" => ["a.c"] do |t|
|
||||
src = t.name.sub(/\.o$/, '.c')
|
||||
sh "gcc #{src} -c -o #{t.name}"
|
||||
end
|
||||
|
||||
file "b.o" => ["b.c"] do |t|
|
||||
src = t.name.sub(/\.o$/, '.c')
|
||||
sh "gcc #{src} -c -o #{t.name}"
|
||||
end
|
||||
|
||||
file "main.o" => ["main.c"] do |t|
|
||||
src = t.name.sub(/\.o$/, '.c')
|
||||
sh "gcc #{src} -c -o #{t.name}"
|
||||
end
|
||||
|
||||
OBJFILES = ["a.o", "b.o", "main.o"]
|
||||
task :obj => OBJFILES
|
||||
|
||||
file "main" => OBJFILES do |t|
|
||||
sh "gcc -o #{t.name} main.o a.o b.o"
|
||||
end
|
||||
|
||||
task :clean do
|
||||
rm_f FileList['*.o']
|
||||
Dir['*~'].each { |fn| rm_f fn }
|
||||
end
|
||||
|
||||
task :clobber => [:clean] do
|
||||
rm_f "main"
|
||||
end
|
||||
|
||||
task :run => ["main"] do
|
||||
sh "./main"
|
||||
end
|
|
@ -0,0 +1,35 @@
|
|||
# Example Rakefile -*- ruby -*-
|
||||
# Using the power of Ruby
|
||||
|
||||
task :default => [:main]
|
||||
|
||||
def ext(fn, newext)
|
||||
fn.sub(/\.[^.]+$/, newext)
|
||||
end
|
||||
|
||||
SRCFILES = Dir['*.c']
|
||||
OBJFILES = SRCFILES.collect { |fn| ext(fn,".o") }
|
||||
|
||||
OBJFILES.each do |objfile|
|
||||
srcfile = ext(objfile, ".c")
|
||||
file objfile => [srcfile] do |t|
|
||||
sh "gcc #{srcfile} -c -o #{t.name}"
|
||||
end
|
||||
end
|
||||
|
||||
file "main" => OBJFILES do |t|
|
||||
sh "gcc -o #{t.name} main.o a.o b.o"
|
||||
end
|
||||
|
||||
task :clean do
|
||||
rm_f FileList['*.o']
|
||||
Dir['*~'].each { |fn| rm_f fn }
|
||||
end
|
||||
|
||||
task :clobber => [:clean] do
|
||||
rm_f "main"
|
||||
end
|
||||
|
||||
task :run => ["main"] do
|
||||
sh "./main"
|
||||
end
|
|
@ -0,0 +1,6 @@
|
|||
#include <stdio.h>
|
||||
|
||||
void a()
|
||||
{
|
||||
printf ("In function a\n");
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
#include <stdio.h>
|
||||
|
||||
void b()
|
||||
{
|
||||
printf ("In function b\n");
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
#include <stdio.h>
|
||||
|
||||
extern void a();
|
||||
extern void b();
|
||||
|
||||
int main ()
|
||||
{
|
||||
a();
|
||||
b();
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,51 @@
|
|||
= Glossary
|
||||
|
||||
[<b>action</b>]
|
||||
Code to be executed in order to perform a task. Actions in a
|
||||
rakefile are specified in a code block (usually delimited by
|
||||
+do+/+end+ pairs.
|
||||
|
||||
[<b>execute</b>]
|
||||
When a task is executed, all of its actions are performed, in
|
||||
the order they were defined. Note that unlike
|
||||
<tt>invoke</tt>, <tt>execute</tt> always executes the actions
|
||||
(without invoking or executing the prerequisites).
|
||||
|
||||
[<b>file task</b> (FileTask)]
|
||||
A file task is a task whose purpose is to create a file
|
||||
(which has the same name as the task). When invoked, a file
|
||||
task will only execute if one or more of the following
|
||||
conditions are true.
|
||||
|
||||
1. The associated file does not exist.
|
||||
2. A prerequisite has a later time stamp than the existing file.
|
||||
|
||||
Because normal Tasks always have the current time as
|
||||
timestamp, a FileTask that has a normal Task prerequisite
|
||||
will always execute.
|
||||
|
||||
[<b>invoke</b>]
|
||||
When a task is invoked, first we check to see if it has been
|
||||
invoked before. if it has been, then nothing else is done.
|
||||
If this is the first time its been invoked, then we invoke
|
||||
each of its prerequisites. Finally, we check to see if we
|
||||
need to execute the actions of this task by calling
|
||||
<tt>needed?</tt>. Finally, if the task is needed, we execute
|
||||
its actions.
|
||||
|
||||
NOTE: Currently prerequisites are invoked even if the task is
|
||||
not needed. This may change in the future.
|
||||
|
||||
[<b>prerequisites</b>]
|
||||
Every task has a set (possiblity empty) of prerequisites. A
|
||||
prerequisite P to Task T is itself a task that must be invoked
|
||||
before Task T.
|
||||
|
||||
[<b>rule</b>]
|
||||
A rule is a recipe for synthesizing a task when no task is
|
||||
explicitly defined. Rules generally synthesize file tasks.
|
||||
|
||||
[<b>task</b> (Task)]
|
||||
Basic unit of work in a rakefile. A task has a name, a set of
|
||||
prerequisites and a list of actions to be performed.
|
||||
|
|
@ -0,0 +1,591 @@
|
|||
module RDoc
|
||||
module Page
|
||||
|
||||
FONTS = "\"Bitstream Vera Sans\", Verdana, Arial, Helvetica, sans-serif"
|
||||
|
||||
STYLE = <<CSS
|
||||
a {
|
||||
color: #00F;
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
a:hover {
|
||||
color: #77F;
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
body, td, p {
|
||||
font-family: %fonts%;
|
||||
background: #FFF;
|
||||
color: #000;
|
||||
margin: 0px;
|
||||
font-size: small;
|
||||
}
|
||||
|
||||
#content {
|
||||
margin: 2em;
|
||||
}
|
||||
|
||||
#description p {
|
||||
margin-bottom: 0.5em;
|
||||
}
|
||||
|
||||
.sectiontitle {
|
||||
margin-top: 1em;
|
||||
margin-bottom: 1em;
|
||||
padding: 0.5em;
|
||||
padding-left: 2em;
|
||||
background: #005;
|
||||
color: #FFF;
|
||||
font-weight: bold;
|
||||
border: 1px dotted black;
|
||||
}
|
||||
|
||||
.attr-rw {
|
||||
padding-left: 1em;
|
||||
padding-right: 1em;
|
||||
text-align: center;
|
||||
color: #055;
|
||||
}
|
||||
|
||||
.attr-name {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.attr-desc {
|
||||
}
|
||||
|
||||
.attr-value {
|
||||
font-family: monospace;
|
||||
}
|
||||
|
||||
.file-title-prefix {
|
||||
font-size: large;
|
||||
}
|
||||
|
||||
.file-title {
|
||||
font-size: large;
|
||||
font-weight: bold;
|
||||
background: #005;
|
||||
color: #FFF;
|
||||
}
|
||||
|
||||
.banner {
|
||||
background: #005;
|
||||
color: #FFF;
|
||||
border: 1px solid black;
|
||||
padding: 1em;
|
||||
}
|
||||
|
||||
.banner td {
|
||||
background: transparent;
|
||||
color: #FFF;
|
||||
}
|
||||
|
||||
h1 a, h2 a, .sectiontitle a, .banner a {
|
||||
color: #FF0;
|
||||
}
|
||||
|
||||
h1 a:hover, h2 a:hover, .sectiontitle a:hover, .banner a:hover {
|
||||
color: #FF7;
|
||||
}
|
||||
|
||||
.dyn-source {
|
||||
display: none;
|
||||
background: #FFE;
|
||||
color: #000;
|
||||
border: 1px dotted black;
|
||||
margin: 0.5em 2em 0.5em 2em;
|
||||
padding: 0.5em;
|
||||
}
|
||||
|
||||
.dyn-source .cmt {
|
||||
color: #00F;
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
.dyn-source .kw {
|
||||
color: #070;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.method {
|
||||
margin-left: 1em;
|
||||
margin-right: 1em;
|
||||
margin-bottom: 1em;
|
||||
}
|
||||
|
||||
.description pre {
|
||||
padding: 0.5em;
|
||||
border: 1px dotted black;
|
||||
background: #FFE;
|
||||
}
|
||||
|
||||
.method .title {
|
||||
font-family: monospace;
|
||||
font-size: large;
|
||||
border-bottom: 1px dashed black;
|
||||
margin-bottom: 0.3em;
|
||||
padding-bottom: 0.1em;
|
||||
}
|
||||
|
||||
.method .description, .method .sourcecode {
|
||||
margin-left: 1em;
|
||||
}
|
||||
|
||||
.description p, .sourcecode p {
|
||||
margin-bottom: 0.5em;
|
||||
}
|
||||
|
||||
.method .sourcecode p.source-link {
|
||||
text-indent: 0em;
|
||||
margin-top: 0.5em;
|
||||
}
|
||||
|
||||
.method .aka {
|
||||
margin-top: 0.3em;
|
||||
margin-left: 1em;
|
||||
font-style: italic;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
h1 {
|
||||
padding: 1em;
|
||||
border: 1px solid black;
|
||||
font-size: x-large;
|
||||
font-weight: bold;
|
||||
color: #FFF;
|
||||
background: #007;
|
||||
}
|
||||
|
||||
h2 {
|
||||
padding: 0.5em 1em 0.5em 1em;
|
||||
border: 1px solid black;
|
||||
font-size: large;
|
||||
font-weight: bold;
|
||||
color: #FFF;
|
||||
background: #009;
|
||||
}
|
||||
|
||||
h3, h4, h5, h6 {
|
||||
padding: 0.2em 1em 0.2em 1em;
|
||||
border: 1px dashed black;
|
||||
color: #000;
|
||||
background: #AAF;
|
||||
}
|
||||
|
||||
.sourcecode > pre {
|
||||
padding: 0.5em;
|
||||
border: 1px dotted black;
|
||||
background: #FFE;
|
||||
}
|
||||
|
||||
CSS
|
||||
|
||||
XHTML_PREAMBLE = %{<?xml version="1.0" encoding="%charset%"?>
|
||||
<!DOCTYPE html
|
||||
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
|
||||
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||
}
|
||||
|
||||
HEADER = XHTML_PREAMBLE + <<ENDHEADER
|
||||
<html>
|
||||
<head>
|
||||
<title>%title%</title>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=%charset%" />
|
||||
<link rel="stylesheet" href="%style_url%" type="text/css" media="screen" />
|
||||
|
||||
<script language="JavaScript" type="text/javascript">
|
||||
// <![CDATA[
|
||||
|
||||
function toggleSource( id )
|
||||
{
|
||||
var elem
|
||||
var link
|
||||
|
||||
if( document.getElementById )
|
||||
{
|
||||
elem = document.getElementById( id )
|
||||
link = document.getElementById( "l_" + id )
|
||||
}
|
||||
else if ( document.all )
|
||||
{
|
||||
elem = eval( "document.all." + id )
|
||||
link = eval( "document.all.l_" + id )
|
||||
}
|
||||
else
|
||||
return false;
|
||||
|
||||
if( elem.style.display == "block" )
|
||||
{
|
||||
elem.style.display = "none"
|
||||
link.innerHTML = "show source"
|
||||
}
|
||||
else
|
||||
{
|
||||
elem.style.display = "block"
|
||||
link.innerHTML = "hide source"
|
||||
}
|
||||
}
|
||||
|
||||
function openCode( url )
|
||||
{
|
||||
window.open( url, "SOURCE_CODE", "width=400,height=400,scrollbars=yes" )
|
||||
}
|
||||
// ]]>
|
||||
</script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
ENDHEADER
|
||||
|
||||
FILE_PAGE = <<HTML
|
||||
<table border='0' cellpadding='0' cellspacing='0' width="100%" class='banner'>
|
||||
<tr><td>
|
||||
<table width="100%" border='0' cellpadding='0' cellspacing='0'><tr>
|
||||
<td class="file-title" colspan="2"><span class="file-title-prefix">File</span><br />%short_name%</td>
|
||||
<td align="right">
|
||||
<table border='0' cellspacing="0" cellpadding="2">
|
||||
<tr>
|
||||
<td>Path:</td>
|
||||
<td>%full_path%
|
||||
IF:cvsurl
|
||||
(<a href="%cvsurl%">CVS</a>)
|
||||
ENDIF:cvsurl
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Modified:</td>
|
||||
<td>%dtm_modified%</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
</table><br>
|
||||
HTML
|
||||
|
||||
###################################################################
|
||||
|
||||
CLASS_PAGE = <<HTML
|
||||
<table width="100%" border='0' cellpadding='0' cellspacing='0' class='banner'><tr>
|
||||
<td class="file-title"><span class="file-title-prefix">%classmod%</span><br />%full_name%</td>
|
||||
<td align="right">
|
||||
<table cellspacing=0 cellpadding=2>
|
||||
<tr valign="top">
|
||||
<td>In:</td>
|
||||
<td>
|
||||
START:infiles
|
||||
HREF:full_path_url:full_path:
|
||||
IF:cvsurl
|
||||
(<a href="%cvsurl%">CVS</a>)
|
||||
ENDIF:cvsurl
|
||||
END:infiles
|
||||
</td>
|
||||
</tr>
|
||||
IF:parent
|
||||
<tr>
|
||||
<td>Parent:</td>
|
||||
<td>
|
||||
IF:par_url
|
||||
<a href="%par_url%">
|
||||
ENDIF:par_url
|
||||
%parent%
|
||||
IF:par_url
|
||||
</a>
|
||||
ENDIF:par_url
|
||||
</td>
|
||||
</tr>
|
||||
ENDIF:parent
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
HTML
|
||||
|
||||
###################################################################
|
||||
|
||||
METHOD_LIST = <<HTML
|
||||
<div id="content">
|
||||
IF:diagram
|
||||
<table cellpadding='0' cellspacing='0' border='0' width="100%"><tr><td align="center">
|
||||
%diagram%
|
||||
</td></tr></table>
|
||||
ENDIF:diagram
|
||||
|
||||
IF:description
|
||||
<div class="description">%description%</div>
|
||||
ENDIF:description
|
||||
|
||||
IF:requires
|
||||
<div class="sectiontitle">Required Files</div>
|
||||
<ul>
|
||||
START:requires
|
||||
<li>HREF:aref:name:</li>
|
||||
END:requires
|
||||
</ul>
|
||||
ENDIF:requires
|
||||
|
||||
IF:toc
|
||||
<div class="sectiontitle">Contents</div>
|
||||
<ul>
|
||||
START:toc
|
||||
<li><a href="#%href%">%secname%</a></li>
|
||||
END:toc
|
||||
</ul>
|
||||
ENDIF:toc
|
||||
|
||||
IF:methods
|
||||
<div class="sectiontitle">Methods</div>
|
||||
<ul>
|
||||
START:methods
|
||||
<li>HREF:aref:name:</li>
|
||||
END:methods
|
||||
</ul>
|
||||
ENDIF:methods
|
||||
|
||||
IF:includes
|
||||
<div class="sectiontitle">Included Modules</div>
|
||||
<ul>
|
||||
START:includes
|
||||
<li>HREF:aref:name:</li>
|
||||
END:includes
|
||||
</ul>
|
||||
ENDIF:includes
|
||||
|
||||
START:sections
|
||||
IF:sectitle
|
||||
<div class="sectiontitle"><a nem="%secsequence%">%sectitle%</a></div>
|
||||
IF:seccomment
|
||||
<div class="description">
|
||||
%seccomment%
|
||||
</div>
|
||||
ENDIF:seccomment
|
||||
ENDIF:sectitle
|
||||
|
||||
IF:classlist
|
||||
<div class="sectiontitle">Classes and Modules</div>
|
||||
%classlist%
|
||||
ENDIF:classlist
|
||||
|
||||
IF:constants
|
||||
<div class="sectiontitle">Constants</div>
|
||||
<table border='0' cellpadding='5'>
|
||||
START:constants
|
||||
<tr valign='top'>
|
||||
<td class="attr-name">%name%</td>
|
||||
<td>=</td>
|
||||
<td class="attr-value">%value%</td>
|
||||
</tr>
|
||||
IF:desc
|
||||
<tr valign='top'>
|
||||
<td> </td>
|
||||
<td colspan="2" class="attr-desc">%desc%</td>
|
||||
</tr>
|
||||
ENDIF:desc
|
||||
END:constants
|
||||
</table>
|
||||
ENDIF:constants
|
||||
|
||||
IF:attributes
|
||||
<div class="sectiontitle">Attributes</div>
|
||||
<table border='0' cellpadding='5'>
|
||||
START:attributes
|
||||
<tr valign='top'>
|
||||
<td class='attr-rw'>
|
||||
IF:rw
|
||||
[%rw%]
|
||||
ENDIF:rw
|
||||
</td>
|
||||
<td class='attr-name'>%name%</td>
|
||||
<td class='attr-desc'>%a_desc%</td>
|
||||
</tr>
|
||||
END:attributes
|
||||
</table>
|
||||
ENDIF:attributes
|
||||
|
||||
IF:method_list
|
||||
START:method_list
|
||||
IF:methods
|
||||
<div class="sectiontitle">%type% %category% methods</div>
|
||||
START:methods
|
||||
<div class="method">
|
||||
<div class="title">
|
||||
IF:callseq
|
||||
<a name="%aref%"></a><b>%callseq%</b>
|
||||
ENDIF:callseq
|
||||
IFNOT:callseq
|
||||
<a name="%aref%"></a><b>%name%</b>%params%
|
||||
ENDIF:callseq
|
||||
IF:codeurl
|
||||
[ <a href="javascript:openCode('%codeurl%')">source</a> ]
|
||||
ENDIF:codeurl
|
||||
</div>
|
||||
IF:m_desc
|
||||
<div class="description">
|
||||
%m_desc%
|
||||
</div>
|
||||
ENDIF:m_desc
|
||||
IF:aka
|
||||
<div class="aka">
|
||||
This method is also aliased as
|
||||
START:aka
|
||||
<a href="%aref%">%name%</a>
|
||||
END:aka
|
||||
</div>
|
||||
ENDIF:aka
|
||||
IF:sourcecode
|
||||
<div class="sourcecode">
|
||||
<p class="source-link">[ <a href="javascript:toggleSource('%aref%_source')" id="l_%aref%_source">show source</a> ]</p>
|
||||
<div id="%aref%_source" class="dyn-source">
|
||||
<pre>
|
||||
%sourcecode%
|
||||
</pre>
|
||||
</div>
|
||||
</div>
|
||||
ENDIF:sourcecode
|
||||
</div>
|
||||
END:methods
|
||||
ENDIF:methods
|
||||
END:method_list
|
||||
ENDIF:method_list
|
||||
END:sections
|
||||
</div>
|
||||
HTML
|
||||
|
||||
FOOTER = <<ENDFOOTER
|
||||
</body>
|
||||
</html>
|
||||
ENDFOOTER
|
||||
|
||||
BODY = HEADER + <<ENDBODY
|
||||
!INCLUDE! <!-- banner header -->
|
||||
|
||||
<div id="bodyContent">
|
||||
#{METHOD_LIST}
|
||||
</div>
|
||||
|
||||
#{FOOTER}
|
||||
ENDBODY
|
||||
|
||||
########################## Source code ##########################
|
||||
|
||||
SRC_PAGE = XHTML_PREAMBLE + <<HTML
|
||||
<html>
|
||||
<head><title>%title%</title>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=%charset%">
|
||||
<style>
|
||||
.ruby-comment { color: green; font-style: italic }
|
||||
.ruby-constant { color: #4433aa; font-weight: bold; }
|
||||
.ruby-identifier { color: #222222; }
|
||||
.ruby-ivar { color: #2233dd; }
|
||||
.ruby-keyword { color: #3333FF; font-weight: bold }
|
||||
.ruby-node { color: #777777; }
|
||||
.ruby-operator { color: #111111; }
|
||||
.ruby-regexp { color: #662222; }
|
||||
.ruby-value { color: #662222; font-style: italic }
|
||||
.kw { color: #3333FF; font-weight: bold }
|
||||
.cmt { color: green; font-style: italic }
|
||||
.str { color: #662222; font-style: italic }
|
||||
.re { color: #662222; }
|
||||
</style>
|
||||
</head>
|
||||
<body bgcolor="white">
|
||||
<pre>%code%</pre>
|
||||
</body>
|
||||
</html>
|
||||
HTML
|
||||
|
||||
########################## Index ################################
|
||||
|
||||
FR_INDEX_BODY = <<HTML
|
||||
!INCLUDE!
|
||||
HTML
|
||||
|
||||
FILE_INDEX = XHTML_PREAMBLE + <<HTML
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=%charset%">
|
||||
<style>
|
||||
<!--
|
||||
body {
|
||||
background-color: #EEE;
|
||||
font-family: #{FONTS};
|
||||
color: #000;
|
||||
margin: 0px;
|
||||
}
|
||||
.banner {
|
||||
background: #005;
|
||||
color: #FFF;
|
||||
padding: 0.2em;
|
||||
font-size: small;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
}
|
||||
.entries {
|
||||
margin: 0.25em 1em 0 1em;
|
||||
font-size: x-small;
|
||||
}
|
||||
a {
|
||||
color: #00F;
|
||||
text-decoration: none;
|
||||
white-space: nowrap;
|
||||
}
|
||||
a:hover {
|
||||
color: #77F;
|
||||
text-decoration: underline;
|
||||
}
|
||||
-->
|
||||
</style>
|
||||
<base target="docwin">
|
||||
</head>
|
||||
<body>
|
||||
<div class="banner">%list_title%</div>
|
||||
<div class="entries">
|
||||
START:entries
|
||||
<a href="%href%">%name%</a><br>
|
||||
END:entries
|
||||
</div>
|
||||
</body></html>
|
||||
HTML
|
||||
|
||||
CLASS_INDEX = FILE_INDEX
|
||||
METHOD_INDEX = FILE_INDEX
|
||||
|
||||
INDEX = XHTML_PREAMBLE + <<HTML
|
||||
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||
<head>
|
||||
<title>%title%</title>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=%charset%">
|
||||
</head>
|
||||
|
||||
<frameset cols="20%,*">
|
||||
<frameset rows="15%,35%,50%">
|
||||
<frame src="fr_file_index.html" title="Files" name="Files" />
|
||||
<frame src="fr_class_index.html" name="Classes" />
|
||||
<frame src="fr_method_index.html" name="Methods" />
|
||||
</frameset>
|
||||
IF:inline_source
|
||||
<frame src="%initial_page%" name="docwin">
|
||||
ENDIF:inline_source
|
||||
IFNOT:inline_source
|
||||
<frameset rows="80%,20%">
|
||||
<frame src="%initial_page%" name="docwin">
|
||||
<frame src="blank.html" name="source">
|
||||
</frameset>
|
||||
ENDIF:inline_source
|
||||
<noframes>
|
||||
<body bgcolor="white">
|
||||
Click <a href="html/index.html">here</a> for a non-frames
|
||||
version of this page.
|
||||
</body>
|
||||
</noframes>
|
||||
</frameset>
|
||||
|
||||
</html>
|
||||
HTML
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
|
|
@ -0,0 +1,127 @@
|
|||
= Original Prototype Rake
|
||||
|
||||
This is the original 100 line prototype rake program.
|
||||
|
||||
---
|
||||
#!/usr/bin/env ruby
|
||||
|
||||
require 'ftools'
|
||||
|
||||
class Task
|
||||
TASKS = Hash.new
|
||||
|
||||
attr_reader :prerequisites
|
||||
|
||||
def initialize(task_name)
|
||||
@name = task_name
|
||||
@prerequisites = []
|
||||
@actions = []
|
||||
end
|
||||
|
||||
def enhance(deps=nil, &block)
|
||||
@prerequisites |= deps if deps
|
||||
@actions << block if block_given?
|
||||
self
|
||||
end
|
||||
|
||||
def name
|
||||
@name.to_s
|
||||
end
|
||||
|
||||
def invoke
|
||||
@prerequisites.each { |n| Task[n].invoke }
|
||||
execute if needed?
|
||||
end
|
||||
|
||||
def execute
|
||||
return if @triggered
|
||||
@triggered = true
|
||||
@actions.collect { |act| result = act.call(self) }.last
|
||||
end
|
||||
|
||||
def needed?
|
||||
true
|
||||
end
|
||||
|
||||
def timestamp
|
||||
Time.now
|
||||
end
|
||||
|
||||
class << self
|
||||
def [](task_name)
|
||||
TASKS[intern(task_name)] or fail "Don't know how to rake #{task_name}"
|
||||
end
|
||||
|
||||
def define_task(args, &block)
|
||||
case args
|
||||
when Hash
|
||||
fail "Too Many Target Names: #{args.keys.join(' ')}" if args.size > 1
|
||||
fail "No Task Name Given" if args.size < 1
|
||||
task_name = args.keys[0]
|
||||
deps = args[task_name]
|
||||
else
|
||||
task_name = args
|
||||
deps = []
|
||||
end
|
||||
deps = deps.collect {|d| intern(d) }
|
||||
get(task_name).enhance(deps, &block)
|
||||
end
|
||||
|
||||
def get(task_name)
|
||||
name = intern(task_name)
|
||||
TASKS[name] ||= self.new(name)
|
||||
end
|
||||
|
||||
def intern(task_name)
|
||||
(Symbol === task_name) ? task_name : task_name.intern
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
class FileTask < Task
|
||||
def needed?
|
||||
return true unless File.exist?(name)
|
||||
latest_prereq = @prerequisites.collect{|n| Task[n].timestamp}.max
|
||||
return false if latest_prereq.nil?
|
||||
timestamp < latest_prereq
|
||||
end
|
||||
|
||||
def timestamp
|
||||
File.new(name.to_s).mtime
|
||||
end
|
||||
end
|
||||
|
||||
def task(args, &block)
|
||||
Task.define_task(args, &block)
|
||||
end
|
||||
|
||||
def file(args, &block)
|
||||
FileTask.define_task(args, &block)
|
||||
end
|
||||
|
||||
def sys(cmd)
|
||||
puts cmd
|
||||
system(cmd) or fail "Command Failed: [#{cmd}]"
|
||||
end
|
||||
|
||||
def rake
|
||||
begin
|
||||
here = Dir.pwd
|
||||
while ! File.exist?("Rakefile")
|
||||
Dir.chdir("..")
|
||||
fail "No Rakefile found" if Dir.pwd == here
|
||||
here = Dir.pwd
|
||||
end
|
||||
puts "(in #{Dir.pwd})"
|
||||
load "./Rakefile"
|
||||
ARGV.push("default") if ARGV.size == 0
|
||||
ARGV.each { |task_name| Task[task_name].invoke }
|
||||
rescue Exception => ex
|
||||
puts "rake aborted ... #{ex.message}"
|
||||
puts ex.backtrace.find {|str| str =~ /Rakefile/ } || ""
|
||||
end
|
||||
end
|
||||
|
||||
if __FILE__ == $0 then
|
||||
rake
|
||||
end
|
|
@ -0,0 +1,534 @@
|
|||
= Rakefile Format (as of version 0.8.3)
|
||||
|
||||
First of all, there is no special format for a Rakefile. A Rakefile
|
||||
contains executable Ruby code. Anything legal in a ruby script is
|
||||
allowed in a Rakefile.
|
||||
|
||||
Now that we understand there is no special syntax in a Rakefile, there
|
||||
are some conventions that are used in a Rakefile that are a little
|
||||
unusual in a typical Ruby program. Since a Rakefile is tailored to
|
||||
specifying tasks and actions, the idioms used in a Rakefile are
|
||||
designed to support that.
|
||||
|
||||
So, what goes into a Rakefile?
|
||||
|
||||
== Tasks
|
||||
|
||||
Tasks are the main unit of work in a Rakefile. Tasks have a name
|
||||
(usually given as a symbol or a string), a list of prerequisites (more
|
||||
symbols or strings) and a list of actions (given as a block).
|
||||
|
||||
=== Simple Tasks
|
||||
|
||||
A task is declared by using the +task+ method. +task+ takes a single
|
||||
parameter that is the name of the task.
|
||||
|
||||
task :name
|
||||
|
||||
=== Tasks with Prerequisites
|
||||
|
||||
Any prerequisites are given as a list (inclosed in square brackets)
|
||||
following the name and an arrow (=>).
|
||||
|
||||
task :name => [:prereq1, :prereq2]
|
||||
|
||||
<b>NOTE:</b> Although this syntax looks a little funky, it is legal
|
||||
Ruby. We are constructing a hash where the key is :name and the value
|
||||
for that key is the list of prerequisites. It is equivalent to the
|
||||
following ...
|
||||
|
||||
hash = Hash.new
|
||||
hash[:name] = [:prereq1, :prereq2]
|
||||
task(hash)
|
||||
|
||||
=== Tasks with Actions
|
||||
|
||||
Actions are defined by passing a block to the +task+ method. Any Ruby
|
||||
code can be placed in the block. The block may reference the task
|
||||
object via the block paramter..
|
||||
|
||||
task :name => [:prereq1, :prereq2] do |t|
|
||||
# actions (may reference t)
|
||||
end
|
||||
|
||||
=== Multiple Definitions
|
||||
|
||||
A task may be specified more than once. Each specification adds its
|
||||
prerequisites and actions to the existing definition. This allows one
|
||||
part of a rakefile to specify the actions and a different rakefile
|
||||
(perhaps separately generated) to specify the dependencies.
|
||||
|
||||
For example, the following is equivalent to the single task
|
||||
specification given above.
|
||||
|
||||
task :name
|
||||
task :name => [:prereq1]
|
||||
task :name => [:prereq2]
|
||||
task :name do |t|
|
||||
# actions
|
||||
end
|
||||
|
||||
== File Tasks
|
||||
|
||||
Some tasks are designed to create a file from one or more other files.
|
||||
Tasks that generate these files may be skipped if the file already
|
||||
exists. File tasks are used to specify file creation tasks.
|
||||
|
||||
File tasks are declared using the +file+ method (instead of the +task+
|
||||
method). In addition, file tasks are usually named with a string
|
||||
rather than a symbol.
|
||||
|
||||
The following file task creates a executable program (named +prog+)
|
||||
given two object files name <tt>a.o</tt> and <tt>b.o</tt>. The tasks
|
||||
for creating <tt>a.o</tt> and <tt>b.o</tt> are not shown.
|
||||
|
||||
file "prog" => ["a.o", "b.o"] do |t|
|
||||
sh "cc -o #{t.name} #{t.prerequisites.join(' ')}"
|
||||
end
|
||||
|
||||
== Directory Tasks
|
||||
|
||||
It is common to need to create directories upon demand. The
|
||||
+directory+ convenience method is a short-hand for creating a FileTask
|
||||
that creates the directory. For example, the following declaration
|
||||
...
|
||||
|
||||
directory "testdata/examples/doc"
|
||||
|
||||
is equivalent to ...
|
||||
|
||||
file "testdata" do |t| mkdir t.name end
|
||||
file "testdata/examples" do |t| mkdir t.name end
|
||||
file "testdata/examples/doc" do |t| mkdir t.name end
|
||||
|
||||
The +directory+ method does not accept prerequisites or actions, but
|
||||
both prerequisites and actions can be added later. For example ...
|
||||
|
||||
directory "testdata"
|
||||
file "testdata" => ["otherdata"]
|
||||
file "testdata" do
|
||||
cp Dir["standard_data/*.data"], "testdata"
|
||||
end
|
||||
|
||||
== Tasks with Parallel Prerequisites
|
||||
|
||||
Rake allows parallel execution of prerequisites using the following syntax:
|
||||
|
||||
multitask :copy_files => [:copy_src, :copy_doc, :copy_bin] do
|
||||
puts "All Copies Complete"
|
||||
end
|
||||
|
||||
In this example, +copy_files+ is a normal rake task. Its actions are
|
||||
executed whereever all of its prerequisites are done. The big
|
||||
difference is that the prerequisites (+copy_src+, +copy_bin+ and
|
||||
+copy_doc+) are executed in parallel. Each of the prerequisites are
|
||||
run in their own Ruby thread, possibly allowing faster overall runtime.
|
||||
|
||||
=== Secondary Prerequisites
|
||||
|
||||
If any of the primary prerequites of a multitask have common secondary
|
||||
prerequisites, all of the primary/parallel prerequisites will wait
|
||||
until the common prerequisites have been run.
|
||||
|
||||
For example, if the <tt>copy_<em>xxx</em></tt> tasks have the
|
||||
following prerequisites:
|
||||
|
||||
task :copy_src => [:prep_for_copy]
|
||||
task :copy_bin => [:prep_for_copy]
|
||||
task :copy_doc => [:prep_for_copy]
|
||||
|
||||
Then the +prep_for_copy+ task is run before starting all the copies in
|
||||
parallel. Once +prep_for_copy+ is complete, +copy_src+, +copy_bin+,
|
||||
and +copy_doc+ are all run in parallel. Note that +prep_for_copy+ is
|
||||
run only once, even though it is referenced in multiple threads.
|
||||
|
||||
=== Thread Safety
|
||||
|
||||
The Rake internal data structures are thread-safe with respect
|
||||
to the multitask parallel execution, so there is no need for the user
|
||||
to do extra synchronization for Rake's benefit. However, if there are
|
||||
user data structures shared between the parallel prerequisites, the
|
||||
user must do whatever is necessary to prevent race conditions.
|
||||
|
||||
== Tasks with Arguments
|
||||
|
||||
Prior to version 0.8.0, rake was only able to handle command line
|
||||
arguments of the form NAME=VALUE that were passed into Rake via the
|
||||
ENV hash. Many folks had asked for some kind of simple command line
|
||||
arguments, perhaps using "--" to separate regular task names from
|
||||
argument values on the command line. The problem is that there was no
|
||||
easy way to associate positional arguments on the command line with
|
||||
different tasks. Suppose both tasks :a and :b expect a command line
|
||||
argument: does the first value go with :a? What if :b is run first?
|
||||
Should it then get the first command line argument.
|
||||
|
||||
Rake 0.8.0 solves this problem by explicitly passing values directly
|
||||
to the tasks that need them. For example, if I had a release task
|
||||
that required a version number, I could say:
|
||||
|
||||
rake release[0.8.2]
|
||||
|
||||
And the string "0.8.2" will be passed to the :release task. Multiple
|
||||
arguments can be passed by separating them with a comma, for example:
|
||||
|
||||
rake name[john,doe]
|
||||
|
||||
Just a few words of caution. The rake task name and its arguments
|
||||
need to be a single command line argument to rake. This generally
|
||||
means no spaces. If spaces are needed, then the entire rake +
|
||||
argument string should be quoted. Something like this:
|
||||
|
||||
rake "name[billy bob, smith]"
|
||||
|
||||
(Quoting rules vary between operating systems and shells, so make sure
|
||||
you consult the proper docs for your OS/shell).
|
||||
|
||||
=== Tasks that Expect Parameters
|
||||
|
||||
Parameters are only given to tasks that are setup to expect them. In
|
||||
order to handle named parameters, the task declaration syntax for
|
||||
tasks has been extended slightly.
|
||||
|
||||
For example, a task that needs a first name and last name might be
|
||||
declared as:
|
||||
|
||||
task :name, [:first_name, :last_name]
|
||||
|
||||
The first argument is still the name of the task (:name in this case).
|
||||
The next to argumements are the names of the parameters expected by
|
||||
:name in an array (:first_name and :last_name in the example).
|
||||
|
||||
To access the values of the paramters, the block defining the task
|
||||
behaviour can now accept a second parameter:
|
||||
|
||||
task :name, [:first_name, :last_name] do |t, args|
|
||||
puts "First name is #{args.first_name}"
|
||||
puts "Last name is #{args.last_name}"
|
||||
end
|
||||
|
||||
The first argument of the block "t" is always bound to the current
|
||||
task object. The second argument "args" is an open-struct like object
|
||||
that allows access to the task arguments. Extra command line
|
||||
arguments to a task are ignored. Missing command line arguments are
|
||||
given the nil value.
|
||||
|
||||
If you wish to specify default values for the arguments, you can use
|
||||
the with_defaults method in the task body. Here is the above example
|
||||
where we specify default values for the first and last names:
|
||||
|
||||
task :name, [:first_name, :last_name] do |t, args|
|
||||
args.with_defaults(:first_name => "John", :last_name => "Dough")
|
||||
puts "First name is #{args.first_name}"
|
||||
puts "Last name is #{args.last_name}"
|
||||
end
|
||||
|
||||
=== Tasks that Expect Parameters and Have Prerequisites
|
||||
|
||||
Tasks that use parameters have a slightly different format for
|
||||
prerequisites. Use the arrow notation to indicate the prerequisites
|
||||
for tasks with arguments. For example:
|
||||
|
||||
task :name, [:first_name, :last_name] => [:pre_name] do |t, args|
|
||||
args.with_defaults(:first_name => "John", :last_name => "Dough")
|
||||
puts "First name is #{args.first_name}"
|
||||
puts "Last name is #{args.last_name}"
|
||||
end
|
||||
|
||||
=== Deprecated Task Parameters Format
|
||||
|
||||
There is an older format for declaring task parameters that omitted
|
||||
the task argument array and used the :needs keyword to introduce the
|
||||
dependencies. That format is still supported for compatibility, but
|
||||
is not recommended for use.
|
||||
|
||||
== Accessing Task Programatically
|
||||
|
||||
Sometimes it is useful to manipulate tasks programatically in a
|
||||
Rakefile. To find a task object, use the <tt>:[]</tt> operator on the
|
||||
<tt>Rake::Task</tt>.
|
||||
|
||||
=== Programmatic Task Example
|
||||
|
||||
For example, the following Rakefile defines two tasks. The :doit task
|
||||
simply prints a simple "DONE" message. The :dont class will lookup
|
||||
the doit class and remove (clear) all of its prerequisites and
|
||||
actions.
|
||||
|
||||
task :doit do
|
||||
puts "DONE"
|
||||
end
|
||||
|
||||
task :dont do
|
||||
Rake::Task[:doit].clear
|
||||
end
|
||||
|
||||
Running this example:
|
||||
|
||||
$ rake doit
|
||||
(in /Users/jim/working/git/rake/x)
|
||||
DONE
|
||||
$ rake dont doit
|
||||
(in /Users/jim/working/git/rake/x)
|
||||
$
|
||||
|
||||
The ability to programmatically manipulate tasks gives rake very
|
||||
powerful meta-programming capabilities w.r.t. task execution, but
|
||||
should be used with cation.
|
||||
|
||||
== Rules
|
||||
|
||||
When a file is named as a prerequisite, but does not have a file task
|
||||
defined for it, Rake will attempt to synthesize a task by looking at a
|
||||
list of rules supplied in the Rakefile.
|
||||
|
||||
Suppose we were trying to invoke task "mycode.o", but no task is
|
||||
defined for it. But the rakefile has a rule that look like this ...
|
||||
|
||||
rule '.o' => ['.c'] do |t|
|
||||
sh "cc #{t.source} -c -o #{t.name}"
|
||||
end
|
||||
|
||||
This rule will synthesize any task that ends in ".o". It has a
|
||||
prerequisite a source file with an extension of ".c" must exist. If
|
||||
Rake is able to find a file named "mycode.c", it will automatically
|
||||
create a task that builds "mycode.o" from "mycode.c".
|
||||
|
||||
If the file "mycode.c" does not exist, rake will attempt
|
||||
to recursively synthesize a rule for it.
|
||||
|
||||
When a task is synthesized from a rule, the +source+ attribute of the
|
||||
task is set to the matching source file. This allows us to write
|
||||
rules with actions that reference the source file.
|
||||
|
||||
=== Advanced Rules
|
||||
|
||||
Any regular expression may be used as the rule pattern. Additionally,
|
||||
a proc may be used to calculate the name of the source file. This
|
||||
allows for complex patterns and sources.
|
||||
|
||||
The following rule is equivalent to the example above.
|
||||
|
||||
rule( /\.o$/ => [
|
||||
proc {|task_name| task_name.sub(/\.[^.]+$/, '.c') }
|
||||
]) do |t|
|
||||
sh "cc #{t.source} -c -o #{t.name}"
|
||||
end
|
||||
|
||||
<b>NOTE:</b> Because of a _quirk_ in Ruby syntax, parenthesis are
|
||||
required on *rule* when the first argument is a regular expression.
|
||||
|
||||
The following rule might be used for Java files ...
|
||||
|
||||
rule '.java' => [
|
||||
proc { |tn| tn.sub(/\.class$/, '.java').sub(/^classes\//, 'src/') }
|
||||
] do |t|
|
||||
java_compile(t.source, t.name)
|
||||
end
|
||||
|
||||
<b>NOTE:</b> +java_compile+ is a hypothetical method that invokes the
|
||||
java compiler.
|
||||
|
||||
== Importing Dependencies
|
||||
|
||||
Any ruby file (including other rakefiles) can be included with a
|
||||
standard Ruby +require+ command. The rules and declarations in the
|
||||
required file are just added to the definitions already accumulated.
|
||||
|
||||
Because the files are loaded _before_ the rake targets are evaluated,
|
||||
the loaded files must be "ready to go" when the rake command is
|
||||
invoked. This make generated dependency files difficult to use. By
|
||||
the time rake gets around to updating the dependencies file, it is too
|
||||
late to load it.
|
||||
|
||||
The +import+ command addresses this by specifying a file to be loaded
|
||||
_after_ the main rakefile is loaded, but _before_ any targets on the
|
||||
command line are specified. In addition, if the file name matches an
|
||||
explicit task, that task is invoked before loading the file. This
|
||||
allows dependency files to be generated and used in a single rake
|
||||
command invocation.
|
||||
|
||||
=== Example:
|
||||
|
||||
require 'rake/loaders/makefile'
|
||||
|
||||
file ".depends.mf" => [SRC_LIST] do |t|
|
||||
sh "makedepend -f- -- #{CFLAGS} -- #{t.prerequisites} > #{t.name}"
|
||||
end
|
||||
|
||||
import ".depends.mf"
|
||||
|
||||
If ".depends" does not exist, or is out of date w.r.t. the source
|
||||
files, a new ".depends" file is generated using +makedepend+ before
|
||||
loading.
|
||||
|
||||
== Comments
|
||||
|
||||
Standard Ruby comments (beginning with "#") can be used anywhere it is
|
||||
legal in Ruby source code, including comments for tasks and rules.
|
||||
However, if you wish a task to be described using the "-T" switch,
|
||||
then you need to use the +desc+ command to describe the task.
|
||||
|
||||
=== Example:
|
||||
|
||||
desc "Create a distribution package"
|
||||
task :package => [ ... ] do ... end
|
||||
|
||||
The "-T" switch (or "--tasks" if you like to spell things out) will
|
||||
display a list of tasks that have a defined comment. If you use
|
||||
+desc+ to describe your major tasks, you have a semi-automatic way of
|
||||
generating a summary of your Rake file.
|
||||
|
||||
traken$ rake -T
|
||||
(in /home/.../rake)
|
||||
rake clean # Remove any temporary products.
|
||||
rake clobber # Remove any generated file.
|
||||
rake clobber_rdoc # Remove rdoc products
|
||||
rake contrib_test # Run tests for contrib_test
|
||||
rake default # Default Task
|
||||
rake install # Install the application
|
||||
rake lines # Count lines in the main rake file
|
||||
rake rdoc # Build the rdoc HTML Files
|
||||
rake rerdoc # Force a rebuild of the RDOC files
|
||||
rake test # Run tests
|
||||
rake testall # Run all test targets
|
||||
|
||||
Only tasks with descriptions will be displayed with the "-T" switch.
|
||||
Use "-P" (or "--prereqs") to get a list of all tasks and their
|
||||
prerequisites.
|
||||
|
||||
== Namespaces
|
||||
|
||||
As projects grow (and along with it, the number of tasks), it is
|
||||
common for task names to begin to clash. For example, if you might
|
||||
have a main program and a set of sample programs built by a single
|
||||
Rakefile. By placing the tasks related to the main program in one
|
||||
namespace, and the tasks for building the sample programs in a
|
||||
different namespace, the task names will not will not interfer with
|
||||
each other.
|
||||
|
||||
For example:
|
||||
|
||||
namespace "main"
|
||||
task :build do
|
||||
# Build the main program
|
||||
end
|
||||
end
|
||||
|
||||
namespace "samples" do
|
||||
task :build do
|
||||
# Build the sample programs
|
||||
end
|
||||
end
|
||||
|
||||
task :build => ["main:build", "samples:build"]
|
||||
|
||||
Referencing a task in a separate namespace can be achieved by
|
||||
prefixing the task name with the namespace and a colon
|
||||
(e.g. "main:build" refers to the :build task in the +main+ namespace).
|
||||
Nested namespaces are supported, so
|
||||
|
||||
Note that the name given in the +task+ command is always the unadorned
|
||||
task name without any namespace prefixes. The +task+ command always
|
||||
defines a task in the current namespace.
|
||||
|
||||
=== FileTasks
|
||||
|
||||
File task names are not scoped by the namespace command. Since the
|
||||
name of a file task is the name of an actual file in the file system,
|
||||
it makes little sense to include file task names in name space.
|
||||
Directory tasks (created by the +directory+ command) are a type of
|
||||
file task and are also not affected by namespaces.
|
||||
|
||||
=== Name Resolution
|
||||
|
||||
When looking up a task name, rake will start with the current
|
||||
namespace and attempt to find the name there. If it fails to find a
|
||||
name in the current namespace, it will search the parent namespaces
|
||||
until a match is found (or an error occurs if there is no match).
|
||||
|
||||
The "rake" namespace is a special implicit namespace that refers to
|
||||
the toplevel names.
|
||||
|
||||
If a task name begins with a "^" character, the name resolution will
|
||||
start in the parent namespace. Multiple "^" characters are allowed.
|
||||
|
||||
Here is an example file with multiple :run tasks and how various names
|
||||
resolve in different locations.
|
||||
|
||||
task :run
|
||||
|
||||
namespace "one" do
|
||||
task :run
|
||||
|
||||
namespace "two" do
|
||||
task :run
|
||||
|
||||
# :run => "one:two:run"
|
||||
# "two:run" => "one:two:run"
|
||||
# "one:two:run" => "one:two:run"
|
||||
# "one:run" => "one:run"
|
||||
# "^run" => "one:run"
|
||||
# "^^run" => "rake:run" (the top level task)
|
||||
# "rake:run" => "rake:run" (the top level task)
|
||||
end
|
||||
|
||||
# :run => "one:run"
|
||||
# "two:run" => "one:two:run"
|
||||
# "^run" => "rake:run"
|
||||
end
|
||||
|
||||
# :run => "rake:run"
|
||||
# "one:run" => "one:run"
|
||||
# "one:two:run" => "one:two:run"
|
||||
|
||||
== FileLists
|
||||
|
||||
FileLists are the way Rake manages lists of files. You can treat a
|
||||
FileList as an array of strings for the most part, but FileLists
|
||||
support some additional operations.
|
||||
|
||||
=== Creating a FileList
|
||||
|
||||
Creating a file list is easy. Just give it the list of file names:
|
||||
|
||||
fl = FileList['file1.rb', file2.rb']
|
||||
|
||||
Or give it a glob pattern:
|
||||
|
||||
fl = FileList['*.rb']
|
||||
|
||||
== Odds and Ends
|
||||
|
||||
=== do/end verses { }
|
||||
|
||||
Blocks may be specified with either a +do+/+end+ pair, or with curly
|
||||
braces in Ruby. We _strongly_ recommend using +do+/+end+ to specify the
|
||||
actions for tasks and rules. Because the rakefile idiom tends to
|
||||
leave off parenthesis on the task/file/rule methods, unusual
|
||||
ambiguities can arise when using curly braces.
|
||||
|
||||
For example, suppose that the method +object_files+ returns a list of
|
||||
object files in a project. Now we use +object_files+ as the
|
||||
prerequistes in a rule specified with actions in curly braces.
|
||||
|
||||
# DON'T DO THIS!
|
||||
file "prog" => object_files {
|
||||
# Actions are expected here (but it doesn't work)!
|
||||
}
|
||||
|
||||
Because curly braces have a higher precedence than +do+/+end+, the
|
||||
block is associated with the +object_files+ method rather than the
|
||||
+file+ method.
|
||||
|
||||
This is the proper way to specify the task ...
|
||||
|
||||
# THIS IS FINE
|
||||
file "prog" => object_files do
|
||||
# Actions go here
|
||||
end
|
||||
|
||||
----
|
||||
|
||||
== See
|
||||
|
||||
* README -- Main documentation for Rake.
|
|
@ -0,0 +1,151 @@
|
|||
= Why rake?
|
||||
|
||||
Ok, let me state from the beginning that I never intended to write this
|
||||
code. I'm not convinced it is useful, and I'm not convinced anyone
|
||||
would even be interested in it. All I can say is that Why's onion truck
|
||||
must by been passing through the Ohio valley.
|
||||
|
||||
What am I talking about? ... A Ruby version of Make.
|
||||
|
||||
See, I can sense you cringing already, and I agree. The world certainly
|
||||
doesn't need yet another reworking of the "make" program. I mean, we
|
||||
already have "ant". Isn't that enough?
|
||||
|
||||
It started yesterday. I was helping a coworker fix a problem in one of
|
||||
the Makefiles we use in our project. Not a particularly tough problem,
|
||||
but during the course of the conversation I began lamenting some of the
|
||||
shortcomings of make. In particular, in one of my makefiles I wanted to
|
||||
determine the name of a file dynamically and had to resort to some
|
||||
simple scripting (in Ruby) to make it work. "Wouldn't it be nice if you
|
||||
could just use Ruby inside a Makefile" I said.
|
||||
|
||||
My coworker (a recent convert to Ruby) agreed, but wondered what it
|
||||
would look like. So I sketched the following on the whiteboard...
|
||||
|
||||
"What if you could specify the make tasks in Ruby, like this ..."
|
||||
|
||||
task "build" do
|
||||
java_compile(...args, etc ...)
|
||||
end
|
||||
|
||||
"The task function would register "build" as a target to be made,
|
||||
and the block would be the action executed whenever the build
|
||||
system determined that it was time to do the build target."
|
||||
|
||||
We agreed that would be cool, but writing make from scratch would be WAY
|
||||
too much work. And that was the end of that!
|
||||
|
||||
... Except I couldn't get the thought out of my head. What exactly
|
||||
would be needed to make the about syntax work as a make file? Hmmm, you
|
||||
would need to register the tasks, you need some way of specifying
|
||||
dependencies between tasks, and some way of kicking off the process.
|
||||
Hey! What if we did ... and fifteen minutes later I had a working
|
||||
prototype of Ruby make, complete with dependencies and actions.
|
||||
|
||||
I showed the code to my coworker and we had a good laugh. It was just
|
||||
about a page worth of code that reproduced an amazing amount of the
|
||||
functionality of make. We were both truely stunned with the power of
|
||||
Ruby.
|
||||
|
||||
But it didn't do everything make did. In particular, it didn't have
|
||||
timestamp based file dependencies (where a file is rebuilt if any of its
|
||||
prerequisite files have a later timestamp). Obviously THAT would be a
|
||||
pain to add and so Ruby Make would remain an interesting experiment.
|
||||
|
||||
... Except as I walked back to my desk, I started thinking about what
|
||||
file based dependecies would really need. Rats! I was hooked again,
|
||||
and by adding a new class and two new methods, file/timestamp
|
||||
dependencies were implemented.
|
||||
|
||||
Ok, now I was really hooked. Last night (during CSI!) I massaged the
|
||||
code and cleaned it up a bit. The result is a bare-bones replacement
|
||||
for make in exactly 100 lines of code.
|
||||
|
||||
For the curious, you can see it at ...
|
||||
* doc/proto_rake.rdoc
|
||||
|
||||
Oh, about the name. When I wrote the example Ruby Make task on my
|
||||
whiteboard, my coworker exclaimed "Oh! I have the perfect name: Rake ...
|
||||
Get it? Ruby-Make. Rake!" He said he envisioned the tasks as leaves
|
||||
and Rake would clean them up ... or something like that. Anyways, the
|
||||
name stuck.
|
||||
|
||||
Some quick examples ...
|
||||
|
||||
A simple task to delete backup files ...
|
||||
|
||||
task :clean do
|
||||
Dir['*~'].each {|fn| rm fn rescue nil}
|
||||
end
|
||||
|
||||
Note that task names are symbols (they are slightly easier to type
|
||||
than quoted strings ... but you may use quoted string if you would
|
||||
rather). Rake makes the methods of the FileUtils module directly
|
||||
available, so we take advantage of the <tt>rm</tt> command. Also note
|
||||
the use of "rescue nil" to trap and ignore errors in the <tt>rm</tt>
|
||||
command.
|
||||
|
||||
To run it, just type "rake clean". Rake will automatically find a
|
||||
Rakefile in the current directory (or above!) and will invoke the
|
||||
targets named on the command line. If there are no targets explicitly
|
||||
named, rake will invoke the task "default".
|
||||
|
||||
Here's another task with dependencies ...
|
||||
|
||||
task :clobber => [:clean] do
|
||||
rm_r "tempdir"
|
||||
end
|
||||
|
||||
Task :clobber depends upon task :clean, so :clean will be run before
|
||||
:clobber is executed.
|
||||
|
||||
Files are specified by using the "file" command. It is similar to the
|
||||
task command, except that the task name represents a file, and the task
|
||||
will be run only if the file doesn't exist, or if its modification time
|
||||
is earlier than any of its prerequisites.
|
||||
|
||||
Here is a file based dependency that will compile "hello.cc" to
|
||||
"hello.o".
|
||||
|
||||
file "hello.cc"
|
||||
file "hello.o" => ["hello.cc"] do |t|
|
||||
srcfile = t.name.sub(/\.o$/, ".cc")
|
||||
sh %{g++ #{srcfile} -c -o #{t.name}}
|
||||
end
|
||||
|
||||
I normally specify file tasks with string (rather than symbols). Some
|
||||
file names can't be represented by symbols. Plus it makes the
|
||||
distinction between them more clear to the casual reader.
|
||||
|
||||
Currently writing a task for each and every file in the project would be
|
||||
tedious at best. I envision a set of libraries to make this job
|
||||
easier. For instance, perhaps something like this ...
|
||||
|
||||
require 'rake/ctools'
|
||||
Dir['*.c'].each do |fn|
|
||||
c_source_file(fn)
|
||||
end
|
||||
|
||||
where "c_source_file" will create all the tasks need to compile all the
|
||||
C source files in a directory. Any number of useful libraries could be
|
||||
created for rake.
|
||||
|
||||
That's it. There's no documentation (other than whats in this
|
||||
message). Does this sound interesting to anyone? If so, I'll continue
|
||||
to clean it up and write it up and publish it on RAA. Otherwise, I'll
|
||||
leave it as an interesting excerise and a tribute to the power of Ruby.
|
||||
|
||||
Why /might/ rake be interesting to Ruby programmers. I don't know,
|
||||
perhaps ...
|
||||
|
||||
* No weird make syntax (only weird Ruby syntax :-)
|
||||
* No need to edit or read XML (a la ant)
|
||||
* Platform independent build scripts.
|
||||
* Will run anywhere Ruby exists, so no need to have "make" installed.
|
||||
If you stay away from the "sys" command and use things like
|
||||
'ftools', you can have a perfectly platform independent
|
||||
build script. Also rake is only 100 lines of code, so it can
|
||||
easily be packaged along with the rest of your code.
|
||||
|
||||
So ... Sorry for the long rambling message. Like I said, I never
|
||||
intended to write this code at all.
|
|
@ -0,0 +1,55 @@
|
|||
= Rake 0.8.7 Released
|
||||
|
||||
Rake version 0.8.5 introduced greatly improved support for executing
|
||||
commands on Windows. The "sh" command now has the same semantics on
|
||||
Windows that it has on Unix based platforms.
|
||||
|
||||
Rake version 0.8.6 includes minor fixes the the RDoc generation.
|
||||
Rake version 0.8.7 includes a minor fix for JRuby running on windows.
|
||||
|
||||
== Changes
|
||||
|
||||
=== New Features / Enhancements in Version 0.8.5
|
||||
|
||||
* Improved implementation of the Rake system command for Windows.
|
||||
(patch from James M. Lawrence/quix)
|
||||
|
||||
* Support for Ruby 1.9's improved system command. (patch from James
|
||||
M. Lawrence/quix)
|
||||
|
||||
* Rake now includes the configured extension when invoking an
|
||||
executable (Config::CONFIG['EXEEXT])
|
||||
|
||||
=== Bug Fixes in Version 0.8.5
|
||||
|
||||
* Environment variable keys are now correctly cased (it matters in
|
||||
some implementations).
|
||||
|
||||
== What is Rake
|
||||
|
||||
Rake is a build tool similar to the make program in many ways. But
|
||||
instead of cryptic make recipes, Rake uses standard Ruby code to
|
||||
declare tasks and dependencies. You have the full power of a modern
|
||||
scripting language built right into your build tool.
|
||||
|
||||
== Availability
|
||||
|
||||
The easiest way to get and install rake is via RubyGems ...
|
||||
|
||||
gem install rake (you may need root/admin privileges)
|
||||
|
||||
Otherwise, you can get it from the more traditional places:
|
||||
|
||||
Home Page:: http://rake.rubyforge.org/
|
||||
Download:: http://rubyforge.org/project/showfiles.php?group_id=50
|
||||
GitHub:: git://github.com/jimweirich/rake.git
|
||||
|
||||
== Thanks
|
||||
|
||||
As usual, it was input from users that drove a alot of these changes. The
|
||||
following people either contributed patches, made suggestions or made
|
||||
otherwise helpful comments. Thanks to ...
|
||||
|
||||
* Charles Nutter
|
||||
|
||||
-- Jim Weirich
|
122
lib/rake.rb
122
lib/rake.rb
|
@ -27,7 +27,7 @@
|
|||
# as a library via a require statement, but it can be distributed
|
||||
# independently as an application.
|
||||
|
||||
RAKEVERSION = '0.8.4'
|
||||
RAKEVERSION = '0.8.7'
|
||||
|
||||
require 'rbconfig'
|
||||
require 'fileutils'
|
||||
|
@ -38,6 +38,8 @@ require 'ostruct'
|
|||
|
||||
require 'rake/win32'
|
||||
|
||||
$trace = false
|
||||
|
||||
######################################################################
|
||||
# Rake extensions to Module.
|
||||
#
|
||||
|
@ -201,7 +203,7 @@ class String
|
|||
when '%f'
|
||||
result << File.basename(self)
|
||||
when '%n'
|
||||
result << File.basename(self, '.*')
|
||||
result << File.basename(self).ext
|
||||
when '%d'
|
||||
result << File.dirname(self)
|
||||
when '%x'
|
||||
|
@ -278,7 +280,7 @@ module Rake
|
|||
|
||||
end
|
||||
|
||||
# ##########################################################################
|
||||
####################################################################
|
||||
# Mixin for creating easily cloned objects.
|
||||
#
|
||||
module Cloneable
|
||||
|
@ -302,6 +304,27 @@ module Rake
|
|||
end
|
||||
end
|
||||
|
||||
####################################################################
|
||||
# Exit status class for times the system just gives us a nil.
|
||||
class PseudoStatus
|
||||
attr_reader :exitstatus
|
||||
def initialize(code=0)
|
||||
@exitstatus = code
|
||||
end
|
||||
def to_i
|
||||
@exitstatus << 8
|
||||
end
|
||||
def >>(n)
|
||||
to_i >> n
|
||||
end
|
||||
def stopped?
|
||||
false
|
||||
end
|
||||
def exited?
|
||||
true
|
||||
end
|
||||
end
|
||||
|
||||
####################################################################
|
||||
# TaskAguments manage the arguments passed to a task.
|
||||
#
|
||||
|
@ -432,7 +455,7 @@ end # module Rake
|
|||
|
||||
module Rake
|
||||
|
||||
# #########################################################################
|
||||
###########################################################################
|
||||
# A Task is the basic unit of work in a Rakefile. Tasks have associated
|
||||
# actions (possibly more than one) and a list of prerequisites. When
|
||||
# invoked, a task will first ensure that all of its prerequisites have an
|
||||
|
@ -732,7 +755,7 @@ module Rake
|
|||
end # class Rake::Task
|
||||
|
||||
|
||||
# #########################################################################
|
||||
###########################################################################
|
||||
# A FileTask is a task that includes time based dependencies. If any of a
|
||||
# FileTask's prerequisites have a timestamp that is later than the file
|
||||
# represented by this task, then the file must be rebuilt (using the
|
||||
|
@ -774,7 +797,7 @@ module Rake
|
|||
end
|
||||
end # class Rake::FileTask
|
||||
|
||||
# #########################################################################
|
||||
###########################################################################
|
||||
# A FileCreationTask is a file task that when used as a dependency will be
|
||||
# needed if and only if the file has not been created. Once created, it is
|
||||
# not re-triggered if any of its dependencies are newer, nor does trigger
|
||||
|
@ -793,7 +816,7 @@ module Rake
|
|||
end
|
||||
end
|
||||
|
||||
# #########################################################################
|
||||
###########################################################################
|
||||
# Same as a regular task, but the immediate prerequisites are done in
|
||||
# parallel using Ruby threads.
|
||||
#
|
||||
|
@ -808,7 +831,7 @@ module Rake
|
|||
end
|
||||
end # module Rake
|
||||
|
||||
# ###########################################################################
|
||||
## ###########################################################################
|
||||
# Task Definition Functions ...
|
||||
|
||||
# Declare a basic task.
|
||||
|
@ -927,12 +950,18 @@ def import(*fns)
|
|||
end
|
||||
end
|
||||
|
||||
# ###########################################################################
|
||||
#############################################################################
|
||||
# This a FileUtils extension that defines several additional commands to be
|
||||
# added to the FileUtils utility functions.
|
||||
#
|
||||
module FileUtils
|
||||
RUBY = File.join(RbConfig::CONFIG['bindir'], RbConfig::CONFIG['ruby_install_name']).
|
||||
RUBY_EXT = ((RbConfig::CONFIG['ruby_install_name'] =~ /\.(com|cmd|exe|bat|rb|sh)$/) ?
|
||||
"" :
|
||||
RbConfig::CONFIG['EXEEXT'])
|
||||
|
||||
RUBY = File.join(
|
||||
RbConfig::CONFIG['bindir'],
|
||||
RbConfig::CONFIG['ruby_install_name'] + RUBY_EXT).
|
||||
sub(/.*\s.*/m, '"\&"')
|
||||
|
||||
OPT_TABLE['sh'] = %w(noop verbose)
|
||||
|
@ -958,7 +987,7 @@ module FileUtils
|
|||
options = (Hash === cmd.last) ? cmd.pop : {}
|
||||
unless block_given?
|
||||
show_command = cmd.join(" ")
|
||||
show_command = show_command[0,42] + "..."
|
||||
show_command = show_command[0,42] + "..." unless $trace
|
||||
# TODO code application logic heref show_command.length > 45
|
||||
block = lambda { |ok, status|
|
||||
ok or fail "Command failed with status (#{status.exitstatus}): [#{show_command}]"
|
||||
|
@ -974,7 +1003,9 @@ module FileUtils
|
|||
rake_output_message cmd.join(" ") if options[:verbose]
|
||||
unless options[:noop]
|
||||
res = rake_system(*cmd)
|
||||
block.call(res, $?)
|
||||
status = $?
|
||||
status = PseudoStatus.new(1) if !res && status.nil?
|
||||
block.call(res, status)
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -1027,7 +1058,7 @@ module FileUtils
|
|||
end
|
||||
end
|
||||
|
||||
# ###########################################################################
|
||||
#############################################################################
|
||||
# RakeFileUtils provides a custom version of the FileUtils methods that
|
||||
# respond to the <tt>verbose</tt> and <tt>nowrite</tt> commands.
|
||||
#
|
||||
|
@ -1158,7 +1189,7 @@ module RakeFileUtils
|
|||
extend self
|
||||
end
|
||||
|
||||
# ###########################################################################
|
||||
#############################################################################
|
||||
# Include the FileUtils file manipulation functions in the top level module,
|
||||
# but mark them private so that they don't unintentionally define methods on
|
||||
# other objects.
|
||||
|
@ -1170,7 +1201,7 @@ private(*RakeFileUtils.instance_methods(false))
|
|||
######################################################################
|
||||
module Rake
|
||||
|
||||
# #########################################################################
|
||||
###########################################################################
|
||||
# A FileList is essentially an array with a few helper methods defined to
|
||||
# make file manipulation a bit easier.
|
||||
#
|
||||
|
@ -1228,21 +1259,17 @@ module Rake
|
|||
# Now do the delegation.
|
||||
DELEGATING_METHODS.each_with_index do |sym, i|
|
||||
if SPECIAL_RETURN.include?(sym)
|
||||
class_eval <<-END, __FILE__, __LINE__+1
|
||||
def #{sym}(*args, &block)
|
||||
resolve
|
||||
result = @items.send(:#{sym}, *args, &block)
|
||||
FileList.new.import(result)
|
||||
end
|
||||
END
|
||||
define_method(sym) do |*args, &block|
|
||||
resolve
|
||||
result = @items.send(sym, *args, &block)
|
||||
FileList.new.import(result)
|
||||
end
|
||||
else
|
||||
class_eval <<-END, __FILE__, __LINE__+1
|
||||
def #{sym}(*args, &block)
|
||||
resolve
|
||||
result = @items.send(:#{sym}, *args, &block)
|
||||
result.object_id == @items.object_id ? self : result
|
||||
end
|
||||
END
|
||||
define_method(sym) do |*args, &block|
|
||||
resolve
|
||||
result = @items.send(sym, *args, &block)
|
||||
result.object_id == @items.object_id ? self : result
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -1450,7 +1477,7 @@ module Rake
|
|||
collect { |fn| fn.pathmap(spec) }
|
||||
end
|
||||
|
||||
# Return a new file list with <tt>String#ext</tt> method applied
|
||||
# Return a new FileList with <tt>String#ext</tt> method applied
|
||||
# to each member of the array.
|
||||
#
|
||||
# This method is a shortcut for:
|
||||
|
@ -1468,9 +1495,9 @@ module Rake
|
|||
# name, line number, and the matching line of text. If no block is given,
|
||||
# a standard emac style file:linenumber:line message will be printed to
|
||||
# standard out.
|
||||
def egrep(pattern, *opt)
|
||||
def egrep(pattern, *options)
|
||||
each do |fn|
|
||||
open(fn, "rb", *opt) do |inf|
|
||||
open(fn, "rb", *options) do |inf|
|
||||
count = 0
|
||||
inf.each do |line|
|
||||
count += 1
|
||||
|
@ -1576,7 +1603,7 @@ end # module Rake
|
|||
# Alias FileList to be available at the top level.
|
||||
FileList = Rake::FileList
|
||||
|
||||
# ###########################################################################
|
||||
#############################################################################
|
||||
module Rake
|
||||
|
||||
# Default Rakefile loader used by +import+.
|
||||
|
@ -1603,7 +1630,7 @@ module Rake
|
|||
EARLY = EarlyTime.instance
|
||||
end # module Rake
|
||||
|
||||
# ###########################################################################
|
||||
#############################################################################
|
||||
# Extensions to time to allow comparisons with an early time class.
|
||||
#
|
||||
class Time
|
||||
|
@ -1960,11 +1987,9 @@ module Rake
|
|||
# application. The define any tasks. Finally, call +top_level+ to run your top
|
||||
# level tasks.
|
||||
def run
|
||||
standard_exception_handling do
|
||||
init
|
||||
load_rakefile
|
||||
top_level
|
||||
end
|
||||
init
|
||||
load_rakefile
|
||||
top_level
|
||||
end
|
||||
|
||||
# Initialize the command line parameters and app name.
|
||||
|
@ -2041,7 +2066,7 @@ module Rake
|
|||
# Exit with error message
|
||||
$stderr.puts "#{name} aborted!"
|
||||
$stderr.puts ex.message
|
||||
if options.trace
|
||||
if options.trace or true
|
||||
$stderr.puts ex.backtrace.join("\n")
|
||||
else
|
||||
$stderr.puts ex.backtrace.find {|str| str =~ /#{@rakefile}/ } || ""
|
||||
|
@ -2362,24 +2387,13 @@ module Rake
|
|||
|
||||
# The directory path containing the system wide rakefiles.
|
||||
def system_dir
|
||||
@system_dir ||=
|
||||
begin
|
||||
if ENV['RAKE_SYSTEM']
|
||||
ENV['RAKE_SYSTEM']
|
||||
else
|
||||
standard_system_dir
|
||||
end
|
||||
end
|
||||
@system_dir ||= ENV['RAKE_SYSTEM'] || standard_system_dir
|
||||
end
|
||||
|
||||
# The standard directory containing system wide rake files.
|
||||
if Win32.windows?
|
||||
unless method_defined?(:standard_system_dir)
|
||||
def standard_system_dir #:nodoc:
|
||||
Win32.win32_system_dir
|
||||
end
|
||||
else
|
||||
def standard_system_dir #:nodoc:
|
||||
File.expand_path('.rake', '~')
|
||||
File.expand_path('~/.rake')
|
||||
end
|
||||
end
|
||||
private :standard_system_dir
|
||||
|
|
|
@ -21,7 +21,7 @@ module Rake
|
|||
def process_line(line)
|
||||
file_tasks, args = line.split(':', 2)
|
||||
return if args.nil?
|
||||
dependents = args.split
|
||||
dependents = args.split.map {|arg| respace(arg)}
|
||||
file_tasks.scan(/\S+/) do |file_task|
|
||||
file_task = respace(file_task)
|
||||
file file_task => dependents
|
||||
|
|
|
@ -19,7 +19,7 @@ module Rake
|
|||
# Rebuild the rdoc files from scratch, even if they are not out
|
||||
# of date.
|
||||
#
|
||||
# Simple example:
|
||||
# Simple Example:
|
||||
#
|
||||
# Rake::RDocTask.new do |rd|
|
||||
# rd.main = "README.rdoc"
|
||||
|
@ -132,7 +132,7 @@ module Rake
|
|||
args = option_list + @rdoc_files
|
||||
if @external
|
||||
argstring = args.join(' ')
|
||||
sh %{ruby -Ivendor vender/rd #{argstring}}
|
||||
sh %{ruby -Ivendor vendor/rd #{argstring}}
|
||||
else
|
||||
require 'rdoc/rdoc'
|
||||
RDoc::RDoc.new.document(args)
|
||||
|
|
|
@ -93,7 +93,7 @@ module Rake
|
|||
|
||||
# Create the tasks defined by this task lib.
|
||||
def define
|
||||
lib_path = @libs.collect {|path| "-I#{File.expand_path(path)}"}
|
||||
lib_path = @libs.join(File::PATH_SEPARATOR)
|
||||
desc "Run tests" + (@name==:test ? "" : " for #{@name}")
|
||||
task @name do
|
||||
run_code = ''
|
||||
|
@ -103,11 +103,11 @@ module Rake
|
|||
when :direct
|
||||
"-e 'ARGV.each{|f| load f}'"
|
||||
when :testrb
|
||||
"-S testrb #{fix}"
|
||||
"-S testrb"
|
||||
when :rake
|
||||
rake_loader
|
||||
end
|
||||
@ruby_opts.unshift( *lib_path )
|
||||
@ruby_opts.unshift( "-I\"#{lib_path}\"" )
|
||||
@ruby_opts.unshift( "-w" ) if @warning
|
||||
ruby @ruby_opts.join(" ") +
|
||||
" \"#{run_code}\" " +
|
||||
|
@ -133,15 +133,6 @@ module Rake
|
|||
end
|
||||
end
|
||||
|
||||
def fix # :nodoc:
|
||||
case RUBY_VERSION
|
||||
when '1.8.2'
|
||||
find_file 'rake/ruby182_test_unit_fix'
|
||||
else
|
||||
nil
|
||||
end || ''
|
||||
end
|
||||
|
||||
def rake_loader # :nodoc:
|
||||
find_file('rake/rake_test_loader') or
|
||||
fail "unable to find rake test loader"
|
||||
|
|
|
@ -5,9 +5,10 @@ module Rake
|
|||
module Win32
|
||||
class << self
|
||||
# True if running on a windows system.
|
||||
def windows?
|
||||
# assume other DOSish systems are extinct.
|
||||
File::ALT_SEPARATOR == '\\'
|
||||
if File::ALT_SEPARATOR == '\\' # assume other DOSish systems are extinct.
|
||||
def windows?; true end
|
||||
else
|
||||
def windows?; false end
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -29,6 +30,17 @@ module Rake
|
|||
end
|
||||
File.expand_path('Rake', win32_shared_path)
|
||||
end
|
||||
|
||||
# Normalize a win32 path so that the slashes are all forward slashes.
|
||||
def normalize(path)
|
||||
path.tr('\\', '/')
|
||||
end
|
||||
end if windows?
|
||||
end
|
||||
|
||||
if Win32.windows?
|
||||
def standard_system_dir
|
||||
Win32.win32_system_dir
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -0,0 +1,24 @@
|
|||
require 'stringio'
|
||||
|
||||
# Mix-in for capturing standard output.
|
||||
module CaptureStdout
|
||||
def capture_stdout
|
||||
s = StringIO.new
|
||||
oldstdout = $stdout
|
||||
$stdout = s
|
||||
yield
|
||||
s.string
|
||||
ensure
|
||||
$stdout = oldstdout
|
||||
end
|
||||
|
||||
def capture_stderr
|
||||
s = StringIO.new
|
||||
oldstderr = $stderr
|
||||
$stderr = s
|
||||
yield
|
||||
s.string
|
||||
ensure
|
||||
$stderr = oldstderr
|
||||
end
|
||||
end
|
|
@ -0,0 +1,5 @@
|
|||
if ARGV[0] != ARGV[1]
|
||||
exit 1
|
||||
else
|
||||
exit 0
|
||||
end
|
|
@ -0,0 +1,5 @@
|
|||
if ARGV[0] != ARGV[1]
|
||||
exit 0
|
||||
else
|
||||
exit 1
|
||||
end
|
|
@ -0,0 +1,15 @@
|
|||
# -*- ruby -*-
|
||||
|
||||
task :default => "play.app"
|
||||
|
||||
file "play.scpt" => "base" do |t|
|
||||
cp t.prerequisites.first, t.name
|
||||
end
|
||||
|
||||
rule ".app" => ".scpt" do |t|
|
||||
cp t.source, t.name
|
||||
end
|
||||
|
||||
file 'base' do
|
||||
touch 'base'
|
||||
end
|
|
@ -0,0 +1,19 @@
|
|||
#!/usr/bin/env ruby
|
||||
|
||||
if ENV['TESTTOPSCOPE']
|
||||
puts "TOPSCOPE"
|
||||
end
|
||||
|
||||
task :default do
|
||||
puts "DEFAULT"
|
||||
end
|
||||
|
||||
task :other => [:default] do
|
||||
puts "OTHER"
|
||||
end
|
||||
|
||||
task :task_scope do
|
||||
if ENV['TESTTASKSCOPE']
|
||||
puts "TASKSCOPE"
|
||||
end
|
||||
end
|
|
@ -0,0 +1,22 @@
|
|||
#
|
||||
|
||||
task :default => ["temp_main"]
|
||||
|
||||
file "temp_main" => [:all_apps] do touch "temp_main" end
|
||||
|
||||
task :all_apps => [:one, :two]
|
||||
task :one => ["temp_one"]
|
||||
task :two => ["temp_two"]
|
||||
|
||||
file "temp_one" do |t|
|
||||
touch "temp_one"
|
||||
end
|
||||
file "temp_two" do |t|
|
||||
touch "temp_two"
|
||||
end
|
||||
|
||||
task :clean do
|
||||
["temp_one", "temp_two", "temp_main"].each do |file|
|
||||
rm_f file
|
||||
end
|
||||
end
|
|
@ -0,0 +1,33 @@
|
|||
#!/usr/bin/env ruby
|
||||
|
||||
N = 2
|
||||
|
||||
task :default => :run
|
||||
|
||||
BUILD_DIR = 'build'
|
||||
task :clean do
|
||||
rm_rf 'build'
|
||||
rm_rf 'src'
|
||||
end
|
||||
|
||||
task :run
|
||||
|
||||
TARGET_DIR = 'build/copies'
|
||||
|
||||
FileList['src/*'].each do |src|
|
||||
directory TARGET_DIR
|
||||
target = File.join TARGET_DIR, File.basename(src)
|
||||
file target => [src, TARGET_DIR] do
|
||||
cp src, target
|
||||
# sleep 3 if src !~ /foo#{N-1}$/ # I'm commenting out this sleep, it doesn't seem to do anything.
|
||||
end
|
||||
task :run => target
|
||||
end
|
||||
|
||||
task :prep => :clean do
|
||||
mkdir_p 'src'
|
||||
N.times do |n|
|
||||
puts "DBG: Touching src/foo#{n}"
|
||||
touch "src/foo#{n}"
|
||||
end
|
||||
end
|
|
@ -0,0 +1,19 @@
|
|||
# -*- ruby -*-
|
||||
|
||||
require 'rake/loaders/makefile'
|
||||
|
||||
task :default
|
||||
|
||||
task :other do
|
||||
puts "OTHER"
|
||||
end
|
||||
|
||||
file "dynamic_deps" do |t|
|
||||
open(t.name, "w") do |f| f.puts "puts 'DYNAMIC'" end
|
||||
end
|
||||
|
||||
import "dynamic_deps"
|
||||
import "static_deps"
|
||||
import "static_deps"
|
||||
import "deps.mf"
|
||||
puts "FIRST"
|
|
@ -0,0 +1 @@
|
|||
default: other
|
|
@ -0,0 +1,17 @@
|
|||
#!/usr/bin/env ruby
|
||||
|
||||
task :b
|
||||
|
||||
desc "A"
|
||||
task :a
|
||||
|
||||
desc "B"
|
||||
task :b
|
||||
|
||||
desc "A2"
|
||||
task :a
|
||||
|
||||
task :c
|
||||
|
||||
desc "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
|
||||
task :d
|
|
@ -0,0 +1,57 @@
|
|||
#!/usr/bin/env ruby
|
||||
|
||||
desc "copy"
|
||||
task :copy do
|
||||
puts "COPY"
|
||||
end
|
||||
|
||||
namespace "nest" do
|
||||
desc "nest copy"
|
||||
task :copy do
|
||||
puts "NEST COPY"
|
||||
end
|
||||
task :xx => :copy
|
||||
end
|
||||
|
||||
anon_ns = namespace do
|
||||
desc "anonymous copy task"
|
||||
task :copy do
|
||||
puts "ANON COPY"
|
||||
end
|
||||
end
|
||||
|
||||
desc "Top level task to run the anonymous version of copy"
|
||||
task :anon => anon_ns[:copy]
|
||||
|
||||
namespace "very" do
|
||||
namespace "nested" do
|
||||
task "run" => "rake:copy"
|
||||
end
|
||||
end
|
||||
|
||||
namespace "a" do
|
||||
desc "Run task in the 'a' namespace"
|
||||
task "run" do
|
||||
puts "IN A"
|
||||
end
|
||||
end
|
||||
|
||||
namespace "b" do
|
||||
desc "Run task in the 'b' namespace"
|
||||
task "run" => "a:run" do
|
||||
puts "IN B"
|
||||
end
|
||||
end
|
||||
|
||||
namespace "file1" do
|
||||
file "xyz.rb" do
|
||||
puts "XYZ1"
|
||||
end
|
||||
end
|
||||
|
||||
namespace "file2" do
|
||||
file "xyz.rb" do
|
||||
puts "XYZ2"
|
||||
end
|
||||
end
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
task :default do
|
||||
puts "TEST1"
|
||||
end
|
|
@ -0,0 +1,3 @@
|
|||
task :default do
|
||||
puts "OK"
|
||||
end
|
|
@ -0,0 +1,14 @@
|
|||
# Comments
|
||||
a: a1 a2 a3 a4
|
||||
b: b1 b2 b3 \
|
||||
b4 b5 b6\
|
||||
# Mid: Comment
|
||||
b7
|
||||
|
||||
a : a5 a6 a7
|
||||
c: c1
|
||||
d: d1 d2 \
|
||||
|
||||
e f : e1 f1
|
||||
|
||||
g\ 0: g1 g\ 2 g\ 3 g4
|
|
@ -0,0 +1,8 @@
|
|||
#!/usr/bin/env ruby
|
||||
|
||||
task :exit5 do
|
||||
exit(5)
|
||||
end
|
||||
|
||||
task :normal do
|
||||
end
|
|
@ -0,0 +1 @@
|
|||
# Empty Rakefile for Unit Test
|
|
@ -0,0 +1,30 @@
|
|||
module FileCreation
|
||||
OLDFILE = "testdata/old"
|
||||
NEWFILE = "testdata/new"
|
||||
|
||||
def create_timed_files(oldfile, *newfiles)
|
||||
return if File.exist?(oldfile) && newfiles.all? { |newfile| File.exist?(newfile) }
|
||||
old_time = create_file(oldfile)
|
||||
newfiles.each do |newfile|
|
||||
while create_file(newfile) <= old_time
|
||||
sleep(0.1)
|
||||
File.delete(newfile) rescue nil
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def create_dir(dirname)
|
||||
FileUtils.mkdir_p(dirname) unless File.exist?(dirname)
|
||||
File.stat(dirname).mtime
|
||||
end
|
||||
|
||||
def create_file(name)
|
||||
create_dir(File.dirname(name))
|
||||
FileUtils.touch(name) unless File.exist?(name)
|
||||
File.stat(name).mtime
|
||||
end
|
||||
|
||||
def delete_file(name)
|
||||
File.delete(name) rescue nil
|
||||
end
|
||||
end
|
|
@ -0,0 +1,30 @@
|
|||
module InEnvironment
|
||||
private
|
||||
|
||||
# Create an environment for a test. At the completion of the yielded
|
||||
# block, the environment is restored to its original conditions.
|
||||
def in_environment(settings)
|
||||
original_settings = set_env(settings)
|
||||
yield
|
||||
ensure
|
||||
set_env(original_settings) if original_settings
|
||||
end
|
||||
|
||||
# Set the environment according to the settings hash.
|
||||
def set_env(settings) # :nodoc:
|
||||
result = {}
|
||||
settings.each do |k, v|
|
||||
result[k] = ENV[k]
|
||||
if k == 'PWD'
|
||||
result[k] = Dir.pwd
|
||||
Dir.chdir(v)
|
||||
elsif v.nil?
|
||||
ENV.delete(k)
|
||||
else
|
||||
ENV[k] = v
|
||||
end
|
||||
end
|
||||
result
|
||||
end
|
||||
|
||||
end
|
|
@ -0,0 +1,9 @@
|
|||
# Common setup for all test files.
|
||||
|
||||
# require 'flexmock/test_unit'
|
||||
|
||||
module TestMethods
|
||||
def assert_exception(ex, msg=nil, &block)
|
||||
assert_raise(ex, msg, &block)
|
||||
end
|
||||
end
|
|
@ -0,0 +1,3 @@
|
|||
# For --require testing
|
||||
|
||||
TESTING_REQUIRE << 1
|
|
@ -0,0 +1,3 @@
|
|||
# For --require testing
|
||||
|
||||
TESTING_REQUIRE << 2
|
|
@ -0,0 +1,3 @@
|
|||
# For --require testing
|
||||
|
||||
TESTING_REQUIRE << 3
|
|
@ -0,0 +1,3 @@
|
|||
#!/usr/bin/env ruby
|
||||
|
||||
exit((ARGV[0] || "0").to_i)
|
|
@ -0,0 +1,687 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
require_relative 'capture_stdout'
|
||||
require_relative 'in_environment'
|
||||
|
||||
TESTING_REQUIRE = [ ]
|
||||
|
||||
######################################################################
|
||||
class TestApplication < Test::Unit::TestCase
|
||||
include CaptureStdout
|
||||
include InEnvironment
|
||||
BASEDIR = File.dirname(__FILE__)
|
||||
|
||||
def defmock(*names, &block)
|
||||
class << (@mock ||= Object.new); self; end.class_eval do
|
||||
names.each do |name|
|
||||
define_method(name, block)
|
||||
end
|
||||
end
|
||||
@mock
|
||||
end
|
||||
|
||||
def setup
|
||||
@app = Rake::Application.new
|
||||
@app.options.rakelib = []
|
||||
end
|
||||
|
||||
def test_constant_warning
|
||||
err = capture_stderr do @app.instance_eval { const_warning("Task") } end
|
||||
assert_match(/warning/i, err)
|
||||
assert_match(/deprecated/i, err)
|
||||
assert_match(/Task/i, err)
|
||||
end
|
||||
|
||||
def test_display_tasks
|
||||
@app.options.show_task_pattern = //
|
||||
@app.last_description = "COMMENT"
|
||||
@app.define_task(Rake::Task, "t")
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
assert_match(/^rake t/, out)
|
||||
assert_match(/# COMMENT/, out)
|
||||
end
|
||||
|
||||
def test_display_tasks_with_long_comments
|
||||
in_environment('RAKE_COLUMNS' => '80') do
|
||||
@app.options.show_task_pattern = //
|
||||
@app.last_description = "1234567890" * 8
|
||||
@app.define_task(Rake::Task, "t")
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
assert_match(/^rake t/, out)
|
||||
assert_match(/# 12345678901234567890123456789012345678901234567890123456789012345\.\.\./, out)
|
||||
end
|
||||
end
|
||||
|
||||
def test_display_tasks_with_task_name_wider_than_tty_display
|
||||
in_environment('RAKE_COLUMNS' => '80') do
|
||||
@app.options.show_task_pattern = //
|
||||
description = "something short"
|
||||
task_name = "task name" * 80
|
||||
@app.last_description = "something short"
|
||||
@app.define_task(Rake::Task, task_name )
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
# Ensure the entire task name is output and we end up showing no description
|
||||
assert_match(/rake #{task_name} # .../, out)
|
||||
end
|
||||
end
|
||||
|
||||
def test_display_tasks_with_very_long_task_name_to_a_non_tty_shows_name_and_comment
|
||||
@app.options.show_task_pattern = //
|
||||
@app.tty_output = false
|
||||
description = "something short"
|
||||
task_name = "task name" * 80
|
||||
@app.last_description = "something short"
|
||||
@app.define_task(Rake::Task, task_name )
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
# Ensure the entire task name is output and we end up showing no description
|
||||
assert_match(/rake #{task_name} # #{description}/, out)
|
||||
end
|
||||
|
||||
def test_display_tasks_with_long_comments_to_a_non_tty_shows_entire_comment
|
||||
@app.options.show_task_pattern = //
|
||||
@app.tty_output = false
|
||||
@app.last_description = "1234567890" * 8
|
||||
@app.define_task(Rake::Task, "t")
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
assert_match(/^rake t/, out)
|
||||
assert_match(/# #{@app.last_description}/, out)
|
||||
end
|
||||
|
||||
def test_display_tasks_with_long_comments_to_a_non_tty_with_columns_set_truncates_comments
|
||||
in_environment("RAKE_COLUMNS" => '80') do
|
||||
@app.options.show_task_pattern = //
|
||||
@app.tty_output = false
|
||||
@app.last_description = "1234567890" * 8
|
||||
@app.define_task(Rake::Task, "t")
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
assert_match(/^rake t/, out)
|
||||
assert_match(/# 12345678901234567890123456789012345678901234567890123456789012345\.\.\./, out)
|
||||
end
|
||||
end
|
||||
|
||||
def test_display_tasks_with_full_descriptions
|
||||
@app.options.show_task_pattern = //
|
||||
@app.options.full_description = true
|
||||
@app.last_description = "COMMENT"
|
||||
@app.define_task(Rake::Task, "t")
|
||||
out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end
|
||||
assert_match(/^rake t$/, out)
|
||||
assert_match(/^ {4}COMMENT$/, out)
|
||||
end
|
||||
|
||||
def test_finding_rakefile
|
||||
in_environment("PWD" => File.join(BASEDIR, "data/unittest")) do
|
||||
assert_match(/Rakefile/i, @app.instance_eval { have_rakefile })
|
||||
end
|
||||
end
|
||||
|
||||
def test_not_finding_rakefile
|
||||
@app.instance_eval { @rakefiles = ['NEVER_FOUND'] }
|
||||
assert( ! @app.instance_eval do have_rakefile end )
|
||||
assert_nil @app.rakefile
|
||||
end
|
||||
|
||||
def test_load_rakefile
|
||||
in_environment("PWD" => File.join(BASEDIR, "data/unittest")) do
|
||||
@app.instance_eval do
|
||||
handle_options
|
||||
options.silent = true
|
||||
load_rakefile
|
||||
end
|
||||
assert_equal "rakefile", @app.rakefile.downcase
|
||||
assert_match(%r(unittest$), Dir.pwd)
|
||||
end
|
||||
end
|
||||
|
||||
def test_load_rakefile_from_subdir
|
||||
in_environment("PWD" => File.join(BASEDIR, "data/unittest/subdir")) do
|
||||
@app.instance_eval do
|
||||
handle_options
|
||||
options.silent = true
|
||||
load_rakefile
|
||||
end
|
||||
assert_equal "rakefile", @app.rakefile.downcase
|
||||
assert_match(%r(unittest$), Dir.pwd)
|
||||
end
|
||||
end
|
||||
|
||||
def test_load_rakefile_not_found
|
||||
in_environment("PWD" => "/", "RAKE_SYSTEM" => 'not_exist') do
|
||||
@app.instance_eval do
|
||||
handle_options
|
||||
options.silent = true
|
||||
end
|
||||
ex = assert_raise(RuntimeError) do
|
||||
@app.instance_eval do raw_load_rakefile end
|
||||
end
|
||||
assert_match(/no rakefile found/i, ex.message)
|
||||
end
|
||||
end
|
||||
|
||||
def test_load_from_system_rakefile
|
||||
system_dir = File.expand_path('../data/default', __FILE__)
|
||||
in_environment('RAKE_SYSTEM' => system_dir) do
|
||||
@app.options.rakelib = []
|
||||
@app.instance_eval do
|
||||
handle_options
|
||||
options.silent = true
|
||||
options.load_system = true
|
||||
options.rakelib = []
|
||||
load_rakefile
|
||||
end
|
||||
assert_equal system_dir, @app.system_dir
|
||||
assert_nil @app.rakefile
|
||||
end
|
||||
end
|
||||
|
||||
def test_windows
|
||||
assert ! (@app.windows? && @app.unix?)
|
||||
end
|
||||
|
||||
def test_loading_imports
|
||||
args = []
|
||||
mock = defmock(:load) {|*a| args << a}
|
||||
@app.instance_eval do
|
||||
add_loader("dummy", mock)
|
||||
add_import("x.dummy")
|
||||
load_imports
|
||||
end
|
||||
assert_equal([["x.dummy"]], args)
|
||||
end
|
||||
|
||||
def test_building_imported_files_on_demand
|
||||
args = []
|
||||
callback = false
|
||||
mock = defmock(:load) {|*a| args << a}
|
||||
@app.instance_eval do
|
||||
intern(Rake::Task, "x.dummy").enhance do callback = true end
|
||||
add_loader("dummy", mock)
|
||||
add_import("x.dummy")
|
||||
load_imports
|
||||
end
|
||||
assert_equal([["x.dummy"]], args)
|
||||
assert(callback)
|
||||
end
|
||||
|
||||
def test_handle_options_should_strip_options_from_ARGV
|
||||
assert !@app.options.trace
|
||||
|
||||
valid_option = '--trace'
|
||||
ARGV.clear
|
||||
ARGV << valid_option
|
||||
|
||||
@app.handle_options
|
||||
|
||||
assert !ARGV.include?(valid_option)
|
||||
assert @app.options.trace
|
||||
end
|
||||
|
||||
def test_good_run
|
||||
ran = false
|
||||
ARGV.clear
|
||||
ARGV << '--rakelib=""'
|
||||
@app.options.silent = true
|
||||
@app.instance_eval do
|
||||
intern(Rake::Task, "default").enhance { ran = true }
|
||||
end
|
||||
in_environment("PWD" => File.join(BASEDIR, "data/default")) do
|
||||
@app.run
|
||||
end
|
||||
assert ran
|
||||
end
|
||||
|
||||
def test_display_task_run
|
||||
ran = false
|
||||
ARGV.clear
|
||||
ARGV << '-f' << '-s' << '--tasks' << '--rakelib=""'
|
||||
@app.last_description = "COMMENT"
|
||||
@app.define_task(Rake::Task, "default")
|
||||
out = capture_stdout { @app.run }
|
||||
assert @app.options.show_tasks
|
||||
assert ! ran
|
||||
assert_match(/rake default/, out)
|
||||
assert_match(/# COMMENT/, out)
|
||||
end
|
||||
|
||||
def test_display_prereqs
|
||||
ran = false
|
||||
ARGV.clear
|
||||
ARGV << '-f' << '-s' << '--prereqs' << '--rakelib=""'
|
||||
@app.last_description = "COMMENT"
|
||||
t = @app.define_task(Rake::Task, "default")
|
||||
t.enhance([:a, :b])
|
||||
@app.define_task(Rake::Task, "a")
|
||||
@app.define_task(Rake::Task, "b")
|
||||
out = capture_stdout { @app.run }
|
||||
assert @app.options.show_prereqs
|
||||
assert ! ran
|
||||
assert_match(/rake a$/, out)
|
||||
assert_match(/rake b$/, out)
|
||||
assert_match(/rake default\n( *(a|b)\n){2}/m, out)
|
||||
end
|
||||
|
||||
def test_bad_run
|
||||
@app.intern(Rake::Task, "default").enhance { fail }
|
||||
ARGV.clear
|
||||
ARGV << '-f' << '-s' << '--rakelib=""'
|
||||
assert_raise(SystemExit) {
|
||||
err = capture_stderr { @app.run }
|
||||
assert_match(/see full trace/, err)
|
||||
}
|
||||
ensure
|
||||
ARGV.clear
|
||||
end
|
||||
|
||||
def test_bad_run_with_trace
|
||||
@app.intern(Rake::Task, "default").enhance { fail }
|
||||
ARGV.clear
|
||||
ARGV << '-f' << '-s' << '-t'
|
||||
assert_raise(SystemExit) {
|
||||
err = capture_stderr { capture_stdout { @app.run } }
|
||||
assert_no_match(/see full trace/, err)
|
||||
}
|
||||
ensure
|
||||
ARGV.clear
|
||||
end
|
||||
|
||||
def test_run_with_bad_options
|
||||
@app.intern(Rake::Task, "default").enhance { fail }
|
||||
ARGV.clear
|
||||
ARGV << '-f' << '-s' << '--xyzzy'
|
||||
assert_raise(SystemExit) {
|
||||
err = capture_stderr { capture_stdout { @app.run } }
|
||||
}
|
||||
ensure
|
||||
ARGV.clear
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
######################################################################
|
||||
class TestApplicationOptions < Test::Unit::TestCase
|
||||
include CaptureStdout
|
||||
|
||||
def setup
|
||||
clear_argv
|
||||
RakeFileUtils.verbose_flag = false
|
||||
RakeFileUtils.nowrite_flag = false
|
||||
TESTING_REQUIRE.clear
|
||||
end
|
||||
|
||||
def teardown
|
||||
clear_argv
|
||||
RakeFileUtils.verbose_flag = false
|
||||
RakeFileUtils.nowrite_flag = false
|
||||
end
|
||||
|
||||
def clear_argv
|
||||
while ! ARGV.empty?
|
||||
ARGV.pop
|
||||
end
|
||||
end
|
||||
|
||||
def test_default_options
|
||||
opts = command_line
|
||||
assert_nil opts.classic_namespace
|
||||
assert_nil opts.dryrun
|
||||
assert_nil opts.full_description
|
||||
assert_nil opts.ignore_system
|
||||
assert_nil opts.load_system
|
||||
assert_nil opts.nosearch
|
||||
assert_equal ['rakelib'], opts.rakelib
|
||||
assert_nil opts.show_prereqs
|
||||
assert_nil opts.show_task_pattern
|
||||
assert_nil opts.show_tasks
|
||||
assert_nil opts.silent
|
||||
assert_nil opts.trace
|
||||
assert_equal ['rakelib'], opts.rakelib
|
||||
assert ! RakeFileUtils.verbose_flag
|
||||
assert ! RakeFileUtils.nowrite_flag
|
||||
end
|
||||
|
||||
def test_dry_run
|
||||
flags('--dry-run', '-n') do |opts|
|
||||
assert opts.dryrun
|
||||
assert opts.trace
|
||||
assert RakeFileUtils.verbose_flag
|
||||
assert RakeFileUtils.nowrite_flag
|
||||
end
|
||||
end
|
||||
|
||||
def test_describe
|
||||
flags('--describe') do |opts|
|
||||
assert opts.full_description
|
||||
assert opts.show_tasks
|
||||
assert_equal(//.to_s, opts.show_task_pattern.to_s)
|
||||
end
|
||||
end
|
||||
|
||||
def test_describe_with_pattern
|
||||
flags('--describe=X') do |opts|
|
||||
assert opts.full_description
|
||||
assert opts.show_tasks
|
||||
assert_equal(/X/.to_s, opts.show_task_pattern.to_s)
|
||||
end
|
||||
end
|
||||
|
||||
def test_execute
|
||||
$xyzzy = 0
|
||||
flags('--execute=$xyzzy=1', '-e $xyzzy=1') do |opts|
|
||||
assert_equal 1, $xyzzy
|
||||
assert_equal :exit, @exit
|
||||
$xyzzy = 0
|
||||
end
|
||||
end
|
||||
|
||||
def test_execute_and_continue
|
||||
$xyzzy = 0
|
||||
flags('--execute-continue=$xyzzy=1', '-E $xyzzy=1') do |opts|
|
||||
assert_equal 1, $xyzzy
|
||||
assert_not_equal :exit, @exit
|
||||
$xyzzy = 0
|
||||
end
|
||||
end
|
||||
|
||||
def test_execute_and_print
|
||||
$xyzzy = 0
|
||||
flags('--execute-print=$xyzzy="pugh"', '-p $xyzzy="pugh"') do |opts|
|
||||
assert_equal 'pugh', $xyzzy
|
||||
assert_equal :exit, @exit
|
||||
assert_match(/^pugh$/, @out)
|
||||
$xyzzy = 0
|
||||
end
|
||||
end
|
||||
|
||||
def test_help
|
||||
flags('--help', '-H', '-h') do |opts|
|
||||
assert_match(/\Arake/, @out)
|
||||
assert_match(/\boptions\b/, @out)
|
||||
assert_match(/\btargets\b/, @out)
|
||||
assert_equal :exit, @exit
|
||||
assert_equal :exit, @exit
|
||||
end
|
||||
end
|
||||
|
||||
def test_libdir
|
||||
flags(['--libdir', 'xx'], ['-I', 'xx'], ['-Ixx']) do |opts|
|
||||
$:.include?('xx')
|
||||
end
|
||||
ensure
|
||||
$:.delete('xx')
|
||||
end
|
||||
|
||||
def test_rakefile
|
||||
flags(['--rakefile', 'RF'], ['--rakefile=RF'], ['-f', 'RF'], ['-fRF']) do |opts|
|
||||
assert_equal ['RF'], @app.instance_eval { @rakefiles }
|
||||
end
|
||||
end
|
||||
|
||||
def test_rakelib
|
||||
flags(['--rakelibdir', 'A:B:C'], ['--rakelibdir=A:B:C'], ['-R', 'A:B:C'], ['-RA:B:C']) do |opts|
|
||||
assert_equal ['A', 'B', 'C'], opts.rakelib
|
||||
end
|
||||
end
|
||||
|
||||
def test_require
|
||||
flags(['--require', File.expand_path('../reqfile', __FILE__)],
|
||||
"-r#{File.expand_path('../reqfile2', __FILE__)}",
|
||||
"-r#{File.expand_path('../reqfile3', __FILE__)}") do |opts|
|
||||
end
|
||||
assert TESTING_REQUIRE.include?(1)
|
||||
assert TESTING_REQUIRE.include?(2)
|
||||
assert TESTING_REQUIRE.include?(3)
|
||||
assert_equal 3, TESTING_REQUIRE.size
|
||||
end
|
||||
|
||||
def test_missing_require
|
||||
ex = assert_raise(LoadError) do
|
||||
flags(['--require', File.expand_path('../missing', __FILE__)]) do |opts|
|
||||
end
|
||||
end
|
||||
assert_match(/no such file/, ex.message)
|
||||
assert_match(/#{File.basename(File.dirname(__FILE__))}\/missing/, ex.message)
|
||||
end
|
||||
|
||||
def test_prereqs
|
||||
flags('--prereqs', '-P') do |opts|
|
||||
assert opts.show_prereqs
|
||||
end
|
||||
end
|
||||
|
||||
def test_quiet
|
||||
flags('--quiet', '-q') do |opts|
|
||||
assert ! RakeFileUtils.verbose_flag
|
||||
assert ! opts.silent
|
||||
end
|
||||
end
|
||||
|
||||
def test_no_search
|
||||
flags('--nosearch', '--no-search', '-N') do |opts|
|
||||
assert opts.nosearch
|
||||
end
|
||||
end
|
||||
|
||||
def test_silent
|
||||
flags('--silent', '-s') do |opts|
|
||||
assert ! RakeFileUtils.verbose_flag
|
||||
assert opts.silent
|
||||
end
|
||||
end
|
||||
|
||||
def test_system
|
||||
flags('--system', '-g') do |opts|
|
||||
assert opts.load_system
|
||||
end
|
||||
end
|
||||
|
||||
def test_no_system
|
||||
flags('--no-system', '-G') do |opts|
|
||||
assert opts.ignore_system
|
||||
end
|
||||
end
|
||||
|
||||
def test_trace
|
||||
flags('--trace', '-t') do |opts|
|
||||
assert opts.trace
|
||||
assert RakeFileUtils.verbose_flag
|
||||
assert ! RakeFileUtils.nowrite_flag
|
||||
end
|
||||
end
|
||||
|
||||
def test_trace_rules
|
||||
flags('--rules') do |opts|
|
||||
assert opts.trace_rules
|
||||
end
|
||||
end
|
||||
|
||||
def test_tasks
|
||||
flags('--tasks', '-T') do |opts|
|
||||
assert opts.show_tasks
|
||||
assert_equal(//.to_s, opts.show_task_pattern.to_s)
|
||||
end
|
||||
flags(['--tasks', 'xyz'], ['-Txyz']) do |opts|
|
||||
assert opts.show_tasks
|
||||
assert_equal(/xyz/, opts.show_task_pattern)
|
||||
end
|
||||
end
|
||||
|
||||
def test_verbose
|
||||
flags('--verbose', '-V') do |opts|
|
||||
assert RakeFileUtils.verbose_flag
|
||||
assert ! opts.silent
|
||||
end
|
||||
end
|
||||
|
||||
def test_version
|
||||
flags('--version', '-V') do |opts|
|
||||
assert_match(/\bversion\b/, @out)
|
||||
assert_match(/\b#{RAKEVERSION}\b/, @out)
|
||||
assert_equal :exit, @exit
|
||||
end
|
||||
end
|
||||
|
||||
def test_classic_namespace
|
||||
flags(['--classic-namespace'], ['-C', '-T', '-P', '-n', '-s', '-t']) do |opts|
|
||||
assert opts.classic_namespace
|
||||
assert_equal opts.show_tasks, $show_tasks
|
||||
assert_equal opts.show_prereqs, $show_prereqs
|
||||
assert_equal opts.trace, $trace
|
||||
assert_equal opts.dryrun, $dryrun
|
||||
assert_equal opts.silent, $silent
|
||||
end
|
||||
end
|
||||
|
||||
def test_bad_option
|
||||
capture_stderr do
|
||||
ex = assert_raise(OptionParser::InvalidOption) do
|
||||
flags('--bad-option')
|
||||
end
|
||||
if ex.message =~ /^While/ # Ruby 1.9 error message
|
||||
assert_match(/while parsing/i, ex.message)
|
||||
else # Ruby 1.8 error message
|
||||
assert_match(/(invalid|unrecognized) option/i, ex.message)
|
||||
assert_match(/--bad-option/, ex.message)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_task_collection
|
||||
command_line("a", "b")
|
||||
assert_equal ["a", "b"], @tasks.sort
|
||||
end
|
||||
|
||||
def test_default_task_collection
|
||||
command_line()
|
||||
assert_equal ["default"], @tasks
|
||||
end
|
||||
|
||||
def test_environment_definition
|
||||
ENV.delete('TESTKEY')
|
||||
command_line("a", "TESTKEY=12")
|
||||
assert_equal ["a"], @tasks.sort
|
||||
assert '12', ENV['TESTKEY']
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def flags(*sets)
|
||||
sets.each do |set|
|
||||
ARGV.clear
|
||||
@out = capture_stdout {
|
||||
@exit = catch(:system_exit) { opts = command_line(*set) }
|
||||
}
|
||||
yield(@app.options) if block_given?
|
||||
end
|
||||
end
|
||||
|
||||
def command_line(*options)
|
||||
options.each do |opt| ARGV << opt end
|
||||
@app = Rake::Application.new
|
||||
def @app.exit(*args)
|
||||
throw :system_exit, :exit
|
||||
end
|
||||
@app.instance_eval do
|
||||
handle_options
|
||||
collect_tasks
|
||||
end
|
||||
@tasks = @app.top_level_tasks
|
||||
@app.options
|
||||
end
|
||||
end
|
||||
|
||||
class TestTaskArgumentParsing < Test::Unit::TestCase
|
||||
def setup
|
||||
@app = Rake::Application.new
|
||||
end
|
||||
|
||||
def test_name_only
|
||||
name, args = @app.parse_task_string("name")
|
||||
assert_equal "name", name
|
||||
assert_equal [], args
|
||||
end
|
||||
|
||||
def test_empty_args
|
||||
name, args = @app.parse_task_string("name[]")
|
||||
assert_equal "name", name
|
||||
assert_equal [], args
|
||||
end
|
||||
|
||||
def test_one_argument
|
||||
name, args = @app.parse_task_string("name[one]")
|
||||
assert_equal "name", name
|
||||
assert_equal ["one"], args
|
||||
end
|
||||
|
||||
def test_two_arguments
|
||||
name, args = @app.parse_task_string("name[one,two]")
|
||||
assert_equal "name", name
|
||||
assert_equal ["one", "two"], args
|
||||
end
|
||||
|
||||
def test_can_handle_spaces_between_args
|
||||
name, args = @app.parse_task_string("name[one, two,\tthree , \tfour]")
|
||||
assert_equal "name", name
|
||||
assert_equal ["one", "two", "three", "four"], args
|
||||
end
|
||||
|
||||
def test_keeps_embedded_spaces
|
||||
name, args = @app.parse_task_string("name[a one ana, two]")
|
||||
assert_equal "name", name
|
||||
assert_equal ["a one ana", "two"], args
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
class TestTaskArgumentParsing < Test::Unit::TestCase
|
||||
include InEnvironment
|
||||
|
||||
def test_terminal_width_using_env
|
||||
app = Rake::Application.new
|
||||
in_environment('RAKE_COLUMNS' => '1234') do
|
||||
assert_equal 1234, app.terminal_width
|
||||
end
|
||||
end
|
||||
|
||||
def test_terminal_width_using_stty
|
||||
app = Rake::Application.new
|
||||
def app.unix?() true end
|
||||
def app.dynamic_width_stty() 1235 end
|
||||
def app.dynamic_width_tput() 0 end
|
||||
in_environment('RAKE_COLUMNS' => nil) do
|
||||
assert_equal 1235, app.terminal_width
|
||||
end
|
||||
end
|
||||
|
||||
def test_terminal_width_using_tput
|
||||
app = Rake::Application.new
|
||||
def app.unix?() true end
|
||||
def app.dynamic_width_stty() 0 end
|
||||
def app.dynamic_width_tput() 1236 end
|
||||
in_environment('RAKE_COLUMNS' => nil) do
|
||||
assert_equal 1236, app.terminal_width
|
||||
end
|
||||
end
|
||||
|
||||
def test_terminal_width_using_hardcoded_80
|
||||
app = Rake::Application.new
|
||||
def app.unix?() false end
|
||||
in_environment('RAKE_COLUMNS' => nil) do
|
||||
assert_equal 80, app.terminal_width
|
||||
end
|
||||
end
|
||||
|
||||
def test_terminal_width_with_failure
|
||||
app = Rake::Application.new
|
||||
called = false
|
||||
class << app; self; end.class_eval do
|
||||
define_method(:unix?) {|*a|
|
||||
called = a
|
||||
raise RuntimeError
|
||||
}
|
||||
end
|
||||
in_environment('RAKE_COLUMNS' => nil) do
|
||||
assert_equal 80, app.terminal_width
|
||||
end
|
||||
assert_equal([], called)
|
||||
end
|
||||
end
|
|
@ -0,0 +1,12 @@
|
|||
require 'test/unit'
|
||||
require 'rake/clean'
|
||||
|
||||
class TestClean < Test::Unit::TestCase
|
||||
include Rake
|
||||
def test_clean
|
||||
assert Task['clean'], "Should define clean"
|
||||
assert Task['clobber'], "Should define clobber"
|
||||
assert Task['clobber'].prerequisites.include?("clean"),
|
||||
"Clobber should require clean"
|
||||
end
|
||||
end
|
|
@ -0,0 +1,81 @@
|
|||
require 'test/unit'
|
||||
require 'fileutils'
|
||||
require 'rake'
|
||||
require_relative 'filecreation'
|
||||
|
||||
######################################################################
|
||||
class TestDefinitions < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
EXISTINGFILE = "testdata/existing"
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
end
|
||||
|
||||
def test_task
|
||||
done = false
|
||||
task :one => [:two] do done = true end
|
||||
task :two
|
||||
task :three => [:one, :two]
|
||||
check_tasks(:one, :two, :three)
|
||||
assert done, "Should be done"
|
||||
end
|
||||
|
||||
def test_file_task
|
||||
done = false
|
||||
file "testdata/one" => "testdata/two" do done = true end
|
||||
file "testdata/two"
|
||||
file "testdata/three" => ["testdata/one", "testdata/two"]
|
||||
check_tasks("testdata/one", "testdata/two", "testdata/three")
|
||||
assert done, "Should be done"
|
||||
end
|
||||
|
||||
def check_tasks(n1, n2, n3)
|
||||
t = Task[n1]
|
||||
assert Task === t, "Should be a Task"
|
||||
assert_equal n1.to_s, t.name
|
||||
assert_equal [n2.to_s], t.prerequisites.collect{|n| n.to_s}
|
||||
t.invoke
|
||||
t2 = Task[n2]
|
||||
assert_equal FileList[], t2.prerequisites
|
||||
t3 = Task[n3]
|
||||
assert_equal [n1.to_s, n2.to_s], t3.prerequisites.collect{|n|n.to_s}
|
||||
end
|
||||
|
||||
def test_incremental_definitions
|
||||
runs = []
|
||||
task :t1 => [:t2] do runs << "A"; 4321 end
|
||||
task :t1 => [:t3] do runs << "B"; 1234 end
|
||||
task :t1 => [:t3]
|
||||
task :t2
|
||||
task :t3
|
||||
Task[:t1].invoke
|
||||
assert_equal ["A", "B"], runs
|
||||
assert_equal ["t2", "t3"], Task[:t1].prerequisites
|
||||
end
|
||||
|
||||
def test_missing_dependencies
|
||||
task :x => ["testdata/missing"]
|
||||
assert_raise(RuntimeError) { Task[:x].invoke }
|
||||
end
|
||||
|
||||
def test_implicit_file_dependencies
|
||||
runs = []
|
||||
create_existing_file
|
||||
task :y => [EXISTINGFILE] do |t| runs << t.name end
|
||||
Task[:y].invoke
|
||||
assert_equal runs, ['y']
|
||||
end
|
||||
|
||||
private # ----------------------------------------------------------
|
||||
|
||||
def create_existing_file
|
||||
Dir.mkdir File.dirname(EXISTINGFILE) unless
|
||||
File.exist?(File.dirname(EXISTINGFILE))
|
||||
open(EXISTINGFILE, "w") do |f| f.puts "HI" end unless
|
||||
File.exist?(EXISTINGFILE)
|
||||
end
|
||||
|
||||
end
|
||||
|
|
@ -0,0 +1,33 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
class TestEarlyTime < Test::Unit::TestCase
|
||||
def test_create
|
||||
early = Rake::EarlyTime.instance
|
||||
time = Time.mktime(1970, 1, 1, 0, 0, 0)
|
||||
assert early <= Time.now
|
||||
assert early < Time.now
|
||||
assert early != Time.now
|
||||
assert Time.now > early
|
||||
assert Time.now >= early
|
||||
assert Time.now != early
|
||||
end
|
||||
|
||||
def test_equality
|
||||
early = Rake::EarlyTime.instance
|
||||
assert_equal early, early, "two early times should be equal"
|
||||
end
|
||||
|
||||
def test_original_time_compare_is_not_messed_up
|
||||
t1 = Time.mktime(1970, 1, 1, 0, 0, 0)
|
||||
t2 = Time.now
|
||||
assert t1 < t2
|
||||
assert t2 > t1
|
||||
assert t1 == t1
|
||||
assert t2 == t2
|
||||
end
|
||||
|
||||
def test_to_s
|
||||
assert_equal "<EARLY TIME>", Rake::EARLY.to_s
|
||||
end
|
||||
end
|
|
@ -0,0 +1,61 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
require 'stringio'
|
||||
|
||||
######################################################################
|
||||
class TestExtension < Test::Unit::TestCase
|
||||
|
||||
module Redirect
|
||||
def error_redirect
|
||||
old_err = $stderr
|
||||
result = StringIO.new
|
||||
$stderr = result
|
||||
yield
|
||||
result
|
||||
ensure
|
||||
$stderr = old_err
|
||||
end
|
||||
end
|
||||
|
||||
class Sample
|
||||
extend Redirect
|
||||
|
||||
def duplicate_method
|
||||
:original
|
||||
end
|
||||
|
||||
OK_ERRS = error_redirect do
|
||||
rake_extension("a") do
|
||||
def ok_method
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
DUP_ERRS = error_redirect do
|
||||
rake_extension("duplicate_method") do
|
||||
def duplicate_method
|
||||
:override
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_methods_actually_exist
|
||||
sample = Sample.new
|
||||
sample.ok_method
|
||||
sample.duplicate_method
|
||||
end
|
||||
|
||||
def test_no_warning_when_defining_ok_method
|
||||
assert_equal "", Sample::OK_ERRS.string
|
||||
end
|
||||
|
||||
def test_extension_complains_when_a_method_that_is_present
|
||||
assert_match(/warning:/i, Sample::DUP_ERRS.string)
|
||||
assert_match(/already exists/i, Sample::DUP_ERRS.string)
|
||||
assert_match(/duplicate_method/i, Sample::DUP_ERRS.string)
|
||||
assert_equal :original, Sample.new.duplicate_method
|
||||
end
|
||||
|
||||
end
|
|
@ -0,0 +1,60 @@
|
|||
require 'test/unit'
|
||||
require 'fileutils'
|
||||
require 'rake'
|
||||
require_relative 'filecreation'
|
||||
|
||||
######################################################################
|
||||
class TestFileCreationTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
include FileCreation
|
||||
|
||||
DUMMY_DIR = 'testdata/dummy_dir'
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
end
|
||||
|
||||
def teardown
|
||||
FileUtils.rm_rf DUMMY_DIR
|
||||
end
|
||||
|
||||
def test_file_needed
|
||||
create_dir DUMMY_DIR
|
||||
fc_task = Task[DUMMY_DIR]
|
||||
assert_equal DUMMY_DIR, fc_task.name
|
||||
FileUtils.rm_rf fc_task.name
|
||||
assert fc_task.needed?, "file should be needed"
|
||||
FileUtils.mkdir fc_task.name
|
||||
assert_equal nil, fc_task.prerequisites.collect{|n| Task[n].timestamp}.max
|
||||
assert ! fc_task.needed?, "file should not be needed"
|
||||
end
|
||||
|
||||
def test_directory
|
||||
directory DUMMY_DIR
|
||||
fc_task = Task[DUMMY_DIR]
|
||||
assert_equal DUMMY_DIR, fc_task.name
|
||||
assert FileCreationTask === fc_task
|
||||
end
|
||||
|
||||
def test_no_retriggers_on_filecreate_task
|
||||
create_timed_files(OLDFILE, NEWFILE)
|
||||
t1 = Rake.application.intern(FileCreationTask, OLDFILE).enhance([NEWFILE])
|
||||
t2 = Rake.application.intern(FileCreationTask, NEWFILE)
|
||||
assert ! t2.needed?, "Should not need to build new file"
|
||||
assert ! t1.needed?, "Should not need to rebuild old file because of new"
|
||||
end
|
||||
|
||||
def test_no_retriggers_on_file_task
|
||||
create_timed_files(OLDFILE, NEWFILE)
|
||||
t1 = Rake.application.intern(FileCreationTask, OLDFILE).enhance([NEWFILE])
|
||||
t2 = Rake.application.intern(FileCreationTask, NEWFILE)
|
||||
assert ! t2.needed?, "Should not need to build new file"
|
||||
assert ! t1.needed?, "Should not need to rebuild old file because of new"
|
||||
end
|
||||
|
||||
def test_very_early_timestamp
|
||||
t1 = Rake.application.intern(FileCreationTask, OLDFILE)
|
||||
assert t1.timestamp < Time.now
|
||||
assert t1.timestamp < Time.now - 1000000
|
||||
end
|
||||
end
|
|
@ -0,0 +1,139 @@
|
|||
require 'test/unit'
|
||||
require 'fileutils'
|
||||
require 'rake'
|
||||
require_relative 'filecreation'
|
||||
|
||||
######################################################################
|
||||
class TestFileTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
include FileCreation
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
@runs = Array.new
|
||||
FileUtils.rm_f NEWFILE
|
||||
FileUtils.rm_f OLDFILE
|
||||
end
|
||||
|
||||
def test_file_need
|
||||
name = "testdata/dummy"
|
||||
file name
|
||||
ftask = Task[name]
|
||||
assert_equal name.to_s, ftask.name
|
||||
File.delete(ftask.name) rescue nil
|
||||
assert ftask.needed?, "file should be needed"
|
||||
open(ftask.name, "w") { |f| f.puts "HI" }
|
||||
assert_equal nil, ftask.prerequisites.collect{|n| Task[n].timestamp}.max
|
||||
assert ! ftask.needed?, "file should not be needed"
|
||||
File.delete(ftask.name) rescue nil
|
||||
end
|
||||
|
||||
def test_file_times_new_depends_on_old
|
||||
create_timed_files(OLDFILE, NEWFILE)
|
||||
|
||||
t1 = Rake.application.intern(FileTask, NEWFILE).enhance([OLDFILE])
|
||||
t2 = Rake.application.intern(FileTask, OLDFILE)
|
||||
assert ! t2.needed?, "Should not need to build old file"
|
||||
assert ! t1.needed?, "Should not need to rebuild new file because of old"
|
||||
end
|
||||
|
||||
def test_file_times_old_depends_on_new
|
||||
create_timed_files(OLDFILE, NEWFILE)
|
||||
|
||||
t1 = Rake.application.intern(FileTask,OLDFILE).enhance([NEWFILE])
|
||||
t2 = Rake.application.intern(FileTask, NEWFILE)
|
||||
assert ! t2.needed?, "Should not need to build new file"
|
||||
preq_stamp = t1.prerequisites.collect{|t| Task[t].timestamp}.max
|
||||
assert_equal t2.timestamp, preq_stamp
|
||||
assert t1.timestamp < preq_stamp, "T1 should be older"
|
||||
assert t1.needed?, "Should need to rebuild old file because of new"
|
||||
end
|
||||
|
||||
def test_file_depends_on_task_depend_on_file
|
||||
create_timed_files(OLDFILE, NEWFILE)
|
||||
|
||||
file NEWFILE => [:obj] do |t| @runs << t.name end
|
||||
task :obj => [OLDFILE] do |t| @runs << t.name end
|
||||
file OLDFILE do |t| @runs << t.name end
|
||||
|
||||
Task[:obj].invoke
|
||||
Task[NEWFILE].invoke
|
||||
assert ! @runs.include?(NEWFILE)
|
||||
end
|
||||
|
||||
def test_existing_file_depends_on_non_existing_file
|
||||
create_file(OLDFILE)
|
||||
delete_file(NEWFILE)
|
||||
file NEWFILE
|
||||
file OLDFILE => NEWFILE
|
||||
assert_nothing_raised do Task[OLDFILE].invoke end
|
||||
end
|
||||
|
||||
# I have currently disabled this test. I'm not convinced that
|
||||
# deleting the file target on failure is always the proper thing to
|
||||
# do. I'm willing to hear input on this topic.
|
||||
def ztest_file_deletes_on_failure
|
||||
task :obj
|
||||
file NEWFILE => [:obj] do |t|
|
||||
FileUtils.touch NEWFILE
|
||||
fail "Ooops"
|
||||
end
|
||||
assert Task[NEWFILE]
|
||||
begin
|
||||
Task[NEWFILE].invoke
|
||||
rescue Exception
|
||||
end
|
||||
assert( ! File.exist?(NEWFILE), "NEWFILE should be deleted")
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
######################################################################
|
||||
class TestDirectoryTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
def setup
|
||||
rm_rf "testdata", :verbose=>false
|
||||
end
|
||||
|
||||
def teardown
|
||||
rm_rf "testdata", :verbose=>false
|
||||
end
|
||||
|
||||
def test_directory
|
||||
desc "DESC"
|
||||
directory "testdata/a/b/c"
|
||||
assert_equal FileCreationTask, Task["testdata"].class
|
||||
assert_equal FileCreationTask, Task["testdata/a"].class
|
||||
assert_equal FileCreationTask, Task["testdata/a/b/c"].class
|
||||
assert_nil Task["testdata"].comment
|
||||
assert_equal "DESC", Task["testdata/a/b/c"].comment
|
||||
assert_nil Task["testdata/a/b"].comment
|
||||
verbose(false) {
|
||||
Task['testdata/a/b'].invoke
|
||||
}
|
||||
assert File.exist?("testdata/a/b")
|
||||
assert ! File.exist?("testdata/a/b/c")
|
||||
end
|
||||
|
||||
if Rake::Win32.windows?
|
||||
def test_directory_win32
|
||||
desc "WIN32 DESC"
|
||||
FileUtils.mkdir_p("testdata")
|
||||
Dir.chdir("testdata") do
|
||||
directory 'c:/testdata/a/b/c'
|
||||
assert_equal FileCreationTask, Task['c:/testdata'].class
|
||||
assert_equal FileCreationTask, Task['c:/testdata/a'].class
|
||||
assert_equal FileCreationTask, Task['c:/testdata/a/b/c'].class
|
||||
assert_nil Task['c:/testdata'].comment
|
||||
assert_equal "WIN32 DESC", Task['c:/testdata/a/b/c'].comment
|
||||
assert_nil Task['c:/testdata/a/b'].comment
|
||||
verbose(false) {
|
||||
Task['c:/testdata/a/b'].invoke
|
||||
}
|
||||
assert File.exist?('c:/testdata/a/b')
|
||||
assert ! File.exist?('c:/testdata/a/b/c')
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
|
@ -0,0 +1,625 @@
|
|||
require 'test/unit'
|
||||
require 'tmpdir'
|
||||
require 'rake'
|
||||
|
||||
require_relative 'capture_stdout'
|
||||
|
||||
class TestFileList < Test::Unit::TestCase
|
||||
FileList = Rake::FileList
|
||||
include CaptureStdout
|
||||
|
||||
def setup
|
||||
@oldwd = Dir.pwd
|
||||
@tmpwd = Dir.mktmpdir
|
||||
Dir.chdir(@tmpwd)
|
||||
create_test_data
|
||||
end
|
||||
|
||||
def teardown
|
||||
# FileList.select_default_ignore_patterns
|
||||
FileUtils.rm_rf("testdata")
|
||||
Dir.chdir(@oldwd)
|
||||
FileUtils.rm_rf(@tmpwd)
|
||||
end
|
||||
|
||||
def test_delgating_methods_do_not_include_to_a_or_to_ary
|
||||
assert ! FileList::DELEGATING_METHODS.include?("to_a"), "should not include to_a"
|
||||
assert ! FileList::DELEGATING_METHODS.include?(:to_a), "should not include to_a"
|
||||
assert ! FileList::DELEGATING_METHODS.include?("to_ary"), "should not include to_ary"
|
||||
assert ! FileList::DELEGATING_METHODS.include?(:to_ary), "should not include to_ary"
|
||||
end
|
||||
|
||||
def test_create
|
||||
fl = FileList.new
|
||||
assert_equal 0, fl.size
|
||||
end
|
||||
|
||||
def test_create_with_args
|
||||
fl = FileList.new("testdata/*.c", "x")
|
||||
assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort,
|
||||
fl.sort
|
||||
end
|
||||
|
||||
def test_create_with_block
|
||||
fl = FileList.new { |f| f.include("x") }
|
||||
assert_equal ["x"], fl.resolve
|
||||
end
|
||||
|
||||
def test_create_with_brackets
|
||||
fl = FileList["testdata/*.c", "x"]
|
||||
assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort,
|
||||
fl.sort
|
||||
end
|
||||
|
||||
def test_create_with_brackets_and_filelist
|
||||
fl = FileList[FileList["testdata/*.c", "x"]]
|
||||
assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort,
|
||||
fl.sort
|
||||
end
|
||||
|
||||
def test_include_with_another_array
|
||||
fl = FileList.new.include(["x", "y", "z"])
|
||||
assert_equal ["x", "y", "z"].sort, fl.sort
|
||||
end
|
||||
|
||||
def test_include_with_another_filelist
|
||||
fl = FileList.new.include(FileList["testdata/*.c", "x"])
|
||||
assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort,
|
||||
fl.sort
|
||||
end
|
||||
|
||||
def test_append
|
||||
fl = FileList.new
|
||||
fl << "a.rb" << "b.rb"
|
||||
assert_equal ['a.rb', 'b.rb'], fl
|
||||
end
|
||||
|
||||
def test_add_many
|
||||
fl = FileList.new
|
||||
fl.include %w(a d c)
|
||||
fl.include('x', 'y')
|
||||
assert_equal ['a', 'd', 'c', 'x', 'y'], fl
|
||||
assert_equal ['a', 'd', 'c', 'x', 'y'], fl.resolve
|
||||
end
|
||||
|
||||
def test_add_return
|
||||
f = FileList.new
|
||||
g = f << "x"
|
||||
assert_equal f.object_id, g.object_id
|
||||
h = f.include("y")
|
||||
assert_equal f.object_id, h.object_id
|
||||
end
|
||||
|
||||
def test_match
|
||||
fl = FileList.new
|
||||
fl.include(File.expand_path('../test*.rb', __FILE__))
|
||||
assert fl.include?(__FILE__)
|
||||
assert fl.size > 3
|
||||
fl.each { |fn| assert_match(/\.rb$/, fn) }
|
||||
end
|
||||
|
||||
def test_add_matching
|
||||
fl = FileList.new
|
||||
fl << "a.java"
|
||||
fl.include(File.dirname(__FILE__)+"/*.rb")
|
||||
assert_equal "a.java", fl[0]
|
||||
assert fl.size > 2
|
||||
assert fl.include?(__FILE__)
|
||||
end
|
||||
|
||||
def test_multiple_patterns
|
||||
create_test_data
|
||||
fl = FileList.new
|
||||
fl.include('*.c', '*xist*')
|
||||
assert_equal [], fl
|
||||
fl.include('testdata/*.c', 'testdata/*xist*')
|
||||
assert_equal [
|
||||
'testdata/x.c', 'testdata/xyz.c', 'testdata/abc.c', 'testdata/existing'
|
||||
].sort, fl.sort
|
||||
end
|
||||
|
||||
def test_square_bracket_pattern
|
||||
fl = FileList.new
|
||||
fl.include("testdata/abc.[ch]")
|
||||
assert fl.size == 2
|
||||
assert fl.include?("testdata/abc.c")
|
||||
assert fl.include?("testdata/abc.h")
|
||||
end
|
||||
|
||||
def test_curly_bracket_pattern
|
||||
fl = FileList.new
|
||||
fl.include("testdata/abc.{c,h}")
|
||||
assert fl.size == 2
|
||||
assert fl.include?("testdata/abc.c")
|
||||
assert fl.include?("testdata/abc.h")
|
||||
end
|
||||
|
||||
def test_reject
|
||||
fl = FileList.new
|
||||
fl.include %w(testdata/x.c testdata/abc.c testdata/xyz.c testdata/existing)
|
||||
fl.reject! { |fn| fn =~ %r{/x} }
|
||||
assert_equal [
|
||||
'testdata/abc.c', 'testdata/existing'
|
||||
], fl
|
||||
end
|
||||
|
||||
def test_exclude
|
||||
fl = FileList['testdata/x.c', 'testdata/abc.c', 'testdata/xyz.c', 'testdata/existing']
|
||||
fl.each { |fn| touch fn, :verbose => false }
|
||||
x = fl.exclude(%r{/x.+\.})
|
||||
assert_equal FileList, x.class
|
||||
assert_equal %w(testdata/x.c testdata/abc.c testdata/existing), fl
|
||||
assert_equal fl.object_id, x.object_id
|
||||
fl.exclude('testdata/*.c')
|
||||
assert_equal ['testdata/existing'], fl
|
||||
fl.exclude('testdata/existing')
|
||||
assert_equal [], fl
|
||||
end
|
||||
|
||||
def test_excluding_via_block
|
||||
fl = FileList['testdata/a.c', 'testdata/b.c', 'testdata/xyz.c']
|
||||
fl.exclude { |fn| fn.pathmap('%n') == 'xyz' }
|
||||
assert fl.exclude?("xyz.c"), "Should exclude xyz.c"
|
||||
assert_equal ['testdata/a.c', 'testdata/b.c'], fl
|
||||
end
|
||||
|
||||
def test_exclude_return_on_create
|
||||
fl = FileList['testdata/*'].exclude(/.*\.[hcx]$/)
|
||||
assert_equal ['testdata/existing', 'testdata/cfiles'].sort, fl.sort
|
||||
assert_equal FileList, fl.class
|
||||
end
|
||||
|
||||
def test_exclude_with_string_return_on_create
|
||||
fl = FileList['testdata/*'].exclude('testdata/abc.c')
|
||||
assert_equal %w(testdata/existing testdata/cfiles testdata/x.c testdata/abc.h testdata/abc.x testdata/xyz.c).sort, fl.sort
|
||||
assert_equal FileList, fl.class
|
||||
end
|
||||
|
||||
def test_default_exclude
|
||||
fl = FileList.new
|
||||
fl.clear_exclude
|
||||
fl.include("**/*~", "**/*.bak", "**/core")
|
||||
assert fl.member?("testdata/core"), "Should include core"
|
||||
assert fl.member?("testdata/x.bak"), "Should include .bak files"
|
||||
end
|
||||
|
||||
def test_unique
|
||||
fl = FileList.new
|
||||
fl << "x.c" << "a.c" << "b.rb" << "a.c"
|
||||
assert_equal ['x.c', 'a.c', 'b.rb', 'a.c'], fl
|
||||
fl.uniq!
|
||||
assert_equal ['x.c', 'a.c', 'b.rb'], fl
|
||||
end
|
||||
|
||||
def test_to_string
|
||||
fl = FileList.new
|
||||
fl << "a.java" << "b.java"
|
||||
assert_equal "a.java b.java", fl.to_s
|
||||
assert_equal "a.java b.java", "#{fl}"
|
||||
end
|
||||
|
||||
def test_to_array
|
||||
fl = FileList['a.java', 'b.java']
|
||||
assert_equal ['a.java', 'b.java'], fl.to_a
|
||||
assert_equal Array, fl.to_a.class
|
||||
assert_equal ['a.java', 'b.java'], fl.to_ary
|
||||
assert_equal Array, fl.to_ary.class
|
||||
end
|
||||
|
||||
def test_to_s_pending
|
||||
fl = FileList['testdata/abc.*']
|
||||
result = fl.to_s
|
||||
assert_match(%r{testdata/abc\.c}, result)
|
||||
assert_match(%r{testdata/abc\.h}, result)
|
||||
assert_match(%r{testdata/abc\.x}, result)
|
||||
assert_match(%r{(testdata/abc\..\b ?){2}}, result)
|
||||
end
|
||||
|
||||
def test_inspect_pending
|
||||
fl = FileList['testdata/abc.*']
|
||||
result = fl.inspect
|
||||
assert_match(%r{"testdata/abc\.c"}, result)
|
||||
assert_match(%r{"testdata/abc\.h"}, result)
|
||||
assert_match(%r{"testdata/abc\.x"}, result)
|
||||
assert_match(%r|^\[("testdata/abc\..", ){2}"testdata/abc\.."\]$|, result)
|
||||
end
|
||||
|
||||
def test_sub
|
||||
fl = FileList["testdata/*.c"]
|
||||
f2 = fl.sub(/\.c$/, ".o")
|
||||
assert_equal FileList, f2.class
|
||||
assert_equal ["testdata/abc.o", "testdata/x.o", "testdata/xyz.o"].sort,
|
||||
f2.sort
|
||||
f3 = fl.gsub(/\.c$/, ".o")
|
||||
assert_equal FileList, f3.class
|
||||
assert_equal ["testdata/abc.o", "testdata/x.o", "testdata/xyz.o"].sort,
|
||||
f3.sort
|
||||
end
|
||||
|
||||
def test_claim_to_be_a_kind_of_array
|
||||
fl = FileList['testdata/*.c']
|
||||
assert fl.is_a?(Array)
|
||||
assert fl.kind_of?(Array)
|
||||
end
|
||||
|
||||
def test_claim_to_be_a_kind_of_filelist
|
||||
fl = FileList['testdata/*.c']
|
||||
assert fl.is_a?(FileList)
|
||||
assert fl.kind_of?(FileList)
|
||||
end
|
||||
|
||||
def test_claim_to_be_a_filelist_instance
|
||||
fl = FileList['testdata/*.c']
|
||||
assert fl.instance_of?(FileList)
|
||||
end
|
||||
|
||||
def test_dont_claim_to_be_an_array_instance
|
||||
fl = FileList['testdata/*.c']
|
||||
assert ! fl.instance_of?(Array)
|
||||
end
|
||||
|
||||
def test_sub!
|
||||
f = "x/a.c"
|
||||
fl = FileList[f, "x/b.c"]
|
||||
res = fl.sub!(/\.c$/, ".o")
|
||||
assert_equal ["x/a.o", "x/b.o"].sort, fl.sort
|
||||
assert_equal "x/a.c", f
|
||||
assert_equal fl.object_id, res.object_id
|
||||
end
|
||||
|
||||
def test_sub_with_block
|
||||
fl = FileList["src/org/onestepback/a.java", "src/org/onestepback/b.java"]
|
||||
# The block version doesn't work the way I want it to ...
|
||||
# f2 = fl.sub(%r{^src/(.*)\.java$}) { |x| "classes/" + $1 + ".class" }
|
||||
f2 = fl.sub(%r{^src/(.*)\.java$}, "classes/\\1.class")
|
||||
assert_equal [
|
||||
"classes/org/onestepback/a.class",
|
||||
"classes/org/onestepback/b.class"
|
||||
].sort,
|
||||
f2.sort
|
||||
end
|
||||
|
||||
def test_string_ext
|
||||
assert_equal "one.net", "one.two".ext("net")
|
||||
assert_equal "one.net", "one.two".ext(".net")
|
||||
assert_equal "one.net", "one".ext("net")
|
||||
assert_equal "one.net", "one".ext(".net")
|
||||
assert_equal "one.two.net", "one.two.c".ext(".net")
|
||||
assert_equal "one/two.net", "one/two.c".ext(".net")
|
||||
assert_equal "one.x/two.net", "one.x/two.c".ext(".net")
|
||||
assert_equal "one.x/two.net", "one.x/two".ext(".net")
|
||||
assert_equal ".onerc.net", ".onerc.dot".ext("net")
|
||||
assert_equal ".onerc.net", ".onerc".ext("net")
|
||||
assert_equal ".a/.onerc.net", ".a/.onerc".ext("net")
|
||||
assert_equal "one", "one.two".ext('')
|
||||
assert_equal "one", "one.two".ext
|
||||
assert_equal ".one", ".one.two".ext
|
||||
assert_equal ".one", ".one".ext
|
||||
assert_equal ".", ".".ext("c")
|
||||
assert_equal "..", "..".ext("c")
|
||||
# These only need to work in windows
|
||||
if Rake::Win32.windows?
|
||||
assert_equal "one.x\\two.net", "one.x\\two.c".ext(".net")
|
||||
assert_equal "one.x\\two.net", "one.x\\two".ext(".net")
|
||||
end
|
||||
end
|
||||
|
||||
def test_filelist_ext
|
||||
assert_equal FileList['one.c', '.one.c'],
|
||||
FileList['one.net', '.one'].ext('c')
|
||||
end
|
||||
|
||||
def test_gsub
|
||||
create_test_data
|
||||
fl = FileList["testdata/*.c"]
|
||||
f2 = fl.gsub(/a/, "A")
|
||||
assert_equal ["testdAtA/Abc.c", "testdAtA/x.c", "testdAtA/xyz.c"].sort,
|
||||
f2.sort
|
||||
end
|
||||
|
||||
def test_gsub!
|
||||
create_test_data
|
||||
f = FileList["testdata/*.c"]
|
||||
f.gsub!(/a/, "A")
|
||||
assert_equal ["testdAtA/Abc.c", "testdAtA/x.c", "testdAtA/xyz.c"].sort,
|
||||
f.sort
|
||||
end
|
||||
|
||||
def test_egrep_with_output
|
||||
files = FileList[File.expand_path('../test*.rb', __FILE__)]
|
||||
the_line_number = __LINE__ + 1
|
||||
out = capture_stdout do files.egrep(/PUGH/) end
|
||||
assert_match(/:#{the_line_number}:/, out)
|
||||
end
|
||||
|
||||
def test_egrep_with_block
|
||||
files = FileList[File.expand_path('../test*.rb', __FILE__)]
|
||||
found = false
|
||||
the_line_number = __LINE__ + 1
|
||||
files.egrep(/XYZZY/) do |fn, ln, line |
|
||||
assert_equal __FILE__, fn
|
||||
assert_equal the_line_number, ln
|
||||
assert_match(/files\.egrep/, line)
|
||||
found = true
|
||||
end
|
||||
assert found, "should have found a matching line"
|
||||
end
|
||||
|
||||
def test_existing
|
||||
fl = FileList['testdata/abc.c', 'testdata/notthere.c']
|
||||
assert_equal ["testdata/abc.c"], fl.existing
|
||||
assert fl.existing.is_a?(FileList)
|
||||
end
|
||||
|
||||
def test_existing!
|
||||
fl = FileList['testdata/abc.c', 'testdata/notthere.c']
|
||||
result = fl.existing!
|
||||
assert_equal ["testdata/abc.c"], fl
|
||||
assert_equal fl.object_id, result.object_id
|
||||
end
|
||||
|
||||
def test_ignore_special
|
||||
f = FileList['testdata/*']
|
||||
assert ! f.include?("testdata/CVS"), "Should not contain CVS"
|
||||
assert ! f.include?("testdata/.svn"), "Should not contain .svn"
|
||||
assert ! f.include?("testdata/.dummy"), "Should not contain dot files"
|
||||
assert ! f.include?("testdata/x.bak"), "Should not contain .bak files"
|
||||
assert ! f.include?("testdata/x~"), "Should not contain ~ files"
|
||||
assert ! f.include?("testdata/core"), "Should not contain core files"
|
||||
end
|
||||
|
||||
def test_clear_ignore_patterns
|
||||
f = FileList['testdata/*', 'testdata/.svn']
|
||||
f.clear_exclude
|
||||
assert f.include?("testdata/abc.c")
|
||||
assert f.include?("testdata/xyz.c")
|
||||
assert f.include?("testdata/CVS")
|
||||
assert f.include?("testdata/.svn")
|
||||
assert f.include?("testdata/x.bak")
|
||||
assert f.include?("testdata/x~")
|
||||
end
|
||||
|
||||
def test_exclude_with_alternate_file_seps
|
||||
fl = FileList.new
|
||||
assert fl.exclude?("x/CVS/y")
|
||||
assert fl.exclude?("x\\CVS\\y")
|
||||
assert fl.exclude?("x/.svn/y")
|
||||
assert fl.exclude?("x\\.svn\\y")
|
||||
assert fl.exclude?("x/core")
|
||||
assert fl.exclude?("x\\core")
|
||||
end
|
||||
|
||||
def test_add_default_exclude_list
|
||||
fl = FileList.new
|
||||
fl.exclude(/~\d+$/)
|
||||
assert fl.exclude?("x/CVS/y")
|
||||
assert fl.exclude?("x\\CVS\\y")
|
||||
assert fl.exclude?("x/.svn/y")
|
||||
assert fl.exclude?("x\\.svn\\y")
|
||||
assert fl.exclude?("x/core")
|
||||
assert fl.exclude?("x\\core")
|
||||
assert fl.exclude?("x/abc~1")
|
||||
end
|
||||
|
||||
def test_basic_array_functions
|
||||
f = FileList['b', 'c', 'a']
|
||||
assert_equal 'b', f.first
|
||||
assert_equal 'b', f[0]
|
||||
assert_equal 'a', f.last
|
||||
assert_equal 'a', f[2]
|
||||
assert_equal 'a', f[-1]
|
||||
assert_equal ['a', 'b', 'c'], f.sort
|
||||
f.sort!
|
||||
assert_equal ['a', 'b', 'c'], f
|
||||
end
|
||||
|
||||
def test_flatten
|
||||
assert_equal ['a', 'testdata/x.c', 'testdata/xyz.c', 'testdata/abc.c'].sort,
|
||||
['a', FileList['testdata/*.c']].flatten.sort
|
||||
end
|
||||
|
||||
def test_clone_and_dup
|
||||
a = FileList['a', 'b', 'c']
|
||||
c = a.clone
|
||||
d = a.dup
|
||||
a << 'd'
|
||||
assert_equal ['a', 'b', 'c', 'd'], a
|
||||
assert_equal ['a', 'b', 'c'], c
|
||||
assert_equal ['a', 'b', 'c'], d
|
||||
end
|
||||
|
||||
def test_dup_and_clone_replicate_taint
|
||||
a = FileList['a', 'b', 'c']
|
||||
a.taint
|
||||
c = a.clone
|
||||
d = a.dup
|
||||
assert c.tainted?, "Clone should be tainted"
|
||||
assert d.tainted?, "Dup should be tainted"
|
||||
end
|
||||
|
||||
def test_duped_items_will_thaw
|
||||
a = FileList['a', 'b', 'c']
|
||||
a.freeze
|
||||
d = a.dup
|
||||
d << 'more'
|
||||
assert_equal ['a', 'b', 'c', 'more'], d
|
||||
end
|
||||
|
||||
def test_cloned_items_stay_frozen
|
||||
a = FileList['a', 'b', 'c']
|
||||
a.freeze
|
||||
c = a.clone
|
||||
assert_raise(TypeError, RuntimeError) do
|
||||
c << 'more'
|
||||
end
|
||||
end
|
||||
|
||||
def test_array_comparisons
|
||||
fl = FileList['b', 'b']
|
||||
a = ['b', 'a']
|
||||
b = ['b', 'b']
|
||||
c = ['b', 'c']
|
||||
assert_equal( 1, fl <=> a )
|
||||
assert_equal( 0, fl <=> b )
|
||||
assert_equal( -1, fl <=> c )
|
||||
assert_equal( -1, a <=> fl )
|
||||
assert_equal( 0, b <=> fl )
|
||||
assert_equal( 1, c <=> fl )
|
||||
end
|
||||
|
||||
def test_array_equality
|
||||
a = FileList['a', 'b']
|
||||
b = ['a', 'b']
|
||||
assert a == b
|
||||
assert b == a
|
||||
# assert a.eql?(b)
|
||||
# assert b.eql?(a)
|
||||
assert ! a.equal?(b)
|
||||
assert ! b.equal?(a)
|
||||
end
|
||||
|
||||
def test_enumeration_methods
|
||||
a = FileList['a', 'b']
|
||||
b = a.collect { |it| it.upcase }
|
||||
assert_equal ['A', 'B'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.map { |it| it.upcase }
|
||||
assert_equal ['A', 'B'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.sort
|
||||
assert_equal ['a', 'b'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.sort_by { |it| it }
|
||||
assert_equal ['a', 'b'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.find_all { |it| it == 'b'}
|
||||
assert_equal ['b'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.select { |it| it.size == 1 }
|
||||
assert_equal ['a', 'b'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.reject { |it| it == 'b' }
|
||||
assert_equal ['a'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.grep(/./)
|
||||
assert_equal ['a', 'b'], b
|
||||
assert_equal FileList, b.class
|
||||
|
||||
b = a.partition { |it| it == 'b' }
|
||||
assert_equal [['b'], ['a']], b
|
||||
assert_equal Array, b.class
|
||||
assert_equal FileList, b[0].class
|
||||
assert_equal FileList, b[1].class
|
||||
|
||||
b = a.zip(['x', 'y']).to_a
|
||||
assert_equal [['a', 'x'], ['b', 'y']], b
|
||||
assert_equal Array, b.class
|
||||
assert_equal Array, b[0].class
|
||||
assert_equal Array, b[1].class
|
||||
end
|
||||
|
||||
def test_array_operators
|
||||
a = ['a', 'b']
|
||||
b = ['c', 'd']
|
||||
f = FileList['x', 'y']
|
||||
g = FileList['w', 'z']
|
||||
|
||||
r = f + g
|
||||
assert_equal ['x', 'y', 'w', 'z'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
r = a + g
|
||||
assert_equal ['a', 'b', 'w', 'z'], r
|
||||
assert_equal Array, r.class
|
||||
|
||||
r = f + b
|
||||
assert_equal ['x', 'y', 'c', 'd'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
r = FileList['w', 'x', 'y', 'z'] - f
|
||||
assert_equal ['w', 'z'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
r = FileList['w', 'x', 'y', 'z'] & f
|
||||
assert_equal ['x', 'y'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
r = f * 2
|
||||
assert_equal ['x', 'y', 'x', 'y'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
r = f * ','
|
||||
assert_equal 'x,y', r
|
||||
assert_equal String, r.class
|
||||
|
||||
r = f | ['a', 'x']
|
||||
assert_equal ['a', 'x', 'y'].sort, r.sort
|
||||
assert_equal FileList, r.class
|
||||
end
|
||||
|
||||
def test_other_array_returning_methods
|
||||
f = FileList['a', nil, 'b']
|
||||
r = f.compact
|
||||
assert_equal ['a', 'b'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
f = FileList['a', 'b']
|
||||
r = f.concat(['x', 'y'])
|
||||
assert_equal ['a', 'b', 'x', 'y'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
f = FileList['a', ['b', 'c'], FileList['d', 'e']]
|
||||
r = f.flatten
|
||||
assert_equal ['a', 'b', 'c', 'd', 'e'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
f = FileList['a', 'b', 'a']
|
||||
r = f.uniq
|
||||
assert_equal ['a', 'b'], r
|
||||
assert_equal FileList, r.class
|
||||
|
||||
f = FileList['a', 'b', 'c', 'd']
|
||||
r = f.values_at(1,3)
|
||||
assert_equal ['b', 'd'], r
|
||||
assert_equal FileList, r.class
|
||||
end
|
||||
|
||||
def test_file_utils_can_use_filelists
|
||||
cfiles = FileList['testdata/*.c']
|
||||
|
||||
cp cfiles, @cdir, :verbose => false
|
||||
|
||||
assert File.exist?(File.join(@cdir, 'abc.c'))
|
||||
assert File.exist?(File.join(@cdir, 'xyz.c'))
|
||||
assert File.exist?(File.join(@cdir, 'x.c'))
|
||||
end
|
||||
|
||||
def create_test_data
|
||||
verbose(false) do
|
||||
|
||||
mkdir "testdata" unless File.exist? "testdata"
|
||||
mkdir "testdata/CVS" rescue nil
|
||||
mkdir "testdata/.svn" rescue nil
|
||||
@cdir = "testdata/cfiles"
|
||||
mkdir @cdir rescue nil
|
||||
touch "testdata/.dummy"
|
||||
touch "testdata/x.bak"
|
||||
touch "testdata/x~"
|
||||
touch "testdata/core"
|
||||
touch "testdata/x.c"
|
||||
touch "testdata/xyz.c"
|
||||
touch "testdata/abc.c"
|
||||
touch "testdata/abc.h"
|
||||
touch "testdata/abc.x"
|
||||
touch "testdata/existing"
|
||||
end
|
||||
end
|
||||
|
||||
end
|
|
@ -0,0 +1,262 @@
|
|||
require 'rake'
|
||||
require 'test/unit'
|
||||
require_relative 'filecreation'
|
||||
require 'fileutils'
|
||||
require 'stringio'
|
||||
|
||||
class TestFileUtils < Test::Unit::TestCase
|
||||
include FileCreation
|
||||
BASEDIR = File.dirname(__FILE__)
|
||||
ShellCommand = "#{BASEDIR}/shellcommand.rb"
|
||||
ENV_RUBY = ENV['RUBY']
|
||||
|
||||
def setup
|
||||
if ruby = ENV_RUBY
|
||||
@oldruby = FileUtils.class_eval {remove_const :RUBY}
|
||||
FileUtils.class_eval {const_set(:RUBY, ruby)}
|
||||
else
|
||||
@oldruby = nil
|
||||
end
|
||||
end
|
||||
|
||||
def teardown
|
||||
FileUtils.rm_rf("testdata")
|
||||
FileUtils::LN_SUPPORTED[0] = true
|
||||
if @oldruby
|
||||
ruby = @oldruby
|
||||
FileUtils.class_eval {remove_const :RUBY}
|
||||
FileUtils.class_eval {const_set(:RUBY, ruby)}
|
||||
end
|
||||
end
|
||||
|
||||
def test_rm_one_file
|
||||
create_file("testdata/a")
|
||||
FileUtils.rm_rf "testdata/a"
|
||||
assert ! File.exist?("testdata/a")
|
||||
end
|
||||
|
||||
def test_rm_two_files
|
||||
create_file("testdata/a")
|
||||
create_file("testdata/b")
|
||||
FileUtils.rm_rf ["testdata/a", "testdata/b"]
|
||||
assert ! File.exist?("testdata/a")
|
||||
assert ! File.exist?("testdata/b")
|
||||
end
|
||||
|
||||
def test_rm_filelist
|
||||
list = Rake::FileList.new << "testdata/a" << "testdata/b"
|
||||
list.each { |fn| create_file(fn) }
|
||||
FileUtils.rm_r list
|
||||
assert ! File.exist?("testdata/a")
|
||||
assert ! File.exist?("testdata/b")
|
||||
end
|
||||
|
||||
def test_ln
|
||||
create_dir("testdata")
|
||||
open("testdata/a", "w") { |f| f.puts "TEST_LN" }
|
||||
RakeFileUtils.safe_ln("testdata/a", "testdata/b", :verbose => false)
|
||||
assert_equal "TEST_LN\n", open("testdata/b") { |f| f.read }
|
||||
end
|
||||
|
||||
class BadLink
|
||||
include RakeFileUtils
|
||||
attr_reader :cp_args
|
||||
def initialize(klass)
|
||||
@failure_class = klass
|
||||
end
|
||||
def cp(*args)
|
||||
@cp_args = args
|
||||
end
|
||||
def ln(*args)
|
||||
fail @failure_class, "ln not supported"
|
||||
end
|
||||
public :safe_ln
|
||||
end
|
||||
|
||||
def test_safe_ln_failover_to_cp_on_standard_error
|
||||
FileUtils::LN_SUPPORTED[0] = true
|
||||
c = BadLink.new(StandardError)
|
||||
c.safe_ln "a", "b"
|
||||
assert_equal ['a', 'b'], c.cp_args
|
||||
c.safe_ln "x", "y"
|
||||
assert_equal ['x', 'y'], c.cp_args
|
||||
end
|
||||
|
||||
def test_safe_ln_failover_to_cp_on_not_implemented_error
|
||||
FileUtils::LN_SUPPORTED[0] = true
|
||||
c = BadLink.new(NotImplementedError)
|
||||
c.safe_ln "a", "b"
|
||||
assert_equal ['a', 'b'], c.cp_args
|
||||
end
|
||||
|
||||
def test_safe_ln_fails_on_script_error
|
||||
FileUtils::LN_SUPPORTED[0] = true
|
||||
c = BadLink.new(ScriptError)
|
||||
assert_raise(ScriptError) do c.safe_ln "a", "b" end
|
||||
end
|
||||
|
||||
def test_verbose
|
||||
verbose true
|
||||
assert_equal true, verbose
|
||||
verbose false
|
||||
assert_equal false, verbose
|
||||
verbose(true) {
|
||||
assert_equal true, verbose
|
||||
}
|
||||
assert_equal false, verbose
|
||||
end
|
||||
|
||||
def test_nowrite
|
||||
nowrite true
|
||||
assert_equal true, nowrite
|
||||
nowrite false
|
||||
assert_equal false, nowrite
|
||||
nowrite(true){
|
||||
assert_equal true, nowrite
|
||||
}
|
||||
assert_equal false, nowrite
|
||||
end
|
||||
|
||||
def test_file_utils_methods_are_available_at_top_level
|
||||
create_file("testdata/a")
|
||||
verbose(false) do
|
||||
rm_rf "testdata/a"
|
||||
end
|
||||
assert ! File.exist?("testdata/a")
|
||||
end
|
||||
|
||||
def test_fileutils_methods_dont_leak
|
||||
obj = Object.new
|
||||
assert_raise(NoMethodError) { obj.copy } # from FileUtils
|
||||
assert_raise(NoMethodError) { obj.ruby } # from RubyFileUtils
|
||||
end
|
||||
|
||||
def test_sh
|
||||
verbose(false) { sh %{ruby #{ShellCommand}} }
|
||||
assert true, "should not fail"
|
||||
end
|
||||
|
||||
# If the :sh method is invoked directly from a test unit instance
|
||||
# (under mini/test), the mini/test version of fail is invoked rather
|
||||
# than the kernel version of fail. So we run :sh from within a
|
||||
# non-test class to avoid the problem.
|
||||
class Sh
|
||||
include FileUtils
|
||||
def run(*args)
|
||||
sh(*args)
|
||||
end
|
||||
def self.run(*args)
|
||||
new.run(*args)
|
||||
end
|
||||
end
|
||||
|
||||
def test_sh_with_a_single_string_argument
|
||||
ENV['RAKE_TEST_SH'] = 'someval'
|
||||
verbose(false) {
|
||||
sh %{ruby #{BASEDIR}/check_expansion.rb #{env_var} someval}
|
||||
}
|
||||
end
|
||||
|
||||
def test_sh_with_multiple_arguments
|
||||
ENV['RAKE_TEST_SH'] = 'someval'
|
||||
verbose(false) {
|
||||
Sh.run 'ruby', File.expand_path('../check_no_expansion.rb', __FILE__), env_var, 'someval'
|
||||
}
|
||||
end
|
||||
|
||||
def test_sh_failure
|
||||
assert_raise(RuntimeError) {
|
||||
verbose(false) { Sh.run "ruby #{File.expand_path('../shellcommand.rb', __FILE__)} 1" }
|
||||
}
|
||||
end
|
||||
|
||||
def test_sh_special_handling
|
||||
count = 0
|
||||
verbose(false) {
|
||||
sh(%{ruby #{ShellCommand}}) do |ok, res|
|
||||
assert(ok)
|
||||
assert_equal 0, res.exitstatus
|
||||
count += 1
|
||||
end
|
||||
sh(%{ruby #{ShellCommand} 1}) do |ok, res|
|
||||
assert(!ok)
|
||||
assert_equal 1, res.exitstatus
|
||||
count += 1
|
||||
end
|
||||
}
|
||||
assert_equal 2, count, "Block count should be 2"
|
||||
end
|
||||
|
||||
def test_sh_noop
|
||||
verbose(false) { sh %{#{ShellCommand} 1}, :noop=>true }
|
||||
assert true, "should not fail"
|
||||
end
|
||||
|
||||
def test_sh_bad_option
|
||||
ex = assert_raise(ArgumentError) {
|
||||
verbose(false) { sh %{#{ShellCommand}}, :bad_option=>true }
|
||||
}
|
||||
assert_match(/bad_option/, ex.message)
|
||||
end
|
||||
|
||||
def test_sh_verbose
|
||||
out = redirect_stderr {
|
||||
verbose(true) {
|
||||
sh %{#{ShellCommand}}, :noop=>true
|
||||
}
|
||||
}
|
||||
assert_match(/^#{Regexp.quote(ShellCommand)}$/o, out)
|
||||
end
|
||||
|
||||
def test_sh_no_verbose
|
||||
out = redirect_stderr {
|
||||
verbose(false) {
|
||||
sh %{#{ShellCommand}}, :noop=>true
|
||||
}
|
||||
}
|
||||
assert_equal '', out
|
||||
end
|
||||
|
||||
def test_ruby_with_a_single_string_argument
|
||||
ENV['RAKE_TEST_SH'] = 'someval'
|
||||
verbose(false) {
|
||||
ruby %{#{BASEDIR}/check_expansion.rb #{env_var} someval}
|
||||
}
|
||||
end
|
||||
|
||||
def test_ruby_with_multiple_arguments
|
||||
ENV['RAKE_TEST_SH'] = 'someval'
|
||||
verbose(false) {
|
||||
ruby "#{BASEDIR}/check_no_expansion.rb", env_var, 'someval'
|
||||
}
|
||||
end
|
||||
|
||||
def test_split_all
|
||||
assert_equal ['a'], RakeFileUtils.split_all('a')
|
||||
assert_equal ['..'], RakeFileUtils.split_all('..')
|
||||
assert_equal ['/'], RakeFileUtils.split_all('/')
|
||||
assert_equal ['a', 'b'], RakeFileUtils.split_all('a/b')
|
||||
assert_equal ['/', 'a', 'b'], RakeFileUtils.split_all('/a/b')
|
||||
assert_equal ['..', 'a', 'b'], RakeFileUtils.split_all('../a/b')
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def redirect_stderr
|
||||
old_err = $stderr
|
||||
$stderr = StringIO.new
|
||||
yield
|
||||
$stderr.string
|
||||
ensure
|
||||
$stderr = old_err
|
||||
end
|
||||
|
||||
def windows?
|
||||
! File::ALT_SEPARATOR.nil?
|
||||
end
|
||||
|
||||
def env_var
|
||||
windows? ? '%RAKE_TEST_SH%' : '$RAKE_TEST_SH'
|
||||
end
|
||||
|
||||
end
|
|
@ -0,0 +1,57 @@
|
|||
require 'date'
|
||||
require 'time'
|
||||
require 'test/unit'
|
||||
require 'rake/contrib/ftptools'
|
||||
|
||||
class FakeDate
|
||||
def self.today
|
||||
Date.new(2003,10,3)
|
||||
end
|
||||
def self.now
|
||||
Time.local(2003,10,3,12,00,00)
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
class TestFtpFile < Test::Unit::TestCase
|
||||
|
||||
def setup
|
||||
Rake::FtpFile.class_eval { @date_class = FakeDate; @time_class = FakeDate }
|
||||
end
|
||||
|
||||
def test_general
|
||||
file = Rake::FtpFile.new("here", "-rw-r--r-- 1 a279376 develop 121770 Mar 6 14:50 wiki.pl")
|
||||
assert_equal "wiki.pl", file.name
|
||||
assert_equal "here/wiki.pl", file.path
|
||||
assert_equal "a279376", file.owner
|
||||
assert_equal "develop", file.group
|
||||
assert_equal 0644, file.mode
|
||||
assert_equal 121770, file.size
|
||||
assert_equal Time.mktime(2003,3,6,14,50,0,0), file.time
|
||||
assert ! file.directory?
|
||||
assert ! file.symlink?
|
||||
end
|
||||
|
||||
def test_far_date
|
||||
file = Rake::FtpFile.new(".", "drwxr-xr-x 3 a279376 develop 4096 Nov 26 2001 vss")
|
||||
assert_equal Time.mktime(2001,11,26,0,0,0,0), file.time
|
||||
end
|
||||
|
||||
def test_close_date
|
||||
file = Rake::FtpFile.new(".", "drwxr-xr-x 3 a279376 develop 4096 Nov 26 15:35 vss")
|
||||
assert_equal Time.mktime(2002,11,26,15,35,0,0), file.time
|
||||
end
|
||||
|
||||
def test_directory
|
||||
file = Rake::FtpFile.new(".", "drwxrwxr-x 9 a279376 develop 4096 Mar 13 14:32 working")
|
||||
assert file.directory?
|
||||
assert !file.symlink?
|
||||
end
|
||||
|
||||
def test_symlink
|
||||
file = Rake::FtpFile.new(".", "lrwxrwxrwx 1 a279376 develop 64 Mar 26 2002 xtrac -> /home/a279376/working/ics/development/java/com/fmr/fwp/ics/xtrac")
|
||||
assert_equal 'xtrac', file.name
|
||||
assert file.symlink?
|
||||
assert !file.directory?
|
||||
end
|
||||
end
|
|
@ -0,0 +1,75 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
######################################################################
|
||||
class TestAnEmptyInvocationChain < Test::Unit::TestCase
|
||||
|
||||
def setup
|
||||
@empty = Rake::InvocationChain::EMPTY
|
||||
end
|
||||
|
||||
def test_should_be_able_to_add_members
|
||||
assert_nothing_raised do
|
||||
@empty.append("A")
|
||||
end
|
||||
end
|
||||
|
||||
def test_to_s
|
||||
assert_equal "TOP", @empty.to_s
|
||||
end
|
||||
end
|
||||
|
||||
######################################################################
|
||||
class TestAnInvocationChainWithOneMember < Test::Unit::TestCase
|
||||
|
||||
def setup
|
||||
@empty = Rake::InvocationChain::EMPTY
|
||||
@first_member = "A"
|
||||
@chain = @empty.append(@first_member)
|
||||
end
|
||||
|
||||
def test_should_report_first_member_as_a_member
|
||||
assert @chain.member?(@first_member)
|
||||
end
|
||||
|
||||
def test_should_fail_when_adding_original_member
|
||||
ex = assert_raise RuntimeError do
|
||||
@chain.append(@first_member)
|
||||
end
|
||||
assert_match(/circular +dependency/i, ex.message)
|
||||
assert_match(/A.*=>.*A/, ex.message)
|
||||
end
|
||||
|
||||
def test_to_s
|
||||
assert_equal "TOP => A", @chain.to_s
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
######################################################################
|
||||
class TestAnInvocationChainWithMultipleMember < Test::Unit::TestCase
|
||||
|
||||
def setup
|
||||
@first_member = "A"
|
||||
@second_member = "B"
|
||||
ch = Rake::InvocationChain::EMPTY.append(@first_member)
|
||||
@chain = ch.append(@second_member)
|
||||
end
|
||||
|
||||
def test_should_report_first_member_as_a_member
|
||||
assert @chain.member?(@first_member)
|
||||
end
|
||||
|
||||
def test_should_report_second_member_as_a_member
|
||||
assert @chain.member?(@second_member)
|
||||
end
|
||||
|
||||
def test_should_fail_when_adding_original_member
|
||||
ex = assert_raise RuntimeError do
|
||||
@chain.append(@first_member)
|
||||
end
|
||||
assert_match(/A.*=>.*B.*=>.*A/, ex.message)
|
||||
end
|
||||
end
|
||||
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
require 'rake/loaders/makefile'
|
||||
|
||||
class TestMakefileLoader < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
def test_parse
|
||||
Task.clear
|
||||
loader = Rake::MakefileLoader.new
|
||||
loader.load("#{File.dirname(__FILE__)}/data/sample.mf")
|
||||
%w(a b c d).each do |t|
|
||||
assert Task.task_defined?(t), "#{t} should be a defined task"
|
||||
end
|
||||
assert_equal %w(a1 a2 a3 a4 a5 a6 a7).sort, Task['a'].prerequisites.sort
|
||||
assert_equal %w(b1 b2 b3 b4 b5 b6 b7).sort, Task['b'].prerequisites.sort
|
||||
assert_equal %w(c1).sort, Task['c'].prerequisites.sort
|
||||
assert_equal %w(d1 d2).sort, Task['d'].prerequisites.sort
|
||||
assert_equal %w(e1 f1).sort, Task['e'].prerequisites.sort
|
||||
assert_equal %w(e1 f1).sort, Task['f'].prerequisites.sort
|
||||
assert_equal ["g1", "g 2", "g 3", "g4"].sort, Task['g 0'].prerequisites.sort
|
||||
assert_equal 7, Task.tasks.size
|
||||
end
|
||||
end
|
|
@ -0,0 +1,43 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
######################################################################
|
||||
class TestMultiTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
@runs = Array.new
|
||||
end
|
||||
|
||||
def test_running_multitasks
|
||||
task :a do 3.times do |i| @runs << "A#{i}"; sleep 0.01; end end
|
||||
task :b do 3.times do |i| @runs << "B#{i}"; sleep 0.01; end end
|
||||
multitask :both => [:a, :b]
|
||||
Task[:both].invoke
|
||||
assert_equal 6, @runs.size
|
||||
assert @runs.index("A0") < @runs.index("A1")
|
||||
assert @runs.index("A1") < @runs.index("A2")
|
||||
assert @runs.index("B0") < @runs.index("B1")
|
||||
assert @runs.index("B1") < @runs.index("B2")
|
||||
end
|
||||
|
||||
def test_all_multitasks_wait_on_slow_prerequisites
|
||||
task :slow do 3.times do |i| @runs << "S#{i}"; sleep 0.05 end end
|
||||
task :a => [:slow] do 3.times do |i| @runs << "A#{i}"; sleep 0.01 end end
|
||||
task :b => [:slow] do 3.times do |i| @runs << "B#{i}"; sleep 0.01 end end
|
||||
multitask :both => [:a, :b]
|
||||
Task[:both].invoke
|
||||
assert_equal 9, @runs.size
|
||||
assert @runs.index("S0") < @runs.index("S1")
|
||||
assert @runs.index("S1") < @runs.index("S2")
|
||||
assert @runs.index("S2") < @runs.index("A0")
|
||||
assert @runs.index("S2") < @runs.index("B0")
|
||||
assert @runs.index("A0") < @runs.index("A1")
|
||||
assert @runs.index("A1") < @runs.index("A2")
|
||||
assert @runs.index("B0") < @runs.index("B1")
|
||||
assert @runs.index("B1") < @runs.index("B2")
|
||||
end
|
||||
end
|
||||
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
class TestNameSpace < Test::Unit::TestCase
|
||||
|
||||
class TM
|
||||
include Rake::TaskManager
|
||||
end
|
||||
|
||||
def test_namespace_creation
|
||||
mgr = TM.new
|
||||
ns = Rake::NameSpace.new(mgr, [])
|
||||
assert_not_nil ns
|
||||
end
|
||||
|
||||
def test_namespace_lookup
|
||||
mgr = TM.new
|
||||
ns = mgr.in_namespace("n") do
|
||||
mgr.define_task(Rake::Task, "t")
|
||||
end
|
||||
|
||||
assert_not_nil ns["t"]
|
||||
assert_equal mgr["n:t"], ns["t"]
|
||||
end
|
||||
|
||||
def test_namespace_reports_tasks_it_owns
|
||||
mgr = TM.new
|
||||
nns = nil
|
||||
ns = mgr.in_namespace("n") do
|
||||
mgr.define_task(Rake::Task, :x)
|
||||
mgr.define_task(Rake::Task, :y)
|
||||
nns = mgr.in_namespace("nn") do
|
||||
mgr.define_task(Rake::Task, :z)
|
||||
end
|
||||
end
|
||||
mgr.in_namespace("m") do
|
||||
mgr.define_task(Rake::Task, :x)
|
||||
end
|
||||
|
||||
assert_equal ["n:nn:z", "n:x", "n:y"],
|
||||
ns.tasks.map { |tsk| tsk.name }
|
||||
assert_equal ["n:nn:z"], nns.tasks.map {|t| t.name}
|
||||
end
|
||||
end
|
|
@ -0,0 +1,105 @@
|
|||
require 'test/unit'
|
||||
require 'rake/packagetask'
|
||||
|
||||
class TestPackageTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
def test_create
|
||||
pkg = Rake::PackageTask.new("pkgr", "1.2.3") { |p|
|
||||
p.package_files << "install.rb"
|
||||
p.package_files.include(
|
||||
'[A-Z]*',
|
||||
'bin/**/*',
|
||||
'lib/**/*.rb',
|
||||
'test/**/*.rb',
|
||||
'doc/**/*',
|
||||
'build/rubyapp.rb',
|
||||
'*.blurb')
|
||||
p.package_files.exclude(/\bCVS\b/)
|
||||
p.package_files.exclude(/~$/)
|
||||
p.package_dir = 'pkg'
|
||||
p.need_tar = true
|
||||
p.need_tar_gz = true
|
||||
p.need_tar_bz2 = true
|
||||
p.need_zip = true
|
||||
}
|
||||
assert_equal "pkg", pkg.package_dir
|
||||
assert pkg.package_files.include?("bin/rake")
|
||||
assert "pkgr", pkg.name
|
||||
assert "1.2.3", pkg.version
|
||||
assert Task[:package]
|
||||
assert Task['pkg/pkgr-1.2.3.tgz']
|
||||
assert Task['pkg/pkgr-1.2.3.tar.gz']
|
||||
assert Task['pkg/pkgr-1.2.3.tar.bz2']
|
||||
assert Task['pkg/pkgr-1.2.3.zip']
|
||||
assert Task["pkg/pkgr-1.2.3"]
|
||||
assert Task[:clobber_package]
|
||||
assert Task[:repackage]
|
||||
end
|
||||
|
||||
def test_missing_version
|
||||
assert_raise(RuntimeError) {
|
||||
pkg = Rake::PackageTask.new("pkgr") { |p| }
|
||||
}
|
||||
end
|
||||
|
||||
def test_no_version
|
||||
pkg = Rake::PackageTask.new("pkgr", :noversion) { |p| }
|
||||
assert "pkgr", pkg.send(:package_name)
|
||||
end
|
||||
|
||||
def test_clone
|
||||
pkg = Rake::PackageTask.new("x", :noversion)
|
||||
p2 = pkg.clone
|
||||
pkg.package_files << "y"
|
||||
p2.package_files << "x"
|
||||
assert_equal ["y"], pkg.package_files
|
||||
assert_equal ["x"], p2.package_files
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
require 'rake/gempackagetask'
|
||||
|
||||
class TestGemPackageTask < Test::Unit::TestCase
|
||||
def test_gem_package
|
||||
gem = Gem::Specification.new do |g|
|
||||
g.name = "pkgr"
|
||||
g.version = "1.2.3"
|
||||
g.files = FileList["x"].resolve
|
||||
end
|
||||
pkg = Rake::GemPackageTask.new(gem) do |p|
|
||||
p.package_files << "y"
|
||||
end
|
||||
assert_equal ["x", "y"], pkg.package_files
|
||||
assert_equal "pkgr-1.2.3.gem", pkg.gem_file
|
||||
end
|
||||
|
||||
def test_gem_package_with_current_platform
|
||||
gem = Gem::Specification.new do |g|
|
||||
g.name = "pkgr"
|
||||
g.version = "1.2.3"
|
||||
g.files = FileList["x"].resolve
|
||||
g.platform = Gem::Platform::CURRENT
|
||||
end
|
||||
pkg = Rake::GemPackageTask.new(gem) do |p|
|
||||
p.package_files << "y"
|
||||
end
|
||||
assert_equal ["x", "y"], pkg.package_files
|
||||
assert_match(/^pkgr-1\.2\.3-(\S+)\.gem$/, pkg.gem_file)
|
||||
end
|
||||
|
||||
def test_gem_package_with_ruby_platform
|
||||
gem = Gem::Specification.new do |g|
|
||||
g.name = "pkgr"
|
||||
g.version = "1.2.3"
|
||||
g.files = FileList["x"].resolve
|
||||
g.platform = Gem::Platform::RUBY
|
||||
end
|
||||
pkg = Rake::GemPackageTask.new(gem) do |p|
|
||||
p.package_files << "y"
|
||||
end
|
||||
assert_equal ["x", "y"], pkg.package_files
|
||||
assert_equal "pkgr-1.2.3.gem", pkg.gem_file
|
||||
end
|
||||
end
|
|
@ -0,0 +1,207 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
# ====================================================================
|
||||
class TestPathMap < Test::Unit::TestCase
|
||||
|
||||
def test_returns_self_with_no_args
|
||||
assert_equal "abc.rb", "abc.rb".pathmap
|
||||
end
|
||||
|
||||
def test_s_returns_file_separator
|
||||
sep = File::ALT_SEPARATOR || File::SEPARATOR
|
||||
assert_equal sep, "abc.rb".pathmap("%s")
|
||||
assert_equal sep, "".pathmap("%s")
|
||||
assert_equal "a#{sep}b", "a/b".pathmap("%d%s%f")
|
||||
end
|
||||
|
||||
def test_f_returns_basename
|
||||
assert_equal "abc.rb", "abc.rb".pathmap("%f")
|
||||
assert_equal "abc.rb", "this/is/a/dir/abc.rb".pathmap("%f")
|
||||
assert_equal "abc.rb", "/this/is/a/dir/abc.rb".pathmap("%f")
|
||||
end
|
||||
|
||||
def test_n_returns_basename_without_extension
|
||||
assert_equal "abc", "abc.rb".pathmap("%n")
|
||||
assert_equal "abc", "abc".pathmap("%n")
|
||||
assert_equal "abc", "this/is/a/dir/abc.rb".pathmap("%n")
|
||||
assert_equal "abc", "/this/is/a/dir/abc.rb".pathmap("%n")
|
||||
assert_equal "abc", "/this/is/a/dir/abc".pathmap("%n")
|
||||
end
|
||||
|
||||
def test_d_returns_dirname
|
||||
assert_equal ".", "abc.rb".pathmap("%d")
|
||||
assert_equal "/", "/abc".pathmap("%d")
|
||||
assert_equal "this/is/a/dir", "this/is/a/dir/abc.rb".pathmap("%d")
|
||||
assert_equal "/this/is/a/dir", "/this/is/a/dir/abc.rb".pathmap("%d")
|
||||
end
|
||||
|
||||
def test_9d_returns_partial_dirname
|
||||
assert_equal "this/is", "this/is/a/dir/abc.rb".pathmap("%2d")
|
||||
assert_equal "this", "this/is/a/dir/abc.rb".pathmap("%1d")
|
||||
assert_equal ".", "this/is/a/dir/abc.rb".pathmap("%0d")
|
||||
assert_equal "dir", "this/is/a/dir/abc.rb".pathmap("%-1d")
|
||||
assert_equal "a/dir", "this/is/a/dir/abc.rb".pathmap("%-2d")
|
||||
assert_equal "this/is/a/dir", "this/is/a/dir/abc.rb".pathmap("%100d")
|
||||
assert_equal "this/is/a/dir", "this/is/a/dir/abc.rb".pathmap("%-100d")
|
||||
end
|
||||
|
||||
def test_x_returns_extension
|
||||
assert_equal "", "abc".pathmap("%x")
|
||||
assert_equal ".rb", "abc.rb".pathmap("%x")
|
||||
assert_equal ".rb", "abc.xyz.rb".pathmap("%x")
|
||||
assert_equal "", ".depends".pathmap("%x")
|
||||
assert_equal "", "dir/.depends".pathmap("%x")
|
||||
end
|
||||
|
||||
def test_X_returns_everything_but_extension
|
||||
assert_equal "abc", "abc".pathmap("%X")
|
||||
assert_equal "abc", "abc.rb".pathmap("%X")
|
||||
assert_equal "abc.xyz", "abc.xyz.rb".pathmap("%X")
|
||||
assert_equal "ab.xyz", "ab.xyz.rb".pathmap("%X")
|
||||
assert_equal "a.xyz", "a.xyz.rb".pathmap("%X")
|
||||
assert_equal "abc", "abc.rb".pathmap("%X")
|
||||
assert_equal "ab", "ab.rb".pathmap("%X")
|
||||
assert_equal "a", "a.rb".pathmap("%X")
|
||||
assert_equal ".depends", ".depends".pathmap("%X")
|
||||
assert_equal "a/dir/.depends", "a/dir/.depends".pathmap("%X")
|
||||
assert_equal "/.depends", "/.depends".pathmap("%X")
|
||||
end
|
||||
|
||||
def test_p_returns_entire_pathname
|
||||
assert_equal "abc.rb", "abc.rb".pathmap("%p")
|
||||
assert_equal "this/is/a/dir/abc.rb", "this/is/a/dir/abc.rb".pathmap("%p")
|
||||
assert_equal "/this/is/a/dir/abc.rb", "/this/is/a/dir/abc.rb".pathmap("%p")
|
||||
end
|
||||
|
||||
def test_dash_returns_empty_string
|
||||
assert_equal "", "abc.rb".pathmap("%-")
|
||||
assert_equal "abc.rb", "abc.rb".pathmap("%X%-%x")
|
||||
end
|
||||
|
||||
def test_percent_percent_returns_percent
|
||||
assert_equal "a%b", "".pathmap("a%%b")
|
||||
end
|
||||
|
||||
def test_undefined_percent_causes_error
|
||||
ex = assert_raise(ArgumentError) {
|
||||
"dir/abc.rb".pathmap("%z")
|
||||
}
|
||||
end
|
||||
|
||||
def test_pattern_returns_substitutions
|
||||
assert_equal "bin/org/osb",
|
||||
"src/org/osb/Xyz.java".pathmap("%{src,bin}d")
|
||||
end
|
||||
|
||||
def test_pattern_can_use_backreferences
|
||||
assert_equal "dir/hi/is", "dir/this/is".pathmap("%{t(hi)s,\\1}p")
|
||||
end
|
||||
|
||||
def test_pattern_with_star_replacement_string_uses_block
|
||||
assert_equal "src/ORG/osb",
|
||||
"src/org/osb/Xyz.java".pathmap("%{/org,*}d") { |d| d.upcase }
|
||||
assert_equal "Xyz.java",
|
||||
"src/org/osb/Xyz.java".pathmap("%{.*,*}f") { |f| f.capitalize }
|
||||
end
|
||||
|
||||
def test_pattern_with_no_replacement_nor_block_substitutes_empty_string
|
||||
assert_equal "bc.rb", "abc.rb".pathmap("%{a}f")
|
||||
end
|
||||
|
||||
def test_pattern_works_with_certain_valid_operators
|
||||
assert_equal "dir/xbc.rb", "dir/abc.rb".pathmap("%{a,x}p")
|
||||
assert_equal "d1r", "dir/abc.rb".pathmap("%{i,1}d")
|
||||
assert_equal "xbc.rb", "dir/abc.rb".pathmap("%{a,x}f")
|
||||
assert_equal ".Rb", "dir/abc.rb".pathmap("%{r,R}x")
|
||||
assert_equal "xbc", "dir/abc.rb".pathmap("%{a,x}n")
|
||||
end
|
||||
|
||||
def test_multiple_patterns
|
||||
assert_equal "this/is/b/directory/abc.rb",
|
||||
"this/is/a/dir/abc.rb".pathmap("%{a,b;dir,\\0ectory}p")
|
||||
end
|
||||
|
||||
def test_partial_directory_selection_works_with_patterns
|
||||
assert_equal "this/is/a/long",
|
||||
"this/is/a/really/long/path/ok.rb".pathmap("%{/really/,/}5d")
|
||||
end
|
||||
|
||||
def test_pattern_with_invalid_operator
|
||||
ex = assert_raise(ArgumentError) do
|
||||
"abc.xyz".pathmap("%{src,bin}z")
|
||||
end
|
||||
assert_match(/unknown.*pathmap.*spec.*z/i, ex.message)
|
||||
end
|
||||
|
||||
def test_works_with_windows_separators
|
||||
if File::ALT_SEPARATOR
|
||||
assert_equal "abc", 'dir\abc.rb'.pathmap("%n")
|
||||
assert_equal 'this\is\a\dir',
|
||||
'this\is\a\dir\abc.rb'.pathmap("%d")
|
||||
end
|
||||
end
|
||||
|
||||
def test_complex_patterns
|
||||
sep = "".pathmap("%s")
|
||||
assert_equal "dir/abc.rb", "dir/abc.rb".pathmap("%d/%n%x")
|
||||
assert_equal "./abc.rb", "abc.rb".pathmap("%d/%n%x")
|
||||
assert_equal "Your file extension is '.rb'",
|
||||
"dir/abc.rb".pathmap("Your file extension is '%x'")
|
||||
assert_equal "bin/org/onstepback/proj/A.class",
|
||||
"src/org/onstepback/proj/A.java".pathmap("%{src,bin}d/%n.class")
|
||||
assert_equal "src_work/bin/org/onstepback/proj/A.class",
|
||||
"src_work/src/org/onstepback/proj/A.java".pathmap('%{\bsrc\b,bin}X.class')
|
||||
assert_equal ".depends.bak", ".depends".pathmap("%X.bak")
|
||||
assert_equal "d#{sep}a/b/c#{sep}file.txt", "a/b/c/d/file.txt".pathmap("%-1d%s%3d%s%f")
|
||||
end
|
||||
end
|
||||
|
||||
class TestPathMapExplode < Test::Unit::TestCase
|
||||
def setup
|
||||
String.class_eval { public :pathmap_explode }
|
||||
end
|
||||
|
||||
def teardown
|
||||
String.class_eval { protected :pathmap_explode }
|
||||
end
|
||||
|
||||
def test_explode
|
||||
assert_equal ['a'], 'a'.pathmap_explode
|
||||
assert_equal ['a', 'b'], 'a/b'.pathmap_explode
|
||||
assert_equal ['a', 'b', 'c'], 'a/b/c'.pathmap_explode
|
||||
assert_equal ['/', 'a'], '/a'.pathmap_explode
|
||||
assert_equal ['/', 'a', 'b'], '/a/b'.pathmap_explode
|
||||
assert_equal ['/', 'a', 'b', 'c'], '/a/b/c'.pathmap_explode
|
||||
if File::ALT_SEPARATOR
|
||||
assert_equal ['c:.', 'a'], 'c:a'.pathmap_explode
|
||||
assert_equal ['c:.', 'a', 'b'], 'c:a/b'.pathmap_explode
|
||||
assert_equal ['c:.', 'a', 'b', 'c'], 'c:a/b/c'.pathmap_explode
|
||||
assert_equal ['c:/', 'a'], 'c:/a'.pathmap_explode
|
||||
assert_equal ['c:/', 'a', 'b'], 'c:/a/b'.pathmap_explode
|
||||
assert_equal ['c:/', 'a', 'b', 'c'], 'c:/a/b/c'.pathmap_explode
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
class TestPathMapPartial < Test::Unit::TestCase
|
||||
def test_pathmap_partial
|
||||
@path = "1/2/file"
|
||||
def @path.call(n)
|
||||
pathmap_partial(n)
|
||||
end
|
||||
assert_equal("1", @path.call(1))
|
||||
assert_equal("1/2", @path.call(2))
|
||||
assert_equal("1/2", @path.call(3))
|
||||
assert_equal(".", @path.call(0))
|
||||
assert_equal("2", @path.call(-1))
|
||||
assert_equal("1/2", @path.call(-2))
|
||||
assert_equal("1/2", @path.call(-3))
|
||||
end
|
||||
end
|
||||
|
||||
class TestFileListPathMap < Test::Unit::TestCase
|
||||
def test_file_list_supports_pathmap
|
||||
assert_equal ['a', 'b'], FileList['dir/a.rb', 'dir/b.rb'].pathmap("%n")
|
||||
end
|
||||
end
|
|
@ -0,0 +1,23 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
require_relative 'capture_stdout'
|
||||
|
||||
class PseudoStatusTest < Test::Unit::TestCase
|
||||
def test_with_zero_exit_status
|
||||
s = Rake::PseudoStatus.new
|
||||
assert_equal 0, s.exitstatus
|
||||
assert_equal 0, s.to_i
|
||||
assert_equal 0, s >> 8
|
||||
assert ! s.stopped?
|
||||
assert s.exited?
|
||||
end
|
||||
def test_with_99_exit_status
|
||||
s = Rake::PseudoStatus.new(99)
|
||||
assert_equal 99, s.exitstatus
|
||||
assert_equal 25344, s.to_i
|
||||
assert_equal 99, s >> 8
|
||||
assert ! s.stopped?
|
||||
assert s.exited?
|
||||
end
|
||||
end
|
|
@ -0,0 +1,39 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
class TestRake < Test::Unit::TestCase
|
||||
def test_each_dir_parent
|
||||
assert_equal ['a'], alldirs('a')
|
||||
assert_equal ['a/b', 'a'], alldirs('a/b')
|
||||
assert_equal ['/a/b', '/a', '/'], alldirs('/a/b')
|
||||
if File.dirname("c:/foo") == "c:"
|
||||
# Under Unix
|
||||
assert_equal ['c:/a/b', 'c:/a', 'c:'], alldirs('c:/a/b')
|
||||
assert_equal ['c:a/b', 'c:a'], alldirs('c:a/b')
|
||||
else
|
||||
# Under Windows
|
||||
assert_equal ['c:/a/b', 'c:/a', 'c:/'], alldirs('c:/a/b')
|
||||
assert_equal ['c:a/b', 'c:a'], alldirs('c:a/b')
|
||||
end
|
||||
end
|
||||
|
||||
def alldirs(fn)
|
||||
result = []
|
||||
Rake.each_dir_parent(fn) { |d| result << d }
|
||||
result
|
||||
end
|
||||
|
||||
def test_can_override_application
|
||||
old_app = Rake.application
|
||||
fake_app = Object.new
|
||||
Rake.application = fake_app
|
||||
assert_equal fake_app, Rake.application
|
||||
ensure
|
||||
Rake.application = old_app
|
||||
end
|
||||
|
||||
def test_original_dir_reports_current_dir
|
||||
assert_equal Dir.pwd, Rake.original_dir
|
||||
end
|
||||
|
||||
end
|
|
@ -0,0 +1,84 @@
|
|||
require 'test/unit'
|
||||
require 'rake/rdoctask'
|
||||
|
||||
class TestRDocTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
end
|
||||
|
||||
def test_tasks_creation
|
||||
Rake::RDocTask.new
|
||||
assert Task[:rdoc]
|
||||
assert Task[:clobber_rdoc]
|
||||
assert Task[:rerdoc]
|
||||
end
|
||||
|
||||
def test_tasks_creation_with_custom_name_symbol
|
||||
rd = Rake::RDocTask.new(:rdoc_dev)
|
||||
assert Task[:rdoc_dev]
|
||||
assert Task[:clobber_rdoc_dev]
|
||||
assert Task[:rerdoc_dev]
|
||||
assert_equal :rdoc_dev, rd.name
|
||||
end
|
||||
|
||||
def test_tasks_creation_with_custom_name_string
|
||||
rd = Rake::RDocTask.new("rdoc_dev")
|
||||
assert Task[:rdoc_dev]
|
||||
assert Task[:clobber_rdoc_dev]
|
||||
assert Task[:rerdoc_dev]
|
||||
assert_equal "rdoc_dev", rd.name
|
||||
end
|
||||
|
||||
def test_tasks_creation_with_custom_name_hash
|
||||
options = { :rdoc => "rdoc", :clobber_rdoc => "rdoc:clean", :rerdoc => "rdoc:force" }
|
||||
rd = Rake::RDocTask.new(options)
|
||||
assert Task[:"rdoc"]
|
||||
assert Task[:"rdoc:clean"]
|
||||
assert Task[:"rdoc:force"]
|
||||
assert_raises(RuntimeError) { Task[:clobber_rdoc] }
|
||||
assert_equal options, rd.name
|
||||
end
|
||||
|
||||
def test_tasks_creation_with_custom_name_hash_will_use_default_if_an_option_isnt_given
|
||||
rd = Rake::RDocTask.new(:clobber_rdoc => "rdoc:clean")
|
||||
assert Task[:rdoc]
|
||||
assert Task[:"rdoc:clean"]
|
||||
assert Task[:rerdoc]
|
||||
end
|
||||
|
||||
def test_tasks_creation_with_custom_name_hash_raises_exception_if_invalid_option_given
|
||||
assert_raises(ArgumentError) do
|
||||
Rake::RDocTask.new(:foo => "bar")
|
||||
end
|
||||
|
||||
begin
|
||||
Rake::RDocTask.new(:foo => "bar")
|
||||
rescue ArgumentError => e
|
||||
assert_match(/foo/, e.message)
|
||||
end
|
||||
end
|
||||
|
||||
def test_inline_source_is_enabled_by_default
|
||||
rd = Rake::RDocTask.new
|
||||
assert rd.option_list.include?('--inline-source')
|
||||
end
|
||||
|
||||
def test_inline_source_option_is_only_appended_if_option_not_already_given
|
||||
rd = Rake::RDocTask.new
|
||||
rd.options << '--inline-source'
|
||||
assert_equal 1, rd.option_list.grep('--inline-source').size
|
||||
|
||||
rd = Rake::RDocTask.new
|
||||
rd.options << '-S'
|
||||
assert_equal 1, rd.option_list.grep('-S').size
|
||||
assert_equal 0, rd.option_list.grep('--inline-source').size
|
||||
end
|
||||
|
||||
def test_inline_source_option_can_be_disabled
|
||||
rd = Rake::RDocTask.new
|
||||
rd.inline_source = false
|
||||
assert !rd.option_list.include?('--inline-source')
|
||||
end
|
||||
end
|
|
@ -0,0 +1,32 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
# ====================================================================
|
||||
class TestRequire < Test::Unit::TestCase
|
||||
RakeLibDir = File.dirname(__FILE__) + '/data/rakelib'
|
||||
|
||||
def test_can_load_rake_library
|
||||
app = Rake::Application.new
|
||||
assert app.instance_eval {
|
||||
rake_require("test1", [RakeLibDir], [])
|
||||
}
|
||||
end
|
||||
|
||||
def test_wont_reload_rake_library
|
||||
app = Rake::Application.new
|
||||
assert ! app.instance_eval {
|
||||
rake_require("test2", [RakeLibDir], ['test2'])
|
||||
}
|
||||
end
|
||||
|
||||
def test_throws_error_if_library_not_found
|
||||
app = Rake::Application.new
|
||||
ex = assert_raise(LoadError) {
|
||||
assert app.instance_eval {
|
||||
rake_require("testx", [RakeLibDir], [])
|
||||
}
|
||||
}
|
||||
assert_match(/x/, ex.message)
|
||||
end
|
||||
end
|
||||
|
|
@ -0,0 +1,345 @@
|
|||
require 'test/unit'
|
||||
require 'fileutils'
|
||||
require 'rake'
|
||||
require_relative 'filecreation'
|
||||
|
||||
######################################################################
|
||||
class TestRules < Test::Unit::TestCase
|
||||
include Rake
|
||||
include FileCreation
|
||||
|
||||
SRCFILE = "testdata/abc.c"
|
||||
SRCFILE2 = "testdata/xyz.c"
|
||||
FTNFILE = "testdata/abc.f"
|
||||
OBJFILE = "testdata/abc.o"
|
||||
FOOFILE = "testdata/foo"
|
||||
DOTFOOFILE = "testdata/.foo"
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
@runs = []
|
||||
end
|
||||
|
||||
def teardown
|
||||
FileList['testdata/*'].uniq.each do |f| rm_r(f, :verbose=>false) end
|
||||
end
|
||||
|
||||
def test_multiple_rules1
|
||||
create_file(FTNFILE)
|
||||
delete_file(SRCFILE)
|
||||
delete_file(OBJFILE)
|
||||
rule(/\.o$/ => ['.c']) do @runs << :C end
|
||||
rule(/\.o$/ => ['.f']) do @runs << :F end
|
||||
t = Task[OBJFILE]
|
||||
t.invoke
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:F], @runs
|
||||
end
|
||||
|
||||
def test_multiple_rules2
|
||||
create_file(FTNFILE)
|
||||
delete_file(SRCFILE)
|
||||
delete_file(OBJFILE)
|
||||
rule(/\.o$/ => ['.f']) do @runs << :F end
|
||||
rule(/\.o$/ => ['.c']) do @runs << :C end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:F], @runs
|
||||
end
|
||||
|
||||
def test_create_with_source
|
||||
create_file(SRCFILE)
|
||||
rule(/\.o$/ => ['.c']) do |t|
|
||||
@runs << t.name
|
||||
assert_equal OBJFILE, t.name
|
||||
assert_equal SRCFILE, t.source
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [OBJFILE], @runs
|
||||
end
|
||||
|
||||
def test_single_dependent
|
||||
create_file(SRCFILE)
|
||||
rule(/\.o$/ => '.c') do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [OBJFILE], @runs
|
||||
end
|
||||
|
||||
def test_rule_can_be_created_by_string
|
||||
create_file(SRCFILE)
|
||||
rule '.o' => ['.c'] do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [OBJFILE], @runs
|
||||
end
|
||||
|
||||
def test_rule_prereqs_can_be_created_by_string
|
||||
create_file(SRCFILE)
|
||||
rule '.o' => '.c' do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [OBJFILE], @runs
|
||||
end
|
||||
|
||||
def test_plain_strings_as_dependents_refer_to_files
|
||||
create_file(SRCFILE)
|
||||
rule '.o' => SRCFILE do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [OBJFILE], @runs
|
||||
end
|
||||
|
||||
def test_file_names_beginning_with_dot_can_be_tricked_into_refering_to_file
|
||||
verbose(false) do
|
||||
chdir("testdata") do
|
||||
create_file('.foo')
|
||||
rule '.o' => "./.foo" do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [OBJFILE], @runs
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_file_names_beginning_with_dot_can_be_wrapped_in_lambda
|
||||
verbose(false) do
|
||||
chdir("testdata") do
|
||||
create_file(".foo")
|
||||
rule '.o' => lambda{".foo"} do |t|
|
||||
@runs << "#{t.name} - #{t.source}"
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal ["#{OBJFILE} - .foo"], @runs
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_file_names_containing_percent_can_be_wrapped_in_lambda
|
||||
verbose(false) do
|
||||
chdir("testdata") do
|
||||
create_file("foo%x")
|
||||
rule '.o' => lambda{"foo%x"} do |t|
|
||||
@runs << "#{t.name} - #{t.source}"
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal ["#{OBJFILE} - foo%x"], @runs
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_non_extension_rule_name_refers_to_file
|
||||
verbose(false) do
|
||||
chdir("testdata") do
|
||||
create_file("abc.c")
|
||||
rule "abc" => '.c' do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
Task["abc"].invoke
|
||||
assert_equal ["abc"], @runs
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_pathmap_automatically_applies_to_name
|
||||
verbose(false) do
|
||||
chdir("testdata") do
|
||||
create_file("zzabc.c")
|
||||
rule ".o" => 'zz%{x,a}n.c' do |t|
|
||||
@runs << "#{t.name} - #{t.source}"
|
||||
end
|
||||
Task["xbc.o"].invoke
|
||||
assert_equal ["xbc.o - zzabc.c"], @runs
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_plain_strings_are_just_filenames
|
||||
verbose(false) do
|
||||
chdir("testdata") do
|
||||
create_file("plainname")
|
||||
rule ".o" => 'plainname' do |t|
|
||||
@runs << "#{t.name} - #{t.source}"
|
||||
end
|
||||
Task["xbc.o"].invoke
|
||||
assert_equal ["xbc.o - plainname"], @runs
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_rule_runs_when_explicit_task_has_no_actions
|
||||
create_file(SRCFILE)
|
||||
create_file(SRCFILE2)
|
||||
delete_file(OBJFILE)
|
||||
rule '.o' => '.c' do |t|
|
||||
@runs << t.source
|
||||
end
|
||||
file OBJFILE => [SRCFILE2]
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [SRCFILE], @runs
|
||||
end
|
||||
|
||||
def test_close_matches_on_name_do_not_trigger_rule
|
||||
create_file("testdata/x.c")
|
||||
rule '.o' => ['.c'] do |t|
|
||||
@runs << t.name
|
||||
end
|
||||
assert_raise(RuntimeError) { Task['testdata/x.obj'].invoke }
|
||||
assert_raise(RuntimeError) { Task['testdata/x.xyo'].invoke }
|
||||
end
|
||||
|
||||
def test_rule_rebuilds_obj_when_source_is_newer
|
||||
create_timed_files(OBJFILE, SRCFILE)
|
||||
rule(/\.o$/ => ['.c']) do
|
||||
@runs << :RULE
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:RULE], @runs
|
||||
end
|
||||
|
||||
def test_rule_with_two_sources_runs_if_both_sources_are_present
|
||||
create_timed_files(OBJFILE, SRCFILE, SRCFILE2)
|
||||
rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do
|
||||
@runs << :RULE
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:RULE], @runs
|
||||
end
|
||||
|
||||
def test_rule_with_two_sources_but_one_missing_does_not_run
|
||||
create_timed_files(OBJFILE, SRCFILE)
|
||||
delete_file(SRCFILE2)
|
||||
rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do
|
||||
@runs << :RULE
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [], @runs
|
||||
end
|
||||
|
||||
def test_rule_with_two_sources_builds_both_sources
|
||||
task 'x.aa'
|
||||
task 'x.bb'
|
||||
rule '.a' => '.aa' do
|
||||
@runs << "A"
|
||||
end
|
||||
rule '.b' => '.bb' do
|
||||
@runs << "B"
|
||||
end
|
||||
rule ".c" => ['.a', '.b'] do
|
||||
@runs << "C"
|
||||
end
|
||||
Task["x.c"].invoke
|
||||
assert_equal ["A", "B", "C"], @runs.sort
|
||||
end
|
||||
|
||||
def test_second_rule_runs_when_first_rule_doesnt
|
||||
create_timed_files(OBJFILE, SRCFILE)
|
||||
delete_file(SRCFILE2)
|
||||
rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do
|
||||
@runs << :RULE1
|
||||
end
|
||||
rule OBJFILE => [lambda{SRCFILE}] do
|
||||
@runs << :RULE2
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:RULE2], @runs
|
||||
end
|
||||
|
||||
def test_second_rule_doest_run_if_first_triggers
|
||||
create_timed_files(OBJFILE, SRCFILE, SRCFILE2)
|
||||
rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do
|
||||
@runs << :RULE1
|
||||
end
|
||||
rule OBJFILE => [lambda{SRCFILE}] do
|
||||
@runs << :RULE2
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:RULE1], @runs
|
||||
end
|
||||
|
||||
def test_second_rule_doest_run_if_first_triggers_with_reversed_rules
|
||||
create_timed_files(OBJFILE, SRCFILE, SRCFILE2)
|
||||
rule OBJFILE => [lambda{SRCFILE}] do
|
||||
@runs << :RULE1
|
||||
end
|
||||
rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do
|
||||
@runs << :RULE2
|
||||
end
|
||||
Task[OBJFILE].invoke
|
||||
assert_equal [:RULE1], @runs
|
||||
end
|
||||
|
||||
def test_rule_with_proc_dependent_will_trigger
|
||||
ran = false
|
||||
mkdir_p("testdata/src/jw")
|
||||
create_file("testdata/src/jw/X.java")
|
||||
rule %r(classes/.*\.class) => [
|
||||
proc { |fn| fn.pathmap("%{classes,testdata/src}d/%n.java") }
|
||||
] do |task|
|
||||
assert_equal task.name, 'classes/jw/X.class'
|
||||
assert_equal task.source, 'testdata/src/jw/X.java'
|
||||
@runs << :RULE
|
||||
end
|
||||
Task['classes/jw/X.class'].invoke
|
||||
assert_equal [:RULE], @runs
|
||||
ensure
|
||||
rm_r("testdata/src", :verbose=>false) rescue nil
|
||||
end
|
||||
|
||||
def test_proc_returning_lists_are_flattened_into_prereqs
|
||||
ran = false
|
||||
mkdir_p("testdata/flatten")
|
||||
create_file("testdata/flatten/a.txt")
|
||||
task 'testdata/flatten/b.data' do |t|
|
||||
ran = true
|
||||
touch t.name, :verbose => false
|
||||
end
|
||||
rule '.html' =>
|
||||
proc { |fn|
|
||||
[
|
||||
fn.ext("txt"),
|
||||
"testdata/flatten/b.data"
|
||||
]
|
||||
} do |task|
|
||||
end
|
||||
Task['testdata/flatten/a.html'].invoke
|
||||
assert ran, "Should have triggered flattened dependency"
|
||||
ensure
|
||||
rm_r("testdata/flatten", :verbose=>false) rescue nil
|
||||
end
|
||||
|
||||
def test_recursive_rules_will_work_as_long_as_they_terminate
|
||||
actions = []
|
||||
create_file("testdata/abc.xml")
|
||||
rule '.y' => '.xml' do actions << 'y' end
|
||||
rule '.c' => '.y' do actions << 'c'end
|
||||
rule '.o' => '.c' do actions << 'o'end
|
||||
rule '.exe' => '.o' do actions << 'exe'end
|
||||
Task["testdata/abc.exe"].invoke
|
||||
assert_equal ['y', 'c', 'o', 'exe'], actions
|
||||
end
|
||||
|
||||
def test_recursive_rules_that_dont_terminate_will_overflow
|
||||
create_file("testdata/a.a")
|
||||
prev = 'a'
|
||||
('b'..'z').each do |letter|
|
||||
rule ".#{letter}" => ".#{prev}" do |t| puts "#{t.name}" end
|
||||
prev = letter
|
||||
end
|
||||
ex = assert_raise(Rake::RuleRecursionOverflowError) {
|
||||
Task["testdata/a.z"].invoke
|
||||
}
|
||||
assert_match(/a\.z => testdata\/a.y/, ex.message)
|
||||
end
|
||||
|
||||
def test_rules_with_bad_dependents_will_fail
|
||||
rule "a" => [ 1 ] do |t| puts t.name end
|
||||
assert_raise(RuntimeError) do Task['a'].invoke end
|
||||
end
|
||||
|
||||
end
|
||||
|
|
@ -0,0 +1,87 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
######################################################################
|
||||
class TestTaskArguments < Test::Unit::TestCase
|
||||
def teardown
|
||||
ENV.delete('rev')
|
||||
ENV.delete('VER')
|
||||
end
|
||||
|
||||
def test_empty_arg_list_is_empty
|
||||
ta = Rake::TaskArguments.new([], [])
|
||||
assert_equal({}, ta.to_hash)
|
||||
end
|
||||
|
||||
def test_multiple_values_in_args
|
||||
ta = Rake::TaskArguments.new([:a, :b, :c], [:one, :two, :three])
|
||||
assert_equal({:a => :one, :b => :two, :c => :three}, ta.to_hash)
|
||||
end
|
||||
|
||||
def test_to_s
|
||||
ta = Rake::TaskArguments.new([:a, :b, :c], [1, 2, 3])
|
||||
assert_equal ta.to_hash.inspect, ta.to_s
|
||||
assert_equal ta.to_hash.inspect, ta.inspect
|
||||
end
|
||||
|
||||
def test_enumerable_behavior
|
||||
ta = Rake::TaskArguments.new([:a, :b, :c], [1, 2 ,3])
|
||||
assert_equal [10, 20, 30], ta.collect { |k,v| v * 10 }.sort
|
||||
end
|
||||
|
||||
def test_named_args
|
||||
ta = Rake::TaskArguments.new(["aa", "bb"], [1, 2])
|
||||
assert_equal 1, ta.aa
|
||||
assert_equal 1, ta[:aa]
|
||||
assert_equal 1, ta["aa"]
|
||||
assert_equal 2, ta.bb
|
||||
assert_nil ta.cc
|
||||
end
|
||||
|
||||
def test_args_knows_its_names
|
||||
ta = Rake::TaskArguments.new(["aa", "bb"], [1, 2])
|
||||
assert_equal ["aa", "bb"], ta.names
|
||||
end
|
||||
|
||||
def test_extra_names_are_nil
|
||||
ta = Rake::TaskArguments.new(["aa", "bb", "cc"], [1, 2])
|
||||
assert_nil ta.cc
|
||||
end
|
||||
|
||||
def test_args_can_reference_env_values
|
||||
ta = Rake::TaskArguments.new(["aa"], [1])
|
||||
ENV['rev'] = "1.2"
|
||||
ENV['VER'] = "2.3"
|
||||
assert_equal "1.2", ta.rev
|
||||
assert_equal "2.3", ta.ver
|
||||
end
|
||||
|
||||
def test_creating_new_argument_scopes
|
||||
parent = Rake::TaskArguments.new(['p'], [1])
|
||||
child = parent.new_scope(['c', 'p'])
|
||||
assert_equal({:p=>1}, child.to_hash)
|
||||
assert_equal 1, child.p
|
||||
assert_equal 1, child["p"]
|
||||
assert_equal 1, child[:p]
|
||||
assert_nil child.c
|
||||
end
|
||||
|
||||
def test_child_hides_parent_arg_names
|
||||
parent = Rake::TaskArguments.new(['aa'], [1])
|
||||
child = Rake::TaskArguments.new(['aa'], [2], parent)
|
||||
assert_equal 2, child.aa
|
||||
end
|
||||
|
||||
def test_default_arguments_values_can_be_merged
|
||||
ta = Rake::TaskArguments.new(["aa", "bb"], [nil, "original_val"])
|
||||
ta.with_defaults({ :aa => 'default_val' })
|
||||
assert_equal 'default_val', ta[:aa]
|
||||
assert_equal 'original_val', ta[:bb]
|
||||
end
|
||||
|
||||
def test_default_arguements_that_dont_match_names_are_ignored
|
||||
ta = Rake::TaskArguments.new(["aa", "bb"], [nil, "original_val"])
|
||||
ta.with_defaults({ "cc" => "default_val" })
|
||||
assert_nil ta[:cc]
|
||||
end
|
||||
end
|
|
@ -0,0 +1,169 @@
|
|||
require 'test/unit'
|
||||
require 'rake'
|
||||
|
||||
class TaskManager
|
||||
include Rake::TaskManager
|
||||
end
|
||||
|
||||
class TestTaskManager < Test::Unit::TestCase
|
||||
|
||||
def setup
|
||||
@tm = TaskManager.new
|
||||
end
|
||||
|
||||
def test_create_task_manager
|
||||
assert_not_nil @tm
|
||||
assert_equal [], @tm.tasks
|
||||
end
|
||||
|
||||
def test_define_task
|
||||
t = @tm.define_task(Rake::Task, :t)
|
||||
assert_equal "t", t.name
|
||||
assert_equal @tm, t.application
|
||||
end
|
||||
|
||||
def test_name_lookup
|
||||
t = @tm.define_task(Rake::Task, :t)
|
||||
assert_equal t, @tm[:t]
|
||||
end
|
||||
|
||||
def test_namespace_task_create
|
||||
@tm.in_namespace("x") do
|
||||
t = @tm.define_task(Rake::Task, :t)
|
||||
assert_equal "x:t", t.name
|
||||
end
|
||||
assert_equal ["x:t"], @tm.tasks.collect { |t| t.name }
|
||||
end
|
||||
|
||||
def test_anonymous_namespace
|
||||
anon_ns = @tm.in_namespace(nil) do
|
||||
t = @tm.define_task(Rake::Task, :t)
|
||||
assert_equal "_anon_1:t", t.name
|
||||
end
|
||||
task = anon_ns[:t]
|
||||
assert_equal "_anon_1:t", task.name
|
||||
end
|
||||
|
||||
def test_create_filetask_in_namespace
|
||||
@tm.in_namespace("x") do
|
||||
t = @tm.define_task(Rake::FileTask, "fn")
|
||||
assert_equal "fn", t.name
|
||||
end
|
||||
assert_equal ["fn"], @tm.tasks.collect { |t| t.name }
|
||||
end
|
||||
|
||||
def test_namespace_yields_same_namespace_as_returned
|
||||
yielded_namespace = nil
|
||||
returned_namespace = @tm.in_namespace("x") do |ns|
|
||||
yielded_namespace = ns
|
||||
end
|
||||
assert_equal returned_namespace, yielded_namespace
|
||||
end
|
||||
|
||||
def test_name_lookup_with_implicit_file_tasks
|
||||
t = @tm["README"]
|
||||
assert_equal "README", t.name
|
||||
assert Rake::FileTask === t
|
||||
end
|
||||
|
||||
def test_name_lookup_with_nonexistent_task
|
||||
assert_raise(RuntimeError) {
|
||||
t = @tm["DOES NOT EXIST"]
|
||||
}
|
||||
end
|
||||
|
||||
def test_name_lookup_in_multiple_scopes
|
||||
aa = nil
|
||||
bb = nil
|
||||
xx = @tm.define_task(Rake::Task, :xx)
|
||||
top_z = @tm.define_task(Rake::Task, :z)
|
||||
@tm.in_namespace("a") do
|
||||
aa = @tm.define_task(Rake::Task, :aa)
|
||||
mid_z = @tm.define_task(Rake::Task, :z)
|
||||
@tm.in_namespace("b") do
|
||||
bb = @tm.define_task(Rake::Task, :bb)
|
||||
bot_z = @tm.define_task(Rake::Task, :z)
|
||||
|
||||
assert_equal ["a", "b"], @tm.current_scope
|
||||
|
||||
assert_equal bb, @tm["a:b:bb"]
|
||||
assert_equal aa, @tm["a:aa"]
|
||||
assert_equal xx, @tm["xx"]
|
||||
assert_equal bot_z, @tm["z"]
|
||||
assert_equal mid_z, @tm["^z"]
|
||||
assert_equal top_z, @tm["^^z"]
|
||||
assert_equal top_z, @tm["rake:z"]
|
||||
end
|
||||
|
||||
assert_equal ["a"], @tm.current_scope
|
||||
|
||||
assert_equal bb, @tm["a:b:bb"]
|
||||
assert_equal aa, @tm["a:aa"]
|
||||
assert_equal xx, @tm["xx"]
|
||||
assert_equal bb, @tm["b:bb"]
|
||||
assert_equal aa, @tm["aa"]
|
||||
assert_equal mid_z, @tm["z"]
|
||||
assert_equal top_z, @tm["^z"]
|
||||
assert_equal top_z, @tm["rake:z"]
|
||||
end
|
||||
|
||||
assert_equal [], @tm.current_scope
|
||||
|
||||
assert_equal [], xx.scope
|
||||
assert_equal ['a'], aa.scope
|
||||
assert_equal ['a', 'b'], bb.scope
|
||||
end
|
||||
|
||||
def test_lookup_with_explicit_scopes
|
||||
t1, t2, t3, s = (0...4).collect { nil }
|
||||
t1 = @tm.define_task(Rake::Task, :t)
|
||||
@tm.in_namespace("a") do
|
||||
t2 = @tm.define_task(Rake::Task, :t)
|
||||
s = @tm.define_task(Rake::Task, :s)
|
||||
@tm.in_namespace("b") do
|
||||
t3 = @tm.define_task(Rake::Task, :t)
|
||||
end
|
||||
end
|
||||
assert_equal t1, @tm[:t, []]
|
||||
assert_equal t2, @tm[:t, ["a"]]
|
||||
assert_equal t3, @tm[:t, ["a", "b"]]
|
||||
assert_equal s, @tm[:s, ["a", "b"]]
|
||||
assert_equal s, @tm[:s, ["a"]]
|
||||
end
|
||||
|
||||
def test_correctly_scoped_prerequisites_are_invoked
|
||||
values = []
|
||||
@tm = Rake::Application.new
|
||||
@tm.define_task(Rake::Task, :z) do values << "top z" end
|
||||
@tm.in_namespace("a") do
|
||||
@tm.define_task(Rake::Task, :z) do values << "next z" end
|
||||
@tm.define_task(Rake::Task, :x => :z)
|
||||
end
|
||||
|
||||
@tm["a:x"].invoke
|
||||
assert_equal ["next z"], values
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
class TestTaskManagerArgumentResolution < Test::Unit::TestCase
|
||||
def test_good_arg_patterns
|
||||
assert_equal [:t, [], []], task(:t)
|
||||
assert_equal [:t, [], [:x]], task(:t => :x)
|
||||
assert_equal [:t, [], [:x, :y]], task(:t => [:x, :y])
|
||||
|
||||
assert_equal [:t, [:a, :b], []], task(:t, :a, :b)
|
||||
assert_equal [:t, [], [:x]], task(:t, :needs => :x)
|
||||
assert_equal [:t, [:a, :b], [:x]], task(:t, :a, :b, :needs => :x)
|
||||
assert_equal [:t, [:a, :b], [:x, :y]], task(:t, :a, :b, :needs => [:x, :y])
|
||||
|
||||
assert_equal [:t, [:a, :b], []], task(:t, [:a, :b])
|
||||
assert_equal [:t, [:a, :b], [:x]], task(:t, [:a, :b] => :x)
|
||||
assert_equal [:t, [:a, :b], [:x, :y]], task(:t, [:a, :b] => [:x, :y])
|
||||
end
|
||||
|
||||
def task(*args)
|
||||
tm = TaskManager.new
|
||||
tm.resolve_args(args)
|
||||
end
|
||||
end
|
|
@ -0,0 +1,10 @@
|
|||
require 'test/unit'
|
||||
require 'rake/tasklib'
|
||||
|
||||
|
||||
class TestTaskLib < Test::Unit::TestCase
|
||||
def test_paste
|
||||
tl = Rake::TaskLib.new
|
||||
assert_equal :ab, tl.paste(:a, :b)
|
||||
end
|
||||
end
|
|
@ -0,0 +1,369 @@
|
|||
require 'test/unit'
|
||||
require 'fileutils'
|
||||
require 'rake'
|
||||
require_relative 'filecreation'
|
||||
require_relative 'capture_stdout'
|
||||
|
||||
######################################################################
|
||||
class TestTask < Test::Unit::TestCase
|
||||
include CaptureStdout
|
||||
include Rake
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
end
|
||||
|
||||
def test_create
|
||||
arg = nil
|
||||
t = task(:name) { |task| arg = task; 1234 }
|
||||
assert_equal "name", t.name
|
||||
assert_equal [], t.prerequisites
|
||||
assert t.needed?
|
||||
t.execute(0)
|
||||
assert_equal t, arg
|
||||
assert_nil t.source
|
||||
assert_equal [], t.sources
|
||||
end
|
||||
|
||||
def test_inspect
|
||||
t = task(:foo, :needs => [:bar, :baz])
|
||||
assert_equal "<Rake::Task foo => [bar, baz]>", t.inspect
|
||||
end
|
||||
|
||||
def test_invoke
|
||||
runlist = []
|
||||
t1 = task(:t1 => [:t2, :t3]) { |t| runlist << t.name; 3321 }
|
||||
t2 = task(:t2) { |t| runlist << t.name }
|
||||
t3 = task(:t3) { |t| runlist << t.name }
|
||||
assert_equal ["t2", "t3"], t1.prerequisites
|
||||
t1.invoke
|
||||
assert_equal ["t2", "t3", "t1"], runlist
|
||||
end
|
||||
|
||||
def test_invoke_with_circular_dependencies
|
||||
runlist = []
|
||||
t1 = task(:t1 => [:t2]) { |t| runlist << t.name; 3321 }
|
||||
t2 = task(:t2 => [:t1]) { |t| runlist << t.name }
|
||||
assert_equal ["t2"], t1.prerequisites
|
||||
assert_equal ["t1"], t2.prerequisites
|
||||
ex = assert_raise RuntimeError do
|
||||
t1.invoke
|
||||
end
|
||||
assert_match(/circular dependency/i, ex.message)
|
||||
assert_match(/t1 => t2 => t1/, ex.message)
|
||||
end
|
||||
|
||||
def test_dry_run_prevents_actions
|
||||
Rake.application.options.dryrun = true
|
||||
runlist = []
|
||||
t1 = task(:t1) { |t| runlist << t.name; 3321 }
|
||||
out = capture_stdout { t1.invoke }
|
||||
assert_match(/execute .*t1/i, out)
|
||||
assert_match(/dry run/i, out)
|
||||
assert_no_match(/invoke/i, out)
|
||||
assert_equal [], runlist
|
||||
ensure
|
||||
Rake.application.options.dryrun = false
|
||||
end
|
||||
|
||||
def test_tasks_can_be_traced
|
||||
Rake.application.options.trace = true
|
||||
t1 = task(:t1)
|
||||
out = capture_stdout {
|
||||
t1.invoke
|
||||
}
|
||||
assert_match(/invoke t1/i, out)
|
||||
assert_match(/execute t1/i, out)
|
||||
ensure
|
||||
Rake.application.options.trace = false
|
||||
end
|
||||
|
||||
def test_no_double_invoke
|
||||
runlist = []
|
||||
t1 = task(:t1 => [:t2, :t3]) { |t| runlist << t.name; 3321 }
|
||||
t2 = task(:t2 => [:t3]) { |t| runlist << t.name }
|
||||
t3 = task(:t3) { |t| runlist << t.name }
|
||||
t1.invoke
|
||||
assert_equal ["t3", "t2", "t1"], runlist
|
||||
end
|
||||
|
||||
def test_can_double_invoke_with_reenable
|
||||
runlist = []
|
||||
t1 = task(:t1) { |t| runlist << t.name }
|
||||
t1.invoke
|
||||
t1.reenable
|
||||
t1.invoke
|
||||
assert_equal ["t1", "t1"], runlist
|
||||
end
|
||||
|
||||
def test_clear
|
||||
t = task("t" => "a") { }
|
||||
t.clear
|
||||
assert t.prerequisites.empty?, "prerequisites should be empty"
|
||||
assert t.actions.empty?, "actions should be empty"
|
||||
end
|
||||
|
||||
def test_clear_prerequisites
|
||||
t = task("t" => ["a", "b"])
|
||||
assert_equal ['a', 'b'], t.prerequisites
|
||||
t.clear_prerequisites
|
||||
assert_equal [], t.prerequisites
|
||||
end
|
||||
|
||||
def test_clear_actions
|
||||
t = task("t") { }
|
||||
t.clear_actions
|
||||
assert t.actions.empty?, "actions should be empty"
|
||||
end
|
||||
|
||||
def test_find
|
||||
task :tfind
|
||||
assert_equal "tfind", Task[:tfind].name
|
||||
ex = assert_raise(RuntimeError) { Task[:leaves] }
|
||||
assert_equal "Don't know how to build task 'leaves'", ex.message
|
||||
end
|
||||
|
||||
def test_defined
|
||||
assert ! Task.task_defined?(:a)
|
||||
task :a
|
||||
assert Task.task_defined?(:a)
|
||||
end
|
||||
|
||||
def test_multi_invocations
|
||||
runs = []
|
||||
p = proc do |t| runs << t.name end
|
||||
task({:t1=>[:t2,:t3]}, &p)
|
||||
task({:t2=>[:t3]}, &p)
|
||||
task(:t3, &p)
|
||||
Task[:t1].invoke
|
||||
assert_equal ["t1", "t2", "t3"], runs.sort
|
||||
end
|
||||
|
||||
def test_task_list
|
||||
task :t2
|
||||
task :t1 => [:t2]
|
||||
assert_equal ["t1", "t2"], Task.tasks.collect {|t| t.name}
|
||||
end
|
||||
|
||||
def test_task_gives_name_on_to_s
|
||||
task :abc
|
||||
assert_equal "abc", Task[:abc].to_s
|
||||
end
|
||||
|
||||
def test_symbols_can_be_prerequisites
|
||||
task :a => :b
|
||||
assert_equal ["b"], Task[:a].prerequisites
|
||||
end
|
||||
|
||||
def test_strings_can_be_prerequisites
|
||||
task :a => "b"
|
||||
assert_equal ["b"], Task[:a].prerequisites
|
||||
end
|
||||
|
||||
def test_arrays_can_be_prerequisites
|
||||
task :a => ["b", "c"]
|
||||
assert_equal ["b", "c"], Task[:a].prerequisites
|
||||
end
|
||||
|
||||
def test_filelists_can_be_prerequisites
|
||||
task :a => FileList.new.include("b", "c")
|
||||
assert_equal ["b", "c"], Task[:a].prerequisites
|
||||
end
|
||||
|
||||
def test_investigation_output
|
||||
t1 = task(:t1 => [:t2, :t3]) { |t| runlist << t.name; 3321 }
|
||||
task(:t2)
|
||||
task(:t3)
|
||||
out = t1.investigation
|
||||
assert_match(/class:\s*Rake::Task/, out)
|
||||
assert_match(/needed:\s*true/, out)
|
||||
assert_match(/pre-requisites:\s*--t[23]/, out)
|
||||
end
|
||||
|
||||
|
||||
def test_extended_comments
|
||||
desc %{
|
||||
This is a comment.
|
||||
|
||||
And this is the extended comment.
|
||||
name -- Name of task to execute.
|
||||
rev -- Software revision to use.
|
||||
}
|
||||
t = task(:t, :name, :rev)
|
||||
assert_equal "[name,rev]", t.arg_description
|
||||
assert_equal "This is a comment.", t.comment
|
||||
assert_match(/^\s*name -- Name/, t.full_comment)
|
||||
assert_match(/^\s*rev -- Software/, t.full_comment)
|
||||
assert_match(/\A\s*This is a comment\.$/, t.full_comment)
|
||||
end
|
||||
|
||||
def test_multiple_comments
|
||||
desc "line one"
|
||||
t = task(:t)
|
||||
desc "line two"
|
||||
task(:t)
|
||||
assert_equal "line one / line two", t.comment
|
||||
end
|
||||
|
||||
def test_settable_comments
|
||||
t = task(:t)
|
||||
t.comment = "HI"
|
||||
assert_equal "HI", t.comment
|
||||
end
|
||||
end
|
||||
|
||||
######################################################################
|
||||
class TestTaskWithArguments < Test::Unit::TestCase
|
||||
include CaptureStdout
|
||||
include Rake
|
||||
|
||||
def setup
|
||||
Task.clear
|
||||
end
|
||||
|
||||
def test_no_args_given
|
||||
t = task :t
|
||||
assert_equal [], t.arg_names
|
||||
end
|
||||
|
||||
def test_args_given
|
||||
t = task :t, :a, :b
|
||||
assert_equal [:a, :b], t.arg_names
|
||||
end
|
||||
|
||||
def test_name_and_needs
|
||||
t = task(:t => [:pre])
|
||||
assert_equal "t", t.name
|
||||
assert_equal [], t.arg_names
|
||||
assert_equal ["pre"], t.prerequisites
|
||||
end
|
||||
|
||||
def test_name_and_explicit_needs
|
||||
t = task(:t, :needs => [:pre])
|
||||
assert_equal "t", t.name
|
||||
assert_equal [], t.arg_names
|
||||
assert_equal ["pre"], t.prerequisites
|
||||
end
|
||||
|
||||
def test_name_args_and_explicit_needs
|
||||
t = task(:t, :x, :y, :needs => [:pre])
|
||||
assert_equal "t", t.name
|
||||
assert_equal [:x, :y], t.arg_names
|
||||
assert_equal ["pre"], t.prerequisites
|
||||
end
|
||||
|
||||
def test_illegal_keys_in_task_name_hash
|
||||
assert_raise RuntimeError do
|
||||
t = task(:t, :x, :y => 1, :needs => [:pre])
|
||||
end
|
||||
end
|
||||
|
||||
def test_arg_list_is_empty_if_no_args_given
|
||||
t = task(:t) { |tt, args| assert_equal({}, args.to_hash) }
|
||||
t.invoke(1, 2, 3)
|
||||
end
|
||||
|
||||
def test_tasks_can_access_arguments_as_hash
|
||||
t = task :t, :a, :b, :c do |tt, args|
|
||||
assert_equal({:a => 1, :b => 2, :c => 3}, args.to_hash)
|
||||
assert_equal 1, args[:a]
|
||||
assert_equal 2, args[:b]
|
||||
assert_equal 3, args[:c]
|
||||
assert_equal 1, args.a
|
||||
assert_equal 2, args.b
|
||||
assert_equal 3, args.c
|
||||
end
|
||||
t.invoke(1, 2, 3)
|
||||
end
|
||||
|
||||
def test_actions_of_various_arity_are_ok_with_args
|
||||
notes = []
|
||||
t = task(:t, :x) do
|
||||
notes << :a
|
||||
end
|
||||
t.enhance do | |
|
||||
notes << :b
|
||||
end
|
||||
t.enhance do |task|
|
||||
notes << :c
|
||||
assert_kind_of Task, task
|
||||
end
|
||||
t.enhance do |t2, args|
|
||||
notes << :d
|
||||
assert_equal t, t2
|
||||
assert_equal({:x => 1}, args.to_hash)
|
||||
end
|
||||
assert_nothing_raised do t.invoke(1) end
|
||||
assert_equal [:a, :b, :c, :d], notes
|
||||
end
|
||||
|
||||
def test_arguments_are_passed_to_block
|
||||
t = task(:t, :a, :b) { |tt, args|
|
||||
assert_equal( { :a => 1, :b => 2 }, args.to_hash )
|
||||
}
|
||||
t.invoke(1, 2)
|
||||
end
|
||||
|
||||
def test_extra_parameters_are_ignored
|
||||
t = task(:t, :a) { |tt, args|
|
||||
assert_equal 1, args.a
|
||||
assert_nil args.b
|
||||
}
|
||||
t.invoke(1, 2)
|
||||
end
|
||||
|
||||
def test_arguments_are_passed_to_all_blocks
|
||||
counter = 0
|
||||
t = task :t, :a
|
||||
task :t do |tt, args|
|
||||
assert_equal 1, args.a
|
||||
counter += 1
|
||||
end
|
||||
task :t do |tt, args|
|
||||
assert_equal 1, args.a
|
||||
counter += 1
|
||||
end
|
||||
t.invoke(1)
|
||||
assert_equal 2, counter
|
||||
end
|
||||
|
||||
def test_block_with_no_parameters_is_ok
|
||||
t = task(:t) { }
|
||||
t.invoke(1, 2)
|
||||
end
|
||||
|
||||
def test_name_with_args
|
||||
desc "T"
|
||||
t = task(:tt, :a, :b)
|
||||
assert_equal "tt", t.name
|
||||
assert_equal "T", t.comment
|
||||
assert_equal "[a,b]", t.arg_description
|
||||
assert_equal "tt[a,b]", t.name_with_args
|
||||
assert_equal [:a, :b],t.arg_names
|
||||
end
|
||||
|
||||
def test_named_args_are_passed_to_prereqs
|
||||
value = nil
|
||||
pre = task(:pre, :rev) { |t, args| value = args.rev }
|
||||
t = task(:t, :name, :rev, :needs => [:pre])
|
||||
t.invoke("bill", "1.2")
|
||||
assert_equal "1.2", value
|
||||
end
|
||||
|
||||
def test_args_not_passed_if_no_prereq_names
|
||||
pre = task(:pre) { |t, args|
|
||||
assert_equal({}, args.to_hash)
|
||||
assert_equal "bill", args.name
|
||||
}
|
||||
t = task(:t, :name, :rev, :needs => [:pre])
|
||||
t.invoke("bill", "1.2")
|
||||
end
|
||||
|
||||
def test_args_not_passed_if_no_arg_names
|
||||
pre = task(:pre, :rev) { |t, args|
|
||||
assert_equal({}, args.to_hash)
|
||||
}
|
||||
t = task(:t, :needs => [:pre])
|
||||
t.invoke("bill", "1.2")
|
||||
end
|
||||
end
|
|
@ -0,0 +1,81 @@
|
|||
require 'tmpdir'
|
||||
require 'test/unit'
|
||||
require 'rake/testtask'
|
||||
|
||||
class TestTestTask < Test::Unit::TestCase
|
||||
include Rake
|
||||
|
||||
def setup
|
||||
@oldwd = Dir.pwd
|
||||
@tmpwd = Dir.mktmpdir
|
||||
Dir.chdir(@tmpwd)
|
||||
Task.clear
|
||||
ENV.delete('TEST')
|
||||
open('install.rb', 'w') {}
|
||||
end
|
||||
|
||||
def teardown
|
||||
FileUtils.rm_rf("testdata")
|
||||
Dir.chdir(@oldwd)
|
||||
FileUtils.rm_rf(@tmpwd)
|
||||
end
|
||||
|
||||
def test_no_task
|
||||
assert ! Task.task_defined?(:test)
|
||||
end
|
||||
|
||||
def test_defaults
|
||||
tt = Rake::TestTask.new do |t| end
|
||||
assert_not_nil tt
|
||||
assert_equal :test, tt.name
|
||||
assert_equal ['lib'], tt.libs
|
||||
assert_equal 'test/test*.rb', tt.pattern
|
||||
assert_equal false, tt.verbose
|
||||
assert Task.task_defined?(:test)
|
||||
end
|
||||
|
||||
def test_non_defaults
|
||||
tt = Rake::TestTask.new(:example) do |t|
|
||||
t.libs = ['src', 'ext']
|
||||
t.pattern = 'test/tc_*.rb'
|
||||
t.verbose = true
|
||||
end
|
||||
assert_not_nil tt
|
||||
assert_equal :example, tt.name
|
||||
assert_equal ['src', 'ext'], tt.libs
|
||||
assert_equal 'test/tc_*.rb', tt.pattern
|
||||
assert_equal true, tt.verbose
|
||||
assert Task.task_defined?(:example)
|
||||
end
|
||||
|
||||
def test_pattern
|
||||
tt = Rake::TestTask.new do |t|
|
||||
t.pattern = '*.rb'
|
||||
end
|
||||
assert_equal ['install.rb'], tt.file_list.to_a
|
||||
end
|
||||
|
||||
def test_env_test
|
||||
ENV['TEST'] = 'testfile.rb'
|
||||
tt = Rake::TestTask.new do |t|
|
||||
t.pattern = '*'
|
||||
end
|
||||
assert_equal ["testfile.rb"], tt.file_list.to_a
|
||||
end
|
||||
|
||||
def test_test_files
|
||||
tt = Rake::TestTask.new do |t|
|
||||
t.test_files = FileList['a.rb', 'b.rb']
|
||||
end
|
||||
assert_equal ["a.rb", 'b.rb'], tt.file_list.to_a
|
||||
end
|
||||
|
||||
def test_both_pattern_and_test_files
|
||||
tt = Rake::TestTask.new do |t|
|
||||
t.test_files = FileList['a.rb', 'b.rb']
|
||||
t.pattern = '*.rb'
|
||||
end
|
||||
assert_equal ['a.rb', 'b.rb', 'install.rb'], tt.file_list.to_a
|
||||
end
|
||||
|
||||
end
|
|
@ -0,0 +1,91 @@
|
|||
require 'test/unit'
|
||||
require_relative 'capture_stdout'
|
||||
require 'rake'
|
||||
|
||||
class TestTopLevelFunctions < Test::Unit::TestCase
|
||||
include CaptureStdout
|
||||
|
||||
def setup
|
||||
super
|
||||
@app = Rake.application
|
||||
Rake.application = @mock = Object.new
|
||||
end
|
||||
|
||||
def teardown
|
||||
Rake.application = @app
|
||||
super
|
||||
end
|
||||
|
||||
def defmock(sym, &block)
|
||||
class << @mock; self; end.class_eval do
|
||||
define_method(sym, block)
|
||||
end
|
||||
end
|
||||
|
||||
def test_namespace
|
||||
args = []
|
||||
defmock(:in_namespace) {|a, *| args << a}
|
||||
namespace "xyz" do end
|
||||
assert_equal(["xyz"], args)
|
||||
end
|
||||
|
||||
def test_import
|
||||
args = []
|
||||
defmock(:add_import) {|a| args << a}
|
||||
import('x', 'y', 'z')
|
||||
assert_equal(['x', 'y', 'z'], args)
|
||||
end
|
||||
|
||||
def test_when_writing
|
||||
out = capture_stdout do
|
||||
when_writing("NOTWRITING") do
|
||||
puts "WRITING"
|
||||
end
|
||||
end
|
||||
assert_equal "WRITING\n", out
|
||||
end
|
||||
|
||||
def test_when_not_writing
|
||||
RakeFileUtils.nowrite_flag = true
|
||||
out = capture_stdout do
|
||||
when_writing("NOTWRITING") do
|
||||
puts "WRITING"
|
||||
end
|
||||
end
|
||||
assert_equal "DRYRUN: NOTWRITING\n", out
|
||||
ensure
|
||||
RakeFileUtils.nowrite_flag = false
|
||||
end
|
||||
|
||||
def test_missing_constants_task
|
||||
args = []
|
||||
defmock(:const_warning) {|a| args << a}
|
||||
Object.const_missing(:Task)
|
||||
assert_equal([:Task], args)
|
||||
end
|
||||
|
||||
def test_missing_constants_file_task
|
||||
args = []
|
||||
defmock(:const_warning) {|a| args << a}
|
||||
Object.const_missing(:FileTask)
|
||||
assert_equal([:FileTask], args)
|
||||
end
|
||||
|
||||
def test_missing_constants_file_creation_task
|
||||
args = []
|
||||
defmock(:const_warning) {|a| args << a}
|
||||
Object.const_missing(:FileCreationTask)
|
||||
assert_equal([:FileCreationTask], args)
|
||||
end
|
||||
|
||||
def test_missing_constants_rake_app
|
||||
args = []
|
||||
defmock(:const_warning) {|a| args << a}
|
||||
Object.const_missing(:RakeApp)
|
||||
assert_equal([:RakeApp], args)
|
||||
end
|
||||
|
||||
def test_missing_other_constant
|
||||
assert_raise(NameError) do Object.const_missing(:Xyz) end
|
||||
end
|
||||
end
|
|
@ -0,0 +1,68 @@
|
|||
require 'test/unit'
|
||||
require_relative 'in_environment'
|
||||
|
||||
require 'rake'
|
||||
|
||||
class TestWin32 < Test::Unit::TestCase
|
||||
include InEnvironment
|
||||
|
||||
Win32 = Rake::Win32
|
||||
|
||||
def test_win32_system_dir_uses_home_if_defined
|
||||
in_environment('RAKE_SYSTEM' => nil, 'HOME' => 'C:\\HP') do
|
||||
assert_equal "C:/HP/Rake", Win32.win32_system_dir
|
||||
end
|
||||
end
|
||||
|
||||
def test_win32_system_dir_uses_homedrive_homepath_when_no_home_defined
|
||||
in_environment(
|
||||
'RAKE_SYSTEM' => nil,
|
||||
'HOME' => nil,
|
||||
'HOMEDRIVE' => "C:",
|
||||
'HOMEPATH' => "\\HP"
|
||||
) do
|
||||
assert_equal "C:/HP/Rake", Win32.win32_system_dir
|
||||
end
|
||||
end
|
||||
|
||||
def test_win32_system_dir_uses_appdata_when_no_home_or_home_combo
|
||||
in_environment(
|
||||
'RAKE_SYSTEM' => nil,
|
||||
'HOME' => nil,
|
||||
'HOMEDRIVE' => nil,
|
||||
'HOMEPATH' => nil,
|
||||
'APPDATA' => "C:\\Documents and Settings\\HP\\Application Data"
|
||||
) do
|
||||
assert_equal "C:/Documents and Settings/HP/Application Data/Rake", Win32.win32_system_dir
|
||||
end
|
||||
end
|
||||
|
||||
def test_win32_system_dir_fallback_to_userprofile_otherwise
|
||||
in_environment(
|
||||
'RAKE_SYSTEM' => nil,
|
||||
'HOME' => nil,
|
||||
'HOMEDRIVE' => nil,
|
||||
'HOMEPATH' => nil,
|
||||
'APPDATA' => nil,
|
||||
'USERPROFILE' => "C:\\Documents and Settings\\HP"
|
||||
) do
|
||||
assert_equal "C:/Documents and Settings/HP/Rake", Win32.win32_system_dir
|
||||
end
|
||||
end
|
||||
|
||||
def test_win32_system_dir_nil_of_no_env_vars
|
||||
in_environment(
|
||||
'RAKE_SYSTEM' => nil,
|
||||
'HOME' => nil,
|
||||
'HOMEDRIVE' => nil,
|
||||
"HOMEPATH" => nil,
|
||||
'APPDATA' => nil,
|
||||
"USERPROFILE" => nil
|
||||
) do
|
||||
assert_raise(Rake::Win32::Win32HomeError) do
|
||||
Win32.win32_system_dir
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
end if Rake::Win32.windows?
|
Загрузка…
Ссылка в новой задаче