I am using the following code to create a folder inside my document library. The event get triggered and executed till the last line of my code without any issues. However the folder is not getting created or listed in my document library.
public override void ItemAdded(SPItemEventProperties properties)
{
base.ItemAdded(properties);
string strDashListRoot = "http://win-hmpjltdbh5q:37642";
using (SPSite site = new SPSite(strDashListRoot))
{
using (SPWeb web = site.OpenWeb())
{
web.AllowUnsafeUpdates = true;
SPList spl = web.Lists["client_documents"];
spl.Items.Add("", SPFileSystemObjectType.Folder, "Helllworld");
spl.Update();
web.AllowUnsafeUpdates = false;
}
}
}
You need
var i = spl.Items.Add("", SPFileSystemObjectType.Folder, "Helllworld");
i.Update();
instead of
spl.Items.Add("", SPFileSystemObjectType.Folder, "Helllworld");
spl.Update();
(assuming your Add call is fine - it looks OK to me)
(Also, are you sure you need the AllowUnsafeUpdates handling? I wouldn't have expected it to be necessary when you're in an ItemAdded handler.)
I developed the following code based on Rawling's answer:
private static void CreateFolder(SPWeb web, SPList spList, SPListItem currentItem, string folderName)
{
if (currentItem.FileSystemObjectType != SPFileSystemObjectType.Folder)
{
string itemUrl = web.Url + "/" + currentItem.Url.Substring(0, currentItem.Url.LastIndexOf('/'));
var folder = spList.Items.Add(itemUrl, SPFileSystemObjectType.Folder, folderName);
string folderUrl = itemUrl + "/" + folder.Name;
if (!FolderExists(folderUrl, web))
{
try
{
folder.Update();
}
catch (Exception)
{
throw;
}
}
}
}
public static bool FolderExists(string url, SPWeb web)
{
if (url.Equals(string.Empty))
{
return false;
}
try
{
return web.GetFolder(url).Exists;
}
catch (ArgumentException)
{
throw;
}
catch (Exception)
{
throw;
}
}
Related
I'm trying to create a folder under my Inbox in Office 365 using MS Graph 2.0, but I'm finding surprisingly little information on the topic anywhere on the internet. The authentication works fine, and I was able to read the existing test folder. My method for doing this is below:
private void SetupMailBoxes()
{
SmartLog.EnterMethod("SetupMailBoxes()");
MailFolder inbox = null;
try
{
bool dbErrorFolder = false;
bool exchangeErrorFolder = false;
inbox = _journalMailbox.MailFolders.Inbox.Request().GetAsync().GetAwaiter().GetResult();
if (inbox.ChildFolderCount > 0)
{
inbox.ChildFolders = _journalMailbox.MailFolders.Inbox.ChildFolders.Request().GetAsync().GetAwaiter().GetResult();
}
if (inbox.ChildFolders != null)
{
for (int i = 0; i < inbox.ChildFolders.Count && (!dbErrorFolder || !exchangeErrorFolder); i++)
{
if (inbox.ChildFolders[i].DisplayName.ToLower() == "db-error-items")
{
dbErrorFolder = true;
}
else if (inbox.ChildFolders[i].DisplayName.ToLower() == "exchange-error-items")
{
exchangeErrorFolder = true;
}
}
}
if (!dbErrorFolder)
{
try
{
//inbox.ODataType = "post";
var folder = _journalMailbox.MailFolders.Inbox.Request().CreateAsync(
new MailFolder()
{
DisplayName = "DB-Error_Items",
}).GetAwaiter().GetResult();
//inbox.ChildFolders.Add(folder);
}
catch (Exception ex)
{
throw;
}
}
}
catch (Exception exp)
{
SmartLog.LeaveMethod("SetupMailBoxes()");
throw;
}
finally
{
}
SmartLog.LeaveMethod("SetupMailBoxes()");
}
Where _clientSecretCredential is created like this:
_graphServiceClient = null;
_options = new TokenCredentialOptions { AuthorityHost = AzureAuthorityHosts.AzurePublicCloud };
_clientSecretCredential = new ClientSecretCredential(
this.FindString(config.TenentID)
, this.FindString(config.AppID)
, this.FindString(config.Secret)
, _options);
string[] apiScope = new string[] { this.FindString(config.Scope) };
_token = _clientSecretCredential.GetToken(new Azure.Core.TokenRequestContext(apiScope));
graphServiceClient = new GraphServiceClient(_clientSecretCredential, apiScope);
IUserRequestBuilder _journalMailbox = _graphServiceClient.Users["journal#mycompany.com"];
The code seems correct, but everytime I execute "_journalMailbox.MailFolders.Inbox.Request().CreateAsync", I get the following error:
Code: ErrorInvalidRequest
Message: The OData request is not supported.
ClientRequestId:Some Guid.
From what I could figure out by searching on the internet, it has to do with the method using the wrong method to access the API. I mean like, its using "GET" in stead of "POST" or something like that, but that would mean its a bug in the MS code, and that would an unimaginably big oversight on Microsoft's part, so I can't think its that.
I've tried searching documentation on how to create subfolders, but of the preciously few results I'm getting, almost none has C# code samples, and of those, all are of the previous version of Microsoft Graph.
I'm really stumped here, I'm amazed at how hard it is to find any documentation to do something that is supposed to be simple and straight forward.
Ok, so it turned out that I was blind again. Here is the correct code for what I was trying to do:
private void SetupMailBoxes()
{
SmartLog.EnterMethod("SetupMailBoxes()");
MailFolder inbox = null;
try
{
bool dbErrorFolder = false;
bool exchangeErrorFolder = false;
inbox = _journalMailbox.MailFolders.Inbox.Request().GetAsync().GetAwaiter().GetResult();
if (inbox.ChildFolderCount > 0)
{
inbox.ChildFolders = _journalMailbox.MailFolders.Inbox.ChildFolders.Request().GetAsync().GetAwaiter().GetResult();
}
if (inbox.ChildFolders != null)
{
for (int i = 0; i < inbox.ChildFolders.Count && (!dbErrorFolder || !exchangeErrorFolder); i++)
{
if (inbox.ChildFolders[i].DisplayName.ToLower() == "db-error-items")
{
dbErrorFolder = true;
}
else if (inbox.ChildFolders[i].DisplayName.ToLower() == "exchange-error-items")
{
exchangeErrorFolder = true;
}
}
}
else
{
inbox.ChildFolders = new MailFolderChildFoldersCollectionPage();
}
if (!dbErrorFolder)
{
try
{
var folder = new MailFolder()
{
DisplayName = "DB-Error-Items",
IsHidden = false,
ParentFolderId = inbox.Id
};
folder = _journalMailbox.MailFolders[inbox.Id].ChildFolders.Request().AddAsync(folder).GetAwaiter().GetResult();
inbox.ChildFolders.Add(folder);
}
catch (Exception ex)
{
throw;
}
}
}
catch (Exception exp)
{
SmartLog.LeaveMethod("SetupMailBoxes()");
throw;
}
finally
{
}
SmartLog.LeaveMethod("SetupMailBoxes()");
}
I'm now getting a file from specific drive on SharePoint,but the customer asked to search for the file without specifying a drive.
public static byte[] SharePointDownload(string token, string fileName, string sharepointTargetLibrary)
{
string baseSiteId = GetSiteId(token);
string folderId;
if (string.IsNullOrEmpty(baseSiteId))
{
return null;
}
else
{
folderId = GetFolderId(token, baseSiteId, sharepointTargetLibrary);
if (string.IsNullOrEmpty(folderId))
{
return null;
}
}
try
{
WebClient wc = new WebClient();
byte[] result;
wc.Headers[HttpRequestHeader.Authorization] = "Bearer " + token;
wc.Headers[HttpRequestHeader.Accept] = "application/json";
result = wc.DownloadData(string.Format(#"https://graph.microsoft.com/v1.0/sites/{0}/drives/{1}/root:/{2}:/content", baseSiteId, folderId, fileName));
wc.Dispose();
if (result.Length>0)
{
return result;
}
else
{
return null;
}
}
catch (Exception ex)
{
LoggerHelper.Log(ex.Message);
return null;
}
}
now i want to know if this line
result=wc.DownloadData(string.Format(#"https://graph.microsoft.com/v1.0/sites/{0}/drives/{1}/root:/{2}:/content", baseSiteId, folderId, fileName));
can get rid of folderId and searches with the fileName only specified
Using Microsoft Graph, you search a drive
GET /sites/{site-id}/drive/root/search(q='{search-text}')
I'am posting an image from a console application to a asp.net web api. I'am getting a file in the folder but the image is black (no image). Do I have something wrong in my code?
public class UploadController : ApiController
{
[System.Web.Mvc.HttpPost]
public string Upload()
{
var request = HttpContext.Current.Request;
var filePath = Path.Combine(HttpContext.Current.Server.MapPath("~/Uploads/"), request.Headers["filename"]);
try
{
using (var fs = new System.IO.FileStream(filePath, System.IO.FileMode.Create))
{
request.InputStream.CopyTo(fs);
}
}
catch (Exception e)
{
return e.Message;
}
return "uploaded";
}
}
Edit
My console app
http://pastebin.com/VsnDMYpb
try this. This works for me. I used this for multiple file upload
var httpRequest = HttpContext.Current.Request;
foreach (string file in httpRequest.Files)
{
var postedFile = httpRequest.Files[file];
var filePath = HttpContext.Current.Server.MapPath("~/Uploads/" + postedFile.FileName);
postedFile.SaveAs(filePath);
}
Use Request.Content.ReadAsMultipartAsync
public Task<IQueryable<HDFile>> Post()
{
try
{
var uploadFolderPath = HostingEnvironment.MapPath("~/App_Data/" + UploadFolder);
log.Debug(uploadFolderPath);
if (Request.Content.IsMimeMultipartContent())
{
var streamProvider = new WithExtensionMultipartFormDataStreamProvider(uploadFolderPath);
var task = Request.Content.ReadAsMultipartAsync(streamProvider).ContinueWith<IQueryable<HDFile>>(t =>
{
if (t.IsFaulted || t.IsCanceled)
{
throw new HttpResponseException(HttpStatusCode.InternalServerError);
}
var fileInfo = streamProvider.FileData.Select(i =>
{
var info = new FileInfo(i.LocalFileName);
return new HDFile(info.Name, Request.RequestUri.AbsoluteUri + "?filename=" + info.Name, (info.Length / 1024).ToString());
});
return fileInfo.AsQueryable();
});
return task;
}
else
{
throw new HttpResponseException(Request.CreateResponse(HttpStatusCode.NotAcceptable, "This request is not properly formatted"));
}
}
catch (Exception ex)
{
log.Error(ex);
throw new HttpResponseException(Request.CreateResponse(HttpStatusCode.BadRequest, ex.Message));
}
}
The code I get from this post
I am building a standard odata client using: Microsoft.Data.Services.Client.Portable Windows 8 VS2013
I have added a service reference to the project (TMALiveData) with authorisation. Now I want to retrieve data but when I do I get the following error: DataServiceQueryException.InvalidOperationException
I looked at the DataServiceQueryResult object the status code is: System.Net.HttpStatusCode.Unauthorized
When I added the reference it asked me for my credentials, so I assumed this would be sent with each query, but it clearly isn't. How do I add the credentials (password and username) in the DataServiceQuery object? Below is my current code:
public class testLSCon
{
static string mResult;
public static string result { get { return mResult; } }
public static void testREADLiveConnection()
{
Uri tmaLiveDataRoot = new Uri("https://xxx.azurewebsites.net/xxx.svc/");
TMLiveData.TMALiveData mLiveData = new TMLiveData.TMALiveData(tmaLiveDataRoot);
mResult = null;
DataServiceQuery<TMLiveData.JobType> query = (DataServiceQuery<TMLiveData.JobType>)mLiveData.JobTypes.Where(c => c.IsActive == true);
mResult = "Trying to READ the data";
try
{
query.BeginExecute(OnQueryComplete, query);
}
catch (Exception ex)
{
mResult = "Error on beginExecute: " + ex.Message;
}
}
private static void OnQueryComplete(IAsyncResult result)
{
DataServiceQuery<TMLiveData.JobType> query = (DataServiceQuery<TMLiveData.JobType>) result.AsyncState;
mResult = "Done!";
try
{
foreach (TMLiveData.JobType jobType in query.EndExecute(result))
{
mResult += jobType.JobType1 + ",";
}
}
catch (DataServiceClientException ex)
{
mResult = "Error looping for items: (DataServiceClientException)" + ex.Message;
}
catch (DataServiceQueryException ex2)
{
mResult = "Error looping for items: (DataServiceQueryException)" ;
}
catch (Exception ex3)
{
mResult = "Error looping for items: (general exception)" + ex3.Message;
}
}
}
You can either set it to the credentials of the current user (so the credentials of the user the client is running as)
mLiveData.Credentials = CredentialCache.DefaultCredentials;
or if you need to impersonate another user you can use this (obviously swap the strings for the details you need - maybe passed in from config.
mLiveData.Credentials = new System.Net.NetworkCredential("UserName", "Password", "Domain");
I need a good example on WCF Streaming File Transfer.
I have found several and tried them but the posts are old and I am wokding on .net 4 and IIS 7 so there are some problems.
Can you gives me a good and up-to-date example on that.
The following answers detail using a few techniques for a posting binary data to a restful service.
Post binary data to a RESTful application
What is a good way to transfer binary data to a HTTP REST API service?
Bad idea to transfer large payload using web services?
The following code is a sample of how you could write a RESTful WCF service and is by no means complete but does give you an indication on where you could start.
Sample Service, note that this is NOT production ready code.
[ServiceContract]
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]
public class FileService
{
private IncomingWebRequestContext m_Request;
private OutgoingWebResponseContext m_Response;
[WebGet(UriTemplate = "{appName}/{id}?action={action}")]
public Stream GetFile(string appName, string id, string action)
{
var repository = new FileRepository();
var response = WebOperationContext.Current.OutgoingResponse;
var result = repository.GetById(int.Parse(id));
if (action != null && action.Equals("download", StringComparison.InvariantCultureIgnoreCase))
{
response.Headers.Add("Content-Disposition", string.Format("attachment; filename={0}", result.Name));
}
response.Headers.Add(HttpResponseHeader.ContentType, result.ContentType);
response.Headers.Add("X-Filename", result.Name);
return result.Content;
}
[WebInvoke(UriTemplate = "{appName}", Method = "POST")]
public void Save(string appName, Stream fileContent)
{
try
{
if (WebOperationContext.Current == null) throw new InvalidOperationException("WebOperationContext is null.");
m_Request = WebOperationContext.Current.IncomingRequest;
m_Response = WebOperationContext.Current.OutgoingResponse;
var file = CreateFileResource(fileContent, appName);
if (!FileIsValid(file)) throw new WebFaultException(HttpStatusCode.BadRequest);
SaveFile(file);
SetStatusAsCreated(file);
}
catch (Exception ex)
{
if (ex.GetType() == typeof(WebFaultException)) throw;
if (ex.GetType().IsGenericType && ex.GetType().GetGenericTypeDefinition() == typeof(WebFaultException<>)) throw;
throw new WebFaultException<string>("An unexpected error occurred.", HttpStatusCode.InternalServerError);
}
}
private FileResource CreateFileResource(Stream fileContent, string appName)
{
var result = new FileResource();
fileContent.CopyTo(result.Content);
result.ApplicationName = appName;
result.Name = m_Request.Headers["X-Filename"];
result.Location = #"C:\SomeFolder\" + result.Name;
result.ContentType = m_Request.Headers[HttpRequestHeader.ContentType] ?? this.GetContentType(result.Name);
result.DateUploaded = DateTime.Now;
return result;
}
private string GetContentType(string filename)
{
// this should be replaced with some form of logic to determine the correct file content type (I.E., use registry, extension, xml file, etc.,)
return "application/octet-stream";
}
private bool FileIsValid(FileResource file)
{
var validator = new FileResourceValidator();
var clientHash = m_Request.Headers[HttpRequestHeader.ContentMd5];
return validator.IsValid(file, clientHash);
}
private void SaveFile(FileResource file)
{
// This will persist the meta data about the file to a database (I.E., size, filename, file location, etc)
new FileRepository().AddFile(file);
}
private void SetStatusAsCreated(FileResource file)
{
var location = new Uri(m_Request.UriTemplateMatch.RequestUri.AbsoluteUri + "/" + file.Id);
m_Response.SetStatusAsCreated(location);
}
}
Sample Client, note that this is NOT production ready code.
// *********************************
// Sample Client
// *********************************
private void UploadButton_Click(object sender, EventArgs e)
{
var uri = "http://dev-fileservice/SampleApplication"
var fullFilename = #"C:\somefile.txt";
var fileContent = File.ReadAllBytes(fullFilename);
using (var webClient = new WebClient())
{
try
{
webClient.Proxy = null;
webClient.Headers.Add(HttpRequestHeader.ContentMd5, this.CalculateFileHash());
webClient.Headers.Add("X-DaysToKeep", DurationNumericUpDown.Value.ToString());
webClient.Headers.Add("X-Filename", Path.GetFileName(fullFilename));
webClient.UploadData(uri, "POST", fileContent);
var fileUri = webClient.ResponseHeaders[HttpResponseHeader.Location];
Console.WriteLine("File can be downloaded at" + fileUri);
}
catch (Exception ex)
{
var exception = ex.Message;
}
}
}
private string CalculateFileHash()
{
var hash = MD5.Create().ComputeHash(File.ReadAllBytes(#"C:\somefile.txt"));
var sb = new StringBuilder();
for (int i = 0; i < hash.Length; i++)
{
sb.Append(hash[i].ToString("x2"));
}
return sb.ToString();
}
private void DownloadFile()
{
var uri = "http://dev-fileservice/SampleApplication/1" // this is the URL returned by the Restful file service
using (var webClient = new WebClient())
{
try
{
webClient.Proxy = null;
var fileContent = webClient.DownloadData(uri);
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
}