I woke up this morning to rain and gloom (can't go golfing) so I decided to channel my energy into creating a Technorati ping utility class for those of you that aren't using a blog engine that already includes this functionality. I made a post a long time ago about this but figured I would roll it into a .dll that I can throw into other projects. It's pretty simple and all I have left to do is finish up all the error-handling (i.e. try-catch). Other than that it's 100% functional and pretty painless to use. I should probably also mention that it is .NET 2.0.
using Technorati;
Ping ping = new Ping("http://www.willasrari.com", "Will Asrari");
PingResponse pingResponse = Ping.AttemptWithResponse(ping);
if (pingResponse.Successful)
{
// high-fives
}
else
Response.Write(pingResponse.Message);
You can also call Attempt : bool as well if you don't care about the response message that Technorati provides.
Ping ping = new Ping("http://www.willasrari.com", "Will Asrari");
bool successfulPing = Ping.Attempt(ping);
if (successfulPing)
{
// high-fives
}
The Technorati Ping API is pretty simple. You only need to provide two things: url and url title. That's it.
Easy. Maybe I'll even get an MVP to ask me how to add a reference as a result of posting this.
Notes
I ran into a couple of issues while testing this utility. Even if you get back a successful response that doesn't necessarily mean that your site will be re-indexed. Your ping could've been successful but if you constantly ping without any new updates Technorati will ignore your pings (at least that's how I see it). There were a couple of times that my ping response came back as false and the message was "Thanks for the ping". Could be me, could be Technorati. Hopefully it isn't me.
Download
Will Asrari Technorati Ping Utility (.NET 2.0)
I'll probably provide source code at a later time. I'm going to finish working on it here and there. If you're hip to Reflector why not give that a try.
Tags:
C#,
XML
Thanks to David for pointing out that my RSS feed was down. I went in and fixed it only after logging into my FeedBurner account and trying to navigate (what I feel like) is a counter-intuitive user-interface. Oh well. The feed was too big so I should wrote a stored procedure to select the top 20 published entries. That should be sufficient.
My next order of business is to write a utility / implement one that is already written for Automatic Kismet (Akismet). It's a pretty cool idea as it is a service that the more people use, the smarter it becomes in fighting incessant comment spamming. I get notified everytime there is a new comment via e-mail / text-message (nerd, I know) and can easily click the link and if it is sketchy I can delete as well. Easy. Still a pain after 30 comments about buying Vicodin via hacked University of Nebraska student site.
Tags:
XML
Probably old-hat but useful nonetheless. Serializing an object into Xml or binary can be useful at times. I found some code online awhile back to use and cleaned up a bit. The Serialize / Deserialize methods are now Generic and I added using constructs.
Serialization
In this case I am taking an object and creating an Xml string. You could just as easily create an xml file on the server (user settings / preferences, security information, etc...).
private static string UTF8ByteArrayToString(byte[] characters)
{
return new UTF8Encoding().GetString(characters);
}
public static string SerializeObject<T>(T item)
{
try
{
MemoryStream stream = new MemoryStream();
using (XmlTextWriter xml = new XmlTextWriter(stream, Encoding.UTF8))
{
XmlSerializer xs = new XmlSerializer(typeof(T));
xs.Serialize(xml, item);
stream = (MemoryStream) xml.BaseStream;
}
return UTF8ByteArrayToString(stream.ToArray());
}
catch
{
return string.Empty;
}
}
Deserialization
Just perform the reverse of Serialization!
private static byte[] StringToUTF8ByteArray(string xml)
{
return new UTF8Encoding().GetBytes(xml);
}
public static T DeserializeObject<T>(string xml)
{
using (MemoryStream stream = new MemoryStream(StringToUTF8ByteArray(xml)))
using (new XmlTextWriter(stream, Encoding.UTF8))
{
return (T) new XmlSerializer(typeof (T)).Deserialize(stream);
}
}
Use (Serialization)
Foo foo = new Foo();
foo.Property = ...
foo.AnotherProperty = ...
string xmlString = SerializeObject(foo);
Use (Deserialization)
Foo foo = DeserializeObject<Foo>(xmlString);
Notes
- Xml Serialization ONLY serializes public fields and property values
- Xml Serialization DOES NOT include type information
- Xml Serialization requires a default constructor (note for ReSharper* jedi's!)
- Read-only properties ARE NOT serialized
*When creating a class in Visual Studio with ReSharper installed you will get a greyed-out constructor with a red lightbulb. When you key ALT + ENTER you get the 'Redundant Constructor' message. I always have a default constructor since I am a fan of overloading constructors so I don't know if this is really an issue.
Easy.
Update
It seems that I am not the only one that edited this original codebase. Paul Whitaker did something very similar a couple of days ago as well!
Tags:
C#,
Code,
XML
For some reason my FeedBurner feed hasn't updated since my entry about List<SqlParameter> and Reflection. Apparently someone (me) forgot to rewrite the code for my RSS feed. I took it upon myself to rewrite this blog application using .NET 2.0 this past weekend and forgot a critical element for my subscribers. Whoops.
On a side note, you should see some of the code that I had back there. Disgusting. Now I can cross off the item of rewriting this site. It's only been on the list for about 1.5 years. ;-)
Long story short, feed is back up.
Tags:
XML
A couple of days ago I wrote about sorting child nodes using JavaScript. It appears that there was a small mistake and I'd like to rectify that. The code I posted was both correct and incorrect in that it did sort and to an extent it did sort numerically. I found that it wasn't a true numerical sort when I had a parent node that contained 1, 2, 3, 10. The order was actually 10, 1, 2, 3. So the following code is a TRUE numerical sort using JavaScript.
I was going to post this awhile ago but have been extremely busy with work.
function numericalSort(a, b) { return (a - b); }
function
reOrderChildren ( productGroupNode )
{
var node = null;
var path = null;
var products = productGroupNode.getElementsByTagName("product");
var items = new Array(products.length);
for ( p = 0; p < products.length; p++ )
items[p] = products[p].attributes[0].nodeValue;
// numerically sorts array (ASC);
items.sort(numericalSort);
for ( i = 0; i < items.length; i++ )
{
path = "//productGroup/product[@productId='" + items[i] + "']"
// xml is the name of my Xml Data Island <asp:Xml>
node = xml.selectSingleNode(path);
productGroupNode.appendChild(node);
}
}
Easy.
Tags:
AJAX,
JavaScript,
XML
Man have I been busy lately. Been working on a very large project that has required working from home a lot (after working at the office or on site). The main reason being I have been doing a lot of JavaScript, XML, and now AJAX components and have become completely addicted. One of the components I am working on lately ( and having the most trouble with ) is the drag and drop screen that allows child nodes to be dragged and dropped into parent nodes. The last piece of that puzzle was to figure out how to reorder child nodes numerically within a given parent node on each onDropEvent. I only care about the onDropEvent because the Xml file is generated on the server after being pulled from SQL where the ideal ordering is computed based on configurable business logic and parameters, etc, etc...
One of the things I found while browsing the Internets is that there is some really ugly JavaScript code out there. By ugly I mean sloppy and hard to read. I figured JavaScript programmers would write neater code than what I am finding. It seems as if everyone who writes JavaScript uses Systems or Apps Hungarian notation. objObject. What's up with that? The Xml I've come across in these examples isn't the prettiest either. It doesn't follow any conventions that I've seen, been taught, or use on a daily basis. Here's a quick example:
<
root>
<productGroup productGroupId="1">
<product>
<productId>1</productId>
<productPrice>5.00</productPrice>
</product>
<product>
<productId>2</productId>
<productPrice>3.21</productPrice>
</product>
<product>
<productId>3</productId>
<productPrice>0.99</productPrice>
</product>
</productGroup>
<productGroup productGroupId="2">
<product>
<productId>4</productId>
<productPrice>3.41</productPrice>
</product>
<product>
<productId>5</productId>
<productPrice>2.97</productPrice>
</product>
<product>
<productId>6</productId>
<productPrice>3.59</productPrice>
</product>
</productGroup>
</root>
Not to tell you how to use / write Xml but for what it's worth I format mine like the example below and will reference it in the sample code later on. In my honest opinion it is much easier to read and looks more convenient and elegant.
<
root>
<productGroup productGroupId="1">
<product productId="1" productPrice="5.00" />
<product productId="2" productPrice="4.40" />
<product productId="3" productPrice="3.33" />
</productGroup>
<productGroup productGroupId="2">
<product productId="4" productPrice="2.27" />
<product productId="5" productPrice="3.10" />
<product productId="6" productPrice="4.20" />
</productGroup>
<productGroup productGroupId="3">
<product productId="7" productPrice="4.76" />
<product productId="8" productPrice="3.77" />
<product productId="9" productPrice="0.59" />
</productGroup>
</root>
So now you've implemented some drag-and-drop functionality ( for whatever reason ) and you want to order your child nodes by productId or anything else that would warrant reordering child nodes. At first I started to write this very long and complicated recursive function that took in the current node and then checked to see if the attribute in question was greater than the previous and if so it would do this and if not it would continue looping and then do that.... Well I instead went with the JavaScript Array (since it has a sort method that defaults to alpha / numerical) and populated it with the child nodes of a given Product Group. Then all you need to is sort the array and then create a node and append said node to the parent. Easy.
FYI: Xml attributes are 0-based. So in this example [0] refers to productId. If you wanted to sort by price you would use [1] as the attribute index.
function
reOrderChildren ( productGroupNode )
{
var node = null;
var path = null;
var products = productGroupNode.getElementsByTagName("product");
var items = new Array(products.length);
for ( p = 0; p < products.length; p++ )
items[p] = products[p].attributes[0].nodeValue;
// numerically sorts array (ASC);
items.sort();
for ( i = 0; i < items.length; i++ )
{
path = "//productGroup/product[@productId='" + items[i] + "']"
// xml is the name of my Xml Data Island <asp:Xml>
node = xml.selectSingleNode(path);
productGroupNode.appendChild(node);
}
}
UPDATE: See also.
Tags:
AJAX,
JavaScript,
XML
Has anyone ever tried to create an Xml Data Layer without having primary keys because the software you are customizing doesn`t really have a relational database? Needless to say it is a thrill-ride.
As bad as this instance sucks, SqlXml is pretty fun. Hopefully I am alive by Friday afternoon!
Update: I think we're going to pull it off. The application will work until someone breathes on it wrong.
Tags:
JavaScript,
XML
Anyone that's been on the web for the past couple of months is at least familiar with blogging and Web 2.0 concepts such as tagging and RSS feeds. Two weeks ago I received the April edition of my ASP.NET Pro magazine and read an interesting article on ASP.NET 2.0's new XML functionality. The article sparked my interest when it talked about filtering XmlDataSources.
If you didn't already know you can setup a regular XmlDataSource and do codeless RSS feeds from your .ASPX page. You just set the XmlDataSource to look at a DataFile that is stored locally or on a different server. You can then set the source of your DataList to this data source. Bam. RSS feed.
<asp:XmlDataSource ID="RSSDataSource" Runat="server" DataFile="http://www.willasrari.com/blog/meta/rss.aspx" XPath="rss/channel/item" EnableCaching="true" CacheDuration="300" CacheExpirationPolicy="Sliding" />
<
asp:DataList ID="dlRSSItems" Runat="server" DataSourceID="RSSDataSource">
<ItemTemplate>
<li><a href=`<%# XPath("link") %>`><%# XPath("title") %></a></li>
</ItemTemplate>
</asp:DataList>
It is now possible to filter this RSS feed by keyword. The example below takes the same XmlDataSource from above but filters the results to only show those titles with 'XML' in it.
<asp:XmlDataSource ID="RSSDataSource" Runat="server" DataFile="http://www.willasrari.com/blog/meta/rss.aspx" XPath="rss/channel/item[contains(title,`XML`)]" EnableCaching="true" CacheDuration="300" CacheExpirationPolicy="Sliding" />
<
asp:DataList ID="dlRSSItems" Runat="server" DataSourceID="RSSDataSource">
<ItemTemplate>
<li><a href=`<%# XPath("link") %>`><%# XPath("title") %></a></li>
</ItemTemplate>
</asp:DataList>
If you prefer to programmatically create and bind your RSS feeds the methods below should help you. The first one (BindDataSet()) is plain 'ole vanilla RSS feed and the one below (BindFilteredDataSet()) utilizes filtering.
public
void BindDataSet()
{
DataSet ds = new DataSet();
ds.ReadXml("http://www.willasrari.com/blog/meta/rss.aspx");
_dlRSSFeed.DataSource = ds;
_dlRSSFeed.DataBind();
}
public void BindFilteredDataSet(string queryFilter)
{
// pass _qryFilter to have keyword-filter RSS Feed
// i.e. _qryFilter = XML -> entries with XML will be returned
DataSet ds = new DataSet();
ds.ReadXml("http://www.willasrari.com/blog/meta/rss.aspx");
DataView dv = ds.Tables[0].DefaultView;
dv.RowFilter = "title LIKE `%" + queryFilter + "%`";
_dlFilteredRSSFeed.DataSource = dv;
_dlFilteredRSSFeed.DataBind();
}
Now you can selectively choose what content you want to display on your site. I know that some sites offer RSS feeds by category (or tag) but this will help you for those sites that you really like that lack this feature.
Tags:
.NET,
C#,
XML
Anyone that regularly reads or publishes blogs is probably familiar with the concept of pings. If you aren't familiar with the concept of the ping, at least you've heard of it right?
A pingback (ping for short) is a method by which a blog authoring tool (such as WordPress sends notification to a "ping server" (such as Technorati) informing of new or updated content. The ping is sent via XML-RPC signal and allows the ping server to generate a list of blogs or sites that have new material. This way when surfers visit these sites they will get a listing of the blogs with the latest content.
Most of the existing blog-authoring tools have built-in pinging technology. If you are like me and want to create your own blogging software then you will have to create the pinging function yourself. Using XML and C# I have successfully created a method of doing this.
This example uses Technorati but can just as easily be configured for any ping-service site that has an API.
private
void UpdatePing()
{
string ping = "http://rpc.technorati.com/rpc/ping";
string url = "http://www.willasrari.com/blog";
string name = "Will Asrari";
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(ping);
request.Method = "POST";
request.ContentType = "text/xml";
(using Stream stream = (Stream)request.GetRequestStream())
using (XmlTextWriter xml = new XmlTextWriter(stream, Encoding.UTF8))
{
xml.WriteStartDocument();
xml.WriteStartElement("methodCall");
xml.WriteElementString("methodName", "weblogUpdates.ping");
xml.WriteStartElement("params");
xml.WriteStartElement("param");
xml.WriteElementString("value", name);
xml.WriteEndElement();
xml.WriteStartElement("param");
xml.WriteElementString("value", url);
xml.WriteEndElement();
xml.WriteEndElement();
xml.WriteEndElement();
}
}
This code is pretty self-explanatory. It is worth mentioning that you should use the System.Xml namespace. After implementing this code in your site you will have an edge over those without pingback capabilities by getting listed at the top-of-the-pile!
You could also use XML configuration to customize the URL, description, and blog names so that you don't have to hardcode them into your function. Also, with a little bit of editing, you could loop through a list of services that allow you to programmatically send pingbacks. I'll probably expand on this a bit later.
Tags:
C#,
Code,
XML
Lately I have been developing larger and larger web applications or adding functionality to existing applications. Over the course of time these applications have either moved to new hosts, domain names, or in different directories within their existing domain. Anyone that has worked in web design / development can vouch for how big of a pain it is to go through each page and change the title, description, application path, etc... When designers first starting using CSS I was excited because this provided a quick and easy way to edit a webpage on a global scale. CSS enables the separation of document content (HTML, XHTML, etc...) from document presentation (CSS). The separation can improve content accessiblity, provide designer with more control, and most importantly (in my opinion) reduce the complexity and repetition in structural content.
web.config
The web.config file is, surprisingly enough, a configuration file for ASP.NET web applications. The configuration file is written in XML and consists of name-value pairs. The web.config file can be used to store data such as database connection strings, site titles and descriptions, application paths, and just about anything else you can think of. I like to think of my web.config as a ASP.NET application's CSS file. In the examples below I will show you how to customize your web application by reading data from a configuration file. First take a look at the example web.config file setup. The information you store in web.config will be safe as Internet Information Services (IIS) prevents direct browser access to configuration files. HTTP access error 403 (forbidden) is returned when a browser attempts to directory request a configuration file.
<?xml version="1.0" encoding="utf-8"?>
<configuration xmlns="http://schemas.microsoft.com/.NetConfiguration/v2.0">
<configSections>
<sectionGroup name="settings">
<section name="blogConfig" type="System.Configuration.NameValueSectionHandler,
System, Version=1.0.3300.0, Culture=neutral,
PublicKeyToken=b77a5c561934e089, Custom=null"/>
</sectionGroup>
</configSections>
<settings>
<blogConfig>
<add key="blogPath" value="/blog/" />
<add key="siteTitle" value="Will Asrari ~ Bellingham, WA Web Developement (ASP.NET, VB .NET, C#)" />
<add key="authorName" value="Will Asrari" />
</blogConfig>
</settings>
<system.web></system.web>
<appSettings></appSettings>
</configuration>
Reading the Configuration File
Let's pretend that you want every page in your application to display your site title. Let's pretend that your site is titled the same as above (Will Asrari yada yada yada). With the code sample below we can easily read the data from the configuration file and display on your page.
using System.Collections;
using System.Collections.Specialized;
protected void Page_Load(object sender, EventArgs e)
{
NameValueCollection blogConfig = (NameValueCollection)
ConfigurationSettings.GetConfig("settings/blogConfig");
string siteTitle = blogConfig["siteTitle"].ToString();
Page.Title = siteTitle;
}
In order for this code to work, you need to add a runat="server" attribute to your opening HEAD tag. This is a default when starting an application in Visual Studio 2005. If you are creating your applications in Notepad, Visual Studio 2003, TextPad, or any other editor you will need to manually add this attribute.
<head runat="server">
<title></title>
</head>
Adding More Customization
You can use the same code above, with a slight variation and variable addition to create an even more customized page title throughout your application.
protected void Page_Load(object sender, EventArgs e)
{
NameValueCollection blogConfig = (NameValueCollection)
ConfigurationSettings.GetConfig("settings/blogConfig");
string siteTitle = blogConfig["siteTitle"].ToString();
string authorName = blogConfig["authorName"].ToString();
Page.Title = siteTitle + " - Blog of " + authorName;
}
This code will display the site title as "Will Asrari ~ Bellingham, WA Web Developement (ASP.NET, VB .NET, C#) - Blog of Will Asrari" in the browser window. I know this title is rather excessive but I am simply trying to prove a concept. I want to say that a search engine-optimized page title should be less than 65 characters. Don't quote me on that.
In the configuration file that I have provided above you will notice that there is a path /blog/. This is the directory where I keep my blog application. If I ever move the blog to a different directory (i.e. /apps/blog) then I can simply change this value and my XML writer and URL rewriting engine will work flawlessly.
I hope this will help some of you tidy up your code!
Tags:
.NET,
XML