Archive

Archive for the ‘Web Services’ Category

How to call Office365 web service in a Console application using WCF

June 25, 2012 1 comment

In my previous post, I showed you how to call the SharePoint web service using a console application. In this post, I’d like to show you how to call the same web service in the cloud, aka Office365.In office365, it uses claims authentication as opposed to windows authentication for normal in-house SharePoint Deployment. For Details of the explanation you can see Wictor’s post on this here. The key to make it work is to understand when you authenticate from Office365, you get your authentication token. You then need to pass this token to your HTTP request as cookie to make the web service call. Here is the code sample to make it work.I have modified Wictor’s by removing the client object references.

static void Main(string[] args)
{
MsOnlineClaimsHelper claimsHelper = new MsOnlineClaimsHelper( "admin@ybbest.onmicrosoft.com", "YourPassword","https://ybbest.sharepoint.com/");
HttpRequestMessageProperty p = new HttpRequestMessageProperty();
var cookie = claimsHelper.CookieContainer;

string cookieHeader = cookie.GetCookieHeader(new Uri("https://ybbest.sharepoint.com/"));
p.Headers.Add("Cookie", cookieHeader);
using (ListsSoapClient proxy = new ListsSoapClient())
{
proxy.Endpoint.Address = new EndpointAddress("https://ybbest.sharepoint.com/_vti_bin/Lists.asmx");

using (new OperationContextScope(proxy.InnerChannel))
{
OperationContext.Current.OutgoingMessageProperties[HttpRequestMessageProperty.Name] = p;
XElement spLists = proxy.GetListCollection();
foreach (var el in spLists.Descendants())
{
//System.Console.WriteLine(el.Name);
foreach (var attrib in el.Attributes())
{
if (attrib.Name.LocalName.ToLower() == "title")
{
System.Console.WriteLine("> " + attrib.Name + " = " + attrib.Value);
}
}
}
}
System.Console.ReadKey();
}
}

You can download the complete code from here.

Reference:

Managing shared cookies in WCF

How to do active authentication to Office 365 and SharePoint Online

Advertisements

How to fix “Collection was modified; enumeration operation may not execute. “when using Copy.asmx in SharePoint2010

April 21, 2012 Leave a comment

Problem:

In my current project, we use copy.asmx web services in SharePoint2010 to upload a document to a document library. In one of the document library, when uploading a document with a choice field, it blows up and the error message is Collection was modified; enumeration operation may not execute.

Analysis:

After some research , we found out the problem is that we have 2 content types that both have a field called Document Type , although the internal name are different but the display name are exactly the same and this cause the problem. I am still not too sure why, it could possibly a SharePoint bug.

Solution:

After rename one of the field display name to a different name, it works like a charm. You can download source code with the problem here and source code without the problem here.

How to create item in SharePoint2010 document library using SharePoint Web service

March 10, 2012 13 comments

Today, I’d like to show you how to create item in SharePoint2010 document library using SharePoint Web service. Originally, I thought I could use the WebSvcLists(list.asmx) that provides methods for working with lists and list data. However, after a bit Googling , I realize that I need to use the WebSvcCopy (copy.asmx).Here are the code used

private const string siteUrl = "http://ybbest";

private static void Main(string[] args)

{

using (CopyWSProxyWrapper copyWSProxyWrapper = new CopyWSProxyWrapper(siteUrl))

{

copyWSProxyWrapper.UploadFile("TestDoc2.pdf",

new[] {string.Format("{0}/Shared Documents/TestDoc2.pdf", siteUrl)},

Resource.TestDoc, GetFieldInfos().ToArray());

}

}

private static List GetFieldInfos()

{

var fieldInfos = new List();

//The InternalName , DisplayName and FieldType are all required to make it work

fieldInfos.Add(new FieldInformation

{

InternalName = "Title",

Value = "TestDoc2.pdf",

DisplayName = "Title",

Type = FieldType.Text

});

return fieldInfos;

}

Note: When setting the metadata of the file(FieldInformation) , you need The InternalName , DisplayName and FieldType are all required to make it work

Here is the code for the proxy wrapper.


public class CopyWSProxyWrapper : IDisposable

{

private readonly string siteUrl;

public CopyWSProxyWrapper(string siteUrl)

{

this.siteUrl = siteUrl;

}

private readonly CopySoapClient proxy = new CopySoapClient();

public void UploadFile(string testdoc2Pdf, string[] destinationUrls, byte[] testDoc,

FieldInformation[] fieldInformations)

{

using (CopySoapClient proxy = new CopySoapClient())

{

proxy.Endpoint.Address = new EndpointAddress(String.Format("{0}/_vti_bin/copy.asmx", siteUrl));

proxy.ClientCredentials.Windows.ClientCredential = CredentialCache.DefaultNetworkCredentials;

proxy.ClientCredentials.Windows.AllowedImpersonationLevel =

TokenImpersonationLevel.Impersonation;

CopyResult[] copyResults = null;

try

{

proxy.CopyIntoItems(testdoc2Pdf,

destinationUrls,

fieldInformations, testDoc, out copyResults);

}

catch (Exception e)

{

System.Console.WriteLine(e);

}

if (copyResults != null) System.Console.WriteLine(copyResults[0].ErrorMessage);

System.Console.ReadLine();

}

}

public void Dispose()

{

proxy.Close();

}

}

You can download the source code here .

******Update**********

It seems to be a bug that , you can not set the contentType when create a document item using Copy.asmx. In sp2007 the field type was Choice, however, in sp2010 it is actually Computed. I have tried using the Computed field type with no luck. I have also tried sending the ContentTypeId and this does not work.

******Update 20/04/2012**********

I was wrong in my previous update about unable to set the contenttype.As jasonkuter  points out in the comment,You can set the contentType by using the following code

fieldInfos.Add(new FieldInformation { InternalName = "ContentTypeId", Value = "0x010100866B1423D33DDA4CA1A4639B54DD464200DED91C30FFF44647AFA0F99FA6F0E2D2", DisplayName = "Content Type ID", Type = FieldType.Text });

You can find the contenttype id by using the SharePoint manager.Note: the contenttype id is the id in the document library not the content type id you defined in the site collection level.You can download the updated sourcecode here.

References:

SharePoint 2010 Web Services

SharePoint2007 Web Services

SharePoint MSDN Forum