Buildr 0.17.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,78 @@
1
+ require "pathname"
2
+
3
+ module Buildr
4
+
5
+ # Global task "eclipse" generates artifacts for all projects.
6
+ desc "Generate Eclipse artifacts for all projects"
7
+ Project.local_task task("eclipse")
8
+
9
+ Project.on_define do |project|
10
+ eclipse = project.recursive_task("eclipse")
11
+
12
+ project.enhance do |project|
13
+
14
+ # We need paths relative to the top project's base directory.
15
+ root_path = lambda { |p| f = lambda { |p| p.parent ? f[p.parent] : p.base_dir } ; f[p] }[project]
16
+ # We're guessing the Rakefile is there, but keep in mind it might not exist
17
+ # (most test cases don't create it).
18
+ rakefile = File.expand_path(Rake.application.rakefile, root_path) if Rake.application.rakefile
19
+
20
+ # Only for projects that are Eclipse packagable.
21
+ if project.packages.detect { |pkg| pkg.type =~ /(jar)|(war)|(rar)|(mar)|(aar)/ }
22
+ eclipse.enhance [ file(project.path_to(".classpath")), file(project.path_to(".project")) ]
23
+
24
+ # The only thing we need to look for is a change in the Rakefile.
25
+ file(project.path_to(".classpath")=>rakefile) do |task|
26
+ puts "Writing #{task.name}" if verbose
27
+
28
+ # Find a path relative to the project's root directory.
29
+ relative = lambda { |path| Pathname.new(path).relative_path_from(Pathname.new(project.path_to)).to_s }
30
+
31
+ File.open(task.name, "w") do |file|
32
+ xml = Builder::XmlMarkup.new(:target=>file, :indent=>2)
33
+ xml.classpath do
34
+ # Internal: projects that create artifacts we find on the classpath.
35
+ # External: other artifacts, typically from the local repository.
36
+ internal, external = project.compile.classpath.map(&:to_s).
37
+ map { |path| projects.detect { |prj| prj.packages.detect { |pkg| pkg.to_s == path } } || path }.
38
+ partition { |path| path.is_a?(Project) }
39
+ # Collect all the classpaths, key is the kind, value is
40
+ # string or array (or anything responding to to_a).
41
+ { :src => project.compile.sources.map { |src| relative[src] },
42
+ :output => relative[project.path_to(:java_target_dir)],
43
+ :con => "org.eclipse.jdt.launching.JRE_CONTAINER",
44
+ :lib => external.map(&:to_s)
45
+ }.each do |kind, paths|
46
+ paths.to_a.each { |path| xml.classpathentry :kind=>kind, :path=>path }
47
+ end
48
+ internal.map(&:name).uniq.each do |prj_name|
49
+ xml.classpathentry :kind=>"src", :combineaccessrules=>"false", :path=>"/#{prj_name}"
50
+ end
51
+ end
52
+ end
53
+ end
54
+
55
+ # The only thing we need to look for is a change in the Rakefile.
56
+ file(project.path_to(".project")=>rakefile) do |task|
57
+ puts "Writing #{task.name}" if verbose
58
+ File.open(task.name, "w") do |file|
59
+ xml = Builder::XmlMarkup.new(:target=>file, :indent=>2)
60
+ xml.projectDescription do
61
+ xml.name project.name
62
+ xml.projects
63
+ xml.buildSpec do
64
+ xml.buildCommand do
65
+ xml.name "org.eclipse.jdt.core.javabuilder"
66
+ end
67
+ end
68
+ xml.natures do
69
+ xml.nature "org.eclipse.jdt.core.javanature"
70
+ end
71
+ end
72
+ end
73
+ end
74
+ end
75
+ end
76
+ end
77
+
78
+ end # module Buildr
@@ -0,0 +1,114 @@
1
+ module Buildr
2
+ module Java
3
+
4
+ JAVA_OPTIONS = [ :verbose, :noop, :cp, :classpath, :name, :java_args ]
5
+
6
+ def self.java(*args)
7
+ options = Hash === args.last ? args.pop : {}
8
+ options[:verbose] ||= Rake.application.options.trace || false
9
+ fu_check_options options, *JAVA_OPTIONS
10
+
11
+ name = options[:name] || "java #{args.first}"
12
+ cmd_args = []
13
+ classpath = classpath_from(options)
14
+ cmd_args << "-cp" << classpath.join(File::PATH_SEPARATOR) unless classpath.empty?
15
+ cmd_args += options[:java_args].flatten if options[:java_args]
16
+ cmd_args += args.flatten.compact
17
+ cmd_args << { :verbose=>options[:verbose] }
18
+ unless options[:noop]
19
+ puts "Running #{name}" if verbose
20
+ sh(path_to_bin("java"), *cmd_args) { |ok, res| fail "Failed to execute #{name}, see errors above" unless ok }
21
+ end
22
+ end
23
+
24
+ def self.apt(*args)
25
+ options = Hash === args.last ? args.pop : {}
26
+ options[:verbose] ||= Rake.application.options.trace || false
27
+ fu_check_options options, :verbose, :noop, :compile, :source, :output, :cp, :classpath
28
+
29
+ files = args.collect { |arg| File.directory?(arg) ? FileList[File.join(arg, "**", "*.java")] : arg }.flatten
30
+ args = [ options[:verbose] ? "-verbose" : "-nowarn" ]
31
+ if options[:compile]
32
+ args << "-d" << options[:output]
33
+ else
34
+ args << "-nocompile" << "-s" << options[:output]
35
+ end
36
+ args << "-source" << options[:source] if options[:source]
37
+ classpath = classpath_from(options)
38
+ args << "-cp" << classpath.join(File::PATH_SEPARATOR) unless classpath.empty?
39
+ args += files
40
+ args << { :verbose=>options[:verbose] }
41
+ unless options[:noop]
42
+ puts "Running apt" if verbose
43
+ sh(path_to_bin("apt"), *args) { |ok, res| fail "Failed to execute apt, see errors above" unless ok }
44
+ end
45
+ end
46
+
47
+ class AptTask < Rake::FileTask
48
+
49
+ def initialize(*args)
50
+ super
51
+ enhance do |task|
52
+ Java.apt *task.prerequisites + [options.merge(:output=>task.name)]
53
+ end
54
+ end
55
+
56
+ def options()
57
+ @options ||= {}
58
+ end
59
+
60
+ def using(options)
61
+ self.options.merge!(options)
62
+ self
63
+ end
64
+
65
+ end
66
+
67
+ def self.apt_task(args)
68
+ output = args.keys.first
69
+ files = args.values.first.collect { |f| File.directory?(f) ? FileList[f + "/**/*.java"] : f }.flatten
70
+ AptTask.define_task(output=>files)
71
+ end
72
+
73
+ def self.javac(*args)
74
+ options = Hash === args.last ? args.pop : {}
75
+ options[:verbose] ||= Rake.application.options.trace || false
76
+ fu_check_options options, :verbose, :noop, :cp, :classpath, :sourcepath, :output, :javac_args, :name
77
+
78
+ files = args.flatten.each { |f| f.invoke if f.respond_to?(:invoke) }.map(&:to_s).
79
+ collect { |arg| File.directory?(arg) ? FileList[File.join(arg, "**", "*.java")] : arg }.flatten
80
+ name = options[:name] || Dir.pwd
81
+
82
+ cmd_args = []
83
+ classpath = classpath_from(options)
84
+ #classpath += options[:output] if options[:output]
85
+ cmd_args << "-cp" << classpath.join(File::PATH_SEPARATOR) unless classpath.empty?
86
+ cmd_args << "-sourcepath" << options[:sourcepath].join(File::PATH_SEPARATOR) if options[:sourcepath]
87
+ cmd_args << "-d" << options[:output] if options[:output]
88
+ cmd_args += options[:javac_args].flatten if options[:javac_args]
89
+ cmd_args += files
90
+ cmd_args << { :verbose=>options[:verbose] }
91
+ unless options[:noop] || files.empty?
92
+ puts "Compiling #{files.size} source files in #{name}" if verbose
93
+ sh(path_to_bin("javac"), *cmd_args) { |ok, res| fail "Failed to compile, see errors above" unless ok }
94
+ end
95
+ end
96
+
97
+ protected
98
+
99
+ def self.path_to_bin(name)
100
+ ENV["JAVA_HOME"] ? File.join(ENV["JAVA_HOME"], "bin", name) : name
101
+ end
102
+
103
+ def self.classpath_from(options)
104
+ classpath = (options[:classpath] || []).collect | (options[:cp] || []).collect
105
+ artifacts(classpath).each { |t| t.invoke if t.respond_to?(:invoke) }.map(&:to_s)
106
+ end
107
+
108
+ end
109
+
110
+ def java(*args)
111
+ Java.java(*args)
112
+ end
113
+
114
+ end
@@ -0,0 +1,88 @@
1
+ module Buildr
2
+
3
+ module JavaCC
4
+
5
+ JAVACC = "net.java.dev.javacc:javacc:jar:4.0"
6
+ JJTREE = "net.java.dev.javacc:javacc:jar:4.0"
7
+
8
+ def self.javacc(*args)
9
+ options = Hash === args.last ? args.pop.clone : {}
10
+ options[:verbose] ||= Rake.application.options.trace || false
11
+ fu_check_options options, *Java::JAVA_OPTIONS + [:output]
12
+
13
+ (options[:classpath] ||= []) << JAVACC
14
+ java_args = ["javacc"]
15
+ java_args << "-OUTPUT_DIRECTORY=#{options[:output]}" if options[:output]
16
+ java_args += args.collect { |f| File.directory?(f) ? FileList[f + "/**/*.jj"] : f }.flatten
17
+ java_args << options.reject { |k, v| !Java::JAVA_OPTIONS.include?(k) }
18
+ Java.java(*java_args)
19
+ end
20
+
21
+ class JavaCCTask < Rake::FileTask
22
+
23
+ def initialize(*args)
24
+ super
25
+ enhance do |task|
26
+ JavaCC.javacc *(task.prerequisites + [task.options.merge(:output=>task.name)])
27
+ end
28
+ end
29
+
30
+ def options()
31
+ @options ||= {}
32
+ end
33
+
34
+ def using(options)
35
+ self.options.merge!(options)
36
+ self
37
+ end
38
+
39
+ end
40
+
41
+ def self.javacc_task(args)
42
+ output = args.keys.first
43
+ files = args.values.first.collect { |f| File.directory?(f) ? FileList[f + "/**/*.jj"] : f }.flatten
44
+ JavaCCTask.define_task(output=>files)
45
+ end
46
+
47
+ def self.jjtree(*args)
48
+ options = Hash === args.last ? args.pop.clone : {}
49
+ options[:verbose] ||= Rake.application.options.trace || false
50
+ fu_check_options options, *Java::JAVA_OPTIONS + [:output, :build_node_files]
51
+
52
+ (options[:classpath] ||= []) << JJTREE
53
+ java_args = ["jjtree"]
54
+ java_args << "-OUTPUT_DIRECTORY=#{options[:output]}" if options[:output]
55
+ java_args << "-BUILD_NODE_FILES=#{options[:build_node_files]}" if options.has_key?(:build_node_files)
56
+ java_args += args.collect { |f| File.directory?(f) ? FileList[f + "/**/*.jjt"] : f }.flatten
57
+ java_args << options.reject { |k, v| !Java::JAVA_OPTIONS.include?(k) }
58
+ Java.java(*java_args)
59
+ end
60
+
61
+ class JJTreeTask < Rake::FileTask
62
+
63
+ def initialize(*args)
64
+ super
65
+ enhance do |task|
66
+ JavaCC.jjtree *(task.prerequisites + [task.options.merge(:output=>task.name)])
67
+ end
68
+ end
69
+
70
+ def options()
71
+ @options ||= {}
72
+ end
73
+
74
+ def using(options)
75
+ self.options.merge!(options)
76
+ self
77
+ end
78
+
79
+ end
80
+
81
+ def self.jjtree_task(args)
82
+ output = args.keys.first
83
+ files = args.values.first.collect { |f| File.directory?(f) ? FileList[f + "/**/*.jjt"] : f }.flatten
84
+ JJTreeTask.define_task(output=>files)
85
+ end
86
+
87
+ end
88
+ end
@@ -0,0 +1,118 @@
1
+ require 'net/http'
2
+
3
+ module Buildr
4
+
5
+ module Jetty
6
+
7
+ VERSION = "6.1.1"
8
+
9
+ REQUIRES = [ "org.mortbay.jetty:jetty:jar:#{VERSION}",
10
+ "org.mortbay.jetty:jetty-util:jar:#{VERSION}",
11
+ "org.mortbay.jetty:servlet-api-2.5:jar:#{VERSION}",
12
+ "log4j:log4j:jar:1.2.13",
13
+ "commons-logging:commons-logging:jar:1.1"
14
+ ]
15
+
16
+ OPTIONS = [ :classpath, :war_path, :context_path, :noop, :base_url, :process_alias ]
17
+
18
+ def self.bounce(options)
19
+ fu_check_options options, *OPTIONS
20
+ options[:classpath] ||= []
21
+
22
+ begin
23
+ verbose { puts "Bouncing webapp #{options[:war_path]}" }
24
+ res = jetty_call('/bounce', :post, options)
25
+ verbose { puts "done." }
26
+ rescue Errno::ECONNREFUSED => e
27
+ puts "Web server not found, spawning it."
28
+ runtool options.merge(:class=>"JettyWrapper",
29
+ :args=>[ options[:war_path], options[:context_path] ],
30
+ :classpath=>options[:classpath] + ['buildr/lib/java/jetty'])
31
+ end
32
+
33
+ case res
34
+ when Net::HTTPNotFound
35
+ fail "A web server seems to be already running without Buildr deployment hooks."
36
+ when Net::HTTPInternalServerError
37
+ fail "Server error occured when redeploying the WAR, see the web server logs."
38
+ end
39
+ end
40
+
41
+ def self.jetty_call(rel_url, get_post, options)
42
+ base_url = URI.parse((options[:base_url] || 'http://localhost:8080/buildr') + rel_url)
43
+ req = get_post == :post ? Net::HTTP::Post.new(base_url.path) : Net::HTTP::Get.new(base_url.path)
44
+ res = Net::HTTP.start(base_url.host, base_url.port) {|http| http.request(req) }
45
+ end
46
+
47
+ protected
48
+
49
+ def self.runtool(options)
50
+ classpath = REQUIRES + (options[:classpath] || []).collect | (options[:cp] || []).collect
51
+ classpath = artifacts(classpath).each { |t| t.invoke if t.respond_to?(:invoke) }.map(&:to_s)
52
+ cmd_args = ["-cp", classpath.join(File::PATH_SEPARATOR)]
53
+ cmd_args << options[:class]
54
+ cmd_args += options[:args]
55
+ unless options[:noop]
56
+ verbose { puts "Starting web server and mounting webapp #{options[:war_path]}" }
57
+ if fork.nil?
58
+ STDOUT.reopen File.new("stdout.log", "w")
59
+ STDERR.reopen File.new("stderr.log", "w")
60
+ exec(([Java.path_to_bin("java")] + cmd_args).join(' '))
61
+ end
62
+ end
63
+ end
64
+
65
+ class JettyTask < Rake::Task
66
+ def initialize(*args)
67
+ super
68
+ enhance do |task|
69
+ Jetty.bounce task.options
70
+ end
71
+ end
72
+
73
+ def options()
74
+ @options ||= {}
75
+ end
76
+
77
+ def using(options)
78
+ self.options.merge!(options)
79
+ self
80
+ end
81
+ end
82
+ end
83
+
84
+ class Project
85
+ def webserve(&block)
86
+ task "jetty:shutdown" do
87
+ begin
88
+ res = Jetty.jetty_call('/stop', :put, @webserve_task.options)
89
+ verbose { puts "Response #{res}" }
90
+ rescue Exception => e
91
+ if (e.class == Errno::ECONNREFUSED)
92
+ puts "Jetty server couldn't be contacted, nothing done."
93
+ elsif (e.class == EOFError)
94
+ puts "Shutdown successful."
95
+ else
96
+ puts "Unexpected error: #{e.class}"
97
+ end
98
+ end
99
+ end
100
+ returning(@webserve_task ||= Jetty::JettyTask.define_task("jetty:bounce")) do |task|
101
+ task.enhance &block if block
102
+ end
103
+ end
104
+ end
105
+
106
+ end
107
+
108
+ module FileUtils
109
+ class Entry_
110
+ alias original_cp copy
111
+ def copy(dest)
112
+ unless path['.svn']
113
+ original_cp(dest)
114
+ end
115
+ end
116
+ end
117
+ end
118
+
@@ -0,0 +1,107 @@
1
+ import org.mortbay.jetty.Server;
2
+ import org.mortbay.jetty.Request;
3
+ import org.mortbay.jetty.Handler;
4
+ import org.mortbay.jetty.handler.AbstractHandler;
5
+ import org.mortbay.jetty.handler.ContextHandler;
6
+ import org.mortbay.jetty.handler.ContextHandlerCollection;
7
+ import org.mortbay.jetty.webapp.WebAppContext;
8
+
9
+ import javax.servlet.http.HttpServletRequest;
10
+ import javax.servlet.http.HttpServletResponse;
11
+ import javax.servlet.ServletException;
12
+ import java.io.IOException;
13
+
14
+ /**
15
+ * @author Matthieu Riou <mriou at apache dot org>
16
+ */
17
+ public class JettyWrapper {
18
+
19
+ private Server _server;
20
+ private WebAppContext _webAppHandler;
21
+ private ContextHandlerCollection _handlerColl;
22
+ private String _webAppDir;
23
+ private String _contextPath;
24
+
25
+ public JettyWrapper(String webAppDir, String contextPath) {
26
+ _server = new Server(8080);
27
+ _webAppDir = webAppDir;
28
+ _contextPath = contextPath;
29
+
30
+ // Adding handler for the war to deploy
31
+ _webAppHandler = new WebAppContext(_webAppDir, _contextPath);
32
+ _webAppHandler.setConfigurationClasses(new String[] {
33
+ "org.mortbay.jetty.webapp.WebInfConfiguration",
34
+ "org.mortbay.jetty.webapp.WebXmlConfiguration"});
35
+
36
+ // Adding the buildr handler to control our server lifecycle
37
+ ContextHandler context = new ContextHandler();
38
+ context.setContextPath("/buildr");
39
+ Handler handler = new BuildrHandler();
40
+ context.setHandler(handler);
41
+
42
+ _handlerColl = new ContextHandlerCollection();
43
+ _handlerColl.setHandlers(new Handler[] {_webAppHandler, context});
44
+
45
+ _server.addHandler(_handlerColl);
46
+ }
47
+
48
+ public void start() {
49
+ try {
50
+ _server.start();
51
+ _server.join();
52
+ } catch (Exception e) {
53
+ e.printStackTrace();
54
+ }
55
+ }
56
+
57
+ public static void main(String[] args) {
58
+ if (args.length != 2) {
59
+ System.out.println("Please provide the webapp directory and the context path.");
60
+ }
61
+ String webAppDir = args[0];
62
+ String contextPath = args[1];
63
+ JettyWrapper jetwrap = new JettyWrapper(webAppDir, contextPath);
64
+ jetwrap.start();
65
+ }
66
+
67
+ private class BuildrHandler extends AbstractHandler {
68
+
69
+ public void handle(String string, HttpServletRequest request,
70
+ HttpServletResponse response, int i) throws IOException, ServletException {
71
+ response.setContentType("text/html");
72
+ if (request.getPathInfo().equals("/bounce")) {
73
+ try {
74
+ _webAppHandler.stop();
75
+ _handlerColl.removeHandler(_webAppHandler);
76
+ _webAppHandler = new WebAppContext(_webAppDir, _contextPath);
77
+ _webAppHandler.setConfigurationClasses(new String[] {
78
+ "org.mortbay.jetty.webapp.WebInfConfiguration",
79
+ "org.mortbay.jetty.webapp.WebXmlConfiguration"});
80
+ _handlerColl.addHandler(_webAppHandler);
81
+ _webAppHandler.start();
82
+ } catch (Throwable e) {
83
+ e.printStackTrace();
84
+ response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
85
+ ((Request)request).setHandled(true);
86
+ return;
87
+ }
88
+ } else if (request.getPathInfo().equals("/stop")) {
89
+ try {
90
+ _server.stop();
91
+ _server.destroy();
92
+ // Brute force
93
+ System.exit(0);
94
+ } catch (Exception e) {
95
+ e.printStackTrace();
96
+ }
97
+ } else if (request.getPathInfo().equals("/war")) {
98
+ response.getWriter().println(_webAppHandler.getTempDirectory());
99
+ ((Request)request).setHandled(true);
100
+ return;
101
+ }
102
+ response.getWriter().println("OK " + request.getPathInfo());
103
+ ((Request)request).setHandled(true);
104
+ }
105
+
106
+ }
107
+ }