001/**
002 * Copyright 2011 Bill Brown
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016package com.colorfulsoftware.rss;
017
018import java.io.Serializable;
019
020/**
021 * <p>
022 * The &lt;category> element.
023 * </p>
024 * <p>
025 * From the <a href="http://cyber.law.harvard.edu/rss/rss.html">RSS 2.0
026 * specification</a>...
027 * </p>
028 * <p>
029 * FOR channels: Specify one or more categories that the channel belongs to.
030 * Follows the same rules as the &lt;item>-level <a href=
031 * "http://cyber.law.harvard.edu/rss/rss.html#ltcategorygtSubelementOfLtitemgt"
032 * >category</a> element. More <a
033 * href="http://cyber.law.harvard.edu/rss/rss.html#syndic8">info</a>.
034 * </p>
035 * 
036 * <p>
037 * FOR items: Includes the item in one or more categories. <a href=
038 * "http://cyber.law.harvard.edu/rss/rss.html#ltcategorygtSubelementOfLtitemgt"
039 * >More</a>.
040 * 
041 * <p>
042 * &lt;category> is an optional sub-element of &lt;item>.
043 * </p>
044 * 
045 * <p>
046 * It has one optional attribute, domain, a string that identifies a
047 * categorization taxonomy.
048 * </p>
049 * 
050 * <p>
051 * The value of the element is a forward-slash-separated string that identifies
052 * a hierarchic location in the indicated taxonomy. Processors may establish
053 * conventions for the interpretation of categories. Two examples are provided
054 * below:
055 * </p>
056 * 
057 * <p>
058 * &lt;category>Grateful Dead&lt;/category>
059 * </p>
060 * 
061 * <p>
062 * &lt;category domain="http://www.fool.com/cusips">MSFT&lt;/category>
063 * </p>
064 * 
065 * <p>
066 * You may include as many category elements as you need to, for different
067 * domains, and to have an item cross-referenced in different parts of the same
068 * domain.
069 * </p>
070 * 
071 * @author Bill Brown
072 * 
073 */
074public class Category implements Serializable {
075
076        private static final long serialVersionUID = 3499943299756566396L;
077
078        private final String category;
079
080        private final Attribute domain;
081
082        Category(Attribute domain, String category) throws RSSpectException {
083                this.domain = (domain == null) ? null : new Attribute(domain);
084                // spec doesn't require it but category should be present
085                if (category == null) {
086                        throw new RSSpectException(
087                                        "Category elements SHOULD contain text data.  Empty strings are allowed.");
088                }
089                this.category = category;
090        }
091
092        Category(Category category) {
093                this.domain = category.getDomain();
094                this.category = category.category;
095        }
096
097        /**
098         * @return the category.
099         */
100        public String getCategory() {
101                return category;
102        }
103
104        /**
105         * @return the domain url for the category.
106         */
107        public Attribute getDomain() {
108                return (domain == null) ? null : new Attribute(domain);
109
110        }
111
112        /**
113         * Shows the contents of the &lt;category> element.
114         */
115        @Override
116        public String toString() {
117                return "<category" + ((domain == null) ? ">" : domain + " >")
118                                + category + "</category>";
119        }
120        
121        @Override
122        public boolean equals(Object obj) {
123                if (obj == this) {
124                        return true;
125                }
126                if (!(obj instanceof Category)) {
127                        return false;
128                }
129                return this.toString().equals(obj.toString());
130        }
131        
132        @Override public int hashCode() {
133                return toString().hashCode();
134        }
135
136}