001: /*
002: * GeoTools - OpenSource mapping toolkit
003: * http://geotools.org
004: * (C) 2004-2006, Geotools Project Managment Committee (PMC)
005: *
006: * This library is free software; you can redistribute it and/or
007: * modify it under the terms of the GNU Lesser General Public
008: * License as published by the Free Software Foundation; either
009: * version 2.1 of the License, or (at your option) any later version.
010: *
011: * This library is distributed in the hope that it will be useful,
012: * but WITHOUT ANY WARRANTY; without even the implied warranty of
013: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
014: * Lesser General Public License for more details.
015: */
016: package org.geotools.xml.wfs;
017:
018: import java.net.URI;
019: import java.net.URISyntaxException;
020: import java.util.Collections;
021: import java.util.Map;
022: import java.util.logging.Logger;
023:
024: import org.geotools.xml.filter.FilterSchema;
025: import org.geotools.xml.gml.GMLSchema;
026: import org.geotools.xml.schema.Attribute;
027: import org.geotools.xml.schema.AttributeGroup;
028: import org.geotools.xml.schema.ComplexType;
029: import org.geotools.xml.schema.Element;
030: import org.geotools.xml.schema.Facet;
031: import org.geotools.xml.schema.Group;
032: import org.geotools.xml.schema.Schema;
033: import org.geotools.xml.schema.SimpleType;
034: import org.geotools.xml.schema.Type;
035: import org.geotools.xml.schema.impl.AttributeGT;
036: import org.geotools.xml.schema.impl.FacetGT;
037: import org.geotools.xml.schema.impl.SimpleTypeGT;
038: import org.geotools.xml.wfs.WFSBasicComplexTypes.DescribeFeatureTypeType;
039: import org.geotools.xml.wfs.WFSBasicComplexTypes.FeatureCollectionType;
040: import org.geotools.xml.wfs.WFSBasicComplexTypes.GetCapabilitiesType;
041: import org.geotools.xml.wfs.WFSBasicComplexTypes.GetFeatureType;
042: import org.geotools.xml.wfs.WFSBasicComplexTypes.QueryType;
043: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.CapabilityType;
044: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.DCPTypeType;
045: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.EmptyType;
046: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.FeatureTypeListType;
047: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.FeatureTypeType;
048: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.GetType;
049: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.HTTPType;
050: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.LatLongBoundingBoxType;
051: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.LockFeatureTypeType;
052: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.MetadataURLType;
053: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.OperationsType;
054: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.PostType;
055: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.RequestType;
056: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.ResultFormatType;
057: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.SchemaDescriptionLanguageType;
058: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.ServiceType;
059: import org.geotools.xml.wfs.WFSCapabilitiesComplexTypes.WFS_CapabilitiesType;
060: import org.geotools.xml.wfs.WFSTransactionComplexTypes.DeleteElementType;
061: import org.geotools.xml.wfs.WFSTransactionComplexTypes.FeaturesLockedType;
062: import org.geotools.xml.wfs.WFSTransactionComplexTypes.FeaturesNotLockedType;
063: import org.geotools.xml.wfs.WFSTransactionComplexTypes.GetFeatureWithLockType;
064: import org.geotools.xml.wfs.WFSTransactionComplexTypes.InsertElementType;
065: import org.geotools.xml.wfs.WFSTransactionComplexTypes.InsertResultType;
066: import org.geotools.xml.wfs.WFSTransactionComplexTypes.LockFeatureType;
067: import org.geotools.xml.wfs.WFSTransactionComplexTypes.LockType;
068: import org.geotools.xml.wfs.WFSTransactionComplexTypes.NativeType;
069: import org.geotools.xml.wfs.WFSTransactionComplexTypes.PropertyType;
070: import org.geotools.xml.wfs.WFSTransactionComplexTypes.StatusType;
071: import org.geotools.xml.wfs.WFSTransactionComplexTypes.TransactionResultType;
072: import org.geotools.xml.wfs.WFSTransactionComplexTypes.TransactionType;
073: import org.geotools.xml.wfs.WFSTransactionComplexTypes.UpdateElementType;
074: import org.geotools.xml.wfs.WFSTransactionComplexTypes.WFS_LockFeatureResponseType;
075: import org.geotools.xml.wfs.WFSTransactionComplexTypes.WFS_TransactionResponseType;
076: import org.geotools.xml.xsi.XSISimpleTypes;
077:
078: /**
079: * <p>
080: * This class represents a hard coded, java interpreted version of the WFS
081: * WFS-basic schema. Instances of this class should be prefered for use over a
082: * parsed instance as this class will create real instances for elements
083: * who's types correspond to types defined in this schema.
084: * </p>
085: *
086: * @author Norman Barker www.comsine.com
087: * @source $URL: http://svn.geotools.org/geotools/tags/2.4.1/modules/plugin/wfs/src/main/java/org/geotools/xml/wfs/WFSSchema.java $
088: */
089: public class WFSSchema implements Schema {
090: static Logger logger = org.geotools.util.logging.Logging
091: .getLogger("net.refractions.xml.wfs");
092: private static Schema instance = new WFSSchema();
093:
094: /** WFS target namespace */
095: public static URI NAMESPACE = makeURI("http://www.opengis.net/wfs");
096: static final Element[] elements = new Element[] {
097: new WFSElement("GetCapabilities", GetCapabilitiesType
098: .getInstance()),
099: new WFSElement("DescribeFeatureType",
100: DescribeFeatureTypeType.getInstance()),
101: new WFSElement("GetFeature", GetFeatureType.getInstance()), // 2
102: new WFSElement("FeatureCollection", FeatureCollectionType
103: .getInstance(), 1, 1, false, findElement(GMLSchema
104: .getInstance(), "_FeatureCollection")),
105: new WFSElement("Query", QueryType.getInstance()),
106: new WFSElement("Abstract", XSISimpleTypes.String
107: .getInstance()),
108: new WFSElement("AccessConstraints", XSISimpleTypes.String
109: .getInstance()),
110: new WFSElement("Fees", XSISimpleTypes.String.getInstance()),
111: new WFSElement("Keywords", XSISimpleTypes.String
112: .getInstance()),
113: new WFSElement("OnlineResource", XSISimpleTypes.String
114: .getInstance()),
115: new WFSElement("SRS", XSISimpleTypes.String.getInstance()),
116: new WFSElement("Title", XSISimpleTypes.String.getInstance()), // 11
117:
118: // TODO check if these should be here - from capabilities ... used in operation type
119: new WFSElement("Query", EmptyType.getInstance()),
120: new WFSElement("Insert", EmptyType.getInstance()),
121: new WFSElement("Update", EmptyType.getInstance()),
122: new WFSElement("Delete", EmptyType.getInstance()),
123: new WFSElement("Lock", EmptyType.getInstance()), // 16
124: new WFSElement("VendorSpecificCapabilities",
125: XSISimpleTypes.String.getInstance()),
126: new WFSElement("WFS_Capabilities", WFS_CapabilitiesType
127: .getInstance()),
128: new WFSElement("GML2", EmptyType.getInstance()),
129: new WFSElement("GML2-GZIP", EmptyType.getInstance()),
130: new WFSElement("XMLSCHEMA", EmptyType.getInstance()), // 21
131: new WFSElement("GetFeatureWithLock", GetFeatureWithLockType
132: .getInstance()),
133: new WFSElement("LockFeature", LockFeatureType.getInstance()),
134: new WFSElement("Transaction", TransactionType.getInstance()),
135: new WFSElement("WFS_TransactionResponse",
136: WFS_TransactionResponseType.getInstance()),
137: new WFSElement("WFS_LockFeatureResponse",
138: WFS_LockFeatureResponseType.getInstance()),
139: new WFSElement("LockId", XSISimpleTypes.String
140: .getInstance()),
141: new WFSElement("Insert", InsertElementType.getInstance()),
142: new WFSElement("Update", UpdateElementType.getInstance()),
143: new WFSElement("Delete", DeleteElementType.getInstance()),
144: new WFSElement("Native", NativeType.getInstance()),
145: new WFSElement("Property", PropertyType.getInstance()),
146: new WFSElement("SUCCESS", EmptyType.getInstance()),
147: new WFSElement("FAILED", EmptyType.getInstance()),
148: new WFSElement("PARTIAL", EmptyType.getInstance()) };
149: static final ComplexType[] complexTypes = new ComplexType[] {
150: GetCapabilitiesType.getInstance(),
151: DescribeFeatureTypeType.getInstance(),
152: GetFeatureType.getInstance(), QueryType.getInstance(),
153: FeatureCollectionType.getInstance(),
154: WFS_CapabilitiesType.getInstance(),
155: ServiceType.getInstance(), CapabilityType.getInstance(),
156: FeatureTypeListType.getInstance(),
157: RequestType.getInstance(), TransactionType.getInstance(),
158: LockFeatureTypeType.getInstance(),
159: DCPTypeType.getInstance(), FeatureTypeType.getInstance(),
160: GetType.getInstance(), HTTPType.getInstance(),
161: LatLongBoundingBoxType.getInstance(),
162: MetadataURLType.getInstance(),
163: OperationsType.getInstance(), PostType.getInstance(),
164: ResultFormatType.getInstance(),
165: SchemaDescriptionLanguageType.getInstance(),
166: EmptyType.getInstance(),
167: GetFeatureWithLockType.getInstance(),
168: LockFeatureType.getInstance(), LockType.getInstance(),
169: InsertElementType.getInstance(),
170: UpdateElementType.getInstance(),
171: DeleteElementType.getInstance(), NativeType.getInstance(),
172: PropertyType.getInstance(),
173: WFS_LockFeatureResponseType.getInstance(),
174: FeaturesLockedType.getInstance(),
175: FeaturesNotLockedType.getInstance(),
176: WFS_TransactionResponseType.getInstance(),
177: TransactionResultType.getInstance(),
178: InsertResultType.getInstance(), StatusType.getInstance() };
179: static final SimpleType[] simpleTypes = new SimpleType[] { new SimpleTypeGT(
180: null, "AllSomeType", NAMESPACE, SimpleType.RESTRICTION,
181: new SimpleType[] { XSISimpleTypes.String.getInstance() },
182: new Facet[] { new FacetGT(Facet.ENUMERATION, "ALL"),
183: new FacetGT(Facet.ENUMERATION, "SOME") },
184: SimpleType.NONE), };
185:
186: // convinience method to deal with the URISyntaxException
187: private static URI makeURI(String s) {
188: try {
189: return new URI(s);
190: } catch (URISyntaxException e) {
191: // do nothing
192: return null;
193: }
194: }
195:
196: /**
197: * @see org.geotools.xml.schema.Schema#getInstance()
198: */
199: public static Schema getInstance() {
200: return instance;
201: }
202:
203: private static Element findElement(Schema s, String name) {
204: if ((name == null) || "".equals(name)) {
205: return null;
206: }
207:
208: Element[] elems = s.getElements();
209:
210: if (elems == null) {
211: return null;
212: }
213:
214: for (int i = 0; i < elems.length; i++)
215: if (name.equals(elems[i].getName())) {
216: return elems[i];
217: }
218:
219: return null;
220: }
221:
222: /**
223: * @see org.geotools.xml.schema.Schema#getAttributeGroups()
224: */
225: public AttributeGroup[] getAttributeGroups() {
226: return new AttributeGroup[0];
227: }
228:
229: /**
230: * @see org.geotools.xml.schema.Schema#getAttributes()
231: */
232: public Attribute[] getAttributes() {
233: return new Attribute[0];
234: }
235:
236: /**
237: * @see org.geotools.xml.schema.Schema#getBlockDefault()
238: */
239: public int getBlockDefault() {
240: return NONE;
241: }
242:
243: /**
244: * @see org.geotools.xml.schema.Schema#getComplexTypes()
245: */
246: public ComplexType[] getComplexTypes() {
247: return complexTypes;
248: }
249:
250: /**
251: * @see org.geotools.xml.schema.Schema#getElements()
252: */
253: public Element[] getElements() {
254: return elements;
255: }
256:
257: /**
258: * @see org.geotools.xml.schema.Schema#getFinalDefault()
259: */
260: public int getFinalDefault() {
261: return NONE;
262: }
263:
264: /**
265: * @see org.geotools.xml.schema.Schema#getGroups()
266: */
267: public Group[] getGroups() {
268: return new Group[0];
269: }
270:
271: /**
272: * @see org.geotools.xml.schema.Schema#getId()
273: */
274: public String getId() {
275: return null;
276: }
277:
278: /**
279: * @see org.geotools.xml.schema.Schema#getImports()
280: */
281: public Schema[] getImports() {
282: return new Schema[] { GMLSchema.getInstance(),
283: FilterSchema.getInstance() };
284: }
285:
286: /**
287: * @see org.geotools.xml.schema.Schema#getSimpleTypes()
288: */
289: public SimpleType[] getSimpleTypes() {
290: return simpleTypes;
291: }
292:
293: /**
294: * @see org.geotools.xml.schema.Schema#getTargetNamespace()
295: */
296: public URI getTargetNamespace() {
297: return NAMESPACE;
298: }
299:
300: /**
301: * @see org.geotools.xml.schema.Schema#getURI()
302: */
303: public URI getURI() {
304: try {
305: return new URI("http://www.opengis.net/wfs");
306: } catch (URISyntaxException e) {
307: logger.warning(e.toString());
308:
309: return null;
310: }
311: }
312:
313: /**
314: * @see org.geotools.xml.schema.Schema#getVersion()
315: */
316: public String getVersion() {
317: return "1.0.0";
318: }
319:
320: /**
321: * @see org.geotools.xml.schema.Schema#includesURI(java.net.URI)
322: */
323: public boolean includesURI(URI uri) {
324: // this is a spec ... we never want the def modified.
325: return true;
326: }
327:
328: /**
329: * @see org.geotools.xml.schema.Schema#isAttributeFormDefault()
330: */
331: public boolean isAttributeFormDefault() {
332: return false;
333: }
334:
335: /**
336: * @see org.geotools.xml.schema.Schema#isElementFormDefault()
337: */
338: public boolean isElementFormDefault() {
339: return true;
340: }
341:
342: /**
343: * @see org.geotools.xml.schema.Schema#getPrefix()
344: */
345: public String getPrefix() {
346: return "wfs";
347: }
348:
349: /**
350: * Returns the implementation hints. The default implementation returns en empty map.
351: */
352: public Map getImplementationHints() {
353: return Collections.EMPTY_MAP;
354: }
355:
356: /**
357: * <p>
358: * This abstract class represents some default and constant values
359: * associated with a GML complexType.
360: * </p>
361: *
362: * @see ComplexType
363: */
364: static abstract class WFSComplexType implements ComplexType {
365: /**
366: * @see schema.ComplexType#getBlock()
367: */
368: public int getBlock() {
369: return Schema.NONE;
370: }
371:
372: /**
373: * @see schema.ComplexType#getFinal()
374: */
375: public int getFinal() {
376: return Schema.NONE;
377: }
378:
379: /**
380: * @see schema.ComplexType#getId()
381: */
382: public String getId() {
383: return null;
384: }
385:
386: /**
387: * @see schema.ComplexType#isMixed()
388: */
389: public boolean isMixed() {
390: return false;
391: }
392:
393: /**
394: * @see schema.ComplexType#getNamespace()
395: */
396: public URI getNamespace() {
397: return WFSSchema.NAMESPACE;
398: }
399:
400: /*
401: * included here to deal generically with a GML complexType ...
402: * part of the singleton pattern.
403: */
404: static WFSComplexType getInstance() {
405: return null;
406: }
407:
408: /**
409: * @see schema.ComplexType#isDerived()
410: */
411: public boolean isDerived() {
412: return false;
413: }
414:
415: /**
416: * @see schema.ComplexType#getParent()
417: */
418: public Type getParent() {
419: return null;
420: }
421:
422: /**
423: * @see org.geotools.xml.schema.ComplexType#cache(org.geotools.xml.schema.Element,
424: * java.util.Map)
425: */
426: public boolean cache(Element element, Map hints) {
427: return true;
428: }
429:
430: /**
431: * @see org.geotools.xml.schema.ComplexType#getAnyAttributeNameSpace()
432: */
433: public String getAnyAttributeNameSpace() {
434: return null;
435: }
436:
437: /**
438: * @see org.geotools.xml.schema.Type#findChildElement(java.lang.String)
439: */
440: public Element findChildElement(String name) {
441: return (getChild() == null) ? null : getChild()
442: .findChildElement(name);
443: }
444:
445: /**
446: * @see org.geotools.xml.schema.ComplexType#isAbstract()
447: */
448: public boolean isAbstract() {
449: return false;
450: }
451: }
452:
453: /**
454: * <p>
455: * Adds some common information and functionality to a base element to be
456: * used by the WFSSchema. The remaining data will be configured upon
457: * creation.
458: * </p>
459: *
460: * @author David Zwiers
461: *
462: * @see Element
463: */
464: static class WFSElement implements Element {
465: // default visibily to remove the set* methods ... this class is
466: // only package visible
467: boolean abstracT = false;
468: int max;
469: int min;
470: String name;
471: Type type;
472: Element substitutionGroup;
473:
474: /*
475: * Should never be called
476: */
477: private WFSElement() {
478: // no op const
479: }
480:
481: /**
482: * Configures the Element for this particular WFS instance. The
483: * following params match schema definition attributes found in an
484: * element declaration. Those missing have been hard coded for the gml
485: * Schema.
486: *
487: * @param name
488: * @param type
489: */
490: public WFSElement(String name, Type type) {
491: this .max = 1;
492: this .min = 1;
493: this .name = name;
494: this .type = type;
495: this .substitutionGroup = null;
496: }
497:
498: /**
499: * Configures the Element for this particular WFS instance. The
500: * following params match schema definition attributes found in an
501: * element declaration. Those missing have been hard coded for the gml
502: * Schema.
503: *
504: * @param name
505: * @param type
506: * @param min
507: * @param max
508: * @param abstracT
509: * @param substitutionGroup
510: */
511: public WFSElement(String name, Type type, int min, int max,
512: boolean abstracT, Element substitutionGroup) {
513: this .abstracT = abstracT;
514: this .max = max;
515: this .min = min;
516: this .name = name;
517: this .type = type;
518: this .substitutionGroup = substitutionGroup;
519: }
520:
521: /**
522: * Creates a clone using the new min/max occurences.
523: *
524: * @param element
525: * @param min
526: * @param max
527: */
528: public WFSElement(Element element, int min, int max) {
529: this .abstracT = element.isAbstract();
530: this .max = max;
531: this .min = min;
532: this .name = element.getName();
533: this .type = element.getType();
534: this .substitutionGroup = element.getSubstitutionGroup();
535: }
536:
537: /**
538: * @see org.geotools.xml.xsi.ElementGrouping#findChildElement(java.lang.String)
539: */
540: public Element findChildElement(String name1) {
541: if (this .name != null) {
542: if (this .name.equals(name1)) {
543: return this ;
544: }
545: }
546:
547: return null;
548: }
549:
550: /**
551: * @see org.geotools.xml.xsi.ElementGrouping#getGrouping()
552: */
553: public int getGrouping() {
554: return ELEMENT;
555: }
556:
557: /**
558: * @see schema.Element#isAbstract()
559: */
560: public boolean isAbstract() {
561: return abstracT;
562: }
563:
564: /**
565: * @see schema.Element#getBlock()
566: */
567: public int getBlock() {
568: return Schema.NONE;
569: }
570:
571: /**
572: * @see schema.Element#getDefault()
573: */
574: public String getDefault() {
575: return null;
576: }
577:
578: /**
579: * @see schema.Element#getFinal()
580: */
581: public int getFinal() {
582: return Schema.NONE;
583: }
584:
585: /**
586: * @see schema.Element#getFixed()
587: */
588: public String getFixed() {
589: return null;
590: }
591:
592: /**
593: * @see schema.Element#isForm()
594: */
595: public boolean isForm() {
596: return false;
597: }
598:
599: /**
600: * @see schema.Element#getId()
601: */
602: public String getId() {
603: return null;
604: }
605:
606: /**
607: * @see schema.Element#getMaxOccurs()
608: */
609: public int getMaxOccurs() {
610: return max;
611: }
612:
613: /**
614: * @see schema.Element#getMinOccurs()
615: */
616: public int getMinOccurs() {
617: return min;
618: }
619:
620: /**
621: * @see schema.Element#getName()
622: */
623: public String getName() {
624: return name;
625: }
626:
627: /**
628: * @see schema.Element#isNillable()
629: */
630: public boolean isNillable() {
631: return false;
632: }
633:
634: /**
635: * @see schema.Element#getSubstitutionGroup()
636: */
637: public Element getSubstitutionGroup() {
638: return substitutionGroup;
639: }
640:
641: /**
642: * @see schema.Element#getType()
643: */
644: public Type getType() {
645: return type;
646: }
647:
648: /**
649: * @see schema.Element#getNamespace()
650: */
651: public URI getNamespace() {
652: return WFSSchema.NAMESPACE;
653: }
654:
655: public Element findChildElement(String localName,
656: URI namespaceURI) {
657: if (this .name != null) {
658: if (this .name.equals(localName)
659: && this .getNamespace().equals(namespaceURI)) {
660: return this ;
661: }
662: }
663:
664: return null;
665: }
666: }
667:
668: /**
669: * <p>
670: * An instance of this class represents a WFS attribute. This
671: * implementation contains some constant data pertinent to the WFS Schema,
672: * and some configurable data depending on the WFS attribute being
673: * represented.
674: * </p>
675: *
676: * @author Norman Barker
677: * @author David Zwiers
678: *
679: * @see Attribute
680: */
681: static class WFSAttribute extends AttributeGT {
682: /*
683: * Should never be called
684: */
685: private WFSAttribute() {
686: super (null, null, WFSSchema.NAMESPACE, null, OPTIONAL,
687: null, null, false);
688: }
689:
690: /**
691: * Creates a GML attribute based on the name and type provided.
692: *
693: * @param name
694: * @param simpleType
695: */
696: public WFSAttribute(String name, SimpleType simpleType) {
697: super (null, name, WFSSchema.NAMESPACE, simpleType,
698: OPTIONAL, null, null, false);
699: }
700:
701: /**
702: * Creates a GML attribute based on the name, use and type provided.
703: *
704: * @param name
705: * @param simpleType
706: * @param use
707: */
708: public WFSAttribute(String name, SimpleType simpleType, int use) {
709: super (null, name, WFSSchema.NAMESPACE, simpleType, use,
710: null, null, false);
711: }
712:
713: /**
714: * Creates a GML attribute based on the name, use, default and type
715: * provided.
716: *
717: * @param name
718: * @param simpleType
719: * @param use
720: * @param def
721: */
722: public WFSAttribute(String name, SimpleType simpleType,
723: int use, String def) {
724: super (null, name, WFSSchema.NAMESPACE, simpleType, use,
725: def, null, false);
726: }
727: }
728: }
|