com.sun.grizzly.jruby.rack.RackApplicationChooser Maven / Gradle / Ivy
package com.sun.grizzly.jruby.rack;
import java.io.File;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.logging.Logger;
import com.sun.grizzly.http.SelectorThread;
import com.sun.grizzly.jruby.RailsAdapter;
/**
* @author Jacob Kessler
* Attempts to determine the RackApplicationFactory most suited to handle
* the given application directory
*/
public class RackApplicationChooser {
static RackApplicationFactory myFactory;
public static RackAdapter getFactory(String appPath, Logger theLog, RailsAdapter adapter) {
String appType = System.getProperty("jruby.applicationType");
if (appType != null) {
// User has specified a file to run. For now, assume that it is single-threaded
myFactory = new GenericApplicationFactory(appType, theLog, appPath);
return new SingleThreadedRackAdapter(myFactory, adapter);
}
// Sinatra may not have a rake file. Check if we were given a .rb file
if (appPath.endsWith(".rb")) {
File appFile = new File(appPath);
String app = inhale(appFile, theLog);
if (app.contains("require 'sinatra'")) {
myFactory = new SinatraApplicationFactory(theLog, appPath);
theLog.info("Detected Sinatra application");
// Sinatra is thread-safe
return new MultiThreadedRackAdapter(myFactory, adapter);
}
}
theLog.fine("Path is " + appPath + ", trying to open " + appPath+"Rakefile");
File rakeFile = new File(appPath + "Rakefile");
if (rakeFile.exists()) {
String rake = inhale(rakeFile, theLog);
// rails
if (rake.contains("require 'tasks/rails'")) {
myFactory = new RailsApplicationFactory(theLog, appPath);
theLog.info("Detected Rails application");
// Check rails version. This is really, really ugly, but will have to do until we have a better way
String environment = inhale(new File(appPath+"/config/environment.rb"), theLog);
int start = environment.indexOf("RAILS_GEM_VERSION");
start = start + "RAILS_GEM_VERSION".length(); // move to the end of the declaration
int firstDot = environment.indexOf(".",start);
int secondDot = environment.indexOf(".", firstDot + 1);
int major = Integer.parseInt(environment.substring(firstDot-1, firstDot));
int minor = Integer.parseInt(environment.substring(firstDot+1, secondDot));
theLog.info("Rails Version: " + major + "." + minor);
boolean multithreaded = false;
if (major > 2) {
multithreaded = true;
} else if (major == 2 && minor >= 2) {
multithreaded = true;
}
if (multithreaded) {
return new MultiThreadedRackAdapter(myFactory, adapter);
} else {
return new SingleThreadedRackAdapter(myFactory, adapter);
}
}
// merb
if (rake.contains("require 'merb-core'")) {
myFactory = new MerbApplicationFactory(theLog, appPath);
theLog.info("Detected merb application");
// Merb is thread-safe
return new MultiThreadedRackAdapter(myFactory, adapter);
}
// Other frameworks go here
} else {
theLog.fine("Rake file not found, checking for non-rake frameworks");
// Check for .rb files
File appDir = new File(appPath);
if (appDir.isDirectory()) {
File[] files = appDir.listFiles();
for (File file : files) {
if (file.getAbsolutePath().endsWith(".rb")) {
// Check for require. This is expensive and we don't want to.
String rb = inhale(file, theLog);
if (rb.contains("require 'sinatra'") || rb.contains("require \"sinatra\"")) {
myFactory = new SinatraApplicationFactory(theLog, appPath);
// Sinatra is still thread-safe
return new MultiThreadedRackAdapter(myFactory, adapter);
}
}
}
}
}
// No framework found
SelectorThread.logger().severe("Framework autodetection failed! Please set -Djruby.applicationType to a script that will start your framework");
throw new IllegalStateException("No framework to start!");
}
public static RackApplicationFactory getFactory() {
return myFactory;
}
private static String inhale (File f, Logger theLog) {
String app = "";
if (f.exists()) {
try {
BufferedReader in = new BufferedReader(new FileReader(f));
String s;
while ((s = in.readLine()) != null) {
// read the file
app = app + s;
}
} catch (IOException e) {
theLog.severe("IO Exception determining framework for " + f.getAbsolutePath() + ": " + e);
}
}
return app;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy