Invoke Javac At Runtime

You can access javac programmatically, that is compile Java source code at runtime from a running program! The javac compiler is made available via the tools.jar in the lib directory from the JDK. To get started with the following example you will need to add the tools.jar to your project’s classpath. You can find tools.jar in the lib directory of your JDK installation path.

One you have tools.jar in you classpath, you can create an instance of com.sun.tools.javac.Main, the entry point for javac.

com.sun.tools.javac.Main javac = new com.sun.tools.javac.Main();

You can call the compile method on the javac instance passing in an array of strings as options. For example, here are the options that include the classpath and the output directory for the file to compile.

String[] options = new String[] {
“-classpath”, classpath, “-d”, outputDir, filename
};

And of course you can use any of the other options such as -deprecation or -g. To compile a source file, just invoke compile as in the following code bit.

javac.compile(options);

Compile Java this way can be helpful if your application generates one off statements that need to run in the system. I have used a mechanism like this to write what essentially is a script file but in Java code instead of Groovy or Jython. One thing to remember is that tools.jar is only available with the Java Development Kit, not the Java Runtime Environment.

Technorati Tags: , , , , , , , , ,

Related posts:

  1. Java SE 6 Compiler API
  2. Embedding Groovy
  3. Software Project Management with Maven 2
  4. Random Shell Script
  5. Fix Common Java Exceptions
  6. Class HighLite File


7 Responses to “Invoke Javac At Runtime”

  • Soham Sengupta Says:

    Can I access reflection Information about a Java Class whose qualified name has not been given?
    Please do let me know at your earliest.
    I searched the web but in vain
    By the way your article very much helped me, but I want the Java DOCs of this tools.jar API.
    How to get it?

  • TechKnow Says:

    @Soham – AFAIK you need the qualified class name to load the class via the ClassLoader.

    To you second question, try using the com.sun.tools.javadoc.Main class to invoke JavaDoc from your own code/classes in a similar manner which I described here.

  • Frederick Says:

    how do print out the errors received after programmatically compiling?

  • Felipe Ortiz's Blog Says:

    Top Java SE 6 Features…

    Now that I have had some time to work with Java SE 6, I thought I share a list what I think are the top five features….

  • mohan Says:

    Hi All,

    PLEASE SUGGEST ME SOME TIPS….!

    I have been trying since 3 days to solve this problem…every thing is fine with tools .jar, web.xml and every thing even classpath also

    please kindly help me to solve this ….

    HTTP Status 500 -

    ——————————————————————————–

    type Exception report

    message

    description The server encountered an internal error () that prevented it from fulfilling this request.

    exception

    javax.servlet.ServletException: java.lang.NoClassDefFoundError: sun/tools/javac/Main
    org.apache.jasper.servlet.JspServlet.service(JspServlet.java:481)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
    com.auth.servlets.Controller.doPost(Controller.java:330)
    com.auth.servlets.Controller.doGet(Controller.java:58)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:690)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:803)

    root cause

    java.lang.NoClassDefFoundError: sun/tools/javac/Main
    org.apache.jasper.compiler.SunJavaCompiler.compile(SunJavaCompiler.java:136)
    org.apache.jasper.compiler.Compiler.compile(Compiler.java:272)
    org.apache.jasper.servlet.JspServlet.loadJSP(JspServlet.java:548)
    org.apache.jasper.servlet.JspServlet$JspServletWrapper.loadIfNecessary(JspServlet.java:176)
    org.apache.jasper.servlet.JspServlet$JspServletWrapper.service(JspServlet.java:188)
    org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:381)
    org.apache.jasper.servlet.JspServlet.service(JspServlet.java:473)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
    com.auth.servlets.Controller.doPost(Controller.java:330)
    com.auth.servlets.Controller.doGet(Controller.java:58)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:690)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:803)

    note The full stack trace of the root cause is available in the Apache Tomcat/6.0.13 logs.

    ——————————————————————————–

    Apache Tomcat/6.0.13

  • konichiwa Says:

    why, oh WHY isn’t javac included in the JRE (and tool.jar et. al.) so that dynamic code generation could be assumed on a user’s machine? there are just some things that are much harder if not impossible to do without the ability to generate code at runtime … arrrgh. !$##!$!$*!!

  • Umesh Says:

    How to set classpath ?
    I am not able to access source files using classpath.

    I get following message :
    javac: file not found: User.java
    Usage: javac
    use -help for a list of possible options

    I have written code like this :
    String[] options = new String[] {“-classpath”, “D:/My Documents/”, “-d”, “D:/My Documents/classes”, “User.java”};

Leave a Reply