001 /* 002 * JBoss, Home of Professional Open Source. 003 * Copyright 2008, Red Hat Middleware LLC, and individual contributors 004 * as indicated by the @author tags. See the copyright.txt file in the 005 * distribution for a full listing of individual contributors. 006 * 007 * This is free software; you can redistribute it and/or modify it 008 * under the terms of the GNU Lesser General Public License as 009 * published by the Free Software Foundation; either version 2.1 of 010 * the License, or (at your option) any later version. 011 * 012 * This software is distributed in the hope that it will be useful, 013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 015 * Lesser General Public License for more details. 016 * 017 * You should have received a copy of the GNU Lesser General Public 018 * License along with this software; if not, write to the Free 019 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 020 * 02110-1301 USA, or see the FSF site: http://www.fsf.org. 021 */ 022 package org.jboss.dna.graph.requests; 023 024 import java.util.Arrays; 025 import java.util.Collection; 026 import java.util.Collections; 027 import java.util.Iterator; 028 import java.util.LinkedList; 029 import java.util.List; 030 import org.jboss.dna.common.util.CheckArg; 031 import org.jboss.dna.graph.GraphI18n; 032 import org.jboss.dna.graph.Location; 033 import org.jboss.dna.graph.properties.Property; 034 035 /** 036 * Instruction to update the properties on the node at the specified location. Any property with no values will be removed. 037 * 038 * @author Randall Hauch 039 */ 040 public class UpdatePropertiesRequest extends Request implements Iterable<Property> { 041 042 private static final long serialVersionUID = 1L; 043 044 private final Location on; 045 private final List<Property> properties; 046 private Location actualLocation; 047 048 /** 049 * Create a request to update the properties on the node at the supplied location. 050 * 051 * @param on the location of the node to be read 052 * @param properties the new properties on the node 053 * @throws IllegalArgumentException if the location is null or if there are no properties to update 054 */ 055 public UpdatePropertiesRequest( Location on, 056 Property... properties ) { 057 CheckArg.isNotNull(on, "on"); 058 CheckArg.isNotEmpty(properties, "properties"); 059 this.on = on; 060 this.properties = Collections.unmodifiableList(Arrays.asList(properties)); 061 } 062 063 /** 064 * Create a request to update the properties on the node at the supplied location. 065 * 066 * @param on the location of the node to be read 067 * @param properties the new properties on the node 068 * @throws IllegalArgumentException if the location is null or if there are no properties to update 069 */ 070 public UpdatePropertiesRequest( Location on, 071 Iterable<Property> properties ) { 072 CheckArg.isNotNull(on, "on"); 073 CheckArg.isNotNull(properties, "properties"); 074 this.on = on; 075 List<Property> props = new LinkedList<Property>(); 076 for (Property property : properties) { 077 if (property != null) props.add(property); 078 } 079 this.properties = Collections.unmodifiableList(props); 080 CheckArg.isNotEmpty(this.properties, "properties"); 081 } 082 083 /** 084 * Create a request to update the properties on the node at the supplied location. 085 * 086 * @param on the location of the node to be read 087 * @param properties the new properties on the node 088 * @throws IllegalArgumentException if the location is null or if there are no properties to update 089 */ 090 public UpdatePropertiesRequest( Location on, 091 Iterator<Property> properties ) { 092 CheckArg.isNotNull(on, "on"); 093 CheckArg.isNotNull(properties, "properties"); 094 this.on = on; 095 List<Property> props = new LinkedList<Property>(); 096 while (properties.hasNext()) { 097 Property property = properties.next(); 098 if (property != null) props.add(property); 099 } 100 this.properties = Collections.unmodifiableList(props); 101 CheckArg.isNotEmpty(this.properties, "properties"); 102 } 103 104 /** 105 * {@inheritDoc} 106 * 107 * @see org.jboss.dna.graph.requests.Request#isReadOnly() 108 */ 109 @Override 110 public boolean isReadOnly() { 111 return false; 112 } 113 114 /** 115 * Get the location defining the node that is to be updated. 116 * 117 * @return the location of the node; never null 118 */ 119 public Location on() { 120 return on; 121 } 122 123 /** 124 * {@inheritDoc} 125 * 126 * @see java.lang.Iterable#iterator() 127 */ 128 public Iterator<Property> iterator() { 129 return this.properties.iterator(); 130 } 131 132 /** 133 * Get the properties for the node. 134 * 135 * @return the collection of properties; never null and never empty 136 */ 137 public Collection<Property> properties() { 138 return properties; 139 } 140 141 /** 142 * Sets the actual and complete location of the node being updated. This method must be called when processing the request, 143 * and the actual location must have a {@link Location#getPath() path}. 144 * 145 * @param actual the actual location of the node being updated, or null if the {@link #on() current location} should be used 146 * @throws IllegalArgumentException if the actual location does represent the {@link Location#isSame(Location) same location} 147 * as the {@link #on() current location}, or if the actual location does not have a path. 148 */ 149 public void setActualLocationOfNode( Location actual ) { 150 if (!on.isSame(actual)) { // not same if actual is null 151 throw new IllegalArgumentException(GraphI18n.actualLocationIsNotSameAsInputLocation.text(actual, on)); 152 } 153 assert actual != null; 154 if (!actual.hasPath()) { 155 throw new IllegalArgumentException(GraphI18n.actualLocationMustHavePath.text(actual)); 156 } 157 this.actualLocation = actual; 158 } 159 160 /** 161 * Get the actual location of the node that was updated. 162 * 163 * @return the actual location, or null if the actual location was not set 164 */ 165 public Location getActualLocationOfNode() { 166 return actualLocation; 167 } 168 169 /** 170 * {@inheritDoc} 171 * 172 * @see java.lang.Object#equals(java.lang.Object) 173 */ 174 @Override 175 public boolean equals( Object obj ) { 176 if (this.getClass().isInstance(obj)) { 177 UpdatePropertiesRequest that = (UpdatePropertiesRequest)obj; 178 if (!this.on().equals(that.on())) return false; 179 if (!this.properties().equals(that.properties())) return false; 180 return true; 181 } 182 return false; 183 } 184 185 /** 186 * {@inheritDoc} 187 * 188 * @see java.lang.Object#toString() 189 */ 190 @Override 191 public String toString() { 192 return "update properties on " + on() + " to " + properties(); 193 } 194 195 }