Uploading files using Client Object Model in SharePoint 2010


There are 2 ways to upload files to SharePoint 2010 document libraries using managed client object model.

The first method uses a client library batch mechanism.  It will encode the binary using BASE64 encoding, which could increase the message size by one third.  There might be problems if this isn’t configured correctly.  An example of this code is below:

   1: ClientContext context = new ClientContext("http://spdevinwin");
   2:  
   3: Web web = context.Web;
   4:  
   5: FileCreationInformation newFile = new FileCreationInformation();
   6: newFile.Content = System.IO.File.ReadAllBytes(@"C:\Work\Files\17580_FAST2010_S05_Administration.pptx");
   7: newFile.Url = "17580_FAST2010_S05_Administration 4MB file uploaded via client OM.pptx";
   8:  
   9: List docs = web.Lists.GetByTitle("Documents");
  10: Microsoft.SharePoint.Client.File uploadFile = docs.RootFolder.Files.Add(newFile);
  11: context.Load(uploadFile);
  12: context.ExecuteQuery();
  13: Console.WriteLine("done");

The above code might fail throwing a (400) Bad Request error depending on the file size.  The following code is used to set a higher limit to the upload size.  Note: This is not the same as the max. file size upload limit option available in the web application settings.

   1: SPWebService ws = SPWebService.ContentService;
   2: SPClientRequestServiceSettings clientSettings = ws.ClientRequestServiceSettings;
   3: clientSettings.MaxReceivedMessageSize = 10485760;
   4: ws.Update();
   5: Console.WriteLine(clientSettings.MaxReceivedMessageSize);

The above code sets the message batch size to 10MB so that larger files can be uploaded using managed client object model.

The second methods uses HTTP DAV and sends raw binary across the wire and does not increase the message size.  It is also the preferred upload method when using managed client object model.  Here’s a sample:

   1: ClientContext context = new ClientContext("http://spdevinwin");
   2: using (FileStream fs = new FileStream(@"C:\Work\Files\17580_FAST2010_S03_Arch.pptx", FileMode.Open))
   3: {
   4:     Microsoft.SharePoint.Client.File.SaveBinaryDirect(context, "/documents/17580_FAST2010_S03_Arch from client OM.pptx", fs, true);
   5: }

Hope this helps!  Stay tuned for most posts on managed client object model.

Comments (48)

  1. 20aman says:

    Hi Sridhara,

    Really excellent article. It helped me a lot.

    I am using the second method(i.e. using FileStream object) to upload files. I am using multiple threads to upload files to same or different libraries in sharepoint 2010 from my win application. I am getting following errors sometimes:

    1. Cannot invoke HTTP DAV request. There is a pending query.

    2. The remote server returned an error: (409) Conflict.

    Can you please let me know the root cause for these and any workaround possible for these issues?

    Thanks in advance.

  2. Reetika says:

    Hi Sridhara

    Thanks for this article. It help me alot

    @am20an if you still face the problem or anybody else is having

    then here is the solution which work for me

    ClientContext ctx = new ClientContext("http://yoursharepointURL");

                   Web currentWeb = ctx.Web;

                   ctx.Load(currentWeb);

                   ctx.ExecuteQuery();

                   using (FileStream fs = new FileStream(@"C:dataTestFile.pptx", FileMode.Open))

    { Microsoft.SharePoint.Client.File.SaveBinaryDirect(ctx, "/Sample Documents/TestFile from client.pptx", fs, true);

                   }

                   Console.WriteLine("Uploaded File Successfully");

    and be sure the "http://yoursharepointURL/Sample Documents" is a valid path where you want to upload the file.

    Hope this work for you too.

    Thanks & Regards

    Reetika Tomer

    (MCTS – .Net Framework 2.0, Web Applications)

    Sr. Software Engineer

    Daffodil Software Ltd

    Gurgaon (HR)

    India

  3. Sven says:

    Hi Sridhara,

    thanks for example code!

    It works fine on the server-machine, but using a other system in the network the method "SaveBinaryDirect" throw an exception ("The underlying connection was closed: A connection that was expected to maintain their closed down the server").

    My activedirectory user has full permission for the site.

    I think it isn't a permission problem, because all other functions for example read items or updating items works fine.

    Only the method SaveBinaryDirect() throw an exception.

    Do you know this error? I hope you can help me.

    Best regards!

    Sven

  4. Kevin says:

    Hey is there anyway to attach meta data to the document during upload )with either method)?  or do you have to come back and do it after?

  5. Blaithin Surgeoner says:

    Hi, I too am having problems uploading files using SaveBinaryDirect. I keep getting an error HTTP DAV, the same as am20an. Have you a solution for this?

    Kind regards

  6. @Blaithin please forgive the asking of potentially stupid questions, I'm just trying to narrow down the problem scope and make sure there's actually a bug:

    Can you connect Windows on the machine you're using directly to the SP site's WebDAV? google.com/search

    Is the URL you've passed as a parameter to the client context constructor the same URL you'd use to connect to the WebDAV through Windows on that client machine?

  7. guru says:

    hi,

    can COM loads 2007 sharepoint sites??? im getting error. "The remote server returned an error: (500) Internal Server Error".?

  8. guru says:

    hi,

    can COM loads 2007 sharepoint sites??? im getting error. "The remote server returned an error: (500) Internal Server Error".?

  9. Francisco says:

    Hi,

    I have problem too (The remote server returned an error: (409) Conflict.)

    I try to create item with attach in a custom list in SharePoint 2010 from a simple Windows Form

    Im working in localmachine and i am Administrator in the server and in the SharePoint

    Can u helpme?

    Thanks

    //using IO= System.IO;

    public string NewItemAdjunto(string _nombreLista, string _url, string _titulo, string _detalles, string _pathArchivo)

           {

               try

               {

                   using (ClientContext ctx = new ClientContext(_url))

                   {

                       Uri url = new Uri(_url);

                       Web site = ctx.Web;

                       ctx.Load(site);

                       ctx.Load(site.Lists);

                       string itemId = "13";

                       List lista = ctx.Web.Lists.GetByTitle(_nombreLista);

                       ListItemCreationInformation newInfo = new ListItemCreationInformation();

                       ListItem item = lista.AddItem(newInfo);

                       // Agregamos Valores

                       item["Title"] = _titulo;

                       item["Descripci_x00f3_n"] = _detalles;

                       item["Fecha"] = new DateTime(2010, 11, 10, 8, 0, 0);// Fecha en Duro

                       item.Update();

                       ctx.ExecuteQuery();

                       using (IO.FileStream strm = new IO.FileInfo(@"C:TestAdjunto1.txt").Open(IO.FileMode.Open))

                       {

                           Microsoft.SharePoint.Client.File.SaveBinaryDirect(ctx, "/Lists/Contenido%201/Attachments/" + itemId + "/" + "Adjunto1.txt", strm, true);

                       }

                   }

                   return "Item Creado con Adjunto";

               }

               catch

               {

                   throw;

               }

           }

  10. Dhileep says:

    Hi All,

    I am getting the error -The remote server returned an error: (404) Not Found.

    While adding the attachment to the list Item using

    Microsoft.SharePoint.Client.File.SaveBinaryDirect(clientContext, attachmentPath, stream, true);

    In my case i have created an event receiver feature already running on this list, which will add an  attachment to the list item and will delete the same when the item is added.

    I hope this will create the attachment folder for this list item, but still while adding attachments i'am getting the above file not found exception.

    Please anybody guide me on this .

    Thanks in Advance,

    Dhileep.

  11. Fire says:

    Plz post code for list item with attachment. here only document library

  12. If I use Microsoft.SharePoint.Client.File.SaveBinaryDirect I get error:

    Microsoft.SharePoint.Client.ClientRequestException was unhandled

     Message=Cannot invoke HTTP DAV request. There is a pending query.

     Source=Microsoft.SharePoint.Client

     StackTrace:

          at Microsoft.SharePoint.Client.File.SaveBinary(ClientContext context, String serverRelativeUrl, Stream stream, String etag, Boolean overwriteIfExists, SaveBinaryCheckMode checkMode)

          at Microsoft.SharePoint.Client.File.SaveBinaryDirect(ClientContext context, String serverRelativeUrl, Stream stream, Boolean overwriteIfExists)

          at DisplayWebTitle.Main() in C:UsershehakamaDocumentsVisual Studio 2010ProjectsConsoleApplicationHH_GetFileConsoleApplicationHH_GetFileProgram.cs:line 69

          at System.AppDomain._nExecuteAssembly(Assembly assembly, String[] args)

          at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)

          at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()

          at System.Threading.ThreadHelper.ThreadStart_Context(Object state)

          at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)

          at System.Threading.ThreadHelper.ThreadStart()

     InnerException:

    Is this because of some protocols are unavailable in our company's intranet?

  13. markt says:

    I found the first method did not work for me until I added a

    context.Load(docs);

    between lines 10 and 11.

  14. Suleman says:

    Sven/Sridhara

    Did you guys found any solution for exception ("The underlying connection was closed: A connection that was expected to maintain their closed down the server"), if so can you please post it here.

  15. Bijay says:

    Hi I can not upload a file more than 3 mb. can u tell me how to upload large files is thr any way??

    I want to use client object model no server side code I want.

    Thanks

    Bijay

    http://www.fewlines4biju.com

  16. Mani says:

    Hi

    I tried to implement the second way to upload documents into SharePoint Foundation 2010  however, all the documents were saved as checked out if "Required Checked Out" option is enabled for a document library. If anyone had encountered similar problem, a little guidance would be helpful.

    Thanks

    Mani

  17. lue@ae.com says:

    This is a great article.

    Thank You!

  18. Krishna says:

    When trying to run from my dev system, getting this same exception

    "client requestexception Cannot invoke HTTP DAV request".

    hope someone posts the solution quickly.

  19. Lahari says:

    Hello,

    I am getting the same exception "Cannot invoke HTTP DAV request", Did anyone resolve it?please let me know

  20. Cheeli Satish says:

               ClientContext clientContext = new ClientContext(siteUrl);

               List CurrentList = clientContext.Web.Lists.GetByTitle(libraryName);

               clientContext.Load(CurrentList.RootFolder);

               clientContext.ExecuteQuery();

               using (FileStream fileStream = new FileStream(fileName, FileMode.Open))

               ClientOM.File.SaveBinaryDirect(clientContext, CurrentList.RootFolder.ServerRelativeUrl.ToString() + "/" + fileName.Split('\')[1], fileStream, true);

    We need to Load the Document Libraries' Root Folder before we execute the query. I've changed the code accordingly and it  worked fine for me, I've tested it with Uploading 40 MB file and it went well. Try It.

    Cheers,

    Satish Cheeli

  21. Nice article, thanks. What is the size limit on WebDav solution?

  22. Fred says:

    I had the following two errors:

    Error 1 = The remote server returned an error: (409) Conflict

    Error 2 = Cannot invoke HTTP DAV request. There is a pending query

    Dug through Google but found no solution…. finally I tried playing with the "SPC.ClientContext" path and the "fileUrl" path … BINGO … it got fixed.  Below is before and after code:

    BEFORE:

               SPC.ClientContext clientContext = new SPC.ClientContext("http://dev:44941/ParentSite");

               string fileUrl = "/CreatedDocs/MyDoc.docx";

    AFTER

               SPC.ClientContext clientContext = new SPC.ClientContext("http://dev:44941");

               string fileUrl = "/ParentSite/CreatedDocs/MyDoc.docx";

    Hope this helps someone.

  23. Darryl says:

    Hi, Try checking or a Pending request first, like so:

     if (clientContext.HasPendingRequest)

                       clientContext.ExecuteQuery();

                   FileInformation fileInfo = Microsoft.SharePoint.Client.File.OpenBinaryDirect(clientContext, (string)v["FileRef"]);

  24. klotin says:

    SaveBinaryDirect throws 403 error if used with saml claims authentication. Bug? Any workarounds?

  25. Jason says:

    Is anyone monitoring this blog?  All I see are tons of questions with no responses.

  26. Damien says:

    Sure why not just leave your requirements and Sridhar can develop your solution FOC!

  27. Sujan says:

    Hi,

    I tried this code in sandboxed visual web part and I am getting below error.

    Error Msg: "Unhandled exception was thrown by the sandboxed code wrapper's Execute method in the partial trust app domain: An unexpected error has occurred."

    Please let me know how to upload File using sandboxed visual web part.

    Thanks in Advanced.

  28. Sang says:

    Hi,

    I could not finr SPwebService class in Managed client object model..?? how I could get it?? Title of this blog post suggest that we can upload large files with the help of Client Object Model but code is say something diffrent isn't it?

    I want to use first methos might be second one work but I need First one for updating metadata with upload folder..

  29. Nandan says:

    When I use Microsoft.SharePoint.Client.File.SaveBinaryDirect(context, "/documents/17580_FAST2010_S03_Arch from client OM.pptx", fs, true);

    I get an exception"

    " The remote server returned an error: (405) Method Not Allowed."

    StackTrace:

    StackTrace = "   at System.Net.HttpWebRequest.GetResponse()rn   at Microsoft.SharePoint.Client.SPWebRequestExecutor.Execute()rn   at Microsoft.SharePoint.Client.File.SaveBinary(ClientContext context, String serverRelativeUrl, Stream stream, String etag, Boolean over…

    Any help would be appreciated

  30. Manoj says:

    HI ,

    Please can anyone tell me how to authenticate Rest service.

    I am doing the same but getting exception while doing any thing with sharepoint.

    I belive this is due to service is not authenticate.

    So please can any one explain how to do that.

    Regards,

    Manoj

  31. prabhash says:

    hI i'm getting 401 error while using the upload with client model as it is working fine on local system. but throwing 401 .. any work arround for big size file upload using client object model.

  32. Thomas Bomann says:

    When using your second approach (SaveBinaryDirect) uploading to a document library works fine, unless you try to upload an exe file. Is there a limitation for some file types in SaveBinaryDirect or how can I solve this problem?

  33. Gnapathi says:

    Thanks Sridhar It resolved my problem

  34. Nathan says:

    I'm getting a 403 Forbidden when trying the HTTP DAV method and passing through authentication credentials. The first method works file but the file sizes are to big!!

  35. Evgeny says:

    Thanks, the code works like a charm!

  36. John says:

    I used second method and uploaded document successfully. But all files are Checked out. I found some code to Check in the the file. But I got Permission error. I just wondering what kind of permission is needed (I can already upload the file). Below is the code.

    Thanks,

    John

          public void TestUsingSharePointClient()

           {

               string sharePointServer = @"https://spo.mycompany.com";

               string sharePointRoot = @"/sites/My Documents";

               string sharePointFileUrl = null;

               string locaFilePath = @"C:PlaygroundZZZ_TestDatamy test file.txt";

               using (ClientContext context = new ClientContext(sharePointServer))

               {

                   context.Credentials = new NetworkCredential("john", "password", "domain");

                   // NOTE1: Below three lines seems unnecessary

                   Web currentWeb = context.Web;

                   context.Load(currentWeb);

                   context.ExecuteQuery();

                   using (FileStream fs = new FileStream(locaFilePath, FileMode.Open))

                   {

                       sharePointFileUrl = sharePointRoot + "/Level One/Level Two/John Test Doc.txt";

                       Microsoft.SharePoint.Client.File.SaveBinaryDirect(context, sharePointFileUrl, fs, true);

                   }

                   //Update metadata and check in the file

                   Microsoft.SharePoint.Client.File file = context.Web.GetFileByServerRelativeUrl(sharePointFileUrl);

                   //Checkout if checked in

                   context.Load(file);

                   context.ExecuteQuery();  // <<<<<< I got permission error. Want kind of permission do I need.

                   if (file.CheckOutType == CheckOutType.None)

                   {

                       file.CheckOut();

                   }

                   file.CheckIn("Batch upload", CheckinType.OverwriteCheckIn);

                   // more code update the fields …

  37. anto52nio says:

    Hi John, have you checked if any mandatory metadata is not filled in?

    You can edit the properties directly in Sharepoint to find that mandatory metadata and then try a manual CheckIn,

    Regards,

  38. Verth says:

    I also have the problem with the webdav pending request!!!

    Any help is highly appreciated!

  39. Verth says:

    In my project i was just able to fix that webdav error i got about pending requests. The pending request warning is actually a mention that there is no access to an UPDATE or EXECUTEQUERY statement.

    Thus, this is not related to the SaveBinaryDirect function but to other function in your code. In my case i tried just doing a savebinarydirect (with the root ClientContext and with the full path including the subsitename path as parameter) and it worked perfectly.

    After adding the file i was getting the file back into a File-object to modify some metadata. I still used the root client context to do that, but then you need to switch back to the specific subsite client context. For me that was the key for not having the pending webdav error anymore….

    Hope i could help someone with this.

    btw: i use Sharepoint 2013 (on premise)

  40. mahesh says:

    HI,

    Please anybody tell me how to call webservice for file increase size limit,

    What is the webservice do i  need to call to increase the file size limit in client object model

    please anybody help me .

  41. Moz says:

    Thanks ! Nice Topic.

  42. preamKumar says:

    hi,

      i facing the error while uploading the file,  all the file are saving in the same name  "newFile.Url = "17580_FAST2010_S05_Administration 4MB file uploaded via client OM.pptx";"

  43. Neha says:

    I want to create a write in MemoryStream and then put the same in Shared documents in Sharepoint Below is the code I am trying:-

        var clientContext = new ClientContext("https://server.info/&quot;);

                       string fileUrl = "/Shared Documents/NewDocumentFromTemplate.txt";

                       var ms = new MemoryStream();

                       using (var file = new StreamWriter(ms))

                       {

                           file.WriteLine("Wrinting in file");

                       }

                       Microsoft.SharePoint.Client.File.SaveBinaryDirect(clientContext, fileUrl, ms, true);

    Its actually creating a new file as NewDocumentFromTemplate.txt but it is empty. Its not writing anything.  🙁

    Actuallly I want to create a file on fly and then upload it in share point.

    Please help I am first time working with Share Point client.

  44. Sharepoint 2010 says:

    Hi, Try checking or a Pending request first, like so:

    if (clientContext.HasPendingRequest)

                      clientContext.ExecuteQuery();

                  FileInformation fileInfo = Microsoft.SharePoint.Client.File.OpenBinaryDirect(clientContext, (string)v["FileRef"]);

    that's working for me… thanks

  45. SharePoint 6996 says:

    The second method doesn't work when you have required columns in the document library or list….

    The first method works as long as you run a powershell command on the Web front end and do iis reset on the all the servers in the farm

  46. Jmune says:

    Can someone help… I would prefer to build out this solution with javascript.  I am using a SharePoint 2010 Enterprise environment.  I have successfully translated all the code from C# to javascript except the coup-de-gras: SPFileCollection.Add().  I consistently receive two errors based on differences in my code.  Please take a look and provide suggestions if you can:

    #################################

    # CODE 1 START

    #################################

    var item = null;

    var clientContext = new SP.ClientContext.get_current();

    var oList = clientContext.get_web().get_lists().getByTitle(libraryName);

    clientContext.load(oList);

    var itemCreateInfo = new SP.ListItemCreationInformation();

    itemCreateInfo.set_underlyingObjectType(SP.FileSystemObjectType.file);

    itemCreateInfo.set_leafName(fileName);

    item = oList.addItem(itemCreateInfo);

    item.set_item("ContentTypeId", "0x0101");

    item.set_item('Title', fileName);

    item.update();

    clientContext.load(item);

    clientContext.executeQueryAsync(Function.createDelegate(this, this.onQuerySucceeded), Function.createDelegate(this, this.onQueryFailed));

    #################################

    # CODE 1 END

    #################################

    The above code produces the following error:

    Request failed.  To add an item to a document library, use SPFileCollection.Add()

    #################################

    # CODE 2 START

    #################################

    var item = null;

    var clientContext = new SP.ClientContext.get_current();

    _oList = clientContext.get_web().get_lists().getByTitle(libraryName);

    clientContext.load(_oList , "RootFolder");

    var rootFolder = _oList.get_rootFolder();

    var files = rootFolder.get_files();

    var fileStr = "Hello World";

    var bytes = [];

    for (var i = 0; i < fileStr.length; ++i)

    {

    bytes.push(fileStr.charCodeAt(i));

    }

    this.newFile = files.add(fileName,bytes,true);

    clientContext.executeQueryAsync(Function.createDelegate(this, this.OnQuerySucceeded), Function.createDelegate(this, this.onQueryFailed));

    #################################

    # CODE 2 END

    #################################

    The above code produces the following error:

    TypeError: Object doesn’t support property or method 'add'

  47. SharePoint 6996 says:

    @Jmune: When you use # CODE 1 START one did you update clientSettings.MaxReceivedMessageSize using powershell?

    Once you update that setting on the server you need to perform iisreset on all the servers in the farm.

    Here is the complete script that you need to run and do iisreset to be able to upload for the files upto 50MB

    $ws = [Microsoft.SharePoint.Administration.SPWebService]::ContentService

    $ws.ClientRequestServiceSettings.MaxReceivedMessageSize =  52428800

    $ws.Update()

  48. Jmune says:

    @SharePoint 6996: I did not update with PowerShell.  The files I need to add are only a few Kilobytes.

    I found a solution with .addTemplateFile.  What really helped was the following code that identifies most (if not all) functions for JS objects:

    function getMethods(txt,obj)

    {

       var res = [];

       var listInfo;

       var dispLimit = 50;

       var currCount = 0;

       for(var m in obj) {

           //if(typeof obj[m] == "function") {

               res.push(m);

               listInfo += m + 'n';

    currCount += 1;

           //}

           if(currCount > dispLimit)

           {

            alert(txt + 'nn' + listInfo);

            currCount = 0;

            listInfo = "";

           }

       }

       alert(txt + 'nn' + listInfo);

       return listInfo;

    }

    After the fact, I found a code snippet on this site: jeremybranham.wordpress.com/…/sharepoint.  It has most of the solution I am looking for.  Now I just need to convince the system to add content to the files.

Skip to main content