blob: 6d828670334be719ca3a68ec5fe441130fc4126e [file] [log] [blame]
/*
* Copyright 2004-2005 The Apache Software Foundation or its licensors,
* as applicable.
*
* 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.jackrabbit.session.nodetype;
import java.util.HashSet;
import java.util.Set;
import javax.jcr.nodetype.NodeDefinition;
import javax.jcr.nodetype.NodeType;
import javax.jcr.nodetype.PropertyDefinition;
import org.apache.jackrabbit.session.SessionHelper;
import org.apache.jackrabbit.base.nodetype.BaseNodeType;
import org.apache.jackrabbit.name.QName;
import org.apache.jackrabbit.state.nodetype.NodeDefinitionState;
import org.apache.jackrabbit.state.nodetype.NodeTypeState;
import org.apache.jackrabbit.state.nodetype.PropertyDefinitionState;
/**
* Immutable and session-bound node type frontend. An instance
* of this class presents the underlying node type state using
* the JCR NodeType interface. This class also contains simple
* implementations of the higher-order methods defined by the
* NodeType interface.
* <p>
* By not exposing the setter methods of the underlying state instance,
* this class intentionally makes it impossible for a JCR client to modify
* node type information.
*/
final class SessionNodeType extends BaseNodeType implements NodeType {
/** The wildcard item definition name. */
private static final String WILDCARD = "*";
/** Helper for accessing the current session. */
private final SessionHelper helper;
/** The underlying node type state. */
private final NodeTypeState state;
/**
* Creates a node type frontend that is bound to the
* given session and underlying node type state.
*
* @param helper helper for accessing the current session
* @param state underlying node type state
*/
public SessionNodeType(SessionHelper helper, NodeTypeState state) {
this.helper = helper;
this.state = state;
}
/**
* Returns the name of the node type. The returned name is retrieved
* from the underlying node type state and converted into a prefixed
* JCR name using the namespace mappings of the current session.
*
* @return node type name
* @see NodeType#getName()
*/
public String getName() {
return helper.getName(state.getName());
}
/**
* Returns the value of the Mixin node type property. The returned
* value is retrieved from the underlying node type state.
*
* @return Mixin property value
* @see NodeType#isMixin()
*/
public boolean isMixin() {
return state.isMixin();
}
/**
* Returns the value of the HasOrderableChildNodes node type property.
* The returned value is retrieved from the underlying node type state.
*
* @return HasOrderableChildNodes property value
* @see NodeType#hasOrderableChildNodes()
*/
public boolean hasOrderableChildNodes() {
return state.hasOrderableChildNodes();
}
/**
* Returns the name of the primary item of this node type.
* The returned name is retrieved from the underlying node type state
* and converted into a prefixed JCR name using the namespace mappings
* of the current session.
*
* @return primary item name, or <code>null</code> if not specified
* @see NodeType#getPrimaryItemName()
*/
public String getPrimaryItemName() {
QName name = state.getPrimaryItemName();
if (name != null) {
return helper.getName(name);
} else {
return null;
}
}
/**
* Returns the declared supertypes of this node type. The returned
* node types are retrieved from the node type manager of the current
* session using the supertype names stored in the underlying state.
* <p>
* The returned array is freshly instantiated and not a part of the
* underlying state, so it can be freely modified.
*
* @return declared supertypes
* @see NodeType#getDeclaredSupertypes()
*/
public NodeType[] getDeclaredSupertypes() {
Set types = new HashSet();
QName[] names = state.getSupertypeNames();
for (int i = 0; i < names.length; i++) {
types.add(helper.getNodeType(names[i]));
}
return (NodeType[]) types.toArray(new NodeType[types.size()]);
}
/**
* Returns the declared child node definitions of this node type.
* The returned child node definitions are SessionNodeDefs instantiated
* using the node definition states returned by the underlying node type
* state.
* <p>
* The returned array is freshly instantiated and not a part of the
* underlying state, so it can be freely modified.
*
* @return declared child node definitions
* @see SessionNodeDefinition
* @see NodeType#getDeclaredChildNodeDefinitions()
*/
public NodeDefinition[] getDeclaredChildNodeDefinitions() {
Set definitions = new HashSet();
NodeDefinitionState[] states = state.getChildNodeDefinitionStates();
for (int i = 0; i < states.length; i++) {
definitions.add(new SessionNodeDefinition(helper, this, states[i]));
}
return (NodeDefinition[])
definitions.toArray(new NodeDefinition[definitions.size()]);
}
/**
* Returns the declared property definitions of this node type.
* The returned property definitions are SessionPropertyDefs instantiated
* using the property definition states returned by the underlying
* node type state.
* <p>
* The returned array is freshly instantiated and not a part of the
* underlying state, so it can be freely modified.
*
* @return declared child node definitions
* @see SessionPropertyDefinition
* @see NodeType#getDeclaredChildNodeDefs()
*/
public PropertyDefinition[] getDeclaredPropertyDefinitions() {
Set definitions = new HashSet();
PropertyDefinitionState[] states =
state.getPropertyDefinitionStates();
for (int i = 0; i < states.length; i++) {
definitions.add(
new SessionPropertyDefinition(helper, this, states[i]));
}
return (PropertyDefinition[])
definitions.toArray(new PropertyDefinition[definitions.size()]);
}
/**
* Compares objects for equality. Returns <code>true</code> if the
* given object is a SessionNodeType with the same underlying node
* type state and session.
* <p>
* Note that the node type state class does not override the equals
* method and thus the mutable state instances are compared for
* reference equality.
*
* @param that the object to compare this object with
* @return <code>true</code> if the objects are equal,
* <code>false</code> otherwise
* @see Object#equals(Object)
*/
public boolean equals(Object that) {
if (this == that) {
return true;
} else if (that instanceof SessionNodeType) {
return state.equals(((SessionNodeType) that).state)
&& helper.equals(((SessionNodeType) that).helper);
} else {
return false;
}
}
/**
* Returns a hash code for this object. To satisfy the equality
* constraints the returned hash code is a combination of the
* hash codes of the underlying node type state and session.
*
* @return hash code
* @see Object#hashCode()
*/
public int hashCode() {
int code = 17;
code = code * 37 + state.hashCode();
code = code * 37 + helper.hashCode();
return code;
}
}