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    
020    package javax.activation;
021    
022    import java.io.Externalizable;
023    import java.io.IOException;
024    import java.io.ObjectInput;
025    import java.io.ObjectOutput;
026    
027    
028    /**
029     * @version $Rev: 467553 $ $Date: 2006-10-25 06:01:51 +0200 (Mi, 25. Okt 2006) $
030     */
031    public class MimeType implements Externalizable {
032        private static final String SPECIALS = "()<>@,;:\\\"/[]?=";
033    
034        static boolean isSpecial(char c) {
035            return Character.isWhitespace(c) || Character.isISOControl(c) || SPECIALS.indexOf(c) != -1;
036        }
037    
038        private String primaryType = "application";
039        private String subType = "*";
040        private final MimeTypeParameterList parameterList = new MimeTypeParameterList();;
041    
042        public MimeType() {
043        }
044    
045        public MimeType(String rawdata) throws MimeTypeParseException {
046            parseMimeType(rawdata);
047        }
048    
049        public MimeType(String primary, String sub) throws MimeTypeParseException {
050            setPrimaryType(primary);
051            setSubType(sub);
052        }
053    
054        public String getPrimaryType() {
055            return primaryType;
056        }
057    
058        public void setPrimaryType(String primary) throws MimeTypeParseException {
059            primaryType = parseToken(primary);
060        }
061    
062        public String getSubType() {
063            return subType;
064        }
065    
066        public void setSubType(String sub) throws MimeTypeParseException {
067            subType = parseToken(sub);
068        }
069    
070        public MimeTypeParameterList getParameters() {
071            return parameterList;
072        }
073    
074        public String getParameter(String name) {
075            return parameterList.get(name);
076        }
077    
078        public void setParameter(String name, String value) {
079            parameterList.set(name, value);
080        }
081    
082        public void removeParameter(String name) {
083            parameterList.remove(name);
084        }
085    
086        public String toString() {
087            return getBaseType() + parameterList.toString();
088        }
089    
090        public String getBaseType() {
091            return getPrimaryType() + '/' + getSubType();
092        }
093    
094        public boolean match(MimeType type) {
095            if (!primaryType.equals(type.primaryType)) return false;
096            if ("*".equals(subType)) return true;
097            if ("*".equals(type.subType)) return true;
098            return subType.equals(type.subType);
099        }
100    
101        public boolean match(String rawdata) throws MimeTypeParseException {
102            return match(new MimeType(rawdata));
103        }
104    
105        public void writeExternal(ObjectOutput out) throws IOException {
106            out.writeUTF(toString());
107            out.flush();
108        }
109    
110        public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException {
111            try {
112                parseMimeType(in.readUTF());
113            } catch (MimeTypeParseException mtpex) {
114                throw new IOException(mtpex.getMessage());
115            }
116        }
117    
118        private void parseMimeType(String rawData) throws MimeTypeParseException {
119            int index = rawData.indexOf('/');
120            if (index == -1) {
121                throw new MimeTypeParseException("Expected '/'");
122            }
123            setPrimaryType(rawData.substring(0, index));
124            int index2 = rawData.indexOf(';', index+1);
125            if (index2 == -1) {
126                setSubType(rawData.substring(index+1));
127            } else {
128                setSubType(rawData.substring(index+1, index2));
129                parameterList.parse(rawData.substring(index2));
130            }
131        }
132    
133        private static String parseToken(String tokenString) throws MimeTypeParseException {
134            tokenString = tokenString.trim();
135            for (int i=0; i < tokenString.length(); i++) {
136                char c = tokenString.charAt(i);
137                if (isSpecial(c)) {
138                    throw new MimeTypeParseException("Special '" + c + "' not allowed in token");
139                }
140            }
141            return tokenString;
142        }
143    }