Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also compare across forks.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also compare across forks.
base fork: macarthy/mirror-quartz-jruby-plugin
base: master
...
head fork: spraints/mirror-quartz-jruby-plugin
compare: master
Checking mergeability… Don’t worry, you can still create the pull request.
  • 2 commits
  • 9 files changed
  • 0 commit comments
  • 1 contributor
View
46 Rakefile
@@ -15,62 +15,24 @@ task :compile do
src_dir = 'src/java'
dest_dir = CLASSES_DIR
- Dir::mkdir(dest_dir) unless File::exist?(dest_dir)
+ FileUtils::mkdir_p(dest_dir) unless File::exist?(dest_dir)
javac(src_dir, dest_dir)
end
def jar(src_dir, target)
- `jar cf #{target} -C #{src_dir} .`
+ sh 'jar', 'cf', target, '-C', src_dir, '.'
end
def build_class_path
- %W(
- dependencies/goldspike-1.4-SNAPSHOT.jar
- dependencies/jruby-complete-1.0.1.jar
- dependencies/servlet-api.jar
- dependencies/quartz.jar
- dependencies/commons-pool-1.3.jar
- ).map{|f| File.expand_path f}.join(':')
+ FileList['dependencies/*.jar'].map{|f| File.expand_path(f)}.join(';')
end
def javac(src_dir, dest_dir)
- #java_files = get_out_of_date_files(src_dir, dest_dir)
java_files = FileList["#{src_dir}/**/*.java"]
unless java_files.empty?
- print "compiling #{java_files.size} java file(s)..."
-
- args = [ '-cp', build_class_path, '-d', dest_dir, *java_files ]
-
- buf = java.io.StringWriter.new
- if com.sun.tools.javac.Main.compile(to_java_array(java.lang.String, args),
- java.io.PrintWriter.new(buf)) != 0
- print "FAILED\n\n"
- print buf.to_s
- print "\n"
- fail 'Compile failed'
- end
- print "done\n"
+ sh 'javac', '-target', '1.5', '-cp', build_class_path, '-d', dest_dir, *java_files
end
end
-def get_out_of_date_files(src_dir, dest_dir)
- java_files = []
- FileList["#{src_dir}/**/*.java"].each do |java_file|
- class_file = dest_dir + java_file[src_dir.length, java_file.length - src_dir.length - '.java'.length] + '.class'
-
- # todo: figure out why File.ctime doesn't work
- unless File.exist?(class_file) && java.io.File.new(class_file).lastModified > java.io.File.new(java_file).lastModified
- java_files << java_file
- end
- end
- return java_files
-end
-
-def to_java_array(element_type, ruby_array)
- java_array = java.lang.reflect.Array.newInstance(element_type, ruby_array.size)
- ruby_array.each_index { |i| java_array[i] = ruby_array[i] }
- return java_array
-end
-
View
BIN  dependencies/goldspike-1.4-SNAPSHOT.jar
Binary file not shown
View
BIN  dependencies/jruby-complete-1.0.1.jar
Binary file not shown
View
BIN  dependencies/jruby-complete-1.1.5.jar
Binary file not shown
View
BIN  dependencies/jruby-rack-0.9.2.jar
Binary file not shown
View
BIN  dependencies/servlet-api.jar
Binary file not shown
View
BIN  lib/quartz-rails.jar
Binary file not shown
View
108 src/java/org/jruby/webapp/quartz/QuartzContextListener.java
@@ -0,0 +1,108 @@
+package org.jruby.webapp.quartz;
+
+import org.jruby.Ruby;
+
+import java.util.Enumeration;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.Iterator;
+
+import javax.servlet.ServletContextListener;
+import javax.servlet.ServletContextEvent;
+import javax.servlet.ServletContext;
+import javax.servlet.ServletException;
+
+import org.quartz.impl.StdSchedulerFactory;
+import org.quartz.Scheduler;
+import org.quartz.Trigger;
+import org.quartz.CronTrigger;
+import org.quartz.JobDetail;
+import org.quartz.SchedulerContext;
+import org.quartz.xml.JobSchedulingDataProcessor;
+
+/**
+ * Initializer for the Quartz-Scheduler and configured jobs
+ */
+public class QuartzContextListener implements ServletContextListener {
+
+ private String command;
+ private int waitBeforeStartSeconds = 30; // wait 30 seconds
+ private boolean stop = false; // wait 30 seconds
+ private Thread thread = null;
+ private int interval = 60;
+ private int minIdle = 0;
+ private Scheduler scheduler;
+ private SchedulerContext schedulerContext;
+ private ServletContext context;
+
+ /**
+ * Initializes the scheduler, and schedules all configured jobs.
+ */
+ public void contextInitialized(ServletContextEvent event) {
+ context = event.getServletContext();
+ context.log("intializing Quartz Scheduler...");
+ try {
+ scheduler = StdSchedulerFactory.getDefaultScheduler();
+ schedulerContext = scheduler.getContext();
+ schedulerContext.put("servlet_context", context);
+ Map commands = getCommands(context);
+ for (Iterator entries = commands.entrySet().iterator(); entries.hasNext(); ) {
+ Map.Entry entry = (Map.Entry) entries.next();
+ scheduleCronJob((String) entry.getKey(), (String[]) entry.getValue());
+ }
+ scheduler.start();
+ context.log("Finished initializing quartz scheduler");
+ } catch (Exception e) {
+ context.log("Quartz Scheduler failed to initialize: " + e.toString());
+ }
+ }
+
+ /**
+ * shuts down the scheduler
+ */
+ public void contextDestroyed(ServletContextEvent event) {
+ try {
+ if (scheduler != null) scheduler.shutdown();
+ } catch (Exception e) {
+ context.log("Quartz Scheduler failed to shut down cleanly: " + e.toString());
+ e.printStackTrace();
+ }
+ context.log("Quartz Scheduler successful shut down.");
+ }
+
+ /**
+ * Parses command names and cron patterns from the context's init parameters
+ * InitParameters have to follow these conventions in order to be recognized:
+ *
+ * yourJobNameCommand - piece of Ruby code to execute
+ * yourJobNameCronPattern - cron pattern saying when to execute this job.
+ */
+ protected Map getCommands(ServletContext context) {
+
+ Map commands = new HashMap();
+ for (Enumeration initParams = context.getInitParameterNames(); initParams.hasMoreElements(); ) {
+ String key = (String) initParams.nextElement();
+ if (key.endsWith("Command")) {
+ String command = context.getInitParameter(key);
+ key = key.replaceFirst("Command$", "");
+ String cron = context.getInitParameter(key + "CronPattern");
+ if (cron != null) {
+ commands.put(key, new String[] { command, cron });
+ }
+ }
+ }
+ return commands;
+ }
+
+ /**
+ * schedules a single job
+ */
+ protected void scheduleCronJob(String name, String[] commandAndCronPattern) throws Exception {
+ JobDetail job = new JobDetail(name+"Job", "railsQuartz",
+ org.jruby.webapp.quartz.RailsJob.class);
+ job.getJobDataMap().put("command", commandAndCronPattern[0]);
+ Trigger trigger = new CronTrigger(name+"Trigger", "railsQuartz", commandAndCronPattern[1]);
+ scheduler.scheduleJob(job, trigger);
+ }
+
+}
View
75 src/java/org/jruby/webapp/quartz/RailsJob.java
@@ -0,0 +1,75 @@
+package org.jruby.webapp.quartz;
+
+import java.io.IOException;
+
+import javax.servlet.ServletConfig;
+import javax.servlet.ServletException;
+import javax.servlet.ServletContext;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import org.jruby.Ruby;
+import org.jruby.rack.RackServletContextListener;
+import org.jruby.rack.RackApplicationFactory;
+import org.jruby.rack.RackApplication;
+
+import org.quartz.Job;
+import org.quartz.JobDataMap;
+import org.quartz.JobExecutionException;
+import org.quartz.JobExecutionContext;
+
+import org.apache.commons.pool.ObjectPool;
+
+/**
+ * Quartz job for running arbitrary Ruby code inside a Rails environment.
+ *
+ * JRuby runtimes are retrieved from the runtime pool created by Goldspike's
+ * RailsContextListener.
+ */
+public class RailsJob implements Job {
+
+ /**
+ * inspired by Goldspike's RailsServlet#service
+ */
+ public void execute(JobExecutionContext context)
+ throws JobExecutionException
+ {
+ try {
+ ServletContext ctx = getServletContext(context);
+ JobDataMap data = context.getJobDetail().getJobDataMap();
+ String command = data.getString("command");
+ ctx.log("starting: " + command);
+
+ RackApplicationFactory rackFactory = (RackApplicationFactory) ctx.getAttribute(RackServletContextListener.FACTORY_KEY);
+ RackApplication rackApp = null;
+ try {
+ rackApp = rackFactory.getApplication();
+ rackApp.getRuntime().evalScriptlet(command);
+ ctx.log("finished: " + command);
+ } catch (Exception e) {
+ ctx.log("Could not execute: " + command, e);
+ } finally {
+ if(rackApp != null) rackFactory.finishedWithApplication(rackApp);
+ }
+ } catch (Exception e) {
+ throw new JobExecutionException(e);
+ }
+ }
+
+ protected RackApplicationFactory getApplicationFactory(ServletContext ctx)
+ throws ServletException
+ {
+ RackApplicationFactory runtimePool =
+ (RackApplicationFactory)ctx.getAttribute(RackServletContextListener.FACTORY_KEY);
+ if (runtimePool == null) {
+ throw new ServletException("No application factory is available, please check RackServletContextListener");
+ }
+ return runtimePool;
+ }
+
+ protected ServletContext getServletContext(JobExecutionContext ctx)
+ throws org.quartz.SchedulerException
+ {
+ return (ServletContext) ctx.getScheduler().getContext().get("servlet_context");
+ }
+}

No commit comments for this range

Something went wrong with that request. Please try again.