Help Team Hanselman Fight Diabetes
It's never too late to spread the word of humanity! I think it's even better to talk about it now because the flood of tweets and blog posts on Scott's action was only on the day he wrote his blog post on this. So after a while, I talk about it again.
Fortunately, neither me nor any of my family members are diabetic. I'm thankful for this because after reading Scott Hanselman's post about a diabetic's problems in his/her life, now I can feel what painful days they can have.
Anyway, if you're a diabetic or not, we can help Team Hanselman. If you wanna know more about Team Hanselman and Diabetics Walk 2010 please read Scott's original post .
You can donate here. Everything is explained in Scott's post and there is no need to repeat all here. I feel this is the least thing I can do.
How to use Google Data API in ASP.NET MVC. Part 1 – Google Analytics
It's really amazing that Google let developers access and use its services data via GData easily. It's really easy to interact with services like Calendar, Analytics, Google Reader, Blogger, YouTube, etc. using GData.
There are also several libraries for languages and technologies to include and use in your project.
Recently I needed to use Google API in a project to interact with YouTube and Google Analytics in an ASP.NET MVC application. My scenario was not too complicated and so I decided to share my experience in two separate blog posts and you're reading the first one of this series: using GData to retrieve a websites' visitors statistics information which is monitored by Google Analytics.
As I mentioned before, my scenario was not complicated and I just wanted to retrieves total number of page views as well as today and yesterday's page views number. Ready? Here we go!
First of all you need to download GData .NET library from Google Code and add references to these assemblies in your project:
- Google.GData.Analytics.dll
- Google.GData.Client.dll
- Google.GData.Extensions.dll
UPDATE: I was working on my project two months ago and I forgot to mention in my post that Google Analytics is not yet officially a part of GData .NET library. Anyway you can download it from Google Code SVN or the easier, I uploaded it here and you can get it.
Next, we need an Action method that returns information which is retrieved from GData to pass to our View:
public ActionResult Stats()
{
string userName = ConfigurationManager.AppSettings["GoogleUsername"];
string passWord = ConfigurationManager.AppSettings["GooglePassword"];
string profileId = ConfigurationManager.AppSettings["GoogleAnalyticsProfileId"];
const string dataFeedUrl = "https://www.google.com/analytics/feeds/data";
var service = new AnalyticsService("WebSiteAnalytics");
service.setUserCredentials(userName, passWord);
var dataQuery = new DataQuery(dataFeedUrl)
{
Ids = profileId,
Metrics = "ga:pageviews",
Sort = "ga:pageviews",
GAStartDate = new DateTime(2010, 3, 1).ToString("yyyy-MM-dd"),
GAEndDate = DateTime.Now.ToString("yyyy-MM-dd")
};
var dataFeed = service.Query(dataQuery);
var totalEntry = dataFeed.Entries[0];
ViewData["Total"] = ((DataEntry)(totalEntry)).Metrics[0].Value;
dataQuery.GAStartDate = DateTime.Now.AddDays(-1).ToString("yyyy-MM-dd");
dataQuery.GAEndDate = DateTime.Now.AddDays(-1).ToString("yyyy-MM-dd");
dataFeed = service.Query(dataQuery);
var yesterdayEntry = dataFeed.Entries[0];
ViewData["Yesterday"] = ((DataEntry)(yesterdayEntry)).Metrics[0].Value;
dataQuery.GAStartDate = DateTime.Now.ToString("yyyy-MM-dd");
dataQuery.GAEndDate = DateTime.Now.ToString("yyyy-MM-dd");
dataFeed = service.Query(dataQuery);
var todayEntry = dataFeed.Entries[0];
ViewData["Today"] = ((DataEntry)(todayEntry)).Metrics[0].Value;
return PartialView(dataFeed.Entries);
}
Now, let me explain the code a little. To authenticate with GData you should pass Google Username (e.g.: myusername@gmail.com), Google Password and ProfileID of website which you want to access data. This ProfileID is in this format: ga:NNNNNNN and you can find this NNNNNNN number in query string when you're logged in to your Google Analytics dashboard.
Next you define the URL of data feed which is https://www.google.com/analytics/feeds/data. Next steps are straightforward enough to understand; you create an instance of AnalyticsService and pass credentials, then send a new DataQuery to AnalyticsService object providing your query information (in this case, PageViews, StartDate and EndDate). DataFeed result which is returned from the service is an array of informtion and in our case we need its first element. If you look at my code you see that we have repeated this process to retrieve yesterday and today statistics.
I have chosen the easiest way to pass data to View which is using ViewData dictionary collection; but you can create a Model class with properties you need and bind it to your view.
Our view to show data looks like this:
< %@ Control Language="C#" Inherits="System.Web.Mvc.ViewUserControl" %> Website Stats:
- Total: < %= ((Convert.ToInt32(ViewData["Total"]))).ToString("##,#")%>
- Yesterday: < %= Convert.ToInt32(ViewData["Yesterday"]).ToString("##,#")%>
- Today: < %= Convert.ToInt32(ViewData["Today"]).ToString("##,#")%>
It was a very simple sample of how to use GData to show Google Analytics data on your ASP.NET MVC powered website. I hope it helps you :-)
Next post in these series will show you how to use GData to interact with YouTube API and upload videos from your application and stream it to your visitors.
Apple is making a mistake with iPhone OS 4 strategy for older iDevices.
Today, Apple unveiled the new generation of iPhone OS which is called iPhone OS 4. There are many new features that are in the box to let the end users have a better experience with their iPhones (and also iPads).
Here’s a list of what Apple offers in this new version:
Ok, so what’s wrong with all these new cool features? Why I’m writing this to claim that Apple is making a big mistake?
Apple explains OS 4 compatibility with old iDevices (iPhones and iPod Touches) here. Apple has dropped support for old 2G devices; no problem with that because Apple has already discontinued selling 2G series and it’s normal they no longer support it in the new OS release. But Oops! There are some limitations for iPhone and iPod Touch 3G too; they can’t enjoy the new revolutionary feature of Multitasking! Something that Apple claims they’re not the first in that but they’re the best:
“Now we weren’t the first to this party, but we’re gonna be the best. Just like cut and paste,” said Jobs. ”We figured out how to implement multitasking for third party apps and avoid those things. So that’s what took so long. I’d like to demo it. We have a great UI.”
There is a big question for Steve Jobs; if you’re going to drop this important feature for 3G series why are you still selling that on Apple Store for $99? Apple claims that iPhone 3G hardware is not powerful enough to support multitasking but who believes that?
Before Apple unveils the new OS 4, my personal prediction was that Apple would limit the number of apps which can stay running in the background on older devices like 3G (e.g. 3 apps at most) and let 3GS series run more apps but I never thought that Apple wouldn’t support multitasking on a device it is being sold right now!
It’s really a down vote for Steve Jobs because I think 3G users number is more than 3GS users and many of them really don’t want to upgrade their devices just to receive multitasking feature (bear in mind, this is the feature that all rivals have already offered: Andriod, Windows Mobile, etc.)
From another point of view, there is another question in my mind: if Apple is going to publicly release OS 4 this summer (and even later in the fall for iPad) why did Steve unveil that 3 months earlier?
I don’t want to judge but I think this is because Steve Jobs is really worried about Google Nexus One and also Microsoft Windows Phone impact on iPhone users. He feels that he is losing the market if he sits and watches what his counterparts are doing for their users; and to be honest I should confess that Google and Microsoft are doing perfect.
Apple policy has been always letting users use their devices as long as they really need a major upgrade. If you are a Mac user you know that a MacBook with 2GB of RAM has a better performance than a current Windows 7 machine with 3GB of RAM and MacBook owner still can upgrade his RAM to 4GB or more and still enjoy his Mac! But now, Apple says: No! Upgrade your device and give me more money to use just one new feature that everybody else has been already offering in the market.
What’s your idea?
Bye SharpLife.NET, Hi Mahdi!
Four years ago I wrote my first blog post on SharpLife.NET. During these four years I was pretty busy to update that blog very rarely and it wasn't what I was looking for in a technical/personal blog.
However, SharpLife.NET was a good experience for me because I had started blogging in English with this blog and this encouraged me to keep going on.
Since A few months ago when I registered mahdi.mp at Chi.mp, I have been always thinking of migrating SharpLife.NET contents and create a single official website for myself to centralize all my online activities there.
I had decided to write my own blog engine using ASP.NET MVC and in fact I already had it ready couple of weeks ago (because I had developed a multilingual blog engine for a client and I could use it for my website as well) but after I took a look at WordPress features I decided to use it as my blog engine because it's much more mature and rich feature in comparison to my own engine. My blog is now running on WordPress 2.9.2.
From now on, all requests to SharpLife.NET will be redirected to mahdi.mp and if you reached a 404 error page please use search box to find the post you're looking for. If you were a subscriber of SharpLife.NET RSS feed there is no need to change anything because I have already changed RSS feed target in FeedBurner and you will receive updates from new mahdi.mp website; but if you were not subscribed and now you want, please add my RSS Feed to your aggregator.
Because of many tools that are available for WordPress powered blogs (e.g. tools for iPhone), I hope I can update my blog more than past and help myself learn more and more. Not only I don't claim I'm a teacher, but also I have always wanted to be a continuous learner and just share what I feel that can be useful for others too. So help me with your comments :-)
Translating your content title using Google Translate API to use in a URL
Following my previous posts on How to handle non-English characters in ASP.NET MVC routes, Build pretty clean URL for your dynamic pages using JavaScript and Non English Words in URL I decided to share another simple tip that let you translate what your user inserts as content’s title (that can be a blog post title, a page name or a news headline) automatically using Google Translate API.
Let me explain it with an example. Suppose that you have a news system in Persian language and your end user enters a Persian phrase like “این یک عنوان خبر است” as the headline of a news story. From SEO point of view it’s better we include original headline words in URL (like something that I explained in this post) instead of using an integer ID or GUID (e.g. /news/?id=1 or /news/1.aspx, etc.) but as we discussed on in that post, including non-English characters in URLs is not the best way! I just wanted to have something like /news/story/this-is-a-title and didn’t want to force user translate his words into English in order to use in URL field.
A few days ago I was thinking on this topic and decided to try a trick to utilize Google Translate API (which has recently started supporting Persian language as well) to translate such titles into meaningful English phrases and then clean them using the way I described in this post.
Fortunately, thanks to Google API simplicity it was so easy and straightforward. Here’s what I wrote:
- First you should include Google API JavaScript source in your page:
[cc lang='html4strict' line_numbers='false'][/cc] - Add this JavaScript code to your page:
[cc lang='javascript' line_numbers='false']
$(document).ready(function() {$("#contentPage_Title").blur(function() { parseUrl($("#contentPage_Title").val()) });
});
google.load("language", "1");
function parseUrl(url) {
$("#loadingImage").attr("style", function() { return "display: inline;" });
google.language.translate(url, "fa", "en", function(result) {
if (!result.error) {
var url = (result.translation + " ").replace(/[^a-zA-Z0-9]+/g, "-");
$("#contentPage_Url").val(url.slice(0, url.length - 1).toLowerCase());
$("#loadingImage").attr("style", function() { return "display: none;" });
}
});
}
[/cc]
You’re done! Now, let me explain the code a little. First using jQuery, you tell the DOM to fire parseUrl() event as soon as you enter the title and go to the next field, then, we load Google Translate service into our script, call translate function to translate from “fa” (Persian) to “en” (English) and finally clean the result using our old trick. That’s all and no magic here!
Please note that we show and hide a “Loading” element (e.g.: a loading image) before and after we call AJAX translate function. So user can see something is happening behind the scene.
