org.apache.xmlbeans.impl.inst2xsd.Inst2Xsd Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of commons-xmlbeans Show documentation
Show all versions of commons-xmlbeans Show documentation
The Apache Commons Codec package contains simple encoder and decoders for
various formats such as Base64 and Hexadecimal. In addition to these
widely used encoders and decoders, the codec package also maintains a
collection of phonetic encoding utilities.
The newest version!
/* Copyright 2004 The Apache Software Foundation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.xmlbeans.impl.inst2xsd;
import org.apache.xmlbeans.SchemaTypeLoader;
import org.apache.xmlbeans.XmlBeans;
import org.apache.xmlbeans.XmlException;
import org.apache.xmlbeans.XmlObject;
import org.apache.xmlbeans.XmlOptions;
import org.apache.xmlbeans.XmlError;
import org.apache.xmlbeans.impl.xb.xsdschema.SchemaDocument;
import org.apache.xmlbeans.impl.inst2xsd.util.TypeSystemHolder;
import org.apache.xmlbeans.impl.tool.CommandLine;
import java.io.File;
import java.io.IOException;
import java.io.Reader;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.Set;
import java.util.HashSet;
/**
* @author Cezar Andrei (cezar.andrei at bea.com) Date: Jul 16, 2004
*
* This class generates a set of XMLSchemas from an instance XML document.
*
* How it works:
* - first: pass through all the instances, building a TypeSystemHolder structure
* - second: serialize the TypeSystemHolder structure into SchemaDocuments
*/
public class Inst2Xsd
{
public static void main(String[] args)
{
if (args==null || args.length == 0)
{
printHelp();
System.exit(0);
return;
}
Set flags = new HashSet();
flags.add("h");
flags.add("help");
flags.add("usage");
flags.add("license");
flags.add("version");
flags.add("verbose");
flags.add("validate");
Set opts = new HashSet();
opts.add("design");
opts.add("simple-content-types");
opts.add("enumerations");
opts.add("outDir");
opts.add("outPrefix");
CommandLine cl = new CommandLine(args, flags, opts);
Inst2XsdOptions inst2XsdOptions = new Inst2XsdOptions();
if (cl.getOpt("license") != null)
{
CommandLine.printLicense();
System.exit(0);
return;
}
if (cl.getOpt("version") != null)
{
CommandLine.printVersion();
System.exit(0);
return;
}
if (cl.getOpt("h") != null || cl.getOpt("help") != null || cl.getOpt("usage") != null)
{
printHelp();
System.exit(0);
return;
}
String[] badopts = cl.getBadOpts();
if (badopts.length > 0)
{
for (int i = 0; i < badopts.length; i++)
System.out.println("Unrecognized option: " + badopts[i]);
printHelp();
System.exit(0);
return;
}
String design = cl.getOpt("design");
if (design==null)
{
// default
}
else if (design.equals("vb"))
{
inst2XsdOptions.setDesign(Inst2XsdOptions.DESIGN_VENETIAN_BLIND);
}
else if (design.equals("rd"))
{
inst2XsdOptions.setDesign(Inst2XsdOptions.DESIGN_RUSSIAN_DOLL);
}
else if (design.equals("ss"))
{
inst2XsdOptions.setDesign(Inst2XsdOptions.DESIGN_SALAMI_SLICE);
}
else
{
printHelp();
System.exit(0);
return;
}
String simpleContent = cl.getOpt("simple-content-types");
if (simpleContent==null)
{
//default
}
else if (simpleContent.equals("smart"))
{
inst2XsdOptions.setSimpleContentTypes(Inst2XsdOptions.SIMPLE_CONTENT_TYPES_SMART);
}
else if (simpleContent.equals("string"))
{
inst2XsdOptions.setSimpleContentTypes(Inst2XsdOptions.SIMPLE_CONTENT_TYPES_STRING);
}
else
{
printHelp();
System.exit(0);
return;
}
String enumerations = cl.getOpt("enumerations");
if (enumerations==null)
{
// default
}
else if (enumerations.equals("never"))
{
inst2XsdOptions.setUseEnumerations(Inst2XsdOptions.ENUMERATION_NEVER);
}
else
{
try
{
int intVal = Integer.parseInt(enumerations);
inst2XsdOptions.setUseEnumerations(intVal);
}
catch (NumberFormatException e)
{
printHelp();
System.exit(0);
return;
}
}
File outDir = new File( cl.getOpt("outDir")==null ? "." : cl.getOpt("outDir"));
String outPrefix = cl.getOpt("outPrefix");
if (outPrefix==null)
outPrefix = "schema";
inst2XsdOptions.setVerbose((cl.getOpt("verbose") != null));
boolean validate = cl.getOpt("validate")!=null;
File[] xmlFiles = cl.filesEndingWith(".xml");
XmlObject[] xmlInstances = new XmlObject[xmlFiles.length];
if ( xmlInstances.length==0 )
{
printHelp();
System.exit(0);
return;
}
int i = 0;
try
{
for (i = 0; i < xmlFiles.length; i++)
{
xmlInstances[i] = XmlObject.Factory.parse(xmlFiles[i]);
}
}
catch (XmlException e)
{
System.err.println("Invalid xml file: '" + xmlFiles[i].getName() + "'. " + e.getMessage());
return;
}
catch (IOException e)
{
System.err.println("Could not read file: '" + xmlFiles[i].getName() + "'. " + e.getMessage());
return;
}
SchemaDocument[] schemaDocs = inst2xsd(xmlInstances, inst2XsdOptions);
try
{
for (i = 0; i < schemaDocs.length; i++)
{
SchemaDocument schema = schemaDocs[i];
if (inst2XsdOptions.isVerbose())
System.out.println("----------------------\n\n" + schema);
schema.save(new File(outDir, outPrefix + i + ".xsd"), new XmlOptions().setSavePrettyPrint());
}
}
catch (IOException e)
{
System.err.println("Could not write file: '" + outDir + File.pathSeparator + outPrefix + i + ".xsd" + "'. " + e.getMessage());
return;
}
if (validate)
{
validateInstances(schemaDocs, xmlInstances);
}
}
private static void printHelp()
{
System.out.println("Generates XMLSchema from instance xml documents.");
System.out.println("Usage: inst2xsd [opts] [instance.xml]*");
System.out.println("Options include:");
System.out.println(" -design [rd|ss|vb] - XMLSchema design type");
System.out.println(" rd - Russian Doll Design - local elements and local types");
System.out.println(" ss - Salami Slice Design - global elements and local types");
System.out.println(" vb - Venetian Blind Design (default) - local elements and global complex types");
System.out.println(" -simple-content-types [smart|string] - Simple content types detection (leaf text). Smart is the default");
System.out.println(" -enumerations [never|NUMBER] - Use enumerations. Default value is " + Inst2XsdOptions.ENUMERATION_NOT_MORE_THAN_DEFAULT + ".");
System.out.println(" -outDir [dir] - Directory for output files. Default is '.'");
System.out.println(" -outPrefix [file_name_prefix] - Prefix for output file names. Default is 'schema'");
System.out.println(" -validate - Validates input instances agaist generated schemas.");
System.out.println(" -verbose - print more informational messages");
System.out.println(" -license - print license information");
System.out.println(" -help - help imformation");
}
private Inst2Xsd() {}
// public entry points
public static SchemaDocument[] inst2xsd(Reader[] instReaders, Inst2XsdOptions options)
throws IOException, XmlException
{
XmlObject[] instances = new XmlObject[ instReaders.length ];
for (int i = 0; i < instReaders.length; i++)
{
instances[i] = XmlObject.Factory.parse(instReaders[i]);
}
return inst2xsd(instances, options);
}
public static SchemaDocument[] inst2xsd(XmlObject[] instances, Inst2XsdOptions options)
{
if (options==null)
options = new Inst2XsdOptions();
// create structure
TypeSystemHolder typeSystemHolder = new TypeSystemHolder();
XsdGenStrategy strategy;
switch (options.getDesign())
{
case Inst2XsdOptions.DESIGN_RUSSIAN_DOLL:
strategy = new RussianDollStrategy();
break;
case Inst2XsdOptions.DESIGN_SALAMI_SLICE:
strategy = new SalamiSliceStrategy();
break;
case Inst2XsdOptions.DESIGN_VENETIAN_BLIND:
strategy = new VenetianBlindStrategy();
break;
default:
throw new IllegalArgumentException("Unknown design.");
}
// processDoc the instance
strategy.processDoc(instances, options, typeSystemHolder);
if (options.isVerbose())
System.out.println("typeSystemHolder.toString(): " + typeSystemHolder);
SchemaDocument[] sDocs = typeSystemHolder.getSchemaDocuments();
return sDocs;
}
private static boolean validateInstances(SchemaDocument[] sDocs, XmlObject[] instances)
{
SchemaTypeLoader sLoader;
Collection compErrors = new ArrayList();
XmlOptions schemaOptions = new XmlOptions();
schemaOptions.setErrorListener(compErrors);
try
{
sLoader = XmlBeans.loadXsd(sDocs, schemaOptions);
}
catch (Exception e)
{
if (compErrors.isEmpty() || !(e instanceof XmlException))
{
e.printStackTrace(System.out);
}
System.out.println("\n-------------------\n\nInvalid schemas.");
for (Iterator errors = compErrors.iterator(); errors.hasNext(); )
{
XmlError xe = (XmlError)errors.next();
System.out.println(xe.getLine() + ":" + xe.getColumn() + " " + xe.getMessage());
}
return false;
}
System.out.println("\n-------------------");
boolean result = true;
for (int i = 0; i < instances.length; i++)
{
XmlObject xobj;
try
{
xobj = sLoader.parse( instances[i].newXMLStreamReader(), null, new XmlOptions().setLoadLineNumbers() );
}
catch (XmlException e)
{
System.out.println("Error:\n" + instances[i].documentProperties().getSourceName() + " not loadable: " + e);
e.printStackTrace(System.out);
result = false;
continue;
}
Collection errors = new ArrayList();
if (xobj.schemaType() == XmlObject.type)
{
System.out.println(instances[i].documentProperties().getSourceName() + " NOT valid. ");
System.out.println(" Document type not found." );
result = false;
}
else if (xobj.validate(new XmlOptions().setErrorListener(errors)))
System.out.println("Instance[" + i + "] valid - " + instances[i].documentProperties().getSourceName());
else
{
System.out.println("Instance[" + i + "] NOT valid - " + instances[i].documentProperties().getSourceName());
for (Iterator it = errors.iterator(); it.hasNext(); )
{
XmlError xe = (XmlError)it.next();
System.out.println(xe.getLine() + ":" + xe.getColumn() + " " + xe.getMessage());
}
result = false;
}
}
return result;
}
}