Query String from the URL - c#

I have an application URL that can be launched from browser with query string passed in.
My Development URL is
http://localhost:15094/MyPage.html?user=username&role=admin
Client URL will be path to MyPage.html in the hard Drive
file:///C:/Program%20Files/Client/MyPage.html?user=username&role=admin
When the url is localhost with http, i can extract the query string using
System.Windows.Browser.HtmlPage.Document.DocumentUri.Query
// this gives me ?user=username&role=admin
// from http://localhost:15094/MyPage.html?user=username&role=admin
But I want ?user=username&role=admin when client use the URL
file:///C:/Program%20Files/Client/MyPage.html?user=username&role=admin
System.Windows.Browser.HtmlPage.Document.DocumentUri.Query does not work with it I suppose.
Please note Development URL is with http and when the application is installed on a Client's machine, the url will be without http, this is how application should work. Please do not suggest to host it in IIS etc.
My Question is very simple:
How would you extract the query string from "file:///C:/Program%20Files/Client/MyPage.html?user=username&role=admin" ?
If System.Windows.Browser.HtmlPage.Document.DocumentUri.Query works fine for url's without http, why I am not getting query string right?

A simple way to do this without being clever is to use IndexOf eg:
var originalUrl = "file:///C:/Program%20Files/Client/MyPage.html?user=username&role=admin";
var extractedQueryString = string.Empty;
if(originalUrl.IndexOf("?") != -1)
{
extractedQueryString = originalUrl.Substring(originalUrl.IndexOf("?"));
}
Wrote this off the top of my head without compiling but think I got it right.
Also to get the filename part of the string if you're wondering would be:
var extractedFileName = originalUrl.Substring(0, originalUrl.IndexOf("?"));

Related

Retrieving everything after ? in a query string

I am actually an HW and FW engineer and very new to web programming.
In a recent product we embedded wi-fi connectivity and our products(clients) send get requests to a server using the format below and it is unfortunately fixed.
IP Number:Port Number/default.aspx?XX-XX-XX-XX-XX-XXY*Z*
XX-XX-XX-XX-XX-XX is the MAC address of the product
Y is an integer which may vary between 1 to 99999
Z is the opcode which may again vary from A to Z
We want to get everything after the ? sign to determine from which terminal this request is coming from and which action we shall take in the database.
Since we are using IIS webserver we think an asp page fits better to such a requirement.
What method would you request to retrieve all the string after the ? sign using C#.
You can parse the Urls using the Uri class
var queryPart = new Uri("your url here").Query;
Try Request.Url.Query if you want the raw query string as a string.
I usually use Request.Url.ToString() to get the full URL (including query string), no concatenation required.

How to maintain the right URL in C#/ASP.NET?

I am given a code and on one of its pages which shows a "search result" after showing different items, it allows user to click on one of records and it is expected to bring up a page so that specific selected record can be modified.
However, when it is trying to bring up the page I get (by IE) "This page cannot be displayed".
It is obvious the URL is wrong because first I see something http://www.Something.org/Search.aspx then it turns into http://localhost:61123/ProductPage.aspx
I did search in the code and found the following line which I think it is the cause. Now, question I have to ask:
What should I do to avoid using a static URL and make it dynamic so it always would be pointing to the right domain?
string url = string.Format("http://localhost:61123/ProductPage.aspx?BC={0}&From={1}", barCode, "Search");
Response.Redirect(url);
Thanks.
Use HttpContext.Current.Request.Url in your controller to see the URL. Url contains many things including Host which is what you're looking for.
By the way, if you're using the latest .Net 4.6+ you can create the string like so:
string url = $"{HttpContext.Current.Request.Url.Host}/ProductPage.aspx?BC={barCode}&From={"Search"}";
Or you can use string.Format
string host = HttpContext.Current.Request.Url.Host;
string url = string.Format("{0}/ProductPage.aspx?BC={1}&From={2}"), host, barCode, "Search";
You can store the Host segment in your AppSettings section of your Web.Config file (per config / environment like so)
Debug / Development Web.Config
Production / Release Web.Config (with config override to replace the localhost value with something.org host)
and then use it in your code like so.
// Creates a URI using the HostUrlSegment set in the current web.config
Uri hostUri = new Uri(ConfigurationManager.AppSettings.Get("HostUrlSegment"));
// does something like Path.Combine(..) to construct a proper Url with the hostName
// and the other url segments. The $ is a new C# construct to do string interpolation
// (makes for readable code)
Uri fullUri = new Uri(hostUri, $"ProductPage.aspx?BC={barCode}&From=Search");
// fullUrl.AbosoluteUri will contain the proper Url
Response.Redirect(fullUri.AbsoluteUri);
The Uri class has a lot of useful properties and methods to give you Relative Url, AbsoluteUrl, your Url Fragments, Host name etc etc.
This should do it.
string url = string.Format("ProductPage.aspx?BC={0}&From={1}", barCode, "Search");
Response.Redirect(url);
If you are using .Net 4.6+ you can also use this string interpolation version
string url = $"ProductPage.aspx?BC={barcode}&From=Search";
Response.Redirect(url);
You should just be able to omit the hostname to stay on the current domain.

Programmatically retrieve the site URL from inside an Azure website

Azure websites have a default "site URL" provided by Azure, something like mysite.azurewebsites.net. Is it possible to get this URL from inside the website itself (i.e. from the ASP.NET application)?
There are several properties in the Environment and HttpRuntime class that contain the name of the website (e.g. "mysite") so that is easily accessible. Things are getting complicated when not the default but e.g. the staging slot of the site is accessed (that has the site URL like mysite-staging.azurewebsites.net).
So I was just wondering whether there is a straightforward way of getting this site URL directly. If not, then using one of the mentioned classes to get the site name and then somehow detecting the site slot (that could e.g. be set through a configuration value from the Azure portal) would be the solution
Edit (2/4/16): You can get the URL from the appSetting/EnvironmentVariable websiteUrl. This will also give you the custom hostname if you have one setup.
There are few of ways you can do that.
1. From the HOSTNAME header
This is valid only if the request is hitting the site using <SiteName>.azurewebsites.net. Then you can just look at the HOSTNAME header for the <SiteName>.azurewebsites.net
var hostName = Request.Headers["HOSTNAME"].ToString()
2. From the WEBSITE_SITE_NAME Environment Variable
This just gives you the <SiteName> part so you will have to append the .azurewebsites.net part
var hostName = string.Format("http://{0}.azurewebsites.net", Environment.ExpandEnvironmentVariables("%WEBSITE_SITE_NAME%"));
3. From bindingInformation in applicationHost.config using MWA
you can use the code here to read the IIS config file applicationHost.config
and then read the bindingInformation property on your site. Your function might look a bit different, something like this
private static string GetBindings()
{
// Get the Site name
string siteName = System.Web.Hosting.HostingEnvironment.SiteName;
// Get the sites section from the AppPool.config
Microsoft.Web.Administration.ConfigurationSection sitesSection =
Microsoft.Web.Administration.WebConfigurationManager.GetSection(null, null,
"system.applicationHost/sites");
foreach (Microsoft.Web.Administration.ConfigurationElement site in sitesSection.GetCollection())
{
// Find the right Site
if (String.Equals((string) site["name"], siteName, StringComparison.OrdinalIgnoreCase))
{
// For each binding see if they are http based and return the port and protocol
foreach (Microsoft.Web.Administration.ConfigurationElement binding in site.GetCollection("bindings")
)
{
var bindingInfo = (string) binding["bindingInformation"];
if (bindingInfo.IndexOf(".azurewebsites.net", StringComparison.InvariantCultureIgnoreCase) > -1)
{
return bindingInfo.Split(':')[2];
}
}
}
}
return null;
}
Personally, I would use number 2
Also, you can use Environment.GetEnvironmentVariable("WEBSITE_HOSTNAME").
This will return full URL ("http://{your-site-name}.azurewebsites.net"), no string manipulations required.
To see a full list of properties available in environment variables just type Get-ChildItem Env: in SCM PowerShell debug console.

How to get website name from domain name?

I fetch the domain from the URL as follows:
var uri = new Uri("Http://www.google.com");
var host = uri.Host;
//host ="www.google.com"
But I want only google.com in Host,
host = "google.com"
Given the accepted answer I guess the issue was not knowing how to manipulate strings rather than how to deal with uris... but for anyone else who ends up here:
The Uri class does not have this property so you will have to parse it yourself.
Presumably you do not know what the subdomain is before time so a simple replace may not be possible.
This is not trivial since the TLDs are so varied (http://en.wikipedia.org/wiki/List_of_Internet_top-level_domains), and there maybe be multiple parts to the url (eg http://pre.subdomain.domain.co.uk).
You will have to decide exactly what you want to get and how complex you want the solution to be.
simple - do a string replace, see ekad's answer
medium - regex that works most of the time, see Strip protocol and subdomain from a URL
or complex - refer to a list of suffixes in order to figure out what is subdomain and what is domain eg
Get the subdomain from a URL
If host begins with "www.", you can replace "www." with an empty string using String.Replace Method like this:
var uri = new Uri("Http://www.google.com");
var host = uri.Host.ToLower();
if (host.StartsWith("www."))
{
host = host.Replace("www.", "");
}

Creating a correct absolute URL when running ASP.NET MVC application under Visual Studio Windows Azure Emulator

I need to create an absolute URL to specific files in my ASP.NET MVC 4 application. I am currently doing this by generating a relative path via Url.Content and then using the following extension method to create the absolute path.
public static string Absolute(this UrlHelper url, string relativeUrl)
{
var request = url.RequestContext.HttpContext.Request;
return string.Format("{0}://{1}{2}{3}",
(request.IsSecureConnection) ? "https" : "http",
request.Url.Host,
(request.Url.Port == 80) ? "" : ":" + request.Url.Port,
VirtualPathUtility.ToAbsolute(relativeUrl));
}
When running under the Azure Emulator, the proper URL that I need to create is http://127.0.0.1/myfile.jpg but when this code executes, the port number comes back as 81 so the URL that is generated is http://127:0.0.1:81/myfile.jpg. However, if I go to http://127:0.0.1:81/myfile.jpg it of course doesn't work as the Azure Emulator is listening on port 80, not 81.
I assume this has to do with the built in Azure Emulator/IIS Express load balancer, but I am not sure what change I need to make to my Url.Absolute method to return an accurate URL.
You can rely on the Host header that is being sent by the client:
public static string Absolute(this UrlHelper url, string relativeUrl)
{
var request = url.RequestContext.HttpContext.Request;
return string.Format("{0}://{1}{2}",
(request.IsSecureConnection) ? "https" : "http",
request.Headers["Host"],
VirtualPathUtility.ToAbsolute(relativeUrl));
}
Why not just use #Url.Content("~/myfile.jpg");? This converts a virtual (relative) path to an application absolute path and works finle in IIS,the emulator and when deployed. See UrlHelper.Content Method
I've written a summary post that shows all the options here: http://benjii.me/2015/05/get-the-absolute-uri-from-asp-net-mvc-content-or-action/
The quick and simple answer is this:
var urlBuilder =
new System.UriBuilder(Request.Url.AbsoluteUri)
{
Path = Url.Content("~/path/to/anything"),
Query = null,
};
string url = urlBuilder.ToString();

Categories