/// <summary>Closes connection to file.</summary> /// <remarks>This method also releases any resources held while reading.</remarks> public void Close() { textInput = null; image = null; cloud = null; channel = null; source = null; enclosure = null; category = null; item = null; if (reader != null) { reader.Close(); reader = null; } elementText = null; xmlNodeStack = null; }
/// <summary>Writes an RSS item</summary> /// <exception cref="InvalidOperationException">Either the RssWriter has already been closed, or the caller is attempting to write an RSS item before an RSS channel.</exception> /// <exception cref="ArgumentNullException">Item must be instanciated with data, before calling Write.</exception> /// <param name="item">RSS item to write</param> public void Write(RssItem item) { // NOTE: Standalone items cannot adhere to modules, hence -1 is passed. This may not be the case, however, no examples have been seen where this is legal. writeItem(item, -1); }
/// <summary>Reads the next RssElement from the stream.</summary> /// <returns>An RSS Element</returns> /// <exception cref="InvalidOperationException">RssReader has been closed, and can not be read.</exception> /// <exception cref="System.IO.FileNotFoundException">RSS file not found.</exception> /// <exception cref="System.Xml.XmlException">Invalid XML syntax in RSS file.</exception> /// <exception cref="System.IO.EndOfStreamException">Unable to read an RssElement. Reached the end of the stream.</exception> public RssElement Read() { var readData = false; var pushElement = true; RssElement rssElement = null; var lineNumber = -1; var linePosition = -1; if (reader == null) { throw new InvalidOperationException("RssReader has been closed, and can not be read."); } do { pushElement = true; try { readData = reader.Read(); } catch (EndOfStreamException e) { throw new EndOfStreamException("Unable to read an RssElement. Reached the end of the stream.", e); } catch (XmlException e) { if (lineNumber != -1 || linePosition != -1) { if (reader.LineNumber == lineNumber && reader.LinePosition == linePosition) { throw exceptions.LastException; } } lineNumber = reader.LineNumber; linePosition = reader.LinePosition; exceptions.Add(e); // just add to list of exceptions and continue :) } if (readData) { var readerName = reader.Name.ToLower(); switch (reader.NodeType) { case XmlNodeType.Element: { if (reader.IsEmptyElement) { break; } elementText = new StringBuilder(); switch (readerName) { case "item": // is this the end of the channel element? (absence of </channel> before <item>) if (!wroteChannel) { wroteChannel = true; rssElement = channel; // return RssChannel readData = false; } item = new RssItem(); // create new RssItem channel.Items.Add(item); break; case "source": source = new RssSource(); item.Source = source; for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); switch (reader.Name.ToLower()) { case "url": try { source.Url = new Uri(reader.Value); } catch (Exception e) { exceptions.Add(e); } break; } } break; case "enclosure": enclosure = new RssEnclosure(); item.Enclosure = enclosure; for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); switch (reader.Name.ToLower()) { case "url": try { enclosure.Url = new Uri(reader.Value); } catch (Exception e) { exceptions.Add(e); } break; case "length": try { enclosure.Length = int.Parse(reader.Value); } catch (Exception e) { exceptions.Add(e); } break; case "type": enclosure.Type = reader.Value; break; } } break; case "guid": guid = new RssGuid(); item.Guid = guid; for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); switch (reader.Name.ToLower()) { case "ispermalink": try { guid.PermaLink = bool.Parse(reader.Value); } catch (Exception e) { exceptions.Add(e); } break; } } break; case "category": category = new RssCategory(); if ((string)xmlNodeStack.Peek() == "channel") { channel.Categories.Add(category); } else { item.Categories.Add(category); } for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); switch (reader.Name.ToLower()) { case "url": goto case "domain"; case "domain": category.Domain = reader.Value; break; } } break; case "channel": channel = new RssChannel(); textInput = null; image = null; cloud = null; source = null; enclosure = null; category = null; item = null; break; case "image": image = new RssImage(); channel.Image = image; break; case "textinput": textInput = new RssTextInput(); channel.TextInput = textInput; break; case "cloud": pushElement = false; cloud = new RssCloud(); channel.Cloud = cloud; for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); switch (reader.Name.ToLower()) { case "domain": cloud.Domain = reader.Value; break; case "port": try { cloud.Port = ushort.Parse(reader.Value); } catch (Exception e) { exceptions.Add(e); } break; case "path": cloud.Path = reader.Value; break; case "registerprocedure": cloud.RegisterProcedure = reader.Value; break; case "protocol": switch (reader.Value.ToLower()) { case "xml-rpc": cloud.Protocol = RssCloudProtocol.XmlRpc; break; case "soap": cloud.Protocol = RssCloudProtocol.Soap; break; case "http-post": cloud.Protocol = RssCloudProtocol.HttpPost; break; default: cloud.Protocol = RssCloudProtocol.Empty; break; } break; } } break; case "rss": for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); if (reader.Name.ToLower() == "version") { switch (reader.Value) { case "0.91": rssVersion = RssVersion.RSS091; break; case "0.92": rssVersion = RssVersion.RSS092; break; case "2.0": rssVersion = RssVersion.RSS20; break; default: rssVersion = RssVersion.NotSupported; break; } } } break; case "rdf": for (var i = 0; i < reader.AttributeCount; i++) { reader.MoveToAttribute(i); if (reader.Name.ToLower() == "version") { switch (reader.Value) { case "0.90": rssVersion = RssVersion.RSS090; break; case "1.0": rssVersion = RssVersion.RSS10; break; default: rssVersion = RssVersion.NotSupported; break; } } } break; } if (pushElement) { xmlNodeStack.Push(readerName); } break; } case XmlNodeType.EndElement: { if (xmlNodeStack.Count == 1) { break; } var childElementName = (string)xmlNodeStack.Pop(); var parentElementName = (string)xmlNodeStack.Peek(); switch (childElementName) // current element { // item classes case "item": rssElement = item; readData = false; break; case "source": source.Name = elementText.ToString(); rssElement = source; readData = false; break; case "enclosure": rssElement = enclosure; readData = false; break; case "guid": guid.Name = elementText.ToString(); rssElement = guid; readData = false; break; case "category": // parent is either item or channel category.Name = elementText.ToString(); rssElement = category; readData = false; break; // channel classes case "channel": if (wroteChannel) { wroteChannel = false; } else { wroteChannel = true; rssElement = channel; readData = false; } break; case "textinput": rssElement = textInput; readData = false; break; case "image": rssElement = image; readData = false; break; case "cloud": rssElement = cloud; readData = false; break; } switch (parentElementName) // parent element { case "item": switch (childElementName) { case "title": item.Title = elementText.ToString(); break; case "link": item.Link = new Uri(elementText.ToString()); break; case "description": item.Description = elementText.ToString(); break; case "author": item.Author = elementText.ToString(); break; case "comments": item.Comments = elementText.ToString(); break; case "pubdate": try { item.PubDate = DateTime.Parse(elementText.ToString()); } catch (Exception e) { try { var tmp = elementText.ToString(); tmp = tmp.Substring(0, tmp.Length - 5); tmp += "GMT"; item.PubDate = DateTime.Parse(tmp); } catch { exceptions.Add(e); } } break; } break; case "channel": switch (childElementName) { case "title": channel.Title = elementText.ToString(); break; case "link": try { channel.Link = new Uri(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; case "description": channel.Description = elementText.ToString(); break; case "language": channel.Language = elementText.ToString(); break; case "copyright": channel.Copyright = elementText.ToString(); break; case "managingeditor": channel.ManagingEditor = elementText.ToString(); break; case "webmaster": channel.WebMaster = elementText.ToString(); break; case "rating": channel.Rating = elementText.ToString(); break; case "pubdate": try { channel.PubDate = DateTime.Parse(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; case "lastbuilddate": try { channel.LastBuildDate = DateTime.Parse(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; case "generator": channel.Generator = elementText.ToString(); break; case "docs": channel.Docs = elementText.ToString(); break; case "ttl": try { channel.TimeToLive = int.Parse(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; } break; case "image": switch (childElementName) { case "url": try { image.Url = new Uri(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; case "title": image.Title = elementText.ToString(); break; case "link": try { image.Link = new Uri(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; case "description": image.Description = elementText.ToString(); break; case "width": try { image.Width = Byte.Parse(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; case "height": try { image.Height = Byte.Parse(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; } break; case "textinput": switch (childElementName) { case "title": textInput.Title = elementText.ToString(); break; case "description": textInput.Description = elementText.ToString(); break; case "name": textInput.Name = elementText.ToString(); break; case "link": try { textInput.Link = new Uri(elementText.ToString()); } catch (Exception e) { exceptions.Add(e); } break; } break; case "skipdays": if (childElementName == "day") { switch (elementText.ToString().ToLower()) { case "monday": channel.SkipDays[0] = true; break; case "tuesday": channel.SkipDays[1] = true; break; case "wednesday": channel.SkipDays[2] = true; break; case "thursday": channel.SkipDays[3] = true; break; case "friday": channel.SkipDays[4] = true; break; case "saturday": channel.SkipDays[5] = true; break; case "sunday": channel.SkipDays[6] = true; break; } } break; case "skiphours": if (childElementName == "hour") { channel.SkipHours[Byte.Parse(elementText.ToString().ToLower())] = true; } break; } break; } case XmlNodeType.Text: elementText.Append(reader.Value); break; case XmlNodeType.CDATA: elementText.Append(reader.Value); break; } } }while (readData); return(rssElement); }
static void Main(string[] args) { var r = new RssFeed(); r.Version = RssVersion.RSS20; var ri1a = new RssItem(); ri1a.Author = "Test Author 1a"; ri1a.Title = "Test Title 1a"; ri1a.Description = "Test Description 1a"; ri1a.Link = new Uri("http://www.yourserver.com/"); ri1a.PubDate = DateTime.Now; var ri1b = new RssItem(); ri1b.Author = "Test Author 1b"; ri1b.Title = "Test Title 1b"; ri1b.Description = "Test Description 1b"; ri1b.Link = new Uri("http://www.yourserver.com/"); ri1b.PubDate = DateTime.Now; var rc1 = new RssChannel(); rc1.Items.Add(ri1a); rc1.Items.Add(ri1b); rc1.Title = "Test Channel Title 1"; rc1.Description = "Test Channel Description 1"; rc1.Link = new Uri("http://www.yourserver.com/channel.html"); rc1.PubDate = DateTime.Now; r.Channels.Add(rc1); var pacpp = new RssPhotoAlbumCategoryPhotoPeople("John Doe"); var pacp1 = new RssPhotoAlbumCategoryPhoto(DateTime.Now.Subtract(new TimeSpan(2, 12, 0, 0)), "Test Photo Description 1", new Uri("http://www.yourserver.com/PhotoAlbumWeb/GetPhoto.aspx?PhotoID=123"), pacpp); var pacp2 = new RssPhotoAlbumCategoryPhoto(DateTime.Now.Subtract(new TimeSpan(2, 10, 0, 0)), "Test Photo Description 2", new Uri("http://www.yourserver.com/PhotoAlbumWeb/GetPhoto.aspx?PhotoID=124")); var pacp3 = new RssPhotoAlbumCategoryPhoto(DateTime.Now.Subtract(new TimeSpan(2, 10, 0, 0)), "Test Photo Description 2", new Uri("http://www.yourserver.com/PhotoAlbumWeb/GetPhoto.aspx?PhotoID=125")); var pacps = new RssPhotoAlbumCategoryPhotos(); pacps.Add(pacp1); pacps.Add(pacp2); var pac1 = new RssPhotoAlbumCategory("Test Photo Album Category 1", "Test Photo Album Category Description 1", DateTime.Now.Subtract(new TimeSpan(5, 10, 0, 0)), DateTime.Now, pacps); var pac2 = new RssPhotoAlbumCategory("Test Photo Album Category 2", "Test Photo Album Category Description 2", DateTime.Now.Subtract(new TimeSpan(9, 10, 0, 0)), DateTime.Now, pacp3); var pacs = new RssPhotoAlbumCategories(); pac1.BindTo(ri1a.GetHashCode()); pac2.BindTo(ri1b.GetHashCode()); pacs.Add(pac1); pacs.Add(pac2); var pa = new RssPhotoAlbum(new Uri("http://your.web.server/PhotoAlbumWeb"), pacs); pa.BindTo(rc1.GetHashCode()); r.Modules.Add(pa); var ri2 = new RssItem(); ri2.Author = "Test Author 2"; ri2.Title = "Test Title 2"; ri2.Description = "Test Description 2"; ri2.Link = new Uri("http://www.yourotherserver.com/"); ri2.PubDate = DateTime.Now; var rc2 = new RssChannel(); rc2.Items.Add(ri2); rc2.Title = "Test Channel Title 2"; rc2.Description = "Test Channel Description 2"; rc2.Link = new Uri("http://www.yourotherserver.com/channel.html"); rc2.PubDate = DateTime.Now; r.Channels.Add(rc2); r.Write("out.xml"); var rbc = new RssBlogChannel(new Uri("http://www.google.com"), new Uri("http://www.google.com"), new Uri("http://www.google.com"), new Uri("http://www.google.com")); }
private void writeItem(RssItem item, int channelHashCode) { if (writer == null) { throw new InvalidOperationException("RssWriter has been closed, and can not be written to."); } if (item == null) { throw new ArgumentNullException("Item must be instanciated with data to be written."); } if (!wroteChannel) { throw new InvalidOperationException("Channel must be written first, before writing an item."); } BeginDocument(); writer.WriteStartElement("item"); switch (rssVersion) { case RssVersion.RSS090: case RssVersion.RSS10: case RssVersion.RSS091: WriteElement("title", item.Title, true); WriteElement("description", item.Description, false); WriteElement("link", item.Link, true); break; case RssVersion.RSS20: if ((item.Title == RssDefault.String) && (item.Description == RssDefault.String)) { throw new ArgumentException("item title and description cannot be null"); } goto case RssVersion.RSS092; case RssVersion.RSS092: WriteElement("title", item.Title, false); WriteElement("description", item.Description, false); WriteElement("link", item.Link, false); if (item.Source != null) { writer.WriteStartElement("source"); WriteAttribute("url", item.Source.Url, true); writer.WriteString(item.Source.Name); writer.WriteEndElement(); } if (item.Enclosure != null) { writer.WriteStartElement("enclosure"); WriteAttribute("url", item.Enclosure.Url, true); WriteAttribute("length", item.Enclosure.Length, true); WriteAttribute("type", item.Enclosure.Type, true); writer.WriteEndElement(); } foreach (RssCategory category in item.Categories) { if (category.Name != RssDefault.String) { writer.WriteStartElement("category"); WriteAttribute("domain", category.Domain, false); writer.WriteString(category.Name); writer.WriteEndElement(); } } break; } if (rssVersion == RssVersion.RSS20) { WriteElement("author", item.Author, false); WriteElement("comments", item.Comments, false); if ((item.Guid != null) && (item.Guid.Name != RssDefault.String)) { writer.WriteStartElement("guid"); try { WriteAttribute("isPermaLink", (bool)item.Guid.PermaLink, false); } catch {} writer.WriteString(item.Guid.Name); writer.WriteEndElement(); } WriteElement("pubDate", item.PubDate, false); foreach (RssModule rssModule in _rssModules) { if (rssModule.IsBoundTo(channelHashCode)) { foreach (RssModuleItemCollection rssModuleItemCollection in rssModule.ItemExtensions) { if (rssModuleItemCollection.IsBoundTo(item.GetHashCode())) { writeSubElements(rssModuleItemCollection, rssModule.NamespacePrefix); } } } } } writer.WriteEndElement(); writer.Flush(); }
/// <summary>Inserts an item into this collection at a specified index.</summary> /// <param name="index">The zero-based index of the collection at which to insert the item.</param> /// <param name="item">The item to insert into this collection.</param> public void Insert(int index, RssItem item) { pubDateChanged = true; List.Insert(index, item); }
/// <summary>Searches for the specified RssItem and returns the zero-based index of the first occurrence within the entire RssItemCollection.</summary> /// <param name="rssItem">The RssItem to locate in the RssItemCollection.</param> /// <returns>The zero-based index of the first occurrence of RssItem within the entire RssItemCollection, if found; otherwise, -1.</returns> public int IndexOf(RssItem rssItem) { return(List.IndexOf(rssItem)); }
/// <summary>Determines whether the RssItemCollection contains a specific element.</summary> /// <param name="rssItem">The RssItem to locate in the RssItemCollection.</param> /// <returns>true if the RssItemCollection contains the specified value; otherwise, false.</returns> public bool Contains(RssItem rssItem) { return(List.Contains(rssItem)); }
/// <summary>Adds a specified item to this collection.</summary> /// <param name="item">The item to add.</param> /// <returns>The zero-based index of the added item.</returns> public int Add(RssItem item) { pubDateChanged = true; return(List.Add(item)); }
/// <summary>Removes a specified item from this collection.</summary> /// <param name="item">The item to remove.</param> public void Remove(RssItem item) { pubDateChanged = true; List.Remove(item); }