001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017:
018: package org.apache.xerces.impl.xs.traversers;
019:
020: import org.apache.xerces.impl.xs.SchemaGrammar;
021: import org.apache.xerces.impl.xs.SchemaSymbols;
022: import org.apache.xerces.impl.xs.XSElementDecl;
023: import org.apache.xerces.impl.xs.identity.IdentityConstraint;
024: import org.apache.xerces.impl.xs.identity.KeyRef;
025: import org.apache.xerces.impl.xs.identity.UniqueOrKey;
026: import org.apache.xerces.xni.QName;
027: import org.w3c.dom.Element;
028:
029: /**
030: * This class contains code that is used to traverse <keyref>s.
031: *
032: * @xerces.internal
033: *
034: * @author Neil Graham, IBM
035: * @version $Id: XSDKeyrefTraverser.java 446725 2006-09-15 20:40:10Z mrglavas $
036: */
037: class XSDKeyrefTraverser extends XSDAbstractIDConstraintTraverser {
038:
039: public XSDKeyrefTraverser(XSDHandler handler,
040: XSAttributeChecker gAttrCheck) {
041: super (handler, gAttrCheck);
042: }
043:
044: void traverse(Element krElem, XSElementDecl element,
045: XSDocumentInfo schemaDoc, SchemaGrammar grammar) {
046:
047: // General Attribute Checking
048: Object[] attrValues = fAttrChecker.checkAttributes(krElem,
049: false, schemaDoc);
050:
051: // create identity constraint
052: String krName = (String) attrValues[XSAttributeChecker.ATTIDX_NAME];
053: if (krName == null) {
054: reportSchemaError("s4s-att-must-appear", new Object[] {
055: SchemaSymbols.ELT_KEYREF, SchemaSymbols.ATT_NAME },
056: krElem);
057: //return this array back to pool
058: fAttrChecker.returnAttrArray(attrValues, schemaDoc);
059: return;
060: }
061: QName kName = (QName) attrValues[XSAttributeChecker.ATTIDX_REFER];
062: if (kName == null) {
063: reportSchemaError("s4s-att-must-appear",
064: new Object[] { SchemaSymbols.ELT_KEYREF,
065: SchemaSymbols.ATT_REFER }, krElem);
066: //return this array back to pool
067: fAttrChecker.returnAttrArray(attrValues, schemaDoc);
068: return;
069: }
070:
071: UniqueOrKey key = null;
072: IdentityConstraint ret = (IdentityConstraint) fSchemaHandler
073: .getGlobalDecl(schemaDoc,
074: XSDHandler.IDENTITYCONSTRAINT_TYPE, kName,
075: krElem);
076: // if ret == null, we've already reported an error in getGlobalDecl
077: // we report an error only when ret != null, and the return type keyref
078: if (ret != null) {
079: if (ret.getCategory() == IdentityConstraint.IC_KEY
080: || ret.getCategory() == IdentityConstraint.IC_UNIQUE) {
081: key = (UniqueOrKey) ret;
082: } else {
083: reportSchemaError("src-resolve",
084: new Object[] { kName.rawname,
085: "identity constraint key/unique" },
086: krElem);
087: }
088: }
089:
090: if (key == null) {
091: fAttrChecker.returnAttrArray(attrValues, schemaDoc);
092: return;
093: }
094:
095: KeyRef keyRef = new KeyRef(schemaDoc.fTargetNamespace, krName,
096: element.fName, key);
097:
098: // add to element decl
099: traverseIdentityConstraint(keyRef, krElem, schemaDoc,
100: attrValues);
101:
102: //Schema Component Constraint: Identity-constraint Definition Properties Correct
103: //2 If the {identity-constraint category} is keyref, the cardinality of the {fields} must equal that of the {fields} of the {referenced key}.
104: if (key.getFieldCount() != keyRef.getFieldCount()) {
105: reportSchemaError("c-props-correct.2", new Object[] {
106: krName, key.getIdentityConstraintName() }, krElem);
107: } else {
108: // add key reference to element decl
109: // and stuff this in the grammar
110: grammar.addIDConstraintDecl(element, keyRef);
111: }
112:
113: // and put back attributes
114: fAttrChecker.returnAttrArray(attrValues, schemaDoc);
115: } // traverse(Element,int,XSDocumentInfo, SchemaGrammar)
116: } // XSDKeyrefTraverser
|