Saturday, January 9, 2010

My Learnings - SharePoint Web Services


In my project, I spent some time on integrating my application with SharePoint. During this, I faced challenges especially with attachments. I am sharing my experience on SharePoint which helps for guys who are new. When you do Google you can find many .NET based solutions to integrate with SharePoint. My application is not .NET based so I have chosen to go with Web Services.
I used XMLHTTP from javascript to send SOAP requests for creating lists, reading and adding attachments to those list items. SharePoint provided Lists web service to achieve my functionality. Even though web services are available I faced challenges in finding  information about web service parameters like listItemID and also during attachment ( attachment support is there only for Custom List category). Here you can find step wise to add an attachment to list Item.

GetListCollection

This web service helps to read all the lists in a site. Using this response you can get List ID, which is GUID and other meta data Information.

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <GetListCollection xmlns="http://schemas.microsoft.com/sharepoint/soap/">
    </GetListCollection>
  </soap:Body>
</soap:Envelope>

UpdateListItems

This web service helps to create, delete and change list items in a List. Before uploading a document/attachment, list item has to be created. The following request creates a list item called "Learnings".

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <UpdateListItems xmlns="http://schemas.microsoft.com/sharepoint/soap/">
      <listName>MyLearnings</listName>
      <updates>
        <Batch OnError="Continue" >
          <Method ID="1" Cmd="New">
            <Field Name="Title">Learnings</Field>
          </Method>
        </Batch>
      </updates>
    </UpdateListItems>
  </soap:Body>
</soap:Envelope>

You can find more information about Batch, Method and Field here.

GetListItems


Once list item is added into Custom List, then this method helps to read ID of a list item and also other meta information. Response contains rows ( i.e. list items ) and each row contains ows_ID, which is list Item ID. This is required for adding an attachment. So before adding, this service helps to read ID of a list item.

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <GetListItems xmlns="http://schemas.microsoft.com/sharepoint/soap/">
      <listName>MyLearnings</listName>
      <query>
        <Query>
          <Where>
            <Contains>
              <FieldRef Name="Title" />
              <Value Type="Text">Learnings</Value>
            </Contains>
          </Where>
        </Query>
      </query>
      <webid>37bbc01f-0ca2-438b-bb77-7ec23f98a962</webid>
    </GetListItems>
  </soap:Body>
</soap:Envelope>

Here <query> and <webid> are optional parameters. But query helps, when you want to read list items based on some conditions. List's webid value can be retrieved from GetListCollectionResponse, which returns list information in a site.

AddAttachment

This method helps to add attachment to a list item. We have seen how to add a list item and also to get list item ID.  In AddAttachment, list name is name of the custom list ( in our case it is MyLearnings), listItemID is ID of list item and fileName is attachment file. Attachment element contains Base64 encoded content of a file.

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
  <AddAttachment xmlns="http://schemas.microsoft.com/sharepoint/soap/">
    <listName>MyLearnings</listName>
    <listItemID>1</listItemID>
    <fileName>HowtouseSharepoint.doc</fileName>
    <attachment>
    </attachment>
  </AddAttachment>
</soap:Body>
</soap:Envelope>

Using HTML + Javascript it is not possible to read file content directly. So with help of server side program, content has to transfer back to client with Base64 encoding in response to FORM POST. User can add attachment server side also  to avoid content downloading to client. In my case, I have chosen client side as authentication of SharePoint is NTLM ( In .NET delegation support is there. With that, you can do  attachment server side itself. ).
I have written a server side handler to return Base 64 Content.  You can find javascript code below.

I hope this helps for those who are new to SharePoint and trying to do integration with Web Services.

( I used IE's XML DOM API in the following example. )


<html>
<head>

<script type="text/javascript">
function getResponse(url, soapAction, request)
{
var connection = getConnection();
connection.open("POST", url, false);
connection.setRequestHeader("SOAPAction", soapAction);
connection.send(request);
response.value = connection.responseText;
}

function getConnection()
{
if ( window.ActiveXObject )
{
return new ActiveXObject("Microsoft.XMLHTTP");
}
else
{
return new XMLHttpRequest();
}
}


function getListItemsFun()
{
getResponse("<<Site URL>>_vti_bin/Lists.asmx",
"http://schemas.microsoft.com/sharepoint/soap/GetListItems",
GetListItemsReq.XMLDocument.cloneNode(true));
}


function updateListItemFun()
{
getResponse("<<Site URL>>_vti_bin/Lists.asmx",
"http://schemas.microsoft.com/sharepoint/soap/UpdateListItems",
UpdateListReq.XMLDocument.cloneNode(true));
}

function upload()
{
document.getElementById("oForm").setAttribute("target", "uploadFrame");
document.getElementById("oForm").submit();
}

function getListCollectionFun()
{
getResponse("<<Site URL>>_vti_bin/Lists.asmx",
"http://schemas.microsoft.com/sharepoint/soap/GetListCollection",
getListCollectionreq.XMLDocument.cloneNode(true));
}
//this method will be called once uploaded
//encodedResponse is an element in downloaded html which contains Base64 Content.
function upLoadStateChanger()
{

if ( !uploadFrame.document.getElementById("encodedResponse") || ! uploadFrame.document.getElementById("encodedResponse").value ) return;

var attachXml = addAttachMentreq.XMLDocument.cloneNode(true);

attachXml.selectSingleNode(".//attachment").text = uploadFrame.document.getElementById("encodedResponse").value;

getResponse("<<Site URL>>_vti_bin/Lists.asmx",
"http://schemas.microsoft.com/sharepoint/soap/AddAttachment",
attachXml);

}

</script>

<xml id="GetListItemsReq">
<soap:Envelope  xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
 <soap:Body>
<GetListItems xmlns="http://schemas.microsoft.com/sharepoint/soap/">
 <listName>MyLearnings</listName>
 <query>
<Query>
 <Where>
<Contains>
 <FieldRef Name="Title" />
 <Value Type="Text">Learnings</Value>
</Contains>
 </Where>
</Query>
 </query>
 <webid>37bbc01f-0ca2-438b-bb77-7ec23f98a962</webid>
</GetListItems>
 </soap:Body>
</soap:Envelope>
</xml>
<xml id="getListCollectionreq">
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
 <soap:Body>
<GetListCollection xmlns="http://schemas.microsoft.com/sharepoint/soap/">
</GetListCollection>
 </soap:Body>
</soap:Envelope>
</xml>
<xml id="addAttachMentreq">
<soap:Envelope  xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
 <AddAttachment xmlns="http://schemas.microsoft.com/sharepoint/soap/">
<listName>MyLearnings</listName>
<listItemID>1</listItemID>
<fileName>HowtouseSharepoint.doc</fileName>
<attachment>
</attachment>
 </AddAttachment>
</soap:Body>
</soap:Envelope>
</xml>
<xml id="UpdateListReq">
<soap:Envelope  xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
 <soap:Body>
<UpdateListItems xmlns="http://schemas.microsoft.com/sharepoint/soap/">
 <listName>MyLearnings</listName>
 <updates>
<Batch OnError="Continue" >
 <Method ID="1" Cmd="New">
<Field Name="Title">Learnings</Field>
 </Method>
</Batch>
 </updates>
</UpdateListItems>
 </soap:Body>
</soap:Envelope>
</xml>
</head>
<body>
<button onclick="getListItemsFun()">Get List Items</button>

<button onclick="updateListItemFun()">Update List Items</button>
<button onclick="getListCollectionFun()">Get Collection</button>

<form name="oForm" action="<<servlet URL>>" enctype="multipart/form-data" method="POST">
<input type="file" name="file1" id="file1" />
</form>
<input id="but" name="Upload" onclick="upload()" type="button" value="Upload" />
<iframe name="uploadFrame" style="display: none" />
</body>
</html>




Friday, December 25, 2009

Other side of the coin

It’s true. In current political system, leader who is leading a particular place ( either town/state/country ) has to be strong in all aspects especially dealing with people who are against to him in his own team otherwise problem starts there. It doesn’t matter for them will that help people? It matters if it helps me and my family!
Currently we are seeing an agitation for separate from Andhra Pradesh, which is a state for Telugu speaking people. Why separate state? Is the question most of the common man thinks when someone says I am for separate state and fighting for people who wants it. Good. Then other side of people asks why do you want?
Then
1. It’s very backward place
2. We don’t have proper “reservation”s in jobs (still reservations in 2010?).
3. Government is not giving funds to this area. Complete development is happening to one place.
4. e.t.c…
I believe, there is no place called backward. It’s created by persons who are representing that place. Who stops him for fighting for funds? For every place, government allocates money. It’s responsibility of that people representative (MLA or MP) to spend for good cause. When someone says its backward place then people of that region should come forward and asks what are you doing for that? We are seeing wonders in the world where people are building islands so what’s not possible if we want to do something. Some part of my education happened in Telangana region. My father was working in this region during that time. He went to PV Narasimha Rao’s village in Karimnagar on his office work. He surprised! Place is not at all looks like a former prime minister’s village. A person from that place says he didn’t do anything for his village. But he has done for country, so we can excuse him here (still not!). This is one example which gives that being separate state is not answer for making development. It has to be there in leaders mind to do that. Recently NDTV organized a debate on Telangana movement in Hyderabad with name “Hyderabad Blues”. In that, one guy asked K Rama Rao, son of KCR, what your father has done to Karimnagar/Siddipet/Mahaboob Nagar for development. He told my father elected to fight for separate Telangana so he is fighting for it. Surprised again! It’s not me and you also know very well about this. We do discuss daily in our Tea meetings. Raising voice against this is required when system is going out of control like today.
Then leaders talk about job opportunities. Now, most of the jobs are in private sector and it will be! We have to ensure proper educational system is there in villages, towns, cities so that students will be ready for that. I studied in a private school in Pedda Palli, Karimnagar. It is very good school. Warangal also has good colleges and schools. As I know about these two places I can say it’s good place for education and students are smart. Government has to ensure infrastructure to develop a place, if it doesn’t have like in case of Adilabad, Srikakulam and Anantpur districts. Now we see very good infrastructure growth so ensuring there is a proper money allocation to your place it is possible to create opportunities.
You take any point, root cause points to public representative and people responsibilities.
We are seeing bandh and violence since last 30 days in State. Politicians are playing with people money. I saw news that NRIs are doing Pada Yatra for separate state. What man? You studied with AP tax payer’s money and spent some time in foreign country and coming back as there is an opportunity for you to grow here to make money again. In that, two NRIs are son and daughter-in-law of a politician. Ministers who are from Telangana region are telling that they have resigned for telangana and sent a fax to Mrs Sonia Gandhi in a letter with all our signs. Mrs. Gandhi, I guess, gets some thousand like this daily. I don’t think she/her office looks into all these. If they really want to resign then they have to give that to CM or Governor. Why are you trying to make people fool (I am sorry, we are already)? Moreover they are representing a state not region. If they want they can resign for MLA not for ministry (I think still they can continue for 6 months even they are not MLAs).
Don’t think that this guy is probably from Andhra region that’s why it smells like that. I have born in Nizamabad and complete primary education done in Telangana region except 2 years. If someone is fighting for right cause then I support not for un-employed politicians.

Wednesday, January 7, 2009

Weekend meet

This weekend, I am going to meet new friends. Here I used "new" because It's my first session at Twincling . I came to know this from my friend Leela, who works with me.
Initially I told them, it will be on Web in general. But this forum is more on developer centric so expectation is on programming model of Web.
Session Agenda will be
1 ) Web1.0 Programming model
2 ) Introduction to AJAX
3 ) AJAX Frameworks
4 ) End user value with Programming models ( here it will be with AJAX )

Ok... my session is on AJAX at