Sample code for C#
On this page you will find a very simplistic sample on how to post a score to KPI Dashboard using our API.
HTTP 417 – Expectation Failed
It seems that this error can also occur on some proxies that don’t support “100 continue” expectation. The workaround is to add the following to the
<configuration>
<system.net>
<settings>
<servicePointManager expect100Continue="false" />
</settings>
</system.net>
</configuration>
See also: http://social.msdn.microsoft.com/Forums/en-US/devdocs/thread/60cd6e6a-4157-4811-8ed3-1e46f9022ea8
WCF REST Starter Kit
The example below uses a simple REST client implemented in the “Send” method. As replacement you might want to take a look at the HttpClient class which is part of Microsofts WCF REST Starter Kit
Getting user details, finding indicators, creating and deleting scores
Download this sample code.
using System;
using System.Collections;
using System.Text;
using System.IO;
using System.Net;
using System.Web;
using System.Xml;
/// <summary>
/// This is an example how to use the KPI Dashboard API.
/// Language: C#
///
/// This sample code shows how to lookup an existing indicator
/// Then it creates a score for this indicator.
/// At the end it removes the created score again.
///
/// ------------------------------------------------------------------
/// You will need to adjust the MY_API_TOKEN value:
///
/// MY_API_TOKEN - Your API token, as displayed on your
/// "Personal Settings" page in KPI Dashboard.
/// ------------------------------------------------------------------
///
/// Feel free to use this code and modify to fit your needs.
/// For more information visit http://dashboard.kpilibrary.com/api
///
/// ------------------------------------------------------------------
/// </summary>
public class ApiSample
{
/// <summary>
/// Replace the info below with your own:
/// MY_API_TOKEN = "find-your-key-in-your-personal-settings-page"
/// </summary>
public static readonly string MY_API_TOKEN = "FILL IN YOUR TOKEN HERE";
public static readonly string API_URI = "https://dashboard.kpilibrary.com/api/v2";
public enum HttpMethod { GET, POST, PUT, DELETE }
/// <summary>
/// Get my user info from KPI Dashboard.
/// </summary>
/// <returns>list of { [user], [tenant], [role] }</returns>
public static ArrayList GetMyUserDetails()
{
Uri uri = new Uri(API_URI + "/me.xml");
string response = Send(uri, HttpMethod.GET, null);
XmlDocument doc = new XmlDocument();
doc.LoadXml(response);
XmlElement root = doc.DocumentElement;
if (root.HasChildNodes)
{
XmlNodeList nodes = root.SelectNodes("user");
System.Collections.IEnumerator ienum = nodes.GetEnumerator();
ArrayList userDetails = new ArrayList();
while (ienum.MoveNext())
{
XmlNode n = (XmlNode)ienum.Current;
string name = n.SelectSingleNode("name").InnerText;
string tenant = n.SelectSingleNode("tenant-name").InnerText;
string role = n.SelectSingleNode("role").InnerText;
userDetails.Add(new string[] { name, tenant, role });
}
return userDetails;
}
else
{
throw new Exception("Error: Invalid response when getting user info.");
}
}
/// <summary>
/// Gets a list of indicators from KPI Dashboard. For demo purposes
/// we simply return the 1st indicator from this list.
/// </summary>
/// <returns>array { [indicator id], [indicator name] } </returns>
public static string[] GetFirstIndicator()
{
Uri uri = new Uri(API_URI + "/indicators.xml");
string response = Send(uri, HttpMethod.GET, null);
XmlDocument doc = new XmlDocument();
doc.LoadXml(response);
XmlElement root = doc.DocumentElement;
if (root.HasChildNodes)
{
// for this demo get the first indicator //
XmlNode n;
n = root.FirstChild.SelectSingleNode("id");
string indicatorId = n.InnerXml;
n = root.FirstChild.SelectSingleNode("name");
string indicatorName = n.InnerXml;
return new string[] { indicatorId, indicatorName};
}
else
{
throw new Exception("Error: No indicators are defined in KPI Dashboard. Try loading the demo data.");
}
}
/// <summary>
/// Add a socre to an indicator in KPI Dashboard
/// </summary>
/// <param name="indicatorId">ID of the indicator to add to score to. <see>ApiSample.GetFirstIndicator()</see></param>
/// <param name="value">The value of the score</param>
/// <param name="date">The date of the score in format YYYY-MM-DD</param>
/// <returns></returns>
public static string PostScore(string indicatorId, string value, string date)
{
Uri uri = new Uri(API_URI <notextile><code> "/indicators/" </code></notextile> indicatorId + "/scores.xml");
StringBuilder xml = new StringBuilder();
xml.Append("<score><value>").Append(value).Append("</value><date>").Append(date).Append("</date></score>");
string response = Send(uri, HttpMethod.POST, xml.ToString());
XmlDocument doc = new XmlDocument();
doc.LoadXml(response);
XmlElement root = doc.DocumentElement;
if (root.HasChildNodes)
{
XmlNode n = root.SelectSingleNode("id");
string scoreId = n.InnerXml;
return scoreId;
}
else
{
throw new Exception("Error: Invalid response when posting score.");
}
}
/// <summary>
/// Delete a score from KPI Dashboard
/// </summary>
/// <param name="scoreId">ID of the score. <see>ApiSample.PostScore()</see></param>
public static void DeleteScore(string scoreId)
{
Uri uri = new Uri(API_URI <notextile><code> "/scores/" </code></notextile> scoreId + ".xml");
Send(uri, HttpMethod.DELETE, null);
}
/// <summary>
/// Communicate with the KPI Dashboard API.
/// </summary>
/// <param name="uri">URI of the API to interact with</param>
/// <param name="method">The HTTP method to be used <see>ApiSample.HttpMethod</see></param>
/// <param name="data"></param>
/// <returns></returns>
private static string Send(Uri uri, HttpMethod method, string data)
{
string PASSWORD = "ignored";
try
{
// Create the web request
HttpWebRequest request = WebRequest.Create(uri) as HttpWebRequest;
//This line ensures the request is processed through Basic Authentication
request.Credentials = new NetworkCredential(MY_API_TOKEN, PASSWORD);
request.Method = Enum.GetName(typeof(HttpMethod), method);
switch (method)
{
case HttpMethod.GET:
break;
case HttpMethod.PUT:
case HttpMethod.POST:
if (string.IsNullOrEmpty(data)) throw new Exception("Error: HttpMethod POST needs data to send");
request.ContentType = "application/xml;charset=utf-8";
data = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" + data;
Stream s = request.GetRequestStream();
s.Write(System.Text.Encoding.ASCII.GetBytes(data), 0, data.Length);
s.Close();
break;
case HttpMethod.DELETE:
break;
}
WebResponse response = request.GetResponse();
StreamReader sr = new StreamReader(response.GetResponseStream());
string xml = sr.ReadToEnd();
//Console.WriteLine("Response from KPI Dashboard:\n{0}\n\n", xml);
return xml;
}
catch (WebException we)
{
StreamReader sr = new StreamReader(we.Response.GetResponseStream());
string errorMsg = sr.ReadToEnd();
throw new Exception(we.Message <notextile><code> " " </code></notextile> errorMsg, we);
}
}
/// <summary>
/// Example code
/// - shows user details
/// - fetches the 1st indicator
/// - posts score of the indicator
/// - removes the socore again
/// </summary>
/// <param name="args"></param>
static void Main(string[] args)
{
try
{
Console.WriteLine("Getting my user info ...");
ArrayList userDeatils = GetMyUserDetails();
foreach (string[] userDetail in userDeatils)
{
Console.WriteLine("{0} has access to {1} as {2}", userDetail[0], userDetail[1], userDetail[2]);
}
Console.WriteLine("Selecting first indicator ...");
string[] indicator = GetFirstIndicator();
string indicatorId = indicator[0];
string indicatorName = indicator[1];
Console.WriteLine("Selected Indicator \"{0}\" with id {1}", indicatorName, indicatorId);
Console.WriteLine("Creating score ...");
string scoreId = PostScore(indicatorId, "33.39", "2010-09-30");
Console.WriteLine("Created score {0}", scoreId);
Console.WriteLine("Deleting score ...");
DeleteScore(scoreId);
Console.WriteLine("Deleted score.");
Console.WriteLine("Done.");
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
Console.WriteLine("\nPress any key close this application");
Console.ReadLine();
}
}
Download this sample code.