     (binding [leiningen.new.templates/*dir* dir]
       (->> [file-name (render file-name data)]
            (leiningen.new.templates/->files data)))))
+
+(defn stale-java-classes
+  [dirs compile-path]
+  (for [dir dirs
+        source (filter #(-> % (.getName) (.endsWith ".java"))
+                       (file-seq (java.io/file dir)))
+        :let [rel-source (.substring (.getPath source) (inc (count dir)))
+              rel-compiled (.replaceFirst rel-source "\\.java$" ".class")
+              compiled (java.io/file compile-path rel-compiled)]
+        :when (>= (.lastModified source) (.lastModified compiled))]
+    (.getPath compiled)))
+
+(defn create-class-map
+  [classes paths]
+  (reduce (fn [class-map path]
+            (let [modified-path (clojure.string/replace path #"[/\\]" ".")
+                  class-symbol (-> #(.contains modified-path (.name %))
+                                   (filter classes)
+                                   first)]
+              (if class-symbol
+                (doto class-map
+                  (.put class-symbol (read-file path)))
+                class-map)))
+          (java.util.HashMap.)
+          paths))
 
 ; check project types
 

                       .attachingConnectors
                       (filter #(= (.name (.transport %)) "dt_socket"))
                       first)]
     (let [prm (.defaultArguments conn)]
       (.setValue (.get prm "port") debug-port)
       (.setValue (.get prm "hostname") "127.0.0.1")
       (when-let [vm (try (.attach conn prm) (catch Exception _))]
         (leiningen.javac/javac project-map)))))

; high-level commands


      (.join pump-out)
      (.join pump-err)
      (.waitFor @process))))

(defn start-process-indirectly
  [process path & args]
