Create Your First RDLC (Local SSRS) Report in ASP.NET using DataSet C#

Following steps demonstrate how to create your first RDLC Report. This blog is divided into 2 parts:-

  1. Prepare the report from a single table and to solve the Report Viewer Configuration Error, if encountered.
  2. Prepare a single report from two different tables (Not-Related).

The database used here is Microsoft’s Northwind database.

Prepare a Report from a Single Table

# Add DataSet.

# Add DataTable
# Add Columns
# Add RDLC Report
# Choose DataSet
# Choose Fields 
# Choose Layout
# Choose Style
# Finish the Wizard. The report will be then displayed
# Add ReportViewer to the ASP.NET page
# Following is the designer code snippet after adding the ReportViewer control
<%@ Register Assembly="Microsoft.ReportViewer.WebForms, Version=10.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" Namespace="Microsoft.Reporting.WebForms" TagPrefix="rsweb" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
	<head runat="server">
		<title></title>
	</head>
	<body>

<form id="form1" runat="server">
			<asp:ScriptManager ID="ScriptManager1" runat="server">
			</asp:ScriptManager>
			<rsweb:ReportViewer ID="ReportViewer1" runat="server" Width="600">
			</rsweb:ReportViewer>
		</form>

	</body>
</html>
# Modifying the Code Behind section
using System.Data;
using System.Configuration;
using System.Data.SqlClient;
using Microsoft.Reporting.WebForms;

protected void Page_Load(object sender, EventArgs e)
{
    if (!IsPostBack)
    {
        ReportViewer1.ProcessingMode = ProcessingMode.Local;
        ReportViewer1.LocalReport.ReportPath = Server.MapPath("~/Report.rdlc");
        Customers dsCustomers = GetData("select top 20 * from customers");
        ReportDataSource datasource = new ReportDataSource("Customers", dsCustomers.Tables[0]);
        ReportViewer1.LocalReport.DataSources.Clear();
        ReportViewer1.LocalReport.DataSources.Add(datasource);
    }
}

private Customers GetData(string query)
{
    string conString = ConfigurationManager.ConnectionStrings["NorthWindConnectionString"]
                                              .ConnectionString;
    SqlCommand cmd = new SqlCommand(query);
    using (SqlConnection con = new SqlConnection(conString))
    {
        using (SqlDataAdapter sda = new SqlDataAdapter())
        {
            cmd.Connection = con;
            sda.SelectCommand = cmd;
            using (Customers dsCustomers = new Customers())
            {
                sda.Fill(dsCustomers, "DataTable1");
                return dsCustomers;
            }
        }
    }
}

# Next Compile the code. There’s a chance that you might encounter the following error

and then when you click Continue, you’ll be finally redirected to your page which will be displaying the following error message.

The error is pretty straight-forward. Just as the message suggests add the following code to the Web.Config file

<system.webServer>
	<validation validateIntegratedModeConfiguration="false" />
	<handlers>
		<add name="ReportViewerWebControlHandler" preCondition="integratedMode" verb="*" path="Reserved.ReportViewerWebControl.axd" type="Microsoft.Reporting.WebForms.HttpHandler, Microsoft.ReportViewer.WebForms, Version=11.0.0.0, Culture=neutral, PublicKeyToken=89845dcd8080cc91" />
	</handlers>
</system.webServer>

 

Plz make sure that your PublicKeyToken is same as that of the Microsoft.ReportViewer.WebForms in the assemblies section of system.web.

# Next again run the code. You’ll be able to see the following result

You can see that field, Country, has appeared twice. This is because of the fact that I had done a GroupBy this field.

That’s it from this blog. Next as a continuation of it, I’ll be demonstrating how to display multiple tables(2) in a single report. You can find the link of that blog very shortly.
Thanks…

Stop/Prevent Browser from Caching the current Page

protected void StopPageCaching()
{
    HttpContext.Current.Response.Cache.SetExpires(DateTime.UtcNow.AddDays(-1));
    HttpContext.Current.Response.Cache.SetValidUntilExpires(false);
    HttpContext.Current.Response.Cache.SetRevalidation(HttpCacheRevalidation.AllCaches);
    HttpContext.Current.Response.Cache.SetCacheability(HttpCacheability.NoCache);
    HttpContext.Current.Response.Cache.SetNoStore();
}

Existing Tomcat server on port 80 gives error: BAD REQUEST after installing/starting IIS on another Port

This is an issue which has caused a lot of trouble to me. My understanding was that I can run Apache & IIS on the same server provided, they are occupying different ports. Though this statement is true, but you should make sure that Apache should be installed on any other port except 80 if you intended to run both Tomcat & IIS on the same server.

The problem is that though your .NET website will run on the port assigned to it, the HTTP service, which is used by the IIS to listen any incoming request, runs on port 80. Now this service blocks the Apache Tomcat server (if it’s also running on port 80)

As of now the only way that crosses my mind to run both the servers on the same machine is not to assign Tomcat server to port 80. Use any other port except 80.

*********************************************************************************
Following are the steps taken to set up a ASP.NET site on the IIS where TOMCAT has occupied the port 80. In case it hampers the existing TOMCAT server then look at the 2nd segment of this document.

1. If the HTTP SSL service is present & stopped then, start the HTTP SSL service (if it’s not running)
If you get the error 1068, Filed to Load the Dependency, then it means the HTTP service is down. To restart it type regedit in run. Then traverse to LOCAL_MACHINE/SYSTEM/CurrentControlSet/Services/HTTP. SET Start = 2; Refer: http://support.microsoft.com/kb/103000.
Then restart the server.
Now you will see HTTP SSL & World Wide Web Publishing services are on.

2. Start the World Wide Web Publishing service (if not on)

3. Inside IIS, select Web Service Extensions and allow ASP.NET v4.0 (Considering the sites target framework is 4.0 (for IIS 6.0 only. For IIS 7.0, select the ASP.NET version from the site App Pool.))

*********************************************************************************

If the localhost (TOMCAT) is throwing the BAD Request error for the TOMCAT server running on port 80, then do the following:

1. Stop the IIS site.

2. Stop the World Wide Web Publishing service

3. If you’re still getting the error then,
type regedit in run. Then traverse to LOCAL_MACHINE/SYSTEM/CurrentControlSet/Services/HTTP.
SET Start = 4; Refer: http://support.microsoft.com/kb/103000. Then restart the server.

*********************************************************************************

Set a String as Enum

There are many instances where, in an Enum we need a string literal. However you can only enter a single word (with no space) against an integer (+ve/-ve). That’s where we use the description attribute.
Look at the Enum declaration below:-


public enum States
{
	[System.ComponentModel.Description("New Delhi")]
	NewDelhi = 1,
	[Description("Uttar Pradesh")]
	UttarPradesh = 2
	[Description("West Bengal")]
	WestBengal = -1,
}

Normally this is how we bind the Enum to a DropDownList

DropDownList1.DataSource = Enum.GetNames(typeof(States));
DropDownList1.DataBind();

This is what we’ll get the output for our Enum States

To get the description value of the Enum, we’ll use the following method


public static string GetEnumDescription(Enum value) 
{ 
	System.Reflection.FieldInfo fi = value.GetType().GetField(value.ToString()); 
	if (fi != null) 
	{ 
		System.ComponentModel.DescriptionAttribute[] attributes = 	(System.ComponentModel.DescriptionAttribute[])fi.GetCustomAttributes(typeof(System.ComponentModel.DescriptionAttribute), false); 
		if (attributes != null && attributes.Length > 0) 
			return attributes[0].Description; else return value.ToString();
	}
	return value.ToString(); 
}

This is how we’ll do to bind the Enum description to a DropDownList


foreach (States value in Enum.GetValues(typeof(States)))
{
	DropDownList1.Items.Add(new ListItem(GetEnumDescription(value), value.ToString()));
}
DropDownList1.DataBind();

Final Output:

 

 

Happy Coding …

Search a DataRow from DataTable1 into DataTable2

Tip

The situation is something like this. A GridView is getting populated at the PageLoad event. Now one of the Column of the Grid contains the CheckBox to represent the True/False state for that Row. There are 2 tables in the SQL Database. Now, if a DataRow is present in both the tables then, that Row’s checkbox should be marked in the GridView. The GridView Columns which contains the checkbox is being added at the runtime i.e, that column is not present in the SQL DataTable.
The question is how can I search a single DataRow of a DataTable against all the DataRows of another DataTable. Look at the code below


DataTable dt = null;
DataTable dtParent = null;

dt = GetList(); // Get the selected List
dtParent = GetNameList(); //Get the Entire List

// Mark a Column(s) as Primary, which will be searched for the given value.
dtParent.PrimaryKey = new DataColumn[] { dtParent.Columns["ID"] };
foreach (DataRow dr in dt.Rows)
{
	//If that Row is Present in dtParent then, mark the row's checkbox as checked.
	dtParent.Rows.Find(dr["ID"])["chkCheckBox"] = true; 
}
gvStudentDetails.DataSource = dtParent;
gvStudentDetails.DataBind();

Happy Coding …

Change DropDownList SelectedIndex on Gridview SelectedIndexChanging Event

Tip

Well, here I would like to set the SelectedIndex of a DropDownList based on a Column’s Text Value from the GridView’s SelectedIndexChanging event. I guess, this can be achieved by many ways however, what I am trying to show here is to do the same in just 1 line.


ddlDropDown.SelectedIndex = ddlDropDown.Items.
								IndexOf(ddlDropDown.Items.
									FindByText(((Label)gvGridView.Rows[e.NewSelectedIndex].
										FindControl("lblLabel")).Text));

Happy Coding …

DataTable’s ImportRow & Clone methods [C#]

Discussion

Here, I will demonstrate the functionality of DataTable’s ImportRow & Clone methods and the difference between the Rows.Add & ImportRow.

Clone method will copy the structure of the existing table, only Columns and Schema, not the data. So in the following

DataTable dt = GetSomeVal();
DataTable dt1 = dt.Clone();
dt1 will have exactly the same Column type as of dt. However, dt1.Rows.Count will return 0.As for the other issue look at the following code::


DataTable dt1 = new DataTable();
DataRow dr1 = dt1.NewRow();
DataTable dt2 = new DataTable();

// will throw an error as dr1 already belongs to another datatable
dt2.Rows.Add(dr1); 

// will execute adding a new row to dt2 Table
dt2.ImportRow(dr1);

dt1.Rows.Add(dr1);

The above code is pretty much self-explanatory. If you have to add a DataRow from a different DataTable use ImportRow method otherwise use Rows.Add.

Happy Coding …

Un-Select a Radio-Button by clicking on it

Problem

The situation is kind of odd however, not uncommon, atleast, I would think so. We have got a Radio Button inside each row of a GridView. As per the requirement, user should be able to select only 1 radio button at a time. This has been achieved with javascript. More details can be found here. Now selecting radio button indicates the selection for that row of the gridview. Similarly, there should be an option for dis-selecting the radio button by clicking on the selected radio button (much like the checkboxes). However, this is against the normal behaviour of the radio button, and obviously there was no simple way of doing it. So I decided to put a check on the OnClick property of the Radio Button. The check was like this


if (rdBtn.checked == true {
	rdBtn.checked = false;
}

However, because of this, I was not able to select the Radio Button in the first place. Unlike, checkbox, once checked, a radio button will always return true when it is checked and my script was simply clearing the checked state thereby, not letting me select any option.

Solution

After doing a bit of R&D I realized that instead of making things complicated, I should put a simple check, & instead of relying on the checked property of the radio button I will check the id of the current selected radio button. If the current radio button’s id matches with that of the hiddenField value, I will simply clear the check of that radio button


<script language="javascript" type="text/javascript">
	function SelectSingleRadiobutton(rdbtnid) {
		var hd = document.getElementById('hdnFld');
		var rest = false;
		var rdBtn = document.getElementById(rdbtnid);
		var rdBtnList = document.getElementsByTagName("input");
		for (i = 0; i < rdBtnList.length; i++) {
			if (rdBtnList[i].type == "radio") {
				if (rdBtnList[i].id != rdBtn.id) {
					rdBtnList[i].checked = false;
				}
				else if (hd.value == rdBtnList[i].id) {
					rdBtnList[i].checked = false;
					rest = true;
				}
			}
		}
		hd.value = (rest) ? "" : rdbtnid;
	}
</script>

Inside the GridView’s ItemTemplate I have called the above script for the OnClick event of the Radio Button


<asp:TemplateField>
	<ItemTemplate>
		<asp:RadioButton ID="rdbOptions" runat="server" OnClick="javascript:SelectSingleRadiobutton(this.id)" />
	</ItemTemplate>
	<ItemStyle HorizontalAlign="Center" />
</asp:TemplateField>

That’s it …

Make Single RadioButton Selection in Gridview using Javascript

Problem

Here, I will be adding two columns in a GridView. One will contain a RadioButton, and the other one will have some text. The user however, can select only one RadioButton at a time. Multi-select needs to be disabled. The problem is that each row contains a new RadioButton so the user was able to select all the RadioButtons.

Solution

Solution is only one thing, javascript. On click on one of the radio button, all other radiobuttons should be disabled. The javascript code is as follows:-


<script language="javascript" type="text/javascript">
	function SelectSingleRadiobutton(rdbtnid) {
		var rdBtn = document.getElementById(rdbtnid);
		var rdBtnList = document.getElementsByTagName("input");
		for (i = 0; i < rdBtnList.length; i++) {
			if (rdBtnList[i].type == "radio" && rdBtnList[i].id != rdBtn.id)
			{
				rdBtnList[i].checked = false;
			}
		}
	}
</script>

The definition of Grid is defined below. Note: the javascript call for the radio Button:-


<asp:GridView ID="gvdata" runat="server" CssClass="Gridview" AutoGenerateColumns="false" >
	<Columns>
		<asp:TemplateField>
			<ItemTemplate>
				<asp:RadioButton id="rdbUser" runat="server" OnClick="javascript:SelectSingleRadiobutton(this.id)" />
			</ItemTemplate>
		</asp:TemplateField>
		<asp:BoundField DataField="SomeData" HeaderText="Some Text"/>
	</Columns>
</asp:GridView>

 

Thanks…