MVC3 deploy to a directory, url issue - c#

I have a mvc3 web application which will be delopyed to an directory of a website. the address of the application seems like http://wwww.xx.com/aopo/. aopo is the name of the directory. After the deployement I find that the url in js file does not work any more. because I had write the js code with hard code url, just like
$.ajax({url:"/employee/getemployee"})
In that case the request will be sent to http://wwww.xx.com/employee/getemployee instead of http://wwww.xx.com/aopo/employee/getemployee, and 404 is returned.
There is lots of code in js like that. I don't want to modify the js. Is there any simple approach to make it work? Can I rewrite the request in global.asax.cs?

I believe you'll need to change your url references to this:
$.ajax({url:"#Url.Action("getemplotee","employee")"})
If this is a script file you can write the correct URL into an element on the page and read that:
<div id='Main' data-url='#Url.Action("getemplotee","employee")' />
Then in your script:
$.ajax({url:$('#Main').data('url')})
Rgarding:
There is lots of code in js like that. I don't want to modify the js
I understand, but you need to use the proper helper methods to account for running under virtual directories, so I would recommending biting the bullet and just fixing it the right way.

One not so clean solution might be,
Setting a url prefix in the layout(in a common place), like
<script type="text/javascript">
#{
string root = Url.Content("~/");
if (root.EndsWith("/", StringComparison.Ordinal))
{
root = root.Substring(0, root.Length - 1);
}
}
window.URL_PREFIX = '#root';
</script>
then use the prefix in the ajaxSend hook and change the url.
$(document).ajaxSend(function (event, jqxhr, settings) {
if (window.URL_PREFIX && settings.url.indexOf(window.URL_PREFIX)) {
settings.url = window.URL_PREFIX + settings.url;
}
});
note: If $.ajax() or $.ajaxSetup() is called with the global option set to false, the .ajaxSend() method will not fire.
its not an ideal solution, but might be helpful in a tight situation.
hope this helps.

No, that's not possible. Since the request doesn't arrive in your application you can't access it and thus you can't rewrite it.
If you have control over the root site, you could use the IIS rewrite module to rewrite the URL to your website.

Related

Link to html page not working in live server/Blazor Wasm App but is working locally in debug?

I am developing a Blazor WASM application and need to add some external links to e.g. a cookies page which I am putting in a seperate tab using:
<a href="/Legal/Cookies.html" class="b-bar-link" target="_blank">
Cookies
</a>
Obviously with a Web assembly blazor app, most of it is loaded on to the client, but I don't think I have quite got my head around objects that still live on the client vs the server.
Images etc. stay on the server in the wwwroot folder. So I thought I should be able to create a /Legal folder in wwwroot and put the files there. These docs might change often so I figured better there.
So my folders look like most wasm template projects:
When I use the link to get to the cookies page, it works fine in VS under debug, but in the live server is heading to the 'Page not found'.
I am using an Azure AppService, and initially thought that maybe the problem may be due to a publishing/build issue. So I checked and the file properties all have 'copy always' as their
content action. Also, I checked the server published files and they are there.
I realise that the VS debug environment is using a cut down IIS and is different to the main Azure one, so I wondered if it could be permissions related. Suggestions please.?
EDIT
I think this is as someone suggested a routing issue. But does anyone know how to have Blazor Wasm mixed with the occasional file on the server? I mean, the default Identity stuff that MS provides does that very thing, though it is hard to figure out... any pointers to a doc? Thanks.
You should look at this for hosting: https://learn.microsoft.com/en-us/aspnet/core/blazor/host-and-deploy/?view=aspnetcore-7.0&tabs=visual-studio#app-base-path
In many hosting scenarios, the relative URL path to the app is the root of the app. In these default cases, the app's relative URL base path is the following:
Blazor WebAssembly: / configured as <base href="/" />.
Blazor Server: ~/ configured as <base href="~/" />.
In other hosting scenarios, such as GitHub Pages and IIS sub-apps, the app base path must be set to the server's relative URL path of the app.
See the rest of the article for how to adapt to your scenario. In short, you can include your path in launchSettings.json and have different configurations based on your dev/production environments.
Also take a look at the following article for absolute url handling inside your app if required: https://swimburger.net/blog/dotnet/how-to-generate-absolute-urls-in-aspdotnet-core
I am answering my own question here in case anyone else falls into this particular set of traps..
I was guided to some extent by a sort of similar question:
blazor-listing-and-linking-local-html-files-from-blazor-page
It wasn't a routing problem as such, more a mis-understanding on my part of how a Blazor app is structured, and that it can't easily switch in an out of being a Single Page App...
Anyway, I am using Blazorise to help with my UI so I constructed a 'Popup' page to handle this sort of thing, like this:
<Modal #ref="modalRef">
<ModalContent IsCentered="true" Size="ModalSize.ExtraLarge">
<ModalHeader>
<CloseButton Clicked="#HideModal" />
</ModalHeader>
<ModalBody Style="min-height: 50vh">
#htmlContent
</ModalBody>
</ModalContent>
</Modal>
This with the code page to activate the popup and get the data as follows:
[Inject] FileService _fileService { get; set; }
Modal? modalRef = new Modal();
[Parameter]
public string urlPath {get; set;}
private MarkupString htmlContent= new MarkupString();
private async Task GetContent()
{
htmlContent = (MarkupString) await _fileService.GetServerFileString(urlPath);
}
public async Task ShowModal(string? url = null)
{
if (!string.IsNullOrEmpty(url))
{
urlPath = url;
}
await GetContent();
modalRef.Show();
}
public void HideModal()
{
modalRef.Hide();
}
The _fileService function being:
public async Task<string> GetServerFileString(string serverURL)
{
string content = await HttpPublic.GetStringAsync(serverURL);
return content;
}
Then to use it in a page, (I am actually referencing straight from the MainLayout) it is as easy as:
<Button #onclick='() => ShowPopup("/Legal/Privacy.html")'>Privacy</Button>
or
<Button #onclick='() => ShowPopup("/Legal/Cookies.html")'>Cookies</Button>
With the code function being:
protected async void ShowPopup(string url)
{
await htmlPopup.ShowModal(url);
}
I did it that way because I am using the component several times in the same page... Given the Parameter function, you could also do it by just referencing the component and passing the param.
Hope this helps someone else. Cheers

Routing Issue want to display domain name even index.aspx is called

routes.MapPageRoute("Main", "", "~/index.aspx");
thats the route I mapped on index page..
when I call the url with index.aspx it displays like
www.abc.com/index.aspx
but I want it to show
www.abc.com
even when index.aspx is called
Regarding my comment, URL Rewrite is also available in IIS and Asp.net. So you can potentially use it.
Another solution would be to redirect to your route. The route alone doesn't change the URL, it just allows you to access the resource via the defined route.
You can redirect to the route though, which will rewrite the URL on the client
For example like this:
if (Request.Path != "/")
{
Context.Response.RedirectToRoute("Main");
}
This is very simplified and might not work in all scenarios, so please be very careful.

URL routing turning /pages/test.aspx into /test

I made a folder called 'pages' in my asp web forms project. In this folder I have a lot of pages:
test.aspx
hello.aspx
When I open these pages in a browser I get:
www.domain.com/pages/test.aspx
www.domain.com/pages/hello.aspx
This is normal, I know. But what if I want to delete the /pages in the url and just show (without .aspx):
www.domain.com/test*.aspx*
www.domain.com/hello*.aspx*
I can do this by manually adding a new route (in RegisterRoutes() method) for each page but is there a way to do this dynamicly?
I found this question but I don't know if I can use it for this problem.
WebForms custom / dynamic routing
Try something like this, not sure if that will do it. But you could always just put your pages in the root directory. I think this would work.
Source Link: http://msdn.microsoft.com/en-us/library/vstudio/cc668177(v=vs.100).aspx
routes.MapPageRoute("PageRoute","{page}", "~/pages/{page}.aspx");
Not sure if that's what you were looking for, this way you can just do something like:
Response.RedirectToRoute("PageRoute", new { page = "test" });

Redirecting webpage in ASP.NET depending on the URL

I've a domain name called mywebsite.com but I prefer users to access to my website through the www subdomain.
How can I achieve a verification and redirection in asp.net mvc3 easily?
When I was using php I did something like that :
if($_SERVER['SERVER_NAME'] != "www.mywebsite.com")
header('Location: www.mywebsite.com');
I'd like to find a similar way to achieve this kind of redirection in asp.net (C#) (I'd prefer not to set a 301 redirection but just a soft redirection like the one I was using in PHP).
I know I could do a verification in each of my controllers action methods and the redirect the user if he is not on the subdomain www.mywebsite.com but I'd prefer to write once the verification and the redirection and I can't find where :/
Thanks a lot !
You could use:
Request.Url.ToString()
This will return the URL , then you can quickly check if it contains 'www.' and redirect if true. However I would suggest that your handle this in the URL rewrite in IIS.
Follow the guide here: http://www.dotnetexpertguide.com/2011/08/iis-7-redirect-domaincom-to.html this is for making domain.com go to www.domain.com, but it works the same way for the opposite.
you could try something like this
if(!Request.Url.Host.Equals("www.mywebsite.com"))
{
Response.Redirect("website");
}
If you are looking to just add/append header information, then use Response.AppendHeader().
The Request.Url.ToString() property can be checked for the url you are looking for as per Ryan's answer.
Actually, the original question asks specifically for a 'soft' redirection (201 or 202) instead of a Moved Permanently/Found (301/302), so i think that instead of Response.Redirect the conditional line should be:
if(!Request.Url.Host.Equals("www.mywebsite.com"))
{
HttpContext.Current.Response.Headers.Add("Location", "www.mywebsite.com");
}
EDIT: I believe the status may also be set directly, used in conjunction with Response.Redirect:
if(!Request.Url.Host.Equals("www.mywebsite.com"))
{
HttpContext.Current.Response.Redirect("www.mywebsite.com");
HttpContext.Current.Response.Status = "201 Created";
}
If I am not totally missing something here, can't you just setup the host-header in the IIS settings for the site to include both www.domain.com as well as domain.com?

Forcing SSL (https) on a page by page basis

How can I set up my page load event in my code behind to redirect to an url that has an https prefix? I would need it to work with urls that have query strings attached too.
It's one thing to construct a link that goes straight to the https page, but I don't want the user to be able to manually change it to an http page.
Also I don't want to do it with javascript because it might be turned off.
I'm guessing a regular expression?
We mark our SSL Required pages with a special attribute ForceSslAttribute. Then we have a HttpModule that pulls down the current page's class and inspect it's attributes.
If the attribute is present on the page, it takes the exact url that was passed and changes the protocol from http to https then calls a redirect.
There's probably a bit simpler way of doing it, but that's how it's done for us.
Attribute:
[AttributeUsage(AttributeTargets.Class, AllowMultiple=false, Inherited=true)]
public sealed class ForceSslAttribute : Attribute
{
// Marker Attribute
}
Page Example (CodeBehind):
[ForceSsl]
public partial class User_Login : Page
{
//...
}
You can figure out the type of the page like this:
HttpContext.Current.CurrentHandler.GetType()
All Page's implement IHttpHandler and when you're visiting a page, it'll work.
The cool part about this method is you can mark anything that's an IHttpHandler and it'll force the redirect too :)
Add this at the top of your Page_Load
if (Request.ServerVariables["HTTPS"] != "ON")
{
Response.Redirect("https://" + Request["HTTP_HOST"] + Request.RawUrl);
}
I use the following in Global.asax Application_BeginRequest
If needsSSL <> Request.IsSecureConnection Then
If needsSSL Then
Response.Redirect(Uri.UriSchemeHttps + Uri.SchemeDelimiter + Request.Url.Host + Request.Url.PathAndQuery, True)
Else
Response.Redirect(Uri.UriSchemeHttp + Uri.SchemeDelimiter + Request.Url.Host + Request.Url.PathAndQuery, True)
End If
End If
There is an IIS7 module for URL rewriting. Very handy, but you need access to the IIS and it requires some time to learn how to write the rules. A simple http->https rule is a matter of seconds.
Just be careful because any rules you add will be stored in your web.config, so don't delete/override it or you will have to write them again.
Forcing SSL using ASP
To force SSL using ASP, follow these steps:
Click Start, click Run, type Notepad, and then click OK.
Paste the following code into a blank Notepad document. On the File menu, click Save As, and then save the following code in the root of your Web server as an include file named ForceSSL.inc:
<%
If Request.ServerVariables("SERVER_PORT")=80 Then
Dim strSecureURL
strSecureURL = "https://"
strSecureURL = strSecureURL & Request.ServerVariables("SERVER_NAME")
strSecureURL = strSecureURL & Request.ServerVariables("URL")
Response.Redirect strSecureURL
End If
%>
For each page that requires SSL, paste the following code at the top of the page to reference the include file from the previous step:
<%#Language="VBSCRIPT"%>
<!--#include virtual="/ForceSSL.inc"-->
When each page is browsed, the ASP code that is contained in the include file detects the port to determine if HTTP is used. If HTTP is used, the browser will be redirected to the same page by using HTTPS.

Categories

Resources