0001: /*
0002: * Portions Copyright 2006 Sun Microsystems, Inc. All Rights Reserved.
0003: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0004: *
0005: * This code is free software; you can redistribute it and/or modify it
0006: * under the terms of the GNU General Public License version 2 only, as
0007: * published by the Free Software Foundation. Sun designates this
0008: * particular file as subject to the "Classpath" exception as provided
0009: * by Sun in the LICENSE file that accompanied this code.
0010: *
0011: * This code is distributed in the hope that it will be useful, but WITHOUT
0012: * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0013: * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0014: * version 2 for more details (a copy is included in the LICENSE file that
0015: * accompanied this code).
0016: *
0017: * You should have received a copy of the GNU General Public License version
0018: * 2 along with this work; if not, write to the Free Software Foundation,
0019: * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0020: *
0021: * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
0022: * CA 95054 USA or visit www.sun.com if you need additional information or
0023: * have any questions.
0024: */
0025: package com.sun.tools.internal.ws.wscompile;
0026:
0027: import com.sun.mirror.apt.AnnotationProcessor;
0028: import com.sun.mirror.apt.AnnotationProcessorEnvironment;
0029: import com.sun.mirror.apt.AnnotationProcessorFactory;
0030: import com.sun.mirror.declaration.AnnotationTypeDeclaration;
0031: import com.sun.tools.internal.ws.processor.Processor;
0032: import com.sun.tools.internal.ws.processor.ProcessorAction;
0033: import com.sun.tools.internal.ws.processor.ProcessorConstants;
0034: import com.sun.tools.internal.ws.processor.ProcessorNotificationListener;
0035: import com.sun.tools.internal.ws.processor.ProcessorOptions;
0036: import com.sun.tools.internal.ws.processor.config.ClassModelInfo;
0037: import com.sun.tools.internal.ws.processor.config.Configuration;
0038: import com.sun.tools.internal.ws.processor.config.WSDLModelInfo;
0039: import com.sun.tools.internal.ws.processor.config.parser.Reader;
0040: import com.sun.tools.internal.ws.processor.generator.CustomExceptionGenerator;
0041: import com.sun.tools.internal.ws.processor.generator.SeiGenerator;
0042: import com.sun.tools.internal.ws.processor.model.Model;
0043: import com.sun.tools.internal.ws.processor.modeler.annotation.AnnotationProcessorContext;
0044: import com.sun.tools.internal.ws.processor.modeler.annotation.WebServiceAP;
0045: import com.sun.tools.internal.ws.processor.util.ClientProcessorEnvironment;
0046: import com.sun.tools.internal.ws.processor.util.GeneratedFileInfo;
0047: import com.sun.tools.internal.ws.processor.util.ProcessorEnvironment;
0048: import com.sun.tools.internal.ws.processor.util.ProcessorEnvironmentBase;
0049: import com.sun.xml.internal.ws.util.JAXWSUtils;
0050: import com.sun.tools.internal.ws.util.JavaCompilerHelper;
0051: import com.sun.tools.internal.ws.util.ToolBase;
0052: import com.sun.tools.internal.ws.util.ForkEntityResolver;
0053: import com.sun.tools.internal.ws.ToolVersion;
0054: import com.sun.xml.internal.ws.util.VersionUtil;
0055: import com.sun.xml.internal.ws.util.xml.XmlUtil;
0056: import com.sun.xml.internal.ws.util.localization.Localizable;
0057: import com.sun.xml.internal.ws.wsdl.writer.WSDLGenerator;
0058: import com.sun.xml.internal.ws.binding.BindingImpl;
0059: import com.sun.xml.internal.ws.binding.soap.SOAPBindingImpl;
0060:
0061: import javax.xml.namespace.QName;
0062: import javax.xml.transform.Result;
0063: import javax.xml.transform.stream.StreamResult;
0064: import javax.xml.ws.BindingType;
0065: import javax.xml.ws.Holder;
0066: import javax.xml.ws.soap.SOAPBinding;
0067: import java.io.File;
0068: import java.io.FileNotFoundException;
0069: import java.io.FileOutputStream;
0070: import java.io.OutputStream;
0071: import java.net.URLClassLoader;
0072: import java.util.ArrayList;
0073: import java.util.Collection;
0074: import java.util.Collections;
0075: import java.util.HashMap;
0076: import java.util.HashSet;
0077: import java.util.Iterator;
0078: import java.util.List;
0079: import java.util.Map;
0080: import java.util.Properties;
0081: import java.util.Set;
0082:
0083: import org.xml.sax.EntityResolver;
0084:
0085: /**
0086: * This is the real implementation class for both WsGen and WsImport.
0087: *
0088: * <P>If the program being executed is WsGen, the CompileTool acts as an
0089: * {@link com.sun.mirror.apt.AnnotationProcessorFactory AnnotationProcessorFactory}
0090: * and uses {@link com.sun.tools.internal.ws.processor.modeler.annotation.WebServiceAP
0091: * WebServiceAP} as the {@link com.sun.mirror.apt.AnnotationProcessor
0092: * AnnotationProcessor} for the APT framework. In this case APT takes control
0093: * while processing the SEI passed to WsGen. The APT framework then invokes the
0094: * WebServiceAP to process classes that contain javax.jws.* annotations.
0095: * WsGen uses the APT reflection library to process the SEI and to generate any
0096: * JAX-WS spec mandated Java beans.
0097: *
0098: * <p>If the program being executed is WsImport, the CompileTool creates a
0099: * {@link com.sun.tools.internal.ws.processor.Processor Processor} to help with the
0100: * processing. First the {@link com.sun.tools.internal.ws.processor.Processor#runModeler()
0101: * Processor.runModeler()} method is called to create an instance of the
0102: * {@link com.sun.tools.internal.ws.processor.modeler.wsdl.WSDLModeler WSDLModeler} to
0103: * process the WSDL being imported, which intern processes the WSDL and creates
0104: * a {@link com.sun.tools.internal.ws.processor.model.Model Model} that is returned to the
0105: * Processor. The CompileTool then registers a number of
0106: * {@link com.sun.tools.internal.ws.processor.ProcessorAction ProcessorActions} with the
0107: * Processor. Some of these ProcessorActions include
0108: * the {@link com.sun.tools.internal.ws.processor.generator.CustomExceptionGenerator
0109: * CustomExceptionGenerator} to generate Exception classes,
0110: * the {@link com.sun.tools.internal.ws.processor.generator.JAXBTypeGenerator
0111: * JAXBTypeGenerator} to generate JAXB types,
0112: * the {@link com.sun.tools.internal.ws.processor.generator.ServiceGenerator
0113: * ServiceGenerator} to generate the Service interface, and
0114: * the {@link com.sun.tools.internal.ws.processor.generator.SeiGenerator
0115: * RemoteInterfaceGenerator} to generate the service endpoint interface.
0116: * The CompileTool then invokes the {@link com.sun.tools.internal.ws.processor.Processor#runActions()
0117: * Processor.runActions()} method to cause these ProcessorActions to run.
0118: * Once the ProcessorActions have been run, the CompileTool will invoke javac
0119: * to compile any classes generated by the ProcessorActions.
0120: *
0121: * @author WS Development Team
0122: *
0123: */
0124: public class CompileTool extends ToolBase implements
0125: ProcessorNotificationListener, AnnotationProcessorFactory {
0126:
0127: public CompileTool(OutputStream out, String program) {
0128: super (out, program);
0129: listener = this ;
0130: }
0131:
0132: protected boolean parseArguments(String[] args) {
0133: for (int i = 0; i < args.length; i++) {
0134: if (args[i].equals("")) {
0135: args[i] = null;
0136: } else if (args[i].equals("-g")) {
0137: compilerDebug = true;
0138: args[i] = null;
0139: } /*else if (args[i].equals("-O")) {
0140: compilerOptimize = true;
0141: args[i] = null;
0142: }*/else if (args[i].equals("-verbose")) {
0143: verbose = true;
0144: args[i] = null;
0145: } else if (args[i].equals("-b")) {
0146: if (program.equals(WSGEN)) {
0147: onError(getMessage("wscompile.invalidOption",
0148: args[i]));
0149: usage();
0150: return false;
0151: }
0152: if ((i + 1) < args.length) {
0153: args[i] = null;
0154: String file = args[++i];
0155: args[i] = null;
0156: bindingFiles.add(JAXWSUtils.absolutize(JAXWSUtils
0157: .getFileOrURLName(file)));
0158: } else {
0159: onError(getMessage(
0160: "wscompile.missingOptionArgument", "-b"));
0161: usage();
0162: return false;
0163: }
0164: } else if (args[i].equals("-version")) {
0165: report(ToolVersion.VERSION.BUILD_VERSION);
0166: doNothing = true;
0167: args[i] = null;
0168: return true;
0169: } else if (args[i].equals("-keep")) {
0170: keepGenerated = true;
0171: args[i] = null;
0172: } else if (args[i].equals("-wsdllocation")) {
0173: if (program.equals(WSGEN)) {
0174: onError(getMessage("wscompile.invalidOption",
0175: args[i]));
0176: usage();
0177: return false;
0178: }
0179: if ((i + 1) < args.length) {
0180: args[i] = null;
0181: wsdlLocation = args[++i];
0182: args[i] = null;
0183: } else {
0184: onError(getMessage(
0185: "wscompile.missingOptionArgument", args[i]));
0186: usage();
0187: return false;
0188: }
0189: } else if (args[i].equals("-p")) {
0190: if (program.equals(WSGEN)) {
0191: onError(getMessage("wscompile.invalidOption",
0192: args[i]));
0193: usage();
0194: return false;
0195: }
0196: if ((i + 1) < args.length) {
0197: args[i] = null;
0198: defaultPackage = args[++i];
0199: args[i] = null;
0200: } else {
0201: onError(getMessage(
0202: "wscompile.missingOptionArgument", args[i]));
0203: usage();
0204: return false;
0205: }
0206: } else if (args[i].equals("-catalog")) {
0207: if (program.equals(WSGEN)) {
0208: onError(getMessage("wscompile.invalidOption",
0209: args[i]));
0210: usage();
0211: return false;
0212: }
0213: if ((i + 1) < args.length) {
0214: args[i] = null;
0215: catalog = args[++i];
0216: args[i] = null;
0217: } else {
0218: onError(getMessage(
0219: "wscompile.missingOptionArgument", args[i]));
0220: usage();
0221: return false;
0222: }
0223: } else if (args[i].equals(SERVICENAME_OPTION)) {
0224: if (program.equals(WSIMPORT)) {
0225: onError(getMessage("wscompile.invalidOption",
0226: args[i]));
0227: usage();
0228: return false;
0229: }
0230: if ((i + 1) < args.length) {
0231: args[i] = null;
0232: serviceName = QName.valueOf(args[++i]);
0233: if (serviceName.getNamespaceURI() == null
0234: || serviceName.getNamespaceURI().length() == 0) {
0235: onError(getMessage(
0236: "wsgen.servicename.missing.namespace",
0237: args[i]));
0238: usage();
0239: return false;
0240: }
0241: if (serviceName.getLocalPart() == null
0242: || serviceName.getLocalPart().length() == 0) {
0243: onError(getMessage(
0244: "wsgen.servicename.missing.localname",
0245: args[i]));
0246: usage();
0247: return false;
0248: }
0249: args[i] = null;
0250: } else {
0251: onError(getMessage(
0252: "wscompile.missingOptionArgument", args[i]));
0253: usage();
0254: return false;
0255: }
0256: } else if (args[i].equals(PORTNAME_OPTION)) {
0257: if (program.equals(WSIMPORT)) {
0258: onError(getMessage("wscompile.invalidOption",
0259: args[i]));
0260: usage();
0261: return false;
0262: }
0263: if ((i + 1) < args.length) {
0264: args[i] = null;
0265: portName = QName.valueOf(args[++i]);
0266: if (portName.getNamespaceURI() == null
0267: || portName.getNamespaceURI().length() == 0) {
0268: onError(getMessage(
0269: "wsgen.portname.missing.namespace",
0270: args[i]));
0271: usage();
0272: return false;
0273: }
0274: if (portName.getLocalPart() == null
0275: || portName.getLocalPart().length() == 0) {
0276: onError(getMessage(
0277: "wsgen.portname.missing.localname",
0278: args[i]));
0279: usage();
0280: return false;
0281: }
0282: args[i] = null;
0283: } else {
0284: onError(getMessage(
0285: "wscompile.missingOptionArgument", args[i]));
0286: usage();
0287: return false;
0288: }
0289: } else if (args[i].equals("-d")) {
0290: if ((i + 1) < args.length) {
0291: if (destDir != null) {
0292: onError(getMessage("wscompile.duplicateOption",
0293: "-d"));
0294: usage();
0295: return false;
0296: }
0297: args[i] = null;
0298: destDir = new File(args[++i]);
0299: args[i] = null;
0300: if (!destDir.exists()) {
0301: onError(getMessage("wscompile.noSuchDirectory",
0302: destDir.getPath()));
0303: usage();
0304: return false;
0305: }
0306: } else {
0307: onError(getMessage(
0308: "wscompile.missingOptionArgument", "-d"));
0309: usage();
0310: return false;
0311: }
0312: } else if (args[i].equals("-r")) {
0313: if (program.equals(WSIMPORT)) {
0314: onError(getMessage("wscompile.invalidOption",
0315: args[i]));
0316: usage();
0317: return false;
0318: }
0319: if ((i + 1) < args.length) {
0320: if (nonclassDestDir != null) {
0321: onError(getMessage("wscompile.duplicateOption",
0322: "-r"));
0323: usage();
0324: return false;
0325: }
0326: args[i] = null;
0327: nonclassDestDir = new File(args[++i]);
0328: args[i] = null;
0329: if (!nonclassDestDir.exists()) {
0330: onError(getMessage("wscompile.noSuchDirectory",
0331: nonclassDestDir.getPath()));
0332: usage();
0333: return false;
0334: }
0335: } else {
0336: onError(getMessage(
0337: "wscompile.missingOptionArgument", "-r"));
0338: usage();
0339: return false;
0340: }
0341: } else if (args[i].equals("-s")) {
0342: if ((i + 1) < args.length) {
0343: if (sourceDir != null) {
0344: onError(getMessage("wscompile.duplicateOption",
0345: "-s"));
0346: usage();
0347: return false;
0348: }
0349: args[i] = null;
0350: sourceDir = new File(args[++i]);
0351: args[i] = null;
0352: if (!sourceDir.exists()) {
0353: onError(getMessage("wscompile.noSuchDirectory",
0354: sourceDir.getPath()));
0355: usage();
0356: return false;
0357: }
0358: keepGenerated = true;
0359: } else {
0360: onError(getMessage(
0361: "wscompile.missingOptionArgument", "-s"));
0362: usage();
0363: return false;
0364: }
0365: } else if (args[i].equals("-classpath")
0366: || args[i].equals("-cp")) {
0367: if (program.equals(WSIMPORT)) {
0368: onError(getMessage("wscompile.invalidOption",
0369: args[i]));
0370: usage();
0371: return false;
0372: }
0373: if ((i + 1) < args.length) {
0374: if (userClasspath != null) {
0375: onError(getMessage("wscompile.duplicateOption",
0376: args[i]));
0377: usage();
0378: return false;
0379: }
0380: args[i] = null;
0381: userClasspath = args[++i];
0382: args[i] = null;
0383: } else {
0384: onError(getMessage(
0385: "wscompile.missingOptionArgument", args[i]));
0386: usage();
0387: return false;
0388: }
0389:
0390: } else if (args[i].startsWith("-httpproxy:")) {
0391: if (program.equals(WSGEN)) {
0392: onError(getMessage("wscompile.invalidOption",
0393: args[i]));
0394: usage();
0395: return false;
0396: }
0397: String value = args[i].substring(11);
0398: if (value.length() == 0) {
0399: onError(getMessage("wscompile.invalidOption",
0400: args[i]));
0401: usage();
0402: return false;
0403: }
0404: int index = value.indexOf(':');
0405: if (index == -1) {
0406: System.setProperty("proxySet", TRUE);
0407: System.setProperty("proxyHost", value);
0408: System.setProperty("proxyPort", "8080");
0409: } else {
0410: System.setProperty("proxySet", TRUE);
0411: System.setProperty("proxyHost", value.substring(0,
0412: index));
0413: System.setProperty("proxyPort", value
0414: .substring(index + 1));
0415: }
0416: args[i] = null;
0417: } else if (args[i].startsWith("-wsdl")) {
0418: if (program.equals(WSIMPORT)) {
0419: onError(getMessage("wscompile.invalidOption",
0420: args[i]));
0421: usage();
0422: return false;
0423: }
0424: genWsdl = true;
0425: String value = args[i].substring(5);
0426: int index = value.indexOf(':');
0427: if (index == 0) {
0428: value = value.substring(1);
0429: index = value.indexOf('/');
0430: if (index == -1) {
0431: protocol = value;
0432: transport = HTTP;
0433: } else {
0434: protocol = value.substring(0, index);
0435: transport = value.substring(index + 1);
0436: }
0437: if (!isValidProtocol(protocol)) {
0438: onError(getMessage("wsgen.invalid.protocol",
0439: protocol, VALID_PROTOCOLS));
0440: }
0441: protocolSet = true;
0442: if (!isValidTransport(transport)) {
0443: onError(getMessage("wsgen.invalid.transport",
0444: transport, VALID_TRANSPORTS));
0445: }
0446: }
0447: args[i] = null;
0448: } else if (args[i].equals("-extension")) {
0449: extensions = true;
0450: args[i] = null;
0451: } else if (args[i].startsWith("-help")) {
0452: help();
0453: return false;
0454: } else if (args[i].equals("-Xdonotoverwrite")) {
0455: if (program.equals(WSIMPORT)) {
0456: onError(getMessage("wscompile.invalidOption",
0457: args[i]));
0458: usage();
0459: return false;
0460: }
0461: doNotOverWrite = true;
0462: args[i] = null;
0463: }
0464: }
0465:
0466: for (String arg : args) {
0467: if (arg != null) {
0468: if (arg.startsWith("-")) {
0469: onError(getMessage("wscompile.invalidOption", arg));
0470: usage();
0471: return false;
0472: }
0473:
0474: // the input source could be a local file or a URL,get the
0475: // abolutized URL string
0476: String fileName = arg;
0477: if (program.equals(WSGEN)) {
0478: if (!isValidWSGenClass(fileName))
0479: return false;
0480: }
0481: inputFiles.add(fileName);
0482: }
0483: }
0484:
0485: if (inputFiles.isEmpty()) {
0486: onError(getMessage(program + ".missingFile"));
0487: usage();
0488: return false;
0489: }
0490: if (!extensions && hasExtensions())
0491: return false;
0492:
0493: // put jaxws and jaxb binding files
0494: properties.put(ProcessorOptions.BINDING_FILES, bindingFiles);
0495: if (!validateArguments()) {
0496: usage();
0497: return false;
0498: }
0499: return true;
0500: }
0501:
0502: protected boolean isValidWSGenClass(String className) {
0503: Class clazz = getClass(className);
0504: if (clazz == null) {
0505: onError(getMessage("wsgen.class.not.found", className));
0506: return false;
0507: }
0508: if (clazz.isEnum() || clazz.isInterface()
0509: || clazz.isPrimitive()) {
0510: onError(getMessage(
0511: "wsgen.class.must.be.implementation.class",
0512: className));
0513: return false;
0514: }
0515: if (genWsdl) {
0516: BindingImpl binding = (BindingImpl) BindingImpl.getBinding(
0517: null, clazz, null, false);
0518: if (!(binding instanceof SOAPBinding)) {
0519: onError(getMessage(
0520: "wsgen.cannot.gen.wsdl.for.non.soap.binding",
0521: new Object[] { className,
0522: binding.getBindingId() }));
0523: return false;
0524: }
0525: SOAPBindingImpl soapBinding = (SOAPBindingImpl) binding;
0526: if ((soapBinding.getActualBindingId().equals(
0527: SOAPBinding.SOAP12HTTP_BINDING) || soapBinding
0528: .getActualBindingId().equals(
0529: SOAPBinding.SOAP12HTTP_MTOM_BINDING))
0530: && !(protocol.equals(X_SOAP12) && extensions)) {
0531: onError(getMessage(
0532: "wsgen.cannot.gen.wsdl.for.soap12.binding",
0533: new Object[] { className,
0534: binding.getBindingId() }));
0535: return false;
0536: }
0537: if (soapBinding.getActualBindingId().equals(
0538: SOAPBindingImpl.X_SOAP12HTTP_BINDING)
0539: && !extensions) {
0540: onError(getMessage(
0541: "wsgen.cannot.gen.wsdl.for.xsoap12.binding.wo.extention",
0542: new Object[] { className,
0543: binding.getBindingId() }));
0544: return false;
0545: }
0546: }
0547: return true;
0548: }
0549:
0550: protected boolean validateArguments() {
0551: if (!genWsdl) {
0552: if (serviceName != null) {
0553: onError(getMessage("wsgen.wsdl.arg.no.genwsdl",
0554: SERVICENAME_OPTION));
0555: return false;
0556: }
0557: if (portName != null) {
0558: onError(getMessage("wsgen.wsdl.arg.no.genwsdl",
0559: PORTNAME_OPTION));
0560: return false;
0561: }
0562: }
0563: return true;
0564: }
0565:
0566: protected boolean hasExtensions() {
0567: if (protocol.equalsIgnoreCase(X_SOAP12)) {
0568: onError(getMessage("wsgen.soap12.without.extension"));
0569: return true;
0570: }
0571: return false;
0572: }
0573:
0574: static public boolean isValidProtocol(String protocol) {
0575: return (protocol.equalsIgnoreCase(SOAP11) || protocol
0576: .equalsIgnoreCase(X_SOAP12));
0577: }
0578:
0579: static public boolean isValidTransport(String transport) {
0580: return (transport.equalsIgnoreCase(HTTP));
0581: }
0582:
0583: protected void run() throws Exception {
0584: if (doNothing) {
0585: return;
0586: }
0587: try {
0588: beforeHook();
0589: if (entityResolver == null) {
0590: if (catalog != null && catalog.length() > 0)
0591: entityResolver = XmlUtil
0592: .createEntityResolver(JAXWSUtils
0593: .getFileOrURL(catalog));
0594: } else if (catalog != null && catalog.length() > 0) {
0595: EntityResolver er = XmlUtil
0596: .createEntityResolver(JAXWSUtils
0597: .getFileOrURL(catalog));
0598: entityResolver = new ForkEntityResolver(er,
0599: entityResolver);
0600: }
0601: environment = createEnvironment();
0602: configuration = createConfiguration();
0603: setEnvironmentValues(environment);
0604: if (configuration.getModelInfo() instanceof ClassModelInfo) {
0605: buildModel(((ClassModelInfo) configuration
0606: .getModelInfo()).getClassName());
0607: } else {
0608: processor = new Processor(configuration, properties);
0609: configuration.getModelInfo().setEntityResolver(
0610: entityResolver);
0611: configuration.getModelInfo().setDefaultJavaPackage(
0612: defaultPackage);
0613: processor.runModeler();
0614: withModelHook();
0615: registerProcessorActions(processor);
0616: processor.runActions();
0617: if (environment.getErrorCount() == 0) {
0618: compileGeneratedClasses();
0619: }
0620: }
0621: afterHook();
0622: } finally {
0623: if (!keepGenerated) {
0624: removeGeneratedFiles();
0625: }
0626: if (environment != null) {
0627: environment.shutdown();
0628: }
0629: }
0630: }
0631:
0632: protected void setEnvironmentValues(ProcessorEnvironment env) {
0633: int envFlags = env.getFlags();
0634: envFlags |= ProcessorEnvironment.F_WARNINGS;
0635: if (verbose) {
0636: envFlags |= ProcessorEnvironment.F_VERBOSE;
0637: }
0638: env.setFlags(envFlags);
0639: }
0640:
0641: protected void initialize() {
0642: super .initialize();
0643: properties = new Properties();
0644: actions = new HashMap<String, ProcessorAction>();
0645: actions
0646: .put(
0647: ActionConstants.ACTION_SERVICE_GENERATOR,
0648: new com.sun.tools.internal.ws.processor.generator.ServiceGenerator());
0649: actions.put(ActionConstants.ACTION_REMOTE_INTERFACE_GENERATOR,
0650: new SeiGenerator());
0651: actions.put(ActionConstants.ACTION_CUSTOM_EXCEPTION_GENERATOR,
0652: new CustomExceptionGenerator());
0653: actions
0654: .put(
0655: ActionConstants.ACTION_JAXB_TYPE_GENERATOR,
0656: new com.sun.tools.internal.ws.processor.generator.JAXBTypeGenerator());
0657: }
0658:
0659: public void removeGeneratedFiles() {
0660: environment.deleteGeneratedFiles();
0661: }
0662:
0663: public void buildModel(String endpoint) {
0664: context = new AnnotationProcessorContext();
0665: webServiceAP = new WebServiceAP(this , environment, properties,
0666: context);
0667:
0668: String classpath = environment.getClassPath();
0669:
0670: String[] args = new String[8];
0671: args[0] = "-d";
0672: args[1] = destDir.getAbsolutePath();
0673: args[2] = "-classpath";
0674: args[3] = classpath;
0675: args[4] = "-s";
0676: args[5] = sourceDir.getAbsolutePath();
0677: args[6] = "-XclassesAsDecls";
0678: args[7] = endpoint;
0679:
0680: int result = com.sun.tools.apt.Main.process(this , args);
0681: if (result != 0) {
0682: environment
0683: .error(getMessage("wscompile.compilationFailed"));
0684: return;
0685: }
0686: if (genWsdl) {
0687: String tmpPath = destDir.getAbsolutePath()
0688: + File.pathSeparator + classpath;
0689: ClassLoader classLoader = new URLClassLoader(
0690: ProcessorEnvironmentBase.pathToURLs(tmpPath), this
0691: .getClass().getClassLoader());
0692: Class<?> endpointClass = null;
0693:
0694: try {
0695: endpointClass = classLoader.loadClass(endpoint);
0696: } catch (ClassNotFoundException e) {
0697: // this should never happen
0698: environment.error(getMessage("wsgen.class.not.found",
0699: endpoint));
0700: }
0701: String bindingID = getBindingID(protocol);
0702: if (!protocolSet) {
0703: BindingImpl binding = (BindingImpl) BindingImpl
0704: .getBinding(null, endpointClass, null, false);
0705: bindingID = binding.getBindingId();
0706: }
0707: com.sun.xml.internal.ws.modeler.RuntimeModeler rtModeler = new com.sun.xml.internal.ws.modeler.RuntimeModeler(
0708: endpointClass, serviceName, bindingID);
0709: rtModeler.setClassLoader(classLoader);
0710: if (portName != null)
0711: rtModeler.setPortName(portName);
0712: com.sun.xml.internal.ws.model.RuntimeModel rtModel = rtModeler
0713: .buildRuntimeModel();
0714: WSDLGenerator wsdlGenerator = new WSDLGenerator(
0715: rtModel,
0716: new com.sun.xml.internal.ws.wsdl.writer.WSDLOutputResolver() {
0717: public Result getWSDLOutput(
0718: String suggestedFilename) {
0719: File wsdlFile = new File(nonclassDestDir,
0720: suggestedFilename);
0721:
0722: Result result = new StreamResult();
0723: try {
0724: result = new StreamResult(
0725: new FileOutputStream(wsdlFile));
0726: result.setSystemId(wsdlFile.toString()
0727: .replace('\\', '/'));
0728: } catch (FileNotFoundException e) {
0729: environment.error(getMessage(
0730: "wsgen.could.not.create.file",
0731: wsdlFile.toString()));
0732: }
0733: return result;
0734: }
0735:
0736: public Result getSchemaOutput(String namespace,
0737: String suggestedFilename) {
0738: if (namespace.equals(""))
0739: return null;
0740: return getWSDLOutput(suggestedFilename);
0741: }
0742:
0743: public Result getAbstractWSDLOutput(
0744: Holder<String> filename) {
0745: return getWSDLOutput(filename.value);
0746: }
0747:
0748: public Result getSchemaOutput(String namespace,
0749: Holder<String> filename) {
0750: return getSchemaOutput(namespace,
0751: filename.value);
0752: }
0753: }, bindingID);
0754: wsdlGenerator.doGeneration();
0755: }
0756: }
0757:
0758: static public String getBindingID(String protocol) {
0759: if (protocol.equals(SOAP11))
0760: return SOAP11_ID;
0761: if (protocol.equals(X_SOAP12))
0762: return SOAP12_ID;
0763: return null;
0764: }
0765:
0766: public void runProcessorActions() {
0767: if (!(configuration.getModelInfo() instanceof ClassModelInfo)) {
0768: onError(getMessage("wscompile.classmodelinfo.expected",
0769: new Object[] { configuration.getModelInfo() }));
0770: return;
0771: }
0772: Model model = context.getSEIContext(
0773: ((ClassModelInfo) configuration.getModelInfo())
0774: .getClassName()).getModel();
0775: processor = new Processor(configuration, properties, model);
0776: withModelHook();
0777: registerProcessorActions(processor);
0778: processor.runActions();
0779: // TODO throw an error
0780: // if (environment.getErrorCount() != 0) {
0781: // }
0782:
0783: }
0784:
0785: /**
0786: * @return the SourceVersion string
0787: */
0788: protected String getSourceVersion() {
0789: if (targetVersion == null) {
0790:
0791: /* no target specified, defaulting to the default version,
0792: * which is the latest version
0793: */
0794: return VersionUtil.JAXWS_VERSION_DEFAULT;
0795: }
0796: return targetVersion;
0797: }
0798:
0799: protected void withModelHook() {
0800: }
0801:
0802: protected void afterHook() {
0803: }
0804:
0805: protected void compileGeneratedClasses() {
0806: List<String> sourceFiles = new ArrayList<String>();
0807:
0808: for (Iterator iter = environment.getGeneratedFiles(); iter
0809: .hasNext();) {
0810: GeneratedFileInfo fileInfo = (GeneratedFileInfo) iter
0811: .next();
0812: File f = fileInfo.getFile();
0813: if (f.exists() && f.getName().endsWith(".java")) {
0814: sourceFiles.add(f.getAbsolutePath());
0815: }
0816: }
0817:
0818: if (sourceFiles.size() > 0) {
0819: String classDir = destDir.getAbsolutePath();
0820: String classpathString = createClasspathString();
0821: String[] args = new String[4 + (compilerDebug ? 1 : 0)
0822: + (compilerOptimize ? 1 : 0) + sourceFiles.size()];
0823: args[0] = "-d";
0824: args[1] = classDir;
0825: args[2] = "-classpath";
0826: args[3] = classpathString;
0827: int baseIndex = 4;
0828: if (compilerDebug) {
0829: args[baseIndex++] = "-g";
0830: }
0831: if (compilerOptimize) {
0832: args[baseIndex++] = "-O";
0833: }
0834: for (int i = 0; i < sourceFiles.size(); ++i) {
0835: args[baseIndex + i] = sourceFiles.get(i);
0836: }
0837:
0838: // ByteArrayOutputStream javacOutput = new ByteArrayOutputStream();
0839: JavaCompilerHelper compilerHelper = new JavaCompilerHelper(
0840: out);
0841: boolean result = compilerHelper.compile(args);
0842: if (!result) {
0843: environment
0844: .error(getMessage("wscompile.compilationFailed"));
0845: }
0846: }
0847: }
0848:
0849: protected ProcessorAction getAction(String name) {
0850: return actions.get(name);
0851: }
0852:
0853: protected String createClasspathString() {
0854: if (userClasspath == null) {
0855: userClasspath = "";
0856: }
0857: return userClasspath + File.pathSeparator
0858: + System.getProperty("java.class.path");
0859: }
0860:
0861: protected void registerProcessorActions(Processor processor) {
0862: register(processor);
0863: }
0864:
0865: protected void register(Processor processor) {
0866: boolean genServiceInterface = false;
0867: boolean genInterface = false;
0868: boolean genCustomClasses = false;
0869:
0870: if (configuration.getModelInfo() instanceof WSDLModelInfo) {
0871: genInterface = true;
0872: //genInterfaceTemplate = true;
0873: genServiceInterface = true;
0874: genCustomClasses = true;
0875: }
0876:
0877: if (genServiceInterface) {
0878: processor
0879: .add(getAction(ActionConstants.ACTION_SERVICE_GENERATOR));
0880: }
0881:
0882: if (genCustomClasses) {
0883: processor
0884: .add(getAction(ActionConstants.ACTION_JAXB_TYPE_GENERATOR));
0885: }
0886:
0887: if (genInterface) {
0888: processor
0889: .add(getAction(ActionConstants.ACTION_CUSTOM_EXCEPTION_GENERATOR));
0890: processor
0891: .add(getAction(ActionConstants.ACTION_REMOTE_INTERFACE_GENERATOR));
0892: }
0893: }
0894:
0895: protected Configuration createConfiguration() throws Exception {
0896: if (environment == null)
0897: environment = createEnvironment();
0898: Reader reader = new Reader(environment, properties);
0899: return reader.parse(entityResolver, inputFiles);
0900: }
0901:
0902: protected void beforeHook() {
0903: if (destDir == null) {
0904: destDir = new File(".");
0905: }
0906: if (sourceDir == null) {
0907: sourceDir = destDir;
0908: }
0909: if (nonclassDestDir == null) {
0910: nonclassDestDir = destDir;
0911: }
0912:
0913: properties.setProperty(
0914: ProcessorOptions.SOURCE_DIRECTORY_PROPERTY, sourceDir
0915: .getAbsolutePath());
0916: properties.setProperty(
0917: ProcessorOptions.DESTINATION_DIRECTORY_PROPERTY,
0918: destDir.getAbsolutePath());
0919: properties
0920: .setProperty(
0921: ProcessorOptions.NONCLASS_DESTINATION_DIRECTORY_PROPERTY,
0922: nonclassDestDir.getAbsolutePath());
0923: properties.setProperty(ProcessorOptions.EXTENSION,
0924: (extensions ? "true" : "false"));
0925: properties.setProperty(
0926: ProcessorOptions.PRINT_STACK_TRACE_PROPERTY,
0927: (verbose ? TRUE : FALSE));
0928: properties.setProperty(ProcessorOptions.PROTOCOL, protocol);
0929: properties.setProperty(ProcessorOptions.TRANSPORT, transport);
0930: properties.setProperty(ProcessorOptions.JAXWS_SOURCE_VERSION,
0931: getSourceVersion());
0932: if (wsdlLocation != null)
0933: properties.setProperty(ProcessorOptions.WSDL_LOCATION,
0934: wsdlLocation);
0935: if (defaultPackage != null)
0936: properties.setProperty(ProcessorOptions.DEFAULT_PACKAGE,
0937: defaultPackage);
0938: properties.setProperty(
0939: ProcessorOptions.DONOT_OVERWRITE_CLASSES,
0940: (doNotOverWrite ? TRUE : FALSE));
0941: }
0942:
0943: protected String getGenericErrorMessage() {
0944: return "wscompile.error";
0945: }
0946:
0947: protected String getResourceBundleName() {
0948: return "com.sun.tools.internal.ws.resources.wscompile";
0949: }
0950:
0951: public Collection<String> supportedOptions() {
0952: return supportedOptions;
0953: }
0954:
0955: public Collection<String> supportedAnnotationTypes() {
0956: return supportedAnnotations;
0957: }
0958:
0959: public void onError(Localizable msg) {
0960: report(getMessage("wscompile.error", localizer.localize(msg)));
0961: }
0962:
0963: public void onWarning(Localizable msg) {
0964: report(getMessage("wscompile.warning", localizer.localize(msg)));
0965: }
0966:
0967: public void onInfo(Localizable msg) {
0968: report(getMessage("wscompile.info", localizer.localize(msg)));
0969: }
0970:
0971: public AnnotationProcessor getProcessorFor(
0972: Set<AnnotationTypeDeclaration> atds,
0973: AnnotationProcessorEnvironment apEnv) {
0974: if (verbose)
0975: apEnv.getMessager().printNotice("\tap round: " + ++round);
0976: webServiceAP.init(apEnv);
0977: return webServiceAP;
0978: }
0979:
0980: private Class getClass(String className) {
0981: try {
0982: ProcessorEnvironment env = createEnvironment();
0983: return env.getClassLoader().loadClass(className);
0984: } catch (ClassNotFoundException e) {
0985: return null;
0986: } catch (Exception e) {
0987: e.printStackTrace();
0988: }
0989: return null;
0990: }
0991:
0992: private ProcessorEnvironment createEnvironment() throws Exception {
0993: String cpath = userClasspath + File.pathSeparator
0994: + System.getProperty("java.class.path");
0995: ProcessorEnvironment env = new ClientProcessorEnvironment(
0996: System.out, cpath, listener);
0997: return env;
0998: }
0999:
1000: protected void usage() {
1001: help();
1002: //report(getMessage(program+".usage", program));
1003: }
1004:
1005: protected void help() {
1006: report(getMessage(program + ".help", program));
1007: report(getMessage(program + ".usage.examples"));
1008: }
1009:
1010: public void setEntityResolver(EntityResolver entityResolver) {
1011: this .entityResolver = entityResolver;
1012: }
1013:
1014: /*
1015: * Processor doesn't examine any options.
1016: */
1017: static final Collection<String> supportedOptions = Collections
1018: .unmodifiableSet(new HashSet<String>());
1019:
1020: /*
1021: * All annotation types are supported.
1022: */
1023: static Collection<String> supportedAnnotations;
1024: static {
1025: Collection<String> types = new HashSet<String>();
1026: types.add("*");
1027: types.add("javax.jws.*");
1028: types.add("javax.jws.soap.*");
1029: supportedAnnotations = Collections
1030: .unmodifiableCollection(types);
1031: }
1032:
1033: private AnnotationProcessorContext context;
1034:
1035: private WebServiceAP webServiceAP;
1036:
1037: private int round = 0;
1038:
1039: // End AnnotationProcessorFactory stuff
1040: // -----------------------------------------------------------------------------
1041:
1042: protected Properties properties;
1043: protected ProcessorEnvironment environment;
1044: protected Configuration configuration;
1045: protected ProcessorNotificationListener listener;
1046: protected Processor processor;
1047: protected Map<String, ProcessorAction> actions;
1048: protected List<String> inputFiles = new ArrayList<String>();
1049: protected File sourceDir;
1050: protected File destDir;
1051: protected File nonclassDestDir;
1052: protected boolean doNothing = false;
1053: protected boolean compilerDebug = false;
1054: protected boolean compilerOptimize = false;
1055: protected boolean verbose = false;
1056: protected boolean keepGenerated = false;
1057: protected boolean doNotOverWrite = false;
1058: protected boolean extensions = false;
1059: protected String userClasspath = null;
1060: protected Set<String> bindingFiles = new HashSet<String>();
1061: protected boolean genWsdl = false;
1062: protected String protocol = SOAP11;
1063: protected boolean protocolSet = false;
1064: protected String transport = HTTP;
1065: protected static final String SOAP11 = "soap1.1";
1066: protected static final String X_SOAP12 = "Xsoap1.2";
1067: protected static final String HTTP = "http";
1068: protected static final String WSIMPORT = "wsimport";
1069: protected static final String WSGEN = "wsgen";
1070: protected static final String SOAP11_ID = javax.xml.ws.soap.SOAPBinding.SOAP11HTTP_BINDING;
1071: protected static final String SOAP12_ID = javax.xml.ws.soap.SOAPBinding.SOAP12HTTP_BINDING;
1072: protected static final String VALID_PROTOCOLS = SOAP11 + ", "
1073: + X_SOAP12;
1074: protected static final String VALID_TRANSPORTS = "http";
1075: protected String targetVersion = null;
1076: protected String wsdlLocation;
1077: protected String defaultPackage;
1078: protected String catalog;
1079: protected QName serviceName;
1080: protected QName portName;
1081: protected static final String PORTNAME_OPTION = "-portname";
1082: protected static final String SERVICENAME_OPTION = "-servicename";
1083: protected EntityResolver entityResolver;
1084: }
|