asp.net mvc application down - asp.net-mvc

I have a Live website called API Web, build with ASP.NET MVC 4.
This application is to provide a JavaScript files for other websites.
I have 20 websites requesting a JavaScript to it.
But, sometimes this API Web is going down and I have a trouble to make the application live again.
I don't know why this happen, and how can I solve this issue?
EDIT
This is the controller, if the website requesting a path say http://api.example.com/get/js/folderA?js=jquery.js
the application will return a javascript content.
but, the requesting website will load slower. and I think if the API Web had too much request, it will going down (bottleneck issue).
public ActionResult js(string id, string js) {
string fileLocation = Server.MapPath("~/content/" + id + "/js/" + CryptKeys.Decrypt(js) + "");
string contentType = "text/javascript";
var file = System.IO.File.Open(fileLocation, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
var stream = (Stream)(file);
return new FileStreamResult(stream, contentType);
}

There is a chance that you are not closing the filestream opened by System.IO.File.Open class which may be leading to next call to return the same file in throwing an exception. And because the exception is not handled, this may eventually be leading to site being shutting down.
Did you check for error logs in event viewer?
Based on your inputs below, could you try this piece of code? Notice the using block that I have added
public ActionResult js(string id, string js) {
string fileLocation = Server.MapPath("~/content/" + id + "/js/" + CryptKeys.Decrypt(js) + "");
string contentType = "text/javascript";
using(var file = System.IO.File.Open(fileLocation, FileMode.Open, FileAccess.Read, FileShare.ReadWrite))
{
var stream = (Stream)(file);
return new FileStreamResult(stream, contentType);
}
}

Related

Umbraco Async SurfaceController

I am working on a project (ASP.NET MVC 5) where I am using Umbraco 7.4.3. I am trying to implement the google analytics api along with oauth2. I used the sample code available on the google documentation platform. After authorizing with my google account I get a correct refresh token. But the problem is this refresh token is returned in the URL and is not getting passed by my controller to my view which remains empty. I have a feeling that my controller does not wait to execute it's code after the user authorized his or her google account hence the controller is not bothered about the await operator.
Link to the sample code
public class GoogleAnalyticsController : SurfaceController
{
public async Task<ActionResult> Add(CancellationToken cancellationToken)
{
var result = await new AuthorizationCodeMvcApp(this, new AppFlowMetadata()).AuthorizeAsync(cancellationToken);
if (result.Credential != null)
{
var service = new AnalyticsService(new BaseClientService.Initializer
{
HttpClientInitializer = result.Credential,
ApplicationName = "Analytics Dashboard"
});
// YOUR CODE SHOULD BE HERE..
ViewBag.AccessToken = result.Credential.Token.AccessToken;
ViewBag.RefreshToken = result.Credential.Token.RefreshToken;
var list = await service.Management.AccountSummaries.List().ExecuteAsync(cancellationToken);
ViewBag.Username = list.Username;
for (int i = 0; i < list.TotalResults; i++)
{
ViewBag.WebsiteNames += list.Items[i].Name + "(" + list.Items[i].WebProperties[0].WebsiteUrl + ")";
}
return View("~/Views/Configboard.cshtml");
}
else
{
return new RedirectResult(result.RedirectUri);
}
}
PS: I have tried this sample code out in a ASP.NET MVC 5 project without Umbraco installed which works perfectly.
Any one able to push me into the right direction?
For anyone else getting this problem, the solution was actually pretty simple:
I made a custom route for the AuthCallbackController (/authcallback/indexasync) and it all worked. Because Umbraco takes over the default routing this URL was not reachable hence the action of the authcallbackcontroller was not executed.

show the pdf url to authenticated people on the application

I'm trying to opening the URL that has the pdf document in the new tab. If I click on 1000 anchor tags then it will display the url in new tab like http://sivls100.eskom.co.za:8080/finalnewnrs/Document.do?method=dt&fn=1000.pdf. But if any person has this URL in the network can see the pdf file. I would like to show the pdf file to authenticated users.I did some investigation and found that we can achieve this by setting authenticated user in attribute like setAttribute and get Attribute. I did some code and it works as long as session valid. My session timeout is 30 min.It will not work after 30 min.
Code:
public ActionForward dt(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
Object obj = request.getSession().getAttribute("userDetail");
String target = new String(SUCCESS);
if (obj == null) {
target = new String(FAILURE);
} else {
String filename = request.getParameter("fn");
request.setAttribute("filename", "upload/dt/" + filename);
}
return mapping.findForward(target);
}
Thank you for any help or atleast for the better design.

Download PDF file and show directly in browser in MVC Project

I am calling a Web API from MVC project. The Web API is returning PDF file that I want to show directly in the browser after clicking on a button. My problem is when I click on the link, it downloads the pdf file and shows the icon at the left bottom corner side and I have to click on it and to open the PDf in acrobat. How I can make it the way that by clicking the link it open the pdf directly in the browser?
This is my code in MVC project that open the pdf:
[HttpGet]
public FileResult openPdf(string name)
{
byte[] pdfByte = DownloadFile();
return File(pdfByte, "application/pdf", name);
}
internal byte[] DownloadFile()
{
string serverUrl = "http://localhost/GetPdf?Number=3671";
var client = new System.Net.WebClient();
client.Headers.Add("Content-Type", "application/pdf");
return client.DownloadData(serverUrl);
}
This is the method in my Web API that returns pdf:
public HttpResponseMessage GetPdfNameByRemRef(string RemoteRefNumber)
{
var stream = new MemoryStream();
var response = new HttpResponseMessage(HttpStatusCode.OK)
{
Content = new ByteArrayContent(stream.GetBuffer())
};
byte[] fileBytes = System.IO.File.ReadAllBytes(#"C:\Pdf\CreditApplication_08192006_102714AM_et montis.pdf");
response.Content = new ByteArrayContent(fileBytes);
response.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment");
response.Content.Headers.ContentDisposition.FileName = customerInfo.Application_Filename;
response.Content.Headers.ContentType = new MediaTypeHeaderValue("application/pdf");
return response;
}
You can try to add Content-Disposition header with value inline.
Response.AddHeader("Content-Disposition", "inline;filename=fileName.pdf");
However, the behavior can differ on different browsers and on file types you are serving. If Content-Disposition is set to inline the browser will try to open the file within the browser, but it may fail if the file type is unknown (ex. .rar, .zip, .pdf /when pdf reader plugin is missing/, if the browser is old .. etc.).

MvcRazorToPdf save as MemoryStream or Byte[]

I'm using MvcRazorToPdf in a Azure website and create my PDF's and output them in the browser.
Now i'm creating a new function to directly email the PDF as attachment (without output them in the browser).
Does anybody know if it is possible to save the PDF (with MvcRazorToPdf) as a MemoryStream or Byte[]?
I think you can handle this in ResultFilter, I used below code to allow user to download file and prompt for download popup, in this way you can grab all your memory stream and store somewhere to send email afterwords.
public class ActionDownloadAttribute : ActionFilterAttribute
{
public override void OnResultExecuted(ResultExecutedContext filterContext)
{
filterContext.HttpContext.Response.AddHeader("content-disposition", "attachment; filename=" + "Report.pdf");
base.OnResultExecuted(filterContext);
}
}
[ActionDownload]
public ActionResult GeneratePdf()
{
List<Comment> comments = null;
using (var db = new CandidateEntities())
{
comments = db.Comments.ToList();
}
return new PdfActionResult("GeneratePdf", comments);
}
I have implemented something like that. So basically I have not been changing my method to output PDF. What I have done is used restsharp to make request at URL where I get PDF then what you have is in lines of (this is partial code only so you can get idea )
var client = new RestClient(IAPIurl);
var request = new RestRequest(String.Format(IAPIurl_generatePDF, targetID), Method.GET);
RestResponse response = (RestResponse) client.Execute(request);
// Here is your byte array
response.RawBytes
Otherwise you can use my answer from here where I discussed directly returning a file.
Hope this helps!

MVC Action taking a long time to return

I have an MVC Controller with an action
public ActionResult GeneratePDF(string id)
{
FileContentResult filePath = this.File(pdfBuffer, MediaTypeNames.Application.Pdf);
return filePath;
}
And for some reason it is taking over 20 seconds when it hits the return line.
The pdfBuffer is working okay, and when I run it on my VS all is okay, but when I deploy to IIS 6 it runs slow.
Anyone know why?
I was running into a similar issue when trying to export to XLS and PDF, the only thing that seem to improve the response time was sending the response directly from the class that generates the file like:
HttpContext.Current.Response.Clear();
HttpContext.Current.Response.ClearContent();
HttpContext.Current.Response.ClearHeaders();
HttpContext.Current.Response.Buffer = true;
HttpContext.Current.Response.BufferOutput = true;
HttpContext.Current.Response.ContentType = "application/pdf";
HttpContext.Current.Response.AddHeader("Content-Disposition", "attachment;filename=" + file + ".pdf");
HttpContext.Current.Response.BinaryWrite(stream.ToArray());
HttpContext.Current.Response.Flush();
stream.Close();
HttpContext.Current.Response.End();
But if you do this you will get a "not all code paths return a value" from the ActionMethod, to avoid that we just send a:
return new EmptyResult();
This last line will actually never be executed because we end the request directly on the method.

Resources