This library is released under a modified BSD license - a certified free
software license. Please take a moment to review the terms and conditions
of the license.
This implementation of the RSS specification was created from original
documents where possible :
Two branches of RSS exist, rooted in versions 0.9 and 0.91 of the
specification. The original 0.9 specification continues on into version
1.0 today, using XML namespaces to define a channel according to the RDF
(Resource Description Framework) defined by the W3C. Version 0.91 simplified
the format and evolved through versions 0.92, 0.93 and version 2.0 today.
Code in this library follows the "0.91" (RSS) branch of the tree due to
its greater popularity. Future versions of this library may revisit this
decision and implement the "0.9" (RDF) branch also.
Code was created test-first using the jUnit and xmlUnit testing
frameworks. Tests captured the specification in an executable form and
ensured compliance. Full source for tests is distributed along with the
library, in the 'test' subpackages. Test classes begin with a "Test_"
prefix and continue with the name of the class they test. For example,
Test_RSSChannelRenderer_v091 tests the rendering of a version 0.91
To avoid ambiguity, class names bear a specification number as a suffix.
Version 0.91 of the specification bearing a "_v091" suffix, "_v092" for
version 0.92 and so on. Where methods deal in objects of particular
types, a suffix was added for clarity - for example getItem_v091() and
getItem_v092() which return channel items for version 0.91 and 0.92
All runtime code is contained under the com.caffeinatedbliss.rss package
hierarchy. Tests in the "test" package under any given java package.
Four classes make up the implementation of each version of the
specification. Two (Channel and Item) are a pure data model implementation
that programmers can use to represent a channel and its items at run time.
The Channel class has a number of properties and a collection of Item
objects, with simple collection management methods to manage them. The
data model is independant of presentation or serialization formats.
An appropriately formatted XML string can be generated for a given RSS
Channel by creating an instance of an RSSChannelRenderer, passing the
channel. Calling toString() will return XML conforming to the appropriate
specification level. The library makes no assumptions as to how
applications will use this XML text though it is likely that it will be
written to a file on a webserver.
Text can be converted to an appropriate RSSChannel object and associated
collection of Items using the RSSParser class. The source of the XML text
is not assumed by the library.
RSS v 0.91 Classes
RSS v 0.92 Classes
Many XML parsers exist. The library shouldn't place a burden on
applications to use any particular implementation of a parser. A
reference implementation of the RSSChannelParser classes were created
for the standard jaxp SAX parser simply because there was a need to
support these parsers in the applications originally driving the
implementation of this library. The RSSChannelParserFactory class
should be expanded to include other parsers as there is need, for
example to utilize MinML, NanoXML, JDOM, DOM4J or (say) Castor.
The RSS Parser Factory creates intances of a given kind of parser.
RSS version differences are wrapped up in the RSSParser_v091 and
RSSParser_v092 interfaces. Applications need to be aware of the
version of the specification that they are dealing with but can
ignore the nuts and bolts of the parsing mechanics. In other words,
does it matter how it gets to the place it's needed, so long as it's
the right type?
The RSSContentHandler class tidies up the nasty SAX ContentHandler
making the _v091 and _v092 SAX parsers a little easier to implement.
An inner class in each handles the nitty-gritty of processing the
Thoughts for future development
- Is there a way to drive the parsing based on the version
number embedded in the XML text?
- Is there a way to remove the version specific suffixes?
- Can the SAX parsers be coded to collect enough data for the
channel object's constructor to be called, and thereby avoid
all the null's? Possibly, collecting the data in a map and
passing the map into a constructor?
- Add other parser implementations?
- SINGLETONS ARE EVIL ... so why the heck did I implement the
parser factory as a singleton? That needs to go sooner
rather than later, as a pretty simple refactoring.
Contacting the author
Feel free to contact me regarding the implementation. If you
have suggestions or improvements I would especially like to see
them. Simply use the Contact form
on the main Chronicle Project website