Adding own custom web service to SharePoint


I posted awhile back about InfoPath and Web Service data connection and I got question about using own web services in SharePoint (or at least I interpreted it that way :-). I tried to describe idea to have own custom "proxy" web service that would do all the necessary stuff inside SharePoint so that you could use local API and not the web service API. So if you know about application pages then you know what I'm talking about. Same things apply to web services too. But as always... I'm not good at telling stuff so let's jump to the code 🙂

I just quickly created Microsoft.MCS.WebService.ExampleWebService.asmx and added it to the layouts folder (=C:\Program Files\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\LAYOUTS). This time I skipped features/solutions and did my example the easy way (as always :-).

Here is the content of the .asmx file:

1
2
<%@ WebService Class="Microsoft.MCS.WebService.ExampleWebService,
Microsoft.MCS.WebService,Version=1.0.0.0,Culture=neutral,PublicKeyToken=a030a6768fa75cfc" %>

And code behind is in here (I signed it and put it into GAC):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
using System;
using System.Web.Services;
using Microsoft.SharePoint;
using System.Security.Principal;

namespace Microsoft.MCS.WebService
{
  public class ExampleWebService : System.Web.Services.WebService
  {
    [WebMethod]
    public string WhoAmI()
    {
      return WindowsIdentity.GetCurrent().Name +
          " <->" + SPContext.Current.Web.CurrentUser.LoginName;
    }
  }
}

Code is pretty simple since it just returns string that contains current users WindowsIdentity name and LoginName using SharePoint API.

If you run this stuff directly from SharePoint using browser you'll get something like this:

And now you can use this stuff from InfoPath as well:


So if you want to have weird SharePoint functionality (like enumerating lists) in your InfoPath forms you could use your own "proxy" web service to make it happen. This example was just skeleton that shows that this kind of stuff can be done but the exact implementation is left to you. I hope that I answered one of the questions that have been asked in my blog 🙂

And if you try to update stuff in your code you'll most likely end up with SPException saying that "The security validation for this page is invalid. Click Back in your Web browser, refresh the page, and try your operation again."... but don't worry because that's the way it works 🙂 You can turn off the security validation check temporary with AllowUnsafeUpdates = true. I'll leave rest of that stuff for you...

Anyways... Happy hacking!

J

Comments (14)

  1. If you have following setup... You need to create InfoPath Form that you're going to use in Forms Server

  2. If you have following setup... You need to create InfoPath Form that you&#39;re going to use in Forms

  3. Basiquement SharePoint expose une grande partie de ses fonctionnalités via des Web Services standards

  4. oren says:

    Hi. Are you using a web service template from visual studio, or just creating asmx file and separately a class libaray that you put it into GAC.

    It would be nice with more details because there is no real tutorial for creating a custom web service with  SharePoint API.

    Thanx

  5. oren says:

    Hi. Are you using a web service template from visual studio, or just creating asmx file and separately a class libaray that you put it into GAC.

    It would be nice with more details because there is no real tutorial for creating a custom web service with  SharePoint API.

    Thanx

  6. Oren says:

    ok! works fine. but I have a problem with SPContext.Current:  the site collection i am working with is http://localhost/sites/test1">http://localhost/sites/test1

    but SPContext.Current returns http://localhost.

    please help

  7. Oren says:

    ooops:

    I mean SPContext.Current.Web

  8. shabana says:

    Thanks for the post ...

    I have a custom webservice to retrieve users of particular group from sharepoint ..It is working fine on servers..

     [WebMethod]

       public ArrayList  RetreiveUserNames_SPA_Evaluation()

       {

               try

               {

                         SPWeb myWeb = SPControl.GetContextWeb(Context);

                       //string user = myWeb.CurrentUser.LoginName;

                       string username = myWeb.CurrentUser.LoginName;

                       SPGroupCollection sGroups = myWeb.Groups;

                       foreach (SPGroup grp in sGroups)

                       {

                           string grpName = grp.Name;

                       }

                       SPGroup SPA_Evaluation_Group = myWeb.Groups["SPA_Evaluation"];

                       SPUserCollection SPA_Evaluation_Group_Members = SPA_Evaluation_Group.Users;

                       string SPA_Evaluation_Group_Members_Collection = string.Empty;

                       ArrayList tstArray = new ArrayList();

                       foreach (SPUser usr in SPA_Evaluation_Group_Members)

                       {

                           tstArray.Add(usr.Name.ToString());

                       }

                       return tstArray;

               }

               catch (Exception e)

               {

                   HttpContext.Current.Response.Write(e.Message);

                   return null;

               }

       }

    But when integrated with Infopath and accessed thru web (the sharepoint site where the form is placed)throwing error

    " Unable to connect to publishing custom string handler for output caching . IIS Instance Id is '439109092' , Url is  'http://..../service.asmx'"

    Please,Help me to resolve this problem..

    Thanks in advance..

  9. Mark Wagner says:

    After creating your web service you can Automatically Generate the SharePoint disco.aspx and wsdl.aspx files using the SPDev utility found here.  Works great and takes only seconds. http://www.crsw.com/mark/Lists/Posts/Post.aspx?ID=57

  10. Miguel says:

    Hi, I have Sharepoint with Anonymous access enabled.

    I have created a custom web service for retrieve list data, but it always ask me for login... i need the web service to be called even from anonymous..

    I've tried to write the WindowsIdentity.GetCurrent().Name from the web service, and I get the one i need using impersonation, etc..

    but when i try SPControl.GetContextWeb(Context).CurrentUser it's null..

    some help please? its driving me mad :@

    thank you!

  11. Simon Ovens says:

    Miguel

    Did you try and wrap your method with                         SPSecurity.RunWithElevatedPrivileges(delegate() ?

  12. csr says:

    Hi, I created my own sharepoint web service, the problem is that the only user capable of working with it is the Site Collection Administrator or a user in the WSS_ADMIN_WPG group, my web service needs to be invoked remotedly (not in the server) and Im using System.Net.NetworkCredential(user,pass), when I use it with another kind of user I get the "401 unauthorized" is there a way to invoke it with another user with lower priviledges?

    I would be very gratefull if you help me, Csr.

  13. Very nice post.. It solved the problem of creating web service so easily that I was amazed.

Skip to main content