001 /* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, 013 * software distributed under the License is distributed on an 014 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 015 * KIND, either express or implied. See the License for the 016 * specific language governing permissions and limitations 017 * under the License. 018 */ 019 package javax.xml.soap; 020 021 import java.util.Iterator; 022 import java.util.Vector; 023 024 /** 025 * A container for <CODE>MimeHeader</CODE> objects, which represent the MIME headers present in a 026 * MIME part of a message.</P> 027 * <p/> 028 * <P>This class is used primarily when an application wants to retrieve specific attachments based 029 * on certain MIME headers and values. This class will most likely be used by implementations of 030 * <CODE>AttachmentPart</CODE> and other MIME dependent parts of the JAXM API. 031 * 032 * @see SOAPMessage#getAttachments() SOAPMessage.getAttachments() 033 * @see AttachmentPart AttachmentPart 034 */ 035 public class MimeHeaders { 036 037 class MatchingIterator implements Iterator { 038 039 private Object nextMatch() { 040 041 label0: 042 while (iterator.hasNext()) { 043 MimeHeader mimeheader = (MimeHeader)iterator.next(); 044 045 if (names == null) { 046 return match 047 ? null 048 : mimeheader; 049 } 050 051 for (int i = 0; i < names.length; i++) { 052 if (!mimeheader.getName().equalsIgnoreCase(names[i])) { 053 continue; 054 } 055 056 if (match) { 057 return mimeheader; 058 } 059 060 continue label0; 061 } 062 063 if (!match) { 064 return mimeheader; 065 } 066 } 067 068 return null; 069 } 070 071 public boolean hasNext() { 072 073 if (nextHeader == null) { 074 nextHeader = nextMatch(); 075 } 076 077 return nextHeader != null; 078 } 079 080 public Object next() { 081 082 if (nextHeader != null) { 083 Object obj = nextHeader; 084 085 nextHeader = null; 086 087 return obj; 088 } 089 090 if (hasNext()) { 091 return nextHeader; 092 } else { 093 return null; 094 } 095 } 096 097 public void remove() { 098 iterator.remove(); 099 } 100 101 private boolean match; 102 103 private Iterator iterator; 104 105 private String names[]; 106 107 private Object nextHeader; 108 109 MatchingIterator(String as[], boolean flag) { 110 111 match = flag; 112 names = as; 113 iterator = headers.iterator(); 114 } 115 } 116 117 /** 118 * Constructs a default <CODE>MimeHeaders</CODE> object initialized with an empty 119 * <CODE>Vector</CODE> object. 120 */ 121 public MimeHeaders() { 122 headers = new Vector(); 123 } 124 125 /** 126 * Returns all of the values for the specified header as an array of <CODE>String</CODE> 127 * objects. 128 * 129 * @param name the name of the header for which values will be returned 130 * @return a <CODE>String</CODE> array with all of the values for the specified header 131 * @see #setHeader(String, String) setHeader(java.lang.String, 132 * java.lang.String) 133 */ 134 public String[] getHeader(String name) { 135 136 Vector vector = new Vector(); 137 138 for (int i = 0; i < headers.size(); i++) { 139 MimeHeader mimeheader = (MimeHeader)headers.elementAt(i); 140 141 if (mimeheader.getName().equalsIgnoreCase(name) 142 && (mimeheader.getValue() != null)) { 143 vector.addElement(mimeheader.getValue()); 144 } 145 } 146 147 if (vector.size() == 0) { 148 return null; 149 } else { 150 String as[] = new String[vector.size()]; 151 152 vector.copyInto(as); 153 154 return as; 155 } 156 } 157 158 /** 159 * Replaces the current value of the first header entry whose name matches the given name with 160 * the given value, adding a new header if no existing header name matches. This method also 161 * removes all matching headers after the first one. 162 * <p/> 163 * <P>Note that RFC822 headers can contain only US-ASCII characters.</P> 164 * 165 * @param name a <CODE>String</CODE> with the name of the header for which to search 166 * @param value a <CODE>String</CODE> with the value that will replace the current value of the 167 * specified header 168 * @throws IllegalArgumentException 169 * if there was a problem in the mime header name or the value being set 170 * @see #getHeader(String) getHeader(java.lang.String) 171 */ 172 public void setHeader(String name, String value) { 173 174 boolean flag = false; 175 176 if ((name == null) || "".equals(name)) { 177 throw new IllegalArgumentException("Illegal MimeHeader name"); 178 } 179 180 for (int i = 0; i < headers.size(); i++) { 181 MimeHeader mimeheader = (MimeHeader)headers.elementAt(i); 182 183 if (mimeheader.getName().equalsIgnoreCase(name)) { 184 if (!flag) { 185 headers.setElementAt(new MimeHeader(mimeheader 186 .getName(), value), i); 187 188 flag = true; 189 } else { 190 headers.removeElementAt(i--); 191 } 192 } 193 } 194 195 if (!flag) { 196 addHeader(name, value); 197 } 198 } 199 200 /** 201 * Adds a <CODE>MimeHeader</CODE> object with the specified name and value to this 202 * <CODE>MimeHeaders</CODE> object's list of headers. 203 * <p/> 204 * <P>Note that RFC822 headers can contain only US-ASCII characters.</P> 205 * 206 * @param name a <CODE>String</CODE> with the name of the header to be added 207 * @param value a <CODE>String</CODE> with the value of the header to be added 208 * @throws IllegalArgumentException 209 * if there was a problem in the mime header name or value being added 210 */ 211 public void addHeader(String name, String value) { 212 213 if ((name == null) || "".equals(name)) { 214 throw new IllegalArgumentException("Illegal MimeHeader name"); 215 } 216 217 int i = headers.size(); 218 219 for (int j = i - 1; j >= 0; j--) { 220 MimeHeader mimeheader = (MimeHeader)headers.elementAt(j); 221 222 if (mimeheader.getName().equalsIgnoreCase(name)) { 223 headers.insertElementAt(new MimeHeader(name, value), j + 1); 224 225 return; 226 } 227 } 228 229 headers.addElement(new MimeHeader(name, value)); 230 } 231 232 /** 233 * Remove all <CODE>MimeHeader</CODE> objects whose name matches the the given name. 234 * 235 * @param name a <CODE>String</CODE> with the name of the header for which to search 236 */ 237 public void removeHeader(String name) { 238 239 for (int i = 0; i < headers.size(); i++) { 240 MimeHeader mimeheader = (MimeHeader)headers.elementAt(i); 241 242 if (mimeheader.getName().equalsIgnoreCase(name)) { 243 headers.removeElementAt(i--); 244 } 245 } 246 } 247 248 /** Removes all the header entries from this <CODE> MimeHeaders</CODE> object. */ 249 public void removeAllHeaders() { 250 headers.removeAllElements(); 251 } 252 253 /** 254 * Returns all the headers in this <CODE>MimeHeaders</CODE> object. 255 * 256 * @return an <CODE>Iterator</CODE> object over this <CODE> MimeHeaders</CODE> object's list of 257 * <CODE> MimeHeader</CODE> objects 258 */ 259 public Iterator getAllHeaders() { 260 return headers.iterator(); 261 } 262 263 /** 264 * Returns all the <CODE>MimeHeader</CODE> objects whose name matches a name in the given array 265 * of names. 266 * 267 * @param names an array of <CODE>String</CODE> objects with the names for which to search 268 * @return an <CODE>Iterator</CODE> object over the <CODE> MimeHeader</CODE> objects whose name 269 * matches one of the names in the given list 270 */ 271 public Iterator getMatchingHeaders(String names[]) { 272 return new MatchingIterator(names, true); 273 } 274 275 /** 276 * Returns all of the <CODE>MimeHeader</CODE> objects whose name does not match a name in the 277 * given array of names. 278 * 279 * @param names an array of <CODE>String</CODE> objects with the names for which to search 280 * @return an <CODE>Iterator</CODE> object over the <CODE> MimeHeader</CODE> objects whose name 281 * does not match one of the names in the given list 282 */ 283 public Iterator getNonMatchingHeaders(String names[]) { 284 return new MatchingIterator(names, false); 285 } 286 287 // fixme: does this need to be a Vector? Will a non-synchronized impl of 288 // List do? 289 /** A <code>Vector</code> containing the headers as <code>MimeHeader</code> instances. */ 290 private Vector headers; 291 }