Passing DateTimeOffset to WebAPI - asp.net-web-api

My WebAPI method looks like this:
[Route("api/v1.0/Profile/Test/{offset}")]
public async Task<ServiceResult> GetTest(DateTimeOffset offset)
{
...
}
Calling it like this works:
http://localhost:54295/api/v1.0/Profile/Test/2016-04-05T13:30:44-11:00
However, this call won't work:
http://localhost:54295/api/v1.0/Profile/Test/2016-04-05T13:30:44+11:00
What's the trick here?
In my Web.config in the system.web section I have this entry:
<httpRuntime targetFramework="4.5" requestPathInvalidCharacters="<,>,%,&,*,\,?" />

I found a solution:
In my web.config in the system.webServer section I added this block:
<security>
<requestFiltering allowDoubleEscaping="true" />
</security>
Now the plus sign works as desired.

Related

rewrite URl from www.m.example.com to m.example.com

I am trying to do a redirect in ASP.NET web.config which contains like www.m.example.com to m.example.com; I have tried different approaches but wasn't able to do it.
Instead of the web.config, you could apply the following to your page:
<script runat="server">
private void Page_Load(object sender, System.EventArgs e)
{
Response.Status = "301 Moved Permanently";
Response.AddHeader("Location","http://www.new-location.com");
}
</script>
Read more here
If you do still want to use the web.config file, you can do the following:
Open web.config in the directory where the old pages reside
Then add code for the old location path and new destination as follows:
<configuration>
<location path="services.htm">
<system.webServer>
<httpRedirect enabled="true" destination="http://domain.com/services" httpResponseStatus="Permanent" />
</system.webServer>
</location>
<location path="products.htm">
<system.webServer>
<httpRedirect enabled="true" destination="http://domain.com/products" httpResponseStatus="Permanent" />
</system.webServer>
</location>
</configuration>

Downloading file with webapi

I'm trying to write an action in a webapi controllers to allow downloading a file.
But for some strange reason, the code doesn't works.
Here is my code:
<RoutePrefix("api/files")>
Public Class PermitFilesController
Inherits ApiController
<Route("download")>
public function GetFile() As HttpResponseMessage
Dim fStream as FileStream = File.Open("C:\Projects\1234.pdf", FileMode.Open, FileAccess.Read )
Dim response = Request.CreateResponse(HttpStatusCode.OK)
response.Content = new StreamContent(fStream)
'response.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment")
'response.Content.Headers.ContentDisposition.FileName = Path.GetFileName(fStream.Name)
response.Content.Headers.ContentType = new MediaTypeHeaderValue("application/pdf")
return response
End Function
I try to download simply using the url in browser:
localhost:<myport>/api/files/download
The error (in Chrome ) is Error code: ERR_CONNECTION_RESET
In FF, it is even stranger: it redirects me to www.localhost.com:/... with the same error - connection reset by host
I put a breakpoint in my code, and I noticed the code gets called twice (as soon as I exit from trace from last line, it gets called again to the first line).
I have several other actions in this controller, and they all work ok.
Anyone having any idea what am I doing wrong?
EDIT
I started Fiddler, and now my browser shown this error:
[Fiddler] ReadResponse() failed: The server did not return a response
for this request. Server returned 0 bytes.
EDIT
I want to mention that webapi is integrated into a legacy classic asp.net application
The initialization code is as follows:
In global.asax.Application_Start
WebApiHelper.Initialize
....
....
Public Class WebApiHelper
Public Shared Sub Initialize()
GlobalConfiguration.Configuration.MessageHandlers.Add(New BasicAuthMessageHandler() With { _
.PrincipalProvider = New MPNAuthProvider() _
})
AreaRegistration.RegisterAllAreas()
WebApiConfig.Register(GlobalConfiguration.Configuration)
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters)
RouteConfig.RegisterRoutes(RouteTable.Routes)
GlobalConfiguration.Configuration.EnsureInitialized()
End Sub
....
MPNAuthProvider is used to ensure authenticated access to some webapi controllers
Public Class MPNAuthProvider
Implements IProviderPrincipal
Public Function CreatePrincipal(username As String, password As String) As IPrincipal Implements IProviderPrincipal.CreatePrincipal
Dim userID As Integer = 0
If Not UserData.ValidateUser(username, password, userID) Then Return Nothing
Dim identity = New GenericIdentity(userID)
Dim principal = New GenericPrincipal(identity, {"User"})
Return principal
End Function
End Class
Anything else I should check to see what happens?
Thank you
Initial Solution
After suggestion from Julien Jacobs, I tested my code into a separate, stand alone webapi project, and indeed the code proved to be correct.
So I started to investigate the web.config.
And I found the following settings that I had to comment out:
<system.web>
....
<httpModules>
<add name="RadUploadModule" type="Telerik.Web.UI.RadUploadHttpModule" />
<add name="RadCompression" type="Telerik.Web.UI.RadCompression" />
</httpModules>
and
<modules runAllManagedModulesForAllRequests="true">
<remove name="RadUploadModule" />
<remove name="RadCompression" />
<add name="RadUploadModule" type="Telerik.Web.UI.RadUploadHttpModule" preCondition="integratedMode" />
<add name="RadCompression" type="Telerik.Web.UI.RadCompression" preCondition="integratedMode" />
</modules>
After I commented them, the code started to work ok.
But this proved to not be the ideal solution, so please read on...
Updated solution
After more tests with the application, I realized that RadCompression, while not absolutely required, is very useful to web applications with Telerik Ajax, because it provides transparent, on the fly compression for all ajax traffic (plus viewstate, is configured).
Because I disabled it, the application started to be slower.
So I had to find a way to re-enable RadCompression, but disable it for certain requests (like webapi endpoint for files download).
And the solution is:
Add special config section for RadCompression configuration
<configSections>
<sectionGroup name="telerik.web.ui">
<section name="radCompression" type="Telerik.Web.UI.RadCompressionConfigurationSection, Telerik.Web.UI, PublicKeyToken=121fae78165ba3d4" allowDefinition="MachineToApplication" requirePermission="false"/>
</sectionGroup>
....
</configSections>
Add handlers in system.web\httpModules
<system.web>
....
<httpModules>
<add name="RadCompression" type="Telerik.Web.UI.RadCompression" />
</httpModules>
Add handlers in system.webServer\modules
<system.webServer>
<modules runAllManagedModulesForAllRequests="false">
<add name="RadCompression" type="Telerik.Web.UI.RadCompression" preCondition="managedHandler" />
</modules>
</system.webServer>
And the critical part, to disable RadCompression for specific requests (URIs), add a new config section as below
<telerik.web.ui>
<radCompression enablePostbackCompression="true">
<excludeHandlers>
<!--This will match every api/permitfiles/download file regardless of its location in the web site--> <add handlerPath="api/permitfiles/download" matchExact="false"/>
</excludeHandlers>
</radCompression>
</telerik.web.ui>
With those changes, RadCompression is empowered globally in the app for all requests, but restricted for specific requests (like webapi files download)

add <clear /> and <remove name=something /> tag to collections in applicationHost.config or web.config using Powershell webadministration module

as per title, can someone help?
just an example:
<system.ftpServer>
<security>
<ipSecurity>
<add ipAddress="1.2.3.4" subnetMask="255.255.255.0" />
</ipSecurity>
</security>
</system.ftpServer>
I would like to add a tag as the first element to stop the elements delegated from its parent.
and a after as well.
So it will look like this:
<system.ftpServer>
<security>
<ipSecurity>
<clear />
<remove ipAddress="1.1.1.1" />
<add ipAddress="1.2.3.4" subnetMask="255.255.255.0" />
</ipSecurity>
</security>
</system.ftpServer>
Without resorting to xml manipulation, the following answer may help you get started with this problem:
Add a 'clear' element to WebDAV authoringRules using powershell
This approach might not be recommended but if you want to do it using xml then here is how you can do it.
$filepath = "C:\scripts\so\webdavconfig.xml"
$xml = [xml](get-Content -Path $filepath)
$elem = $xml.CreateElement("clear");
$elem2 = $xml.CreateElement("remove");
$attr = $xml.CreateAttribute("ipAddress");
$attr.Value="1.1.1.1";
$elem2.Attributes.Append($attr);
$xmlnode = $xml."system.ftpserver".security.ipSecurity
$xmlnode.AppendChild($elem);
$xmlnode.AppendChild($elem2);
$xml.Save($filepath);
$xml."system.ftpserver".security.ipSecurity

FormsAuthentication.SetAuthCookie problem

In my MVC 3 application I have a very basic controller
[HttpPost]
public ActionResult SignIn(LogonModel logonModel)
{
string logonMessage;
if(_authenticationService.Login(logonModel.UserName, logonModel.Password,
out logonMessage))
{
FormsAuthentication.SetAuthCookie(logonModel.UserName,true);
return RedirectToAction("Index", "Home");
}
return View();
}
I see the cookie getting set in the browser however when I close the browser and come back to the site, it is not logging me in automatically. It is almost like the cookie is not being processed, which it should be.
The first and most obvious question is: are cookies enabled in your browser?
What you could check as well is, whether in your web.config, you have configured the <authentication> section to have a timeout:
<authentication mode="Forms">
<forms loginUrl="~/login" timeout="60" />
</authentication>
if you don't specify a timeout it'll use the default value of 30 minutes, but maybe you set it to some other (invalid) value?
timeout attribute:
Specifies the time, in integer minutes, after which the cookie expires.
You could also check the CookiesSupported property (boolean) to see that that returns.
Be sure to remove the following <modules> tag from the web.config if using MVC 5+
<system.webServer>
<modules>
<remove name="FormsAuthentication" />
</modules>
</system.webServer>
I had a situation where the domain was wrong in the authenticaion section:
<authentication mode="Forms">
<forms name="yourAuthCookie" loginUrl="/user/login" protection="All" path="/" enableCrossAppRedirects="true" timeout="90" domain="WRONGDOMAIN.COM" />
</authentication>
Removing the domain did the trick:
<authentication mode="Forms">
<forms name="yourAuthCookie" loginUrl="/user/login" protection="All" path="/" enableCrossAppRedirects="true" timeout="90" />
</authentication>

asp.net mvc 3 and elmah.axd - yet another 404

Hi all I know that this has been posted as a prior question several times, but I've gone through each question and their proposed solutions and I'm still not able to surmount my 404 issue. I'm running Elmah 1.1 32-bit. I've referred to ASP.NET MVC - Elmah not working and returning 404 page for elmah.axd but I haven't had any luck after applying the suggestions.
I'm running ASP.NET MVC 3. Here's my web.config:
...
<httpHandlers>
<add verb="POST,GET,HEAD" path="elmah.axd" type="Elmah.ErrorLogPageFactory, Elmah" />
</httpHandlers>
<httpModules>
<add name="ErrorLog" type="Elmah.ErrorLogModule, Elmah"/>
<add name="ErrorMail" type="Elmah.ErrorMailModule, Elmah" />
<add name="ErrorFilter" type="Elmah.ErrorFilterModule, Elmah" />
</httpModules>
...
<errorLog type="Elmah.SqlErrorLog, Elmah"
connectionStringName="dbconn" />
<errorFilter>
<test>
<jscript>
<expression>
<![CDATA[
// #assembly mscorlib
// #assembly System.Web, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a
// #import System.IO
// #import System.Web
HttpStatusCode == 404
|| BaseException instanceof FileNotFoundException
|| BaseException instanceof HttpRequestValidationException
/* Using RegExp below (see http://msdn.microsoft.com/en-us/library/h6e2eb7w.aspx) */
|| Context.Request.UserAgent.match(/crawler/i)
|| Context.Request.ServerVariables['REMOTE_ADDR'] == '127.0.0.1' // IPv4 only
]]>
</expression>
</jscript>
</test>
</errorFilter>
I have my .axd routes ignored using:
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
I'm running the site on IIS7, 32 bit mode enabled. I've tried many different configuration options but all to no avail. Any ideas?
Thanks
Shan
My bad. My .axd ignore route rule was ordered after the default route mapping. The default route mapping rule was matching the URL elmah.axd. I guess I didn't realize that the ignore rules had to be listed above this route. Thanks everyone for your help!
routes.MapRoute(
"Default", // Route name
"{controller}/{action}/{id}", // URL with parameters
new
{
controller = "Home",
action = "Index",
id = UrlParameter.Optional
} // Parameter defaults
);
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
Simply moving routes.IgnoreRoute("{resource}.axd/{*pathInfo}"); before the Default route mapping resolved this issue.
Copy the .dll to your bin and reference... add the elmah defaults to configSections
Don't put the handler inside the system.webServer as mentioned above, try system.web section like this instead in your web.config.
<system.web>
<httpHandlers>
<add verb="POST,GET,HEAD" path="elmah.axd" type="Elmah.ErrorLogPageFactory, Elmah" />
</httpHandlers>
</system.web>
just leave your global.asax as default:
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
browse to the axd locally
then if working, lock it down with the config section Gedas mentioned above.
Have you tried this?
<configuration>
<system.webServer>
<handlers>
<add name="elmah" verb="POST,GET,HEAD" path="elmah.axd" type="Elmah.ErrorLogPageFactory, Elmah" />
</handlers>
</system.webServer>
</configuration>
also make sure to secure elmah.axd location from regular users:
<location path="elmah.axd">
<system.web>
<authorization>
<allow roles="Admin" />
<deny users="*" />
</authorization>
</system.web>
</location>
I was getting a 404 error due to the SQLServer Compact database being over the default max file size. Just deleted the SDF data file and 404 went away.
In asp.net mvc 3 global.asax.cs file
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
//filters.Add(new HandleErrorAttribute());
}
HandleErrorAttribute will swallow all exceptions, leaving nothing for ELMAH to handle.
See Joe's blog http://joel.net/wordpress/index.php/2011/02/logging-errors-with-elmah-in-asp-net-mvc3-part1/

Resources