Monday, November 08, 2010 at 12:02 AM.
system.verbs.builtins.Frontier.tools.commands.addFeed
<<Changes <<4/29/10; 5:16:20 PM by DW <<If the user gives us an HTML page, do the auto-discovery routine, cribbed from river2website.quicksub. <<5/21/08; 8:40:30 PM by DW <<Rewrite to handle RSS 2.0, 1.0 and Atom feeds. Faster. Much simpler. <<3/19/06; 2:31:34 PM by DW <<Cribbed from newsRiverSuite.menuCommands.addRssAtts. <<Adds a node of type "rss" to the frontmost outline, after prompting the user for the URL of the feed. on decode (s) { return (xml.rss.decodeString (s))}; if not defined (user.tools.prefs.lastFeedToLinkTo) { if defined (newsRiverData.prefs.lastFeedUrl) { user.tools.prefs.lastFeedToLinkTo = newsRiverData.prefs.lastFeedUrl} else { user.tools.prefs.lastFeedToLinkTo = "http://"}}; local (url = user.tools.prefs.lastFeedToLinkTo); local (clipboardValue = clipboard.getValue (stringType)); if string.lower (clipboardValue) beginswith "http://" { url = clipboardValue}; op.attributes.getOne ("xmlUrl", @url); if dialog.ask ("URL for feed:", @url) { local (xmltext = tcp.httpreadurl (url), xstruct, atts); try { xml.compile (xmltext, @xstruct)} else { //4/29/10 by DW local (linktable, flfoundfeed = false); xml.getHtmlLinks ("", @linktable, @xmltext); on getlink (type) { local (adrlink); for adrlink in @linktable { if adrlink^.rel == "alternate" { if adrlink^.type == type { url = nameof (adrlink^); flfoundfeed = true; return (true)}}}; return (false)}; if not getlink ("application/rss+xml") { if not getlink ("application/atom+xml") { return ("<h1>Can't subscribe because there are no suitable links in the HTML.</h1>")}}; if not flfoundfeed { scriptError ("Can't add the feed because there is no feed link in the web page.")}; xml.compile (tcp.httpreadurl (url), @xstruct)}; <<scratchpad.xstruct = xstruct new (tabletype, @atts); atts.type = "rss"; atts.xmlUrl = url; atts.title = "Untitled"; atts.htmlUrl = "http://"; bundle { //set atts.title, atts.htmlUrl try { //try RSS 2.0 first local (adrrss = xml.getaddress (@xstruct, "rss")); local (adrchannel = xml.getaddress (adrrss, "channel")); try {atts.title = decode (xml.getvalue (adrchannel, "title"))}; try {atts.htmlUrl = decode (xml.getvalue (adrchannel, "link"))}} else { //then Atom, then RSS 1.0 try { //see if it's Atom local (adrfeed = xml.getaddress (@xstruct, "feed"), adr); try {atts.title = decode (xml.getvalue (adrfeed, "title"))}; for adr in adrfeed { //find atts.htmlUrl, which is buried in a link element (there could be many) if nameof (adr^) endswith "link" { try { local (adratts = @adr^.["/atts"]); if adratts^.rel == "alternate" { if string.lower (adratts^.type) == "text/html" { atts.htmlUrl = decode (adratts^.href)}}}}}} else { //see if it's RSS 1.0 try { local (adrrdf = xml.getAddress (@xstruct, "RDF")); local (adrchannel = xml.getAddress (adrrdf, "channel")); try {atts.title = decode (xml.getValue (adrchannel, "title"))}; try {atts.htmlUrl = decode (xml.getValue (adrchannel, "link"))}}}}}; op.setDisplay (false); op.attributes.addgroup (@atts); op.setlinetext (atts.title); op.setDisplay (true); } <<bundle //old code, 5/21/08 by DW <<local (adrdata = xml.aggregator.init ()) <<local (adrservice = @adrdata^.services.[url], atts) <<user.tools.prefs.lastFeedToLinkTo = url << <<local (servicestable) <<if not defined (adrservice^) <<new (tabletype, @servicestable) <<xml.aggregator.readService (url, @servicestable) <<adrservice = @servicestable.[url] << <<if string.trimwhitespace (op.getlinetext ()) == "" <<op.setlinetext (adrservice^.compilation.channeltitle) <<new (tabletype, @atts) <<atts.title = adrservice^.compilation.channeltitle <<atts.htmlUrl = adrservice^.compilation.channellink
This listing is for code that runs in the OPML Editor environment. I created these listings because I wanted the search engines to index it, so that when I want to look up something in my codebase I don't have to use the much slower search functionality in my object database. Dave Winer.