Home > Others > Build A Static RSS Reader To Fight Your Inner FOMO

Build A Static RSS Reader To Fight Your Inner FOMO

October 7th, 2024 Leave a comment Go to comments

In a fast-paced industry like tech, it can be hard to deal with the fear of missing out on important news. But, as many of us know, there’s an absolutely huge amount of information coming in daily, and finding the right time and balance to keep up can be difficult, if not stressful. A classic piece of technology like an RSS feed is a delightful way of taking back ownership of our own time. In this article, we will create a static Really Simple Syndication (RSS) reader that will bring you the latest curated news only once (yes: once) a day.

We’ll obviously work with RSS technology in the process, but we’re also going to combine it with some things that maybe you haven’t tried before, including Astro (the static site framework), TypeScript (for JavaScript goodies), a package called rss-parser (for connecting things together), as well as scheduled functions and build hooks provided by Netlify (although there are other services that do this).

I chose these technologies purely because I really, really enjoy them! There may be other solutions out there that are more performant, come with more features, or are simply more comfortable to you — and in those cases, I encourage you to swap in whatever you’d like. The most important thing is getting the end result!

The Plan

Here’s how this will go. Astro generates the website. I made the intentional decision to use a static site because I want the different RSS feeds to be fetched only once during build time, and that’s something we can control each time the site is “rebuilt” and redeployed with updates. That’s where Netlify’s scheduled functions come into play, as they let us trigger rebuilds automatically at specific times. There is no need to manually check for updates and deploy them! Cron jobs can just as readily do this if you prefer a server-side solution.

During the triggered rebuild, we’ll let the rss-parser package do exactly what it says it does: parse a list of RSS feeds that are contained in an array. The package also allows us to set a filter for the fetched results so that we only get ones from the past day, week, and so on. Personally, I only render the news from the last seven days to prevent content overload. We’ll get there!

But first…

What Is RSS?

RSS is a web feed technology that you can feed into a reader or news aggregator. Because RSS is standardized, you know what to expect when it comes to the feed’s format. That means we have a ton of fun possibilities when it comes to handling the data that the feed provides. Most news websites have their own RSS feed that you can subscribe to (this is Smashing Magazine’s RSS feed: https://www.smashingmagazine.com/feed/). An RSS feed is capable of updating every time a site publishes new content, which means it can be a quick source of the latest news, but we can tailor that frequency as well.

RSS feeds are written in an Extensible Markup Language (XML) format and have specific elements that can be used within it. Instead of focusing too much on the technicalities here, I’ll give you a link to the RSS specification. Don’t worry; that page should be scannable enough for you to find the most pertinent information you need, like the kinds of elements that are supported and what they represent. For this tutorial, we’re only using the following elements: </code></strong>, <strong><code></code></strong>, <strong><code></code></strong>, <strong><code></code></strong>, and <strong><code></code></strong>. We’ll also let our RSS parser package do some of the work for us.</p> <p>Creating The State Site</p> <p>We’ll start by creating our Astro site! In your terminal run <code>pnpm create astro@latest</code>. You can use any package manager you want — I’m simply trying out <a target="_blank" href="https://pnpm.io/" rel="noopener">pnpm</a> for myself.</p> <p>After running the command, Astro’s chat-based helper, Houston, walks through some setup questions to get things started.</p> <pre><code> astro Launch sequence initiated. dir Where should we create your new project? ./rss-buddy tmpl How would you like to start your new project? Include sample files ts Do you plan to write TypeScript? Yes use How strict should TypeScript be? Strict deps Install dependencies? Yes git Initialize a new git repository? Yes </code></pre> <p>I like to use Astro’s sample files so I can get started quickly, but we’re going to clean them up a bit in the process. Let’s clean up the <code>src/pages/index.astro</code> file by removing everything inside of the <code><main></main></code> tags. Then we’re good to go!</p> <p>From there, we can spin things by running <code>pnpm start</code>. Your terminal will tell you which localhost address you can find your site at.</p> <p>Pulling Information From RSS feeds</p> <p>The <code>src/pages/index.astro</code> file is where we will make an array of RSS feeds we want to follow. We will be using <a target="_blank" href="https://docs.astro.build/en/basics/astro-syntax/" rel="noopener">Astro’s template syntax</a>, so between the two code fences (—), create an array of <code>feedSources</code> and add some feeds. If you need inspiration, you can copy this:</p> <pre><code>const feedSources = [ 'https://www.smashingmagazine.com/feed/', 'https://developer.mozilla.org/en-US/blog/rss.xml', // etc. ] </code></pre> <p>Now we’ll install the <a target="_blank" href="https://github.com/rbren/rss-parser" rel="noopener">rss-parser package</a> in our project by running <code>pnpm install rss-parser</code>. This package is a small library that turns the XML that we get from fetching an RSS feed into JavaScript objects. This makes it easy for us to read our RSS feeds and manipulate the data any way we want.</p> <p>Once the package is installed, open the <code>src/pages/index.astro</code> file, and at the top, we’ll import the rss-parser and instantiate the <code>Partner</code> class.</p> <pre><code>import Parser from 'rss-parser'; const parser = new Parser(); </code></pre> <p>We use this parser to read our RSS feeds and (surprise!) <em>parse</em> them to JavaScript. We’re going to be dealing with a list of promises here. Normally, I would probably use <code>Promise.all()</code>, but the thing is, this is supposed to be a complicated experience. If one of the feeds doesn’t work for some reason, I’d prefer to simply ignore it.</p> <p>Why? Well, because <code>Promise.all()</code> rejects everything even if only one of its promises is rejected. That might mean that if one feed doesn’t behave the way I’d expect it to, my entire page would be blank when I grab my hot beverage to read the news in the morning. I do not want to start my day confronted by an error.</p> <p>Instead, I’ll opt to use <code>Promise.allSettled()</code>. This method will actually let all promises complete even if one of them fails. In our case, this means any feed that errors will just be ignored, which is perfect.</p> <p>Let’s add this to the <code>src/pages/index.astro</code> file:</p> <div> <pre><code>interface FeedItem { feed?: string; title?: string; link?: string; date?: Date; } const feedItems: FeedItem[] = []; await Promise.allSettled( feedSources.map(async (source) => { try { const feed = await parser.parseURL(source); feed.items.forEach((item) => { const date = item.pubDate ? new Date(item.pubDate) : undefined; feedItems.push({ feed: feed.title, title: item.title, link: item.link, date, }); }); } catch (error) { console.error(<code>Error fetching feed from ${source}:</code>, error); } }) ); </code></pre> </div> <p>This creates an array (or more) named <code>feedItems</code>. For each URL in the <code>feedSources</code> array we created earlier, the rss-parser retrieves the items and, yes, parses them into JavaScript. Then, we return whatever data we want! We’ll keep it simple for now and only return the following:</p> <ul> <li>The feed title,</li> <li>The title of the feed item,</li> <li>The link to the item,</li> <li>And the item’s published date.</li> </ul> <p>The next step is to ensure that all items are sorted by date so we’ll truly get the “latest” news. Add this small piece of code to our work:</p> <div> <pre><code>const sortedFeedItems = feedItems.sort((a, b) => (b.date ?? new Date()).getTime() - (a.date ?? new Date()).getTime()); </code></pre> </div> <p>Oh, and… remember when I said I didn’t want this RSS reader to render anything older than seven days? Let’s tackle that right now since we’re already in this code.</p> <p>We’ll make a new variable called <code>sevenDaysAgo</code> and assign it a date. We’ll then set that date to seven days ago and use that logic before we add a new item to our <code>feedItems</code> array.</p> <p>This is what the <code>src/pages/index.astro</code> file should now look like at this point:</p> <div> <pre><code>--- import Layout from '../layouts/Layout.astro'; import Parser from 'rss-parser'; const parser = new Parser(); const sevenDaysAgo = new Date(); sevenDaysAgo.setDate(sevenDaysAgo.getDate() - 7); const feedSources = [ '<a target="_blank" href="https://www.smashingmagazine.com/feed/'" rel="noopener">https://www.smashingmagazine.com/feed/'</a>, '<a target="_blank" href="https://developer.mozilla.org/en-US/blog/rss.xml'" rel="noopener">https://developer.mozilla.org/en-US/blog/rss.xml'</a>, ] interface FeedItem { feed?: string; title?: string; link?: string; date?: Date; } const feedItems: FeedItem[] = []; await Promise.allSettled( feedSources.map(async (source) => { try { const feed = await parser.parseURL(source); feed.items.forEach((item) => { const date = item.pubDate ? new Date(item.pubDate) : undefined; if (date && date >= sevenDaysAgo) { feedItems.push({ feed: feed.title, title: item.title, link: item.link, date, }); } }); } catch (error) { console.error(<code>Error fetching feed from ${source}:</code>, error); } }) ); const sortedFeedItems = feedItems.sort((a, b) => (b.date ?? new Date()).getTime() - (a.date ?? new Date()).getTime()); --- <Layout title="Welcome to Astro."> <main> </main> </Layout> </code></pre> </div> <p>Rendering XML Data</p> <p>It’s time to show our news articles on the Astro site! To keep this simple, we’ll format the items in an unordered list rather than some other fancy layout.</p> <p>All we need to do is update the <code></code> element in the file with the XML objects sprinkled in for a feed item’s title, URL, and publish date.</p> <pre><code><Layout title="Welcome to Astro."> <main> {sortedFeedItems.map(item => ( <ul> <li> <a href={item.link}>{item.title}</a> <p>{item.feed}</p> <p>{item.date}</p> </li> </ul> ))} </main> </Layout> </code></pre> <p>Go ahead and run <code>pnpm start</code> from the terminal. The page should display an unordered list of feed items. Of course, everything is styled at the moment, but luckily for you, you can make it look exactly like you want with CSS!</p> <p>And remember that there are even <strong>more fields available in the XML for each item</strong> if you want to display more information. If you run the following snippet in your DevTools console, you’ll see all of the fields you have at your disposal:</p> <pre><code>feed.items.forEach(item => {} </code></pre> <p>Scheduling Daily Static Site Builds</p> <p>We’re nearly done! The feeds are being fetched, and they are returning data back to us in JavaScript for use in our Astro page template. Since feeds are updated whenever new content is published, we need a way to fetch the latest items from it.</p> <p>We want to avoid doing any of this manually. So, let’s set this site on Netlify to gain access to their scheduled functions that trigger a rebuild and their build hooks that do the building. Again, other services do this, and you’re welcome to roll this work with another provider — I’m just partial to Netlify since I work there. In any case, you can follow Netlify’s documentation for <a target="_blank" href="https://docs.netlify.com/welcome/add-new-site/#import-from-an-existing-repository" rel="noopener">setting up a new site</a>. </p> <p>Once your site is hosted and live, you are ready to schedule your rebuilds. A <a target="_blank" href="https://docs.netlify.com/configure-builds/build-hooks/" rel="noopener">build hook</a> gives you a URL to use to trigger the new build, looking something like this:</p> <pre><code>https://api.netlify.com/build_hooks/your-build-hook-id </code></pre> <p>Let’s trigger builds every day at midnight. We’ll use Netlify’s <a target="_blank" href="https://docs.netlify.com/functions/scheduled-functions/" rel="noopener">scheduled functions</a>. That’s really why I’m using Netlify to host this in the first place. Having them at the ready via the host greatly simplifies things since there’s no server work or complicated configurations to get this going. Set it and forget it!</p> <p>We’ll install <code>@netlify/functions</code> (<a target="_blank" href="https://docs.netlify.com/functions/get-started/" rel="noopener">instructions</a>) to the project and then create the following file in the project’s root directory: <code>netlify/functions/deploy.ts</code>.</p> <p>This is what we want to add to that file:</p> <div> <pre><code>// netlify/functions/deploy.ts import type { Config } from '@netlify/functions'; const BUILD_HOOK = '<a target="_blank" href="https://api.netlify.com/build_hooks/your-build-hook-id'" rel="noopener">https://api.netlify.com/build_hooks/your-build-hook-id'</a>; // replace me! export default async (req: Request) => { await fetch(BUILD_HOOK, { method: 'POST', }).then((response) => { console.log('Build hook response:', response.json()); }); return { statusCode: 200, }; }; export const config: Config = { schedule: '0 0 * * *', }; </code></pre> </div> <p>If you commit your code and push it, your site should re-deploy automatically. From that point on, it follows a schedule that rebuilds the site every day at midnight, ready for you to take your morning brew and catch up on everything that <em>you</em> think is important.</p> <div class="fixed"></div> </div> <div class="under"> <span class="categories">Categories: </span><span><a href="http://www.webmastersgallery.com/category/uncategorized/" rel="category tag">Others</a></span> <span class="tags">Tags: </span><span></span> </div> </div> <!-- related posts START --> <!-- related posts END --> <script type="text/javascript" src="http://www.webmastersgallery.com/wp-content/themes/inove/js/comment.js"></script> <div id="comments"> <div id="cmtswitcher"> <a id="commenttab" class="curtab" href="javascript:void(0);">Comments (0)</a> <span class="addcomment"><a href="#respond">Leave a comment</a></span> <div class="fixed"></div> </div> <div id="commentlist"> <!-- comments START --> <ol id="thecomments"> <li class="messagebox"> No comments yet. </li> </ol> <!-- comments END --> <!-- trackbacks START --> <div class="fixed"></div> <!-- trackbacks END --> </div> </div> <div id="comment_login" class="messagebox"> You must be <a href="http://www.webmastersgallery.com/wp-login.php">logged in</a> to post a comment. </div> <div id="postnavi"> <span class="prev"><a href="http://www.webmastersgallery.com/2024/10/07/scaling-your-small-business-when-and-how-to-hire-your-first-employees/" rel="next">Scaling Your Small Business: When and How to Hire Your First Employees</a></span> <span class="next"><a href="http://www.webmastersgallery.com/2024/10/07/exciting-new-tools-for-designers-october-2024/" rel="prev">Exciting New Tools for Designers, October 2024</a></span> <div class="fixed"></div> </div> </div> <!-- main END --> <!-- sidebar START --> <div id="sidebar"> <!-- sidebar north START --> <div id="northsidebar" class="sidebar"> <!-- feeds --> <div class="widget widget_feeds"> <div class="content"> <div id="subscribe"> <a rel="external nofollow" id="feedrss" title="Subscribe to this blog..." href="http://www.webmastersgallery.com/feed/"><abbr title="Really Simple Syndication">RSS</abbr></a> </div> <div class="fixed"></div> </div> </div> <!-- showcase --> <div id="text-389627311" class="widget widget_text"> <div class="textwidget"><a href="http://feeds2.feedburner.com/webmastersgallery" title="Subscribe to my feed" rel="alternate" type="application/rss+xml"><img src="http://www.feedburner.com/fb/images/pub/feed-icon32x32.png" alt="" style="border:0"/></a><a href="http://feeds2.feedburner.com/webmastersgallery" title="Subscribe to my feed" rel="alternate" type="application/rss+xml">Subscribe for latest Updates</a></div> </div><div id="text-389629461" class="widget widget_text"> <div class="textwidget"><form style="border:1px solid #ccc;padding:3px;text-align:center;" action="http://feedburner.google.com/fb/a/mailverify" method="post" target="popupwindow" onsubmit="window.open('http://feedburner.google.com/fb/a/mailverify?uri=webmastersgallery', 'popupwindow', 'scrollbars=yes,width=550,height=520');return true"><p>Enter your email address:</p><p><input type="text" style="width:140px" name="email"/></p><input type="hidden" value="webmastersgallery" name="uri"/><input type="hidden" name="loc" value="en_US"/><input type="submit" value="Subscribe" /><p>Delivered by <a href="http://feedburner.google.com" target="_blank" rel="noopener">FeedBurner</a></p></form></div> </div></div> <!-- sidebar north END --> <div id="centersidebar"> <!-- sidebar east START --> <div id="eastsidebar" class="sidebar"> <!-- categories --> <div class="widget widget_categories"> <h3>Categories</h3> <ul> <li class="cat-item cat-item-518"><a href="http://www.webmastersgallery.com/category/affiliate-programs/">Affiliate Programs</a> </li> <li class="cat-item cat-item-147"><a href="http://www.webmastersgallery.com/category/design/">Designing</a> </li> <li class="cat-item cat-item-519"><a href="http://www.webmastersgallery.com/category/domain-names/">Domain Names</a> </li> <li class="cat-item cat-item-37"><a href="http://www.webmastersgallery.com/category/e-commerce/">E-commerce</a> </li> <li class="cat-item cat-item-509"><a href="http://www.webmastersgallery.com/category/internet-directories/">Internet Directories</a> </li> <li class="cat-item cat-item-510"><a href="http://www.webmastersgallery.com/category/message-boards/">Message Boards</a> </li> <li class="cat-item cat-item-1"><a href="http://www.webmastersgallery.com/category/uncategorized/">Others</a> </li> <li class="cat-item cat-item-506"><a href="http://www.webmastersgallery.com/category/programming/">Programming</a> </li> <li class="cat-item cat-item-511"><a href="http://www.webmastersgallery.com/category/promotion-and-marketing/">Promotion and Marketing</a> </li> <li class="cat-item cat-item-534"><a href="http://www.webmastersgallery.com/category/scripts-and-programming/">Scripts and Programming</a> </li> <li class="cat-item cat-item-513"><a href="http://www.webmastersgallery.com/category/search-engines/">Search Engines</a> </li> <li class="cat-item cat-item-135"><a href="http://www.webmastersgallery.com/category/social-media/">Social Media</a> </li> <li class="cat-item cat-item-514"><a href="http://www.webmastersgallery.com/category/softwares/">Softwares</a> </li> <li class="cat-item cat-item-515"><a href="http://www.webmastersgallery.com/category/tips-and-tutorials/">Tips and Tutorials</a> </li> <li class="cat-item cat-item-338"><a href="http://www.webmastersgallery.com/category/web-hosting/">Web Hosting</a> </li> <li class="cat-item cat-item-516"><a href="http://www.webmastersgallery.com/category/webmaster-tools/">Webmaster Tools</a> </li> <li class="cat-item cat-item-501"><a href="http://www.webmastersgallery.com/category/webmaster-resources/">Webmasters Resources</a> </li> <li class="cat-item cat-item-3"><a href="http://www.webmastersgallery.com/category/web-design/">Website Design</a> </li> </ul> </div> </div> <!-- sidebar east END --> <!-- sidebar west START --> <div id="westsidebar" class="sidebar"> <!-- blogroll --> <div class="widget widget_links"> <h3>Blogroll</h3> <ul> <li><a href="http://wordpress.org/development/">Development Blog</a></li> <li><a href="http://codex.wordpress.org/">Documentation</a></li> <li><a href="http://wordpress.org/extend/plugins/">Plugins</a></li> <li><a href="http://wordpress.org/extend/ideas/">Suggest Ideas</a></li> <li><a href="http://wordpress.org/support/">Support Forum</a></li> <li><a href="http://wordpress.org/extend/themes/">Themes</a></li> <li><a href="http://planet.wordpress.org/">WordPress Planet</a></li> </ul> </div> </div> <!-- sidebar west END --> <div class="fixed"></div> </div> <!-- sidebar south START --> <div id="southsidebar" class="sidebar"> <!-- archives --> <div class="widget"> <h3>Archives</h3> <ul> <li><a href='http://www.webmastersgallery.com/2024/11/'>November 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/10/'>October 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/09/'>September 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/08/'>August 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/07/'>July 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/06/'>June 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/05/'>May 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/04/'>April 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/03/'>March 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/02/'>February 2024</a></li> <li><a href='http://www.webmastersgallery.com/2024/01/'>January 2024</a></li> <li><a href='http://www.webmastersgallery.com/2023/12/'>December 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/11/'>November 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/10/'>October 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/09/'>September 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/08/'>August 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/07/'>July 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/06/'>June 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/05/'>May 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/04/'>April 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/03/'>March 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/02/'>February 2023</a></li> <li><a href='http://www.webmastersgallery.com/2023/01/'>January 2023</a></li> <li><a href='http://www.webmastersgallery.com/2022/12/'>December 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/11/'>November 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/10/'>October 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/09/'>September 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/08/'>August 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/07/'>July 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/06/'>June 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/05/'>May 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/04/'>April 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/03/'>March 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/02/'>February 2022</a></li> <li><a href='http://www.webmastersgallery.com/2022/01/'>January 2022</a></li> <li><a href='http://www.webmastersgallery.com/2021/12/'>December 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/11/'>November 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/10/'>October 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/09/'>September 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/08/'>August 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/07/'>July 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/06/'>June 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/05/'>May 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/04/'>April 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/03/'>March 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/02/'>February 2021</a></li> <li><a href='http://www.webmastersgallery.com/2021/01/'>January 2021</a></li> <li><a href='http://www.webmastersgallery.com/2020/12/'>December 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/11/'>November 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/10/'>October 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/09/'>September 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/08/'>August 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/07/'>July 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/06/'>June 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/05/'>May 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/04/'>April 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/03/'>March 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/02/'>February 2020</a></li> <li><a href='http://www.webmastersgallery.com/2020/01/'>January 2020</a></li> <li><a href='http://www.webmastersgallery.com/2019/12/'>December 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/11/'>November 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/10/'>October 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/09/'>September 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/08/'>August 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/07/'>July 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/06/'>June 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/05/'>May 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/04/'>April 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/03/'>March 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/02/'>February 2019</a></li> <li><a href='http://www.webmastersgallery.com/2019/01/'>January 2019</a></li> <li><a href='http://www.webmastersgallery.com/2018/12/'>December 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/11/'>November 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/10/'>October 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/09/'>September 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/08/'>August 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/07/'>July 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/04/'>April 2018</a></li> <li><a href='http://www.webmastersgallery.com/2018/01/'>January 2018</a></li> <li><a href='http://www.webmastersgallery.com/2017/12/'>December 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/11/'>November 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/09/'>September 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/08/'>August 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/07/'>July 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/06/'>June 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/05/'>May 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/04/'>April 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/03/'>March 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/02/'>February 2017</a></li> <li><a href='http://www.webmastersgallery.com/2017/01/'>January 2017</a></li> <li><a href='http://www.webmastersgallery.com/2016/12/'>December 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/11/'>November 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/10/'>October 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/09/'>September 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/08/'>August 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/07/'>July 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/06/'>June 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/05/'>May 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/04/'>April 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/03/'>March 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/02/'>February 2016</a></li> <li><a href='http://www.webmastersgallery.com/2016/01/'>January 2016</a></li> <li><a href='http://www.webmastersgallery.com/2015/12/'>December 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/11/'>November 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/10/'>October 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/09/'>September 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/08/'>August 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/07/'>July 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/06/'>June 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/05/'>May 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/04/'>April 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/03/'>March 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/02/'>February 2015</a></li> <li><a href='http://www.webmastersgallery.com/2015/01/'>January 2015</a></li> <li><a href='http://www.webmastersgallery.com/2014/12/'>December 2014</a></li> <li><a href='http://www.webmastersgallery.com/2014/11/'>November 2014</a></li> <li><a href='http://www.webmastersgallery.com/2014/10/'>October 2014</a></li> <li><a href='http://www.webmastersgallery.com/2014/09/'>September 2014</a></li> <li><a href='http://www.webmastersgallery.com/2014/08/'>August 2014</a></li> <li><a href='http://www.webmastersgallery.com/2014/07/'>July 2014</a></li> <li><a href='http://www.webmastersgallery.com/2014/06/'>June 2014</a></li> <li><a href='http://www.webmastersgallery.com/2013/07/'>July 2013</a></li> <li><a href='http://www.webmastersgallery.com/2013/01/'>January 2013</a></li> <li><a href='http://www.webmastersgallery.com/2012/12/'>December 2012</a></li> <li><a href='http://www.webmastersgallery.com/2012/08/'>August 2012</a></li> <li><a href='http://www.webmastersgallery.com/2012/07/'>July 2012</a></li> <li><a href='http://www.webmastersgallery.com/2012/06/'>June 2012</a></li> <li><a href='http://www.webmastersgallery.com/2012/05/'>May 2012</a></li> <li><a href='http://www.webmastersgallery.com/2012/04/'>April 2012</a></li> <li><a href='http://www.webmastersgallery.com/2012/01/'>January 2012</a></li> <li><a href='http://www.webmastersgallery.com/2011/11/'>November 2011</a></li> <li><a href='http://www.webmastersgallery.com/2011/06/'>June 2011</a></li> <li><a href='http://www.webmastersgallery.com/2011/03/'>March 2011</a></li> <li><a href='http://www.webmastersgallery.com/2011/02/'>February 2011</a></li> <li><a href='http://www.webmastersgallery.com/2011/01/'>January 2011</a></li> <li><a href='http://www.webmastersgallery.com/2010/12/'>December 2010</a></li> <li><a href='http://www.webmastersgallery.com/2010/11/'>November 2010</a></li> <li><a href='http://www.webmastersgallery.com/2010/09/'>September 2010</a></li> <li><a href='http://www.webmastersgallery.com/2010/07/'>July 2010</a></li> <li><a href='http://www.webmastersgallery.com/2010/06/'>June 2010</a></li> <li><a href='http://www.webmastersgallery.com/2010/05/'>May 2010</a></li> <li><a href='http://www.webmastersgallery.com/2010/02/'>February 2010</a></li> <li><a href='http://www.webmastersgallery.com/2009/12/'>December 2009</a></li> <li><a href='http://www.webmastersgallery.com/2009/08/'>August 2009</a></li> <li><a href='http://www.webmastersgallery.com/2009/07/'>July 2009</a></li> <li><a href='http://www.webmastersgallery.com/2009/06/'>June 2009</a></li> <li><a href='http://www.webmastersgallery.com/2009/05/'>May 2009</a></li> <li><a href='http://www.webmastersgallery.com/2009/04/'>April 2009</a></li> <li><a href='http://www.webmastersgallery.com/2009/03/'>March 2009</a></li> </ul> </div> <!-- meta --> <div class="widget"> <h3>Meta</h3> <ul> <li><a href="http://www.webmastersgallery.com/wp-login.php">Log in</a></li> </ul> </div> </div> <!-- sidebar south END --> </div> <!-- sidebar END --> <div class="fixed"></div> </div> <!-- content END --> <!-- footer START --> <div id="footer"> <a id="gotop" href="#" onclick="MGJS.goTop();return false;">Top</a> <a id="powered" href="http://wordpress.org/">WordPress</a> <div id="copyright"> Copyright © 2009-2024 Webmasters Gallery </div> <div id="themeinfo"> Theme by <a href="http://www.neoease.com/">NeoEase</a>. Valid <a href="http://validator.w3.org/check?uri=referer">XHTML 1.1</a> and <a href="http://jigsaw.w3.org/css-validator/check/referer?profile=css3">CSS 3</a>. </div> </div> <!-- footer END --> </div> <!-- container END --> </div> <!-- wrap END --> </body> </html>