001 /* 002 * JBoss DNA (http://www.jboss.org/dna) 003 * See the COPYRIGHT.txt file distributed with this work for information 004 * regarding copyright ownership. Some portions may be licensed 005 * to Red Hat, Inc. under one or more contributor license agreements. 006 * See the AUTHORS.txt file in the distribution for a full listing of 007 * individual contributors. 008 * 009 * JBoss DNA is free software. Unless otherwise indicated, all code in JBoss DNA 010 * is licensed to you under the terms of the GNU Lesser General Public License as 011 * published by the Free Software Foundation; either version 2.1 of 012 * the License, or (at your option) any later version. 013 * 014 * JBoss DNA is distributed in the hope that it will be useful, 015 * but WITHOUT ANY WARRANTY; without even the implied warranty of 016 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 017 * Lesser General Public License for more details. 018 * 019 * You should have received a copy of the GNU Lesser General Public 020 * License along with this software; if not, write to the Free 021 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 022 * 02110-1301 USA, or see the FSF site: http://www.fsf.org. 023 */ 024 package org.jboss.dna.graph.property.basic; 025 026 import java.util.Arrays; 027 import java.util.Iterator; 028 import net.jcip.annotations.Immutable; 029 import org.jboss.dna.common.text.TextEncoder; 030 import org.jboss.dna.common.util.CheckArg; 031 import org.jboss.dna.graph.property.Name; 032 import org.jboss.dna.graph.property.NamespaceRegistry; 033 import org.jboss.dna.graph.property.Path; 034 import org.jboss.dna.graph.property.Property; 035 import org.jboss.dna.graph.property.ValueComparators; 036 037 /** 038 * @author Randall Hauch 039 */ 040 @Immutable 041 public abstract class BasicProperty implements Property { 042 043 private final Name name; 044 045 /** 046 * @param name 047 */ 048 public BasicProperty( Name name ) { 049 this.name = name; 050 } 051 052 /** 053 * {@inheritDoc} 054 */ 055 public Name getName() { 056 return name; 057 } 058 059 /** 060 * {@inheritDoc} 061 */ 062 public Iterator<?> getValues() { 063 return iterator(); 064 } 065 066 /** 067 * {@inheritDoc} 068 */ 069 public Object[] getValuesAsArray() { 070 if (size() == 0) return null; 071 Object[] results = new Object[size()]; 072 Iterator<?> iter = iterator(); 073 int index = 0; 074 while (iter.hasNext()) { 075 Object value = iter.next(); 076 results[index++] = value; 077 } 078 return results; 079 } 080 081 /** 082 * {@inheritDoc} 083 */ 084 public int compareTo( Property that ) { 085 if (this == that) return 0; 086 int diff = this.getName().compareTo(that.getName()); 087 if (diff != 0) return diff; 088 diff = this.size() - that.size(); 089 if (diff != 0) return diff; 090 Iterator<?> thisIter = iterator(); 091 Iterator<?> thatIter = that.iterator(); 092 while (thisIter.hasNext()) { // && thatIter.hasNext() 093 Object thisValue = thisIter.next(); 094 Object thatValue = thatIter.next(); 095 diff = ValueComparators.OBJECT_COMPARATOR.compare(thisValue, thatValue); 096 if (diff != 0) return diff; 097 } 098 return 0; 099 } 100 101 /** 102 * {@inheritDoc} 103 */ 104 @Override 105 public int hashCode() { 106 return name.hashCode(); 107 } 108 109 /** 110 * {@inheritDoc} 111 */ 112 @Override 113 public boolean equals( Object obj ) { 114 if (this == obj) return true; 115 if (obj instanceof Property) { 116 Property that = (Property)obj; 117 if (!this.getName().equals(that.getName())) return false; 118 if (this.size() != that.size()) return false; 119 Iterator<?> thisIter = iterator(); 120 Iterator<?> thatIter = that.iterator(); 121 while (thisIter.hasNext()) { // && thatIter.hasNext() 122 Object thisValue = thisIter.next(); 123 Object thatValue = thatIter.next(); 124 if (ValueComparators.OBJECT_COMPARATOR.compare(thisValue, thatValue) != 0) return false; 125 } 126 return true; 127 } 128 return false; 129 } 130 131 /** 132 * {@inheritDoc} 133 */ 134 public String getString() { 135 return getString(null, null, null); 136 } 137 138 /** 139 * {@inheritDoc} 140 */ 141 public String getString( TextEncoder encoder ) { 142 return getString(null, encoder, null); 143 } 144 145 /** 146 * {@inheritDoc} 147 */ 148 public String getString( NamespaceRegistry namespaceRegistry ) { 149 return getString(namespaceRegistry, null, null); 150 } 151 152 /** 153 * {@inheritDoc} 154 */ 155 public String getString( NamespaceRegistry namespaceRegistry, 156 TextEncoder encoder ) { 157 CheckArg.isNotNull(namespaceRegistry, "namespaceRegistry"); 158 return getString(namespaceRegistry, encoder, null); 159 } 160 161 /** 162 * {@inheritDoc} 163 * 164 * @see org.jboss.dna.graph.property.Path#getString(org.jboss.dna.graph.property.NamespaceRegistry, 165 * org.jboss.dna.common.text.TextEncoder, org.jboss.dna.common.text.TextEncoder) 166 */ 167 public String getString( NamespaceRegistry namespaceRegistry, 168 TextEncoder encoder, 169 TextEncoder delimiterEncoder ) { 170 StringBuilder sb = new StringBuilder(); 171 sb.append(getName().getString(namespaceRegistry, encoder, delimiterEncoder)); 172 sb.append(" = "); 173 if (isEmpty()) { 174 sb.append("null"); 175 } else { 176 if (isMultiple()) sb.append("["); 177 boolean first = true; 178 for (Object value : this) { 179 if (first) first = false; 180 else sb.append(","); 181 if (value instanceof Path) { 182 Path path = (Path)value; 183 sb.append(path.getString(namespaceRegistry, encoder, delimiterEncoder)); 184 } else if (value instanceof Name) { 185 Name name = (Name)value; 186 sb.append(name.getString(namespaceRegistry, encoder, delimiterEncoder)); 187 } else { 188 sb.append(value); 189 } 190 } 191 if (isMultiple()) sb.append("]"); 192 } 193 return sb.toString(); 194 } 195 196 /** 197 * {@inheritDoc} 198 * 199 * @see java.lang.Object#toString() 200 */ 201 @Override 202 public String toString() { 203 StringBuilder sb = new StringBuilder(); 204 sb.append(getName()); 205 sb.append(" = "); 206 if (isSingle()) { 207 sb.append(getValues().next()); 208 } else if (isEmpty()) { 209 sb.append("null"); 210 } else { 211 sb.append(Arrays.asList(getValuesAsArray())); 212 } 213 return sb.toString(); 214 } 215 }