Since crystal report is a server control, we need a webpage/usercontrol to display the report. And never put this webform/user control inside views folder in mvc, you will get broken buttons with 404 in CrViewer. You can also use an Iframe in a razor view to display the report. Following is a working model[VS2010], please go through.
Step-1: Setup Crystal Report
1. Create top level folder in website root directory.
2. Put your Crystal report.rpt file in this folder
3. Add a web page (.aspx) to this folder. This page serves as report viewer page. Add a CrystalReportViewer control in this page.
<div align="center" style="width:100%; height:100%;">
<CR:CrystalReportViewer ID="crViewer" runat="server" AutoDataBind="true" />
</div>
Following assembly registration will be added on the top of aspx page.
<%@ Register Assembly="CrystalDecisions.Web, Version=13.0.2000.0, Culture=neutral, PublicKeyToken=692fbea5521e1304" Namespace="CrystalDecisions.Web" TagPrefix="CR" %>
Check the version of CrystalReportViewer. For this, select “choose items” from Toolbox on VS Sidebar. Compare this version with CrystalDecisions.Web version on top of the aspx page. If both are same, leave it, else change the assembly registration version same as of CRViewer.
Go to web.config file under website root folder; check the assemblies starting with ‘CrystalDecisions’ under tag. Change their versions same as of CrystalReportViewer Version (here Version=13.0.2000.0).
Step-2: Set Up Controller, Action & View
1. Add a new action in report controller class.
2. Write necessary steps to load data from database/files.
3. Set the data into Session.
4. Do not add view for this action. Instead use Response.Redirect method.
public class ReportController : Controller
{
public ActionResult reportView(string id)
{
Session["ReportSource"] = GetdataFromDb();
Response.Redirect("~/Reports/WebForm1.aspx");
return View();
}
}
Add page load event to the .aspx page.
protected void Page_Load(object sender, EventArgs e)
{
CrystalDecisions.CrystalReports.Engine.ReportDocument report =
new CrystalDecisions.CrystalReports.Engine.ReportDocument();
report.Load(Server.MapPath("~/Reports/CR_report.rpt"));
report.SetDataSource(Session["ReportSource"]);
crViewer.ReportSource =report;
}
Step-3: Little hack in Global.asax
1. To avoid “Session state has created a session id, but cannot save it because the response was already flushed by the application.” error or a "blank crystal report page output" add following code in Global.asax.
void Session_Start(object sender, EventArgs e)
{
string sessionId = Session.SessionID;
}
Now you can call the reportView() action in ReportController to display the Crystal Report.
Have a nice day!