Download File From SharePoint 365 - c#

string remoteUri = "http://www.contoso.com/library/homepage/images/";
string fileName = "ms-banner.gif", myStringWebResource = null;
// Create a new WebClient instance.
WebClient myWebClient = new WebClient();
// Concatenate the domain with the Web resource filename.
myStringWebResource = remoteUri + fileName;
Console.WriteLine("Downloading File \"{0}\" from \"{1}\" .......\n\n", fileName, myStringWebResource);
// Download the Web resource and save it into the current filesystem folder.
myWebClient.DownloadFile(myStringWebResource,fileName);
Console.WriteLine("Successfully Downloaded File \"{0}\" from \"{1}\"", fileName, myStringWebResource);
Console.WriteLine("\nDownloaded file saved in the following file system folder:\n\t" + Application.StartupPath);
I'am Using this code from MSDN Web Site
But I have coming across the error: 403 forbidden
Can someone Help me Put this working ?

I was facing the same issue and tried the answer suggested by Vadim Gremyachev. However, it still kept giving 403 error. I added two extra headers to force form based authentication like below:
client.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f");
client.Headers.Add("User-Agent: Other");
After this it started working. So the full code goes like below:
const string username = "username#tenant.onmicrosoft.com";
const string password = "password";
const string url = "https://tenant.sharepoint.com/";
var securedPassword = new SecureString();
foreach (var c in password.ToCharArray()) securedPassword.AppendChar(c);
var credentials = new SharePointOnlineCredentials(username, securedPassword);
DownloadFile(url,credentials,"/Shared Documents/Report.xslx");
private static void DownloadFile(string webUrl, ICredentials credentials, string fileRelativeUrl)
{
using(var client = new WebClient())
{
client.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f");
client.Headers.Add("User-Agent: Other");
client.Credentials = credentials;
client.DownloadFile(webUrl, fileRelativeUrl);
}
}

This error occurs since the request is not authenticated. In order to access resource in Office/SharePoint Online you could utilize SharePointOnlineCredentials class from SharePoint Server 2013 Client Components SDK (user credentials flow).
The following example demonstrates how to download a file from SPO:
const string username = "username#tenant.onmicrosoft.com";
const string password = "password";
const string url = "https://tenant.sharepoint.com/";
var securedPassword = new SecureString();
foreach (var c in password.ToCharArray()) securedPassword.AppendChar(c);
var credentials = new SharePointOnlineCredentials(username, securedPassword);
DownloadFile(url,credentials,"/Shared Documents/Report.xslx");
private static void DownloadFile(string webUrl, ICredentials credentials, string fileRelativeUrl)
{
using(var client = new WebClient())
{
client.Credentials = credentials;
client.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f");
client.DownloadFile(webUrl, fileRelativeUrl);
}
}

Related

C# Application to upload file to SharePoint with MFA

I am creating a Windows Form Application to insert data into MSSQL but also upload a file of user's choosing to SharePoint.
I tried to use the below code, however I have some serious problem due to Multi-Factor Authentication (MFA) not being lifted for my service account. IT is very firm on this matter.
string SiteUrl = "https://company.sharepoint.com/sites/mySite";
string DocumentLibrary = "Documents";
string FileName = #chkAttach1.Text.ToString();
string CustomerFolder = "Application Test";
string Username = "testuser";
string Password = "123";
foreach (char c in Password)
{ securePassword.AppendChar(c); }
var olCred = new SharePointOnlineCredentials(UserName, securePassword);
using (ClientContext cContext = new ClientContext(SiteUrl))
{
cContext.Credentials = olCred;
Web web = cContext.Web;
FileCreationInformation newFile = new FileCreationInformation();
byte[] FileContent = System.IO.File.ReadAllBytes(FileName);
newFile.ContentStream = new System.IO.MemoryStream(FileContent);
newFile.Url = System.IO.Path.GetFileName(FileName);
Microsoft.SharePoint.Client.List docLib = web.Lists.GetByTitle(DocumentLibrary);
Microsoft.SharePoint.Client.Folder uplFold = docLib.RootFolder.Folders.Add(CustomerFolder);
uplFold.Update();
Microsoft.SharePoint.Client.File uplFile = uplFold.Files.Add(newFile);
cContext.Load(docLib);
cContext.Load(uplFile);
cContext.ExecuteQuery();
}
So obviously the above is not working.
Speaking to a fellow from IT, he advised me to use API, but I have difficulties in finding a sample code online to upload a file to SharePoint using the user's current credentials.
Any advice?

How can i download an excel file from sharepoint server?

I have a project (c# console application), in which I want to automatically download an excel file, via URL, with login credentials.
I have been using a webclient to download the file automatically, and all I receive is an html page as response, informing me to login into the site (I have run it in Chrome.)
private static string url = "[the whole url link to the file, deleted for privacy]";
public void test()
{
const string username = "[mail]";
const string password = "[password]";
var securedPassword = new SecureString();
foreach (var c in password.ToCharArray())
{
securedPassword.AppendChar(c);
}
var credentials = new SharePointOnlineCredentials(username, securedPassword);
DownloadFile(url, credentials, #"C:\Documents\ExcelFilesSinc\test.xlsx");
}
private static void DownloadFile(string webUrl, ICredentials credentials, string fileRelativeUrl)
{
using (var client = new WebClient())
{
client.Credentials = credentials;
string _UserAgent = "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.2; .NET CLR 1.0.3705;)";
client.Headers.Add(HttpRequestHeader.UserAgent, _UserAgent);
client.DownloadFile(webUrl, fileRelativeUrl);
}
}
In this way, the file is generated, but the whole content saved in it is an HTML page that requires me to login to Microsoft. Any suggestions?
You can try to add headers for base auth like
client.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f");
client.Headers.Add("User-Agent: Other");
client.Credentials = credentials;
see also here:
Download File From SharePoint 365

Download a file from sharepoint

I am trying to download a file from sharepoint, I have this code and throw error code 500.
static void DownloadFile(){
string serverFilePath = "Here goes my URL, that open the file from any tab";
var password = new SecureString();
foreach (char c in Configuration.password) {
password.AppendChar(c);
}
// theese are the credentials and work fine because I tested in another method
var o365credentials = new SharePointOnlineCredentials(Configuration.userName, password);
var url = string.Format("{0}/{1}", Configuration.siteUrl, serverFilePath);
// My destination folder
string destPath = #"C:\publisher";
var request = System.Net.HttpWebRequest.Create(url);
request.Credentials = o365credentials;
using (var sReader = new StreamReader(request.GetResponse().GetResponseStream())) {
using (var sWriter = new StreamWriter(destPath)) {
sWriter.Write(sReader.ReadToEnd());
}
}
}
you can achieve this task using WebRequest in order to download files from sharepoint site:
public void DownloadFile(string serverFilePath, string destPath)
{
var url = string.Format("{0}/{1}", ServerURL, serverFilePath);
Directory.CreateDirectory(Path.GetDirectoryName(destPath)); // this method creates your directory
var request = System.Net.HttpWebRequest.Create(url);
request.Credentials = System.Net.CredentialCache.DefaultCredentials;
using (var sReader = new StreamReader(request.GetResponse().GetResponseStream()))
{
using (var sWriter = new StreamWriter(destPath))
{
sWriter.Write(sReader.ReadToEnd());
}
}
}
if you wish to use the Client-object-model you read that:
How to get a file using SharePoint Client Object Model with only an absolute url at hand?
Edit: fixed the spelling of CreateDirectory call

How to upload a file to a document library in sharepoint?

I have a byte[] data and I want to upload it to sharepoint site using c#. I also want to pass credentials for it. Can anyone please guide me.
The code I tried is:
Uri destUri = new Uri("http://test.net/excel/docs/Forms/AllItems.aspx/");
WebRequest req = WebRequest.Create(destUri);
req.Method = "PUT";
req.Credentials = CredentialCache.DefaultCredentials;
using (req.GetRequestStream())
{
string destFilename = #"\\test.net\excel\docs\501.xls";
byte[] data = new byte[10];
System.IO.File.WriteAllBytes(destFilename, data);
}
ERROR:
Access Denied
Current user should have add permissions on this library
public void UploadFileToDocmentLibrary(Byte[] contentArray)
{
using (SPSite sharePointtopLevelSite = new SPSite("http://localhost"))
{
SPWeb websiteCollection = sharePointtopLevelSite.AllWebs["webName"];
websiteCollection.AllowUnsafeUpdates = true;
websiteCollection.Lists.IncludeRootFolder = true;
SPList docLibrary = websiteCollection.Lists["listName"];
SPFile file = websiteCollection.Files.Add(websiteCollection.Url.ToString() + "/" + docLibrary.Title.ToString() + "/" + "fileName.ext", contentArray);
file.Update();
}
}
If user without permissions should do it, use RunWithElevatedPrivileges statement
If I understood your requirements properly, you need to upload file into SharePoint On-Premise, right? There are several options on how to accomplish it.
Send file via HTTP POST using .NET
At least the following components could be utilized for that purpose:
HttpWebRequest
WebClient
HttpClient
Example
The example demonstrates how to upload file using WebClient.UploadFile Method:
public static void UploadFile(Uri targeUri, ICredentials credentials, string fileName)
{
using (var client = new WebClient())
{
client.Credentials = credentials;
//client.Headers.Add("X-FORMS_BASED_AUTH_ACCEPTED", "f");
var targetFileUri = targeUri + "/" + Path.GetFileName(fileName);
client.UploadFile(targetFileUri, "PUT", fileName);
}
}
Usage
var filePath = #"C:\Documents\SharePoint User Guide.docx";
var credentials = new NetworkCredential(userName, password, domain);
UploadFile(new Uri("https://contoso.sharepoint.com/documents"),credentials, filePath);
Using Microsoft SharePoint Server Object Model
using (var site = new SPSite(url))
{
using (var web = site.OpenWeb())
{
var list = web.Lists.TryGetList(listTitle);
var targetFolder = list.RootFolder;
var fileContent = System.IO.File.ReadAllBytes(fileName);
var fileUrl = Path.GetFileName(fileName);
targetFolder.Files.Add(fileUrl, fileContent);
}
}
Using Microsoft SharePoint Client Object Model
SharePoint 2010 Client Components SDK
SharePoint 2013 Client Components SDK
How to upload a file to a SharePoint site using File.SaveBinaryDirect Method
using (var ctx = new ClientContext(url))
{
ctx.Credentials = new NetworkCredential(userName, password, domain);
using (var fs = new FileStream(fileName, FileMode.Open))
{
var fi = new FileInfo(fileName);
var list = ctx.Web.Lists.GetByTitle(listTitle);
ctx.Load(list.RootFolder);
ctx.ExecuteQuery();
var fileUrl = String.Format("{0}/{1}", list.RootFolder.ServerRelativeUrl, fi.Name);
Microsoft.SharePoint.Client.File.SaveBinaryDirect(ctx, fileUrl, fs, true);
}
}
Using SharePoint Web Services
How to upload file using Copy Web Service:
var webUri = new Uri("http://contoso.sharepoint.com");
string sourceUrl = #"C:\Documents\SharePoint User Guide.docx";
string destinationUrl = webUri + "/documents/SharePoint User Guide 2013.docx";
var fieldInfo = new FieldInformation();
FieldInformation[] fieldInfos = { fieldInfo };
CopyResult[] result;
using (var proxyCopy = new Copy())
{
proxyCopy.Url = webUri + "/_vti_bin/Copy.asmx";
proxyCopy.Credentials= new NetworkCredential(userName, password, domain);
var fileContent = System.IO.File.ReadAllBytes(sourceUrl);
proxyCopy.CopyIntoItems(sourceUrl, new[] { destinationUrl }, fieldInfos, fileContent, out result);
}

Get location of client machine using ip address

I am trying to get the location of client machine using ip address. Client can access the internet only if
he/she provide the proxy authenication.
Let us say client need to access the 'www.google.com' on the browser then immediately Authenication Required
prompt window open and then client enter his/her username and password. But it is possible the few users does
not required the provide the authenication in order to access internet.
This segment of code does not helped me...
string url = "http://freegeoip.net/xml/";
WebClient wc = new WebClient();
WebProxy proxyObj = new WebProxy("http://freegeoip.net/xml/");
proxyObj.Credentials = CredentialCache.DefaultCredentials;
Uri uri = new Uri(url);
MemoryStream ms = new MemoryStream(wc.DownloadData(uri));
XmlTextReader rdr = new XmlTextReader(url);
XmlDocument doc = new XmlDocument();
ms.Position = 0;
doc.Load(ms);
ms.Dispose();
In the above code if i add network credential instance with username, password and domain then it's work perfectly
Instead of providing the default net credential in code itself, I need to get the username and password from the users(client
machine).
My question is how to prompt the Authentication Required Window and get the username and password to load the download from url
I would be glad if someone throw light on this issue...
Edit: Somehow basic authentication window prompt and now i can get the username and password which can use for credential
try
{
var reg = HttpContext.Current.Request;
if (!String.IsNullOrEmpty(reg.Headers["Authorization"]))
{
var cred = System.Text.ASCIIEncoding.ASCII.GetString(Convert.FromBase64String(Request.Headers["Authorization"].Substring(6))).Split(':');
var user = new { Name = cred[0], Pass = cred[1] };
string url = "http://freegeoip.net/xml/";
WebClient wc = new WebClient();
WebProxy wProxy = new WebProxy();
ICredentials crd;
crd = new NetworkCredential("'" + cred[0] + "'", "'" + cred[1] + "'");
wProxy = new WebProxy("myproxy", true, null, crd);
wc.Proxy = wProxy;
Uri uri = new Uri(url);
string content = wc.DownloadString(uri);
}
else
{
try
{
//var reg = HttpContext.Current.Request;
if (String.IsNullOrEmpty(reg.Headers["Authorization"]))
{
var res = HttpContext.Current.Response;
res.StatusCode = 401;
res.AddHeader("WWW-Authenticate", "Basic realm = \"freegeoip\"");
//res.End();
}
}
catch (Exception ex)
{
}
}
}
catch(Exception ex)
{
}
But Still It throwing the "Unable to connect to the remote server"

Categories