This is my current function below. Its used to create a folder in a document library in SharePoint but using web dav functionality, which is easier than MOSS stuff.
I need to find a way to determine reliably if the folder already exists... Notice now I am relying on that try catch, but this means that ANY protocol exception will not throw an error, so its not a reliable function. How can I check using web dav if a folder exists?
private void createFolderUsingWebDav(string siteAddress, string listAddress, string folderName)
{
//Check Databox Folder Exists
string folderAddress = siteAddress + #"/" + listAddress + #"/" + folderName;
HttpWebResponse response;
try
{
HttpWebRequest request = (System.Net.HttpWebRequest)HttpWebRequest.Create(folderAddress);
request.Credentials = wsLists.Credentials; // CredentialCache.DefaultCredentials;
request.Method = "MKCOL";
response = (System.Net.HttpWebResponse)request.GetResponse();
response.Close();
}
catch (WebException ex)
{
if (ex.Status != WebExceptionStatus.ProtocolError)
{
throw ex;
}
}
}
Essentially I want the unwrapped version of what this product achieves here:
http://www.independentsoft.de/webdav/tutorial/exists.html
If you do a PROPFIND on the url, you will get a 404 back if the folder does not exist.
Make the PROPFIND look something like this (only showing the relevant headers)
PROPFIND /yourfolder HTTP/1.1
Content-Type: application/xml
<?xml version="1.0"?>
<propfind xmlns="DAV:">
<prop>
<resourcetype />
</prop>
</propfind>
404 means the resource doesn't exist, 207 means it does.
PROPFIND is your friend: the DAV:resourcetype property (http://greenbytes.de/tech/webdav/rfc4918.html#rfc.section.15.9) has a DAV:collection child element for collections. Just retrieve it using PROPFIND with DAV:allprop or DAV:prop (both described in http://greenbytes.de/tech/webdav/rfc4918.html#rfc.section.9).
Related
I don't want to display the 404 message to the user, I want the message to be displayed in the normal page instead.
public ActionResult Download(string fileName, string filePath){
try{
filePath = (filePath != null && filePath != "") ? Cryptography.DecryptAESFromBase64(filePath) : filePath;
if (!filePath.Contains(fileName))
{
var fs = System.IO.File.OpenRead(Server.MapPath(filePath + "_" + fileName));
return File(fs, "application/octet-stream", fileName);
}
else
{
byte[] data;
this._documentService.DownloadAmazonObject(filePath, out data);
return File(data, "application/octet-stream", fileName);
}
}
catch{
throw new HttpException("Couldn't find ", ex);
}
}
This is the code that I have, I keep having the throw new HttpException display in the yellow page.
This answer depends a lot on your whole setup. Whats happening is basically the following: The browser sends a request to your HTTP server. It might be part of your program itself or an application server which in turn hands the request over to your application after transforming the HTTP request into objects and a function call. This is called binding or deserialization.
The application works with the objects (strings in your case) and throws an Exception which the application server in turn transforms into a Response with the HttpStatus 404.
Depending on your setup you have to tell your web server resp. application server how to handle erroneous status codes by explicitly defining an error page.
The dirty alternative would be to catch the exception and return the message as part of a valid response. But that basically bypasses the way errors are handled in HTTP so I would very much discourage it.
Hope this helps a bit :-)
I have a function that is coded to get the Content-Type of a web file.
Here is the function:
public string GetContentTypeOfUri(string uri)
{
try
{
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(uri);
request.Method = "HEAD";
using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
{
var contentType = response.Headers["Content-Type"];
return (contentType);
}
}
catch (Exception ex)
{
return "error";
}
}
Rather than writing a whole different function to detect if a web file exists, how can I calculate if a file exists from the same code as used to get the Content-Type?
If I use a uri of a file that does not exist, an exception occurs. The ex.HResult equals -2146233079 when this exception occurs, with a message = "The remote name could not be resolved: '[address name]'".
Is it safe to say that when an exception occurs, and the ex.HResult equals -2146233079, the file does not exist?
Is there an easier/better way to work this out?
Thanks in advance
EDIT
Here is the HttpClient code that I have:
public async Task<string> GetContentTypeAsync(string uri)
{
using (var httpClient = new HttpClient())
{
var request = new HttpRequestMessage(HttpMethod.Post, uri);
request.Method = new HttpMethod("HEAD");
var response = await httpClient.SendAsync(request);
string contentType = response.Content.Headers.ContentType.ToString();
return contentType;
}
}
Your example web address does inform me that the address does not exist, however, if I have a web address that does not exist such as http://www.usa.canon.com/app/html/HDV/HG10/images/hg10_sample_image_03.jpg5, I am getting a StatusCode of OK, as a Text content type is returned as a custom error page.
There are two possible "not exists" scenarios. It sounds like you've identified one of them - when the server name in the URL is incorrect and so the request cannot even be sent.
But you're not accounting for the other error - that you can reach a remote server but it denies all knowledge of a specific file. For that scenario, you ought to be checking for status 404 on the response.
For cleaner handling of your current scenario (server doesn't exist) you could use the Uri class to extract the Host name from the uri string and perform a manual DNS lookup - which would allow you to code for this likely scenario without having to catch exceptions - which is generally frowned upon when its an expected scenario.
I am working with an api that also returns a valid xml string containing the error that was encountered on their system.
<?xml version="1.0" encoding="UTF-8"?>
<error>
<request>Request made to server</request>
<message>No user found for account 12345</message>
</error>
Is there any way to get that xml from the remote server out of the System.Net.WebException object?
Thanks in advance :)
Direct from the MSDN docs:
When WebException is thrown by a descendant of the WebRequest class,
the Response property provides the Internet response to the
application.
So if you are if you are getting the exception while reading the response, you should just be able to read the Response property to get the XML contents.
Sure ya can! Just need to throw a try-catch around your request.GetResponse(), catch a WebException and read from the exceptions Response property.
WebRequest request = WebRequest.Create("http://www.google.com/ohnoa404");
WebResponse response;
try
{
response = request.GetResponse();
}
catch (WebException ex)
{
response = ex.Response;
}
String responseString = String.Empty;
using (StreamReader reader = new StreamReader(response.GetResponseStream()))
{
responseString = reader.ReadToEnd();
}
I have files that I want to delete. Connection can be from file sharing, http, and ftp.
Example of files to delete:
//mytest//delete//filename.bin
ftp://mytest/delete/filename.bin
http://mytest/delete/filename.bin
Here's what I did:
Uri target = new Uri(#"ftp://mytest/delete/filename.bin");
FileInfo fi = new FileInfo(target.AbsoluteUri);
fi.Delete();
The error I get is:
The given paths format is not supported
Is there a single code that can delete in all these file types?
I have created a simple code for this task(based on thread response).
This is the input:
Uri target = new Uri(#"ftp://tabletijam/FileServer/upload.bin");
Uri target = new Uri(#"http://tabletijam/FileServer/upload.bin");
Uri target = new Uri(#"\\tabletijam\FileServer\upload.bin");
This is the code:
bool DeleteFileOnServer(Uri serverUri)
{
if (serverUri.Scheme == Uri.UriSchemeFtp)
{
FtpWebRequest request = (FtpWebRequest)WebRequest.Create(serverUri);
request.Method = WebRequestMethods.Ftp.DeleteFile;
FtpWebResponse response = (FtpWebResponse)request.GetResponse();
lblStatus.Content = response.StatusDescription;
response.Close();
return true;
}
else if (serverUri.Scheme == Uri.UriSchemeFile)
{
System.IO.File.Delete(serverUri.LocalPath);
return true;
}
else if (serverUri.Scheme == Uri.UriSchemeHttp || serverUri.Scheme == Uri.UriSchemeHttps)
{
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(serverUri);
request.Method = WebRequestMethods.Http.DeleteFile;
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
lblStatus.Content = response.StatusDescription;
response.Close();
return true;
}
else
{
lblStatus.Content = "Unknown uri scheme.";
return false;
}
}
Ftp and File deleted successfully. WebRequestMethods.Http does not contain DeleteFile.
So my question is, how do I delete file from this URI?
http://tabletijam/FileServer/upload.bin
Because FileInfo only works with local files. For each connection you will need a special implementation.
For FTP: (example from MSDN)
public static bool DeleteFileOnServer(Uri serverUri)
{
// The serverUri parameter should use the ftp:// scheme.
// It contains the name of the server file that is to be deleted.
// Example: ftp://contoso.com/someFile.txt.
//
if (serverUri.Scheme != Uri.UriSchemeFtp)
{
return false;
}
// Get the object used to communicate with the server.
FtpWebRequest request = (FtpWebRequest)WebRequest.Create(serverUri);
request.Method = WebRequestMethods.Ftp.DeleteFile;
FtpWebResponse response = (FtpWebResponse) request.GetResponse();
Console.WriteLine("Delete status: {0}",response.StatusDescription);
response.Close();
return true;
}
Using the \\server... notation, you can delete file (that you have access) to on remote servers.
Using FTP, you should the FtpWebRequest.
For HTTP, you could issue a DELETE request, using HttpWebRequest.
For both FTP and HTTP, you might need to supply a username and password. Also normally HTTP servers are not configured to delete files when receiving a DELETE request by default.
For a whole lot of reasons, no, there is not a single unified way you can delete files via each of these protocols.
You could abstract this away into some implementation of your own, however, using an implementation specific to each of the protocols you want to support...
how do i delete file from this uri?
request.Method = "DELETE";
Also, there's a different header supported by WebDAV for controlling the delete...
No, this is not possible. FTP and HTTP are protocols that you are required to stick to. Even though you may be able to delete files when viewing FTP folders in the Explorer doesn't mean it works from C#, too, because the Explorer uses an integrated FTP client. Deleting files via HTTP like that isn't possible at all.
I am developing a tool for validation of links in url entered. suppose i have entered a url
(e.g http://www-review-k6.thinkcentral.com/content/hsp/science/hspscience/na/gr3/se_9780153722271_/content/nlsg3_006.html
) in textbox1 and i want to check whether the contents of all the links exists on remote server or not. finally i want a log file for the broken links.
You can use HttpWebRequest.
Note four things
1) The webRequest will throw exception if the link doesn't exist
2) You may like to disable auto redirect
3) You may also like to check if it's a valid url. If not, it will throw UriFormatException.
UPDATED
4) Per Paige suggested , Use "Head" in request.Method so that it won't download the whole remote file
static bool UrlExists(string url)
{
try
{
HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(url);
request.Method = "HEAD";
request.AllowAutoRedirect = false;
request.GetResponse();
}
catch (UriFormatException)
{
// Invalid Url
return false;
}
catch (WebException ex)
{
// Valid Url but not exists
HttpWebResponse webResponse = (HttpWebResponse)ex.Response;
if (webResponse.StatusCode == HttpStatusCode.NotFound)
{
return false;
}
}
return true;
}
Use the HttpWebResponse class:
HttpWebRequest webRequest = (HttpWebRequest)WebRequest.Create("http://www.gooogle.com/");
HttpWebResponse response = (HttpWebResponse)webRequest.GetResponse();
if (response.StatusCode == HttpStatusCode.NotFound)
{
// do something
}
bool LinkExist(string link)
{
HttpWebRequest webRequest = (HttpWebRequest) webRequest.Create(link);
HttpWebResponse webResponse = (HttpWebResponse)webRequest.GetResponse();
return !(webResponse.StatusCode != HttpStatusCode.NotFound);
}
Use an HTTP HEAD request as explained in this article: http://www.eggheadcafe.com/tutorials/aspnet/2c13cafc-be1c-4dd8-9129-f82f59991517/the-lowly-http-head-reque.aspx
Make a HTTP request to the URL and see if you get a 404 response. If so then it does not exist.
Do you need a code example?
If your goal is robust validation of page source, consider usign a tool that is already written, like the W3C Link Checker. It can be run as a command-line program that handles finding links, pictures, css, etc and checking them for validity. It can also recursively check an entire web-site.