Exceptions: System.NullReferenceException while trying to create relation between tables in dataSet - c#

using C#, .net framework 4.5, VS 2012
Try to create simple relation between tables in data set, but got System.NullReferenceException, as I can see on MSDN, it's mean occurs when you try to reference an object in your code that does not exist. But, think i create all required objects.
My code below:
//create place for storing all tables from data base
private DataSet myDS = new DataSet("AutoLot");
//command builders for easy way access to tables
private SqlCommandBuilder sqlCInventory;
private SqlCommandBuilder sqlCOrders;
private SqlCommandBuilder sqlCCustomers;
//adapters for each table
private SqlDataAdapter sqlAInventory;
private SqlDataAdapter sqlAOrders;
private SqlDataAdapter sqlACustomers;
//connection string
private string cnStr = string.Empty;
public MainForm()
{
InitializeComponent();
//get connection string from .config file
cnStr =
ConfigurationManager.ConnectionStrings["AutoLotSqlProvider"].ConnectionString;
//create adapters
sqlACustomers = new SqlDataAdapter("Select * From Customers", cnStr);
sqlAInventory = new SqlDataAdapter("Select * From Inventory", cnStr);
sqlAOrders = new SqlDataAdapter("Select * From Orders", cnStr);
//automatic generate commands
sqlCCustomers = new SqlCommandBuilder(sqlACustomers);
sqlCInventory = new SqlCommandBuilder(sqlAInventory);
sqlCOrders = new SqlCommandBuilder(sqlAOrders);
//add table to data Set
sqlAInventory.Fill(myDS);
sqlAOrders.Fill(myDS);
sqlACustomers.Fill(myDS);
//create relationship between tables
BuildTableRelationShip();
//create DataSourse for datGrids on UI
dataGridViewCustomer.DataSource = myDS.Tables["Inventory"];
dataGridViewOrders.DataSource = myDS.Tables["Orders"];
dataGridViewCustomer.DataSource = myDS.Tables["Customers"];
}
and here I got exception
private void BuildTableRelationShip()
{
//create object of relationShips
DataRelation dr = new DataRelation("CustomersOrders", //name of relation
myDS.Tables["Customers"].Columns["CustID"], //main columns
myDS.Tables["Orders"].Columns["OrderID"]); //related columns
myDS.Relations.Add(dr);
//second relation
dr = new DataRelation("InventoryOrder",
myDS.Tables["Inventory"].Columns["CarID"],
myDS.Tables["Orders"].Columns["OrderID"]);
//add relations to dataset
myDS.Relations.Add(dr);
}
Why i got this Null reference Exception? What i miss?
EDIT

You should call fill on individual DataTables rather than the whole DataSet.
sqlAInventory.Fill(myDS);
sqlAOrders.Fill(myDS);
sqlACustomers.Fill(myDS);
would become
sqlAInventory.Fill(myDS, "Inventory");
sqlAOrders.Fill(myDS, "Orders");
sqlACustomers.Fill(myDS, "Customers");
This method will automatically add a table to your DataSet if it doesn't exist, and populates it with data if it does. MSDN has more information on this method of the fill.

Related

How to load the datagridview using OOP C#

I am a beginner at C# and .NET oop concepts. I want to load the datagridview. I don't know how to pass the data. What I tried so far I attached below.
I created a class std
public void get()
{
SqlConnection con = new SqlConnection("server =.; initial catalog=testdb; User ID=sa; Password=123");
string sql = "select * from std";
con.Open();
SqlCommand cm = new SqlCommand(sql, con);
SqlDataReader dr = cm.ExecuteReader();
while ( dr.Read())
{
string stname = dr["st_name"].ToString();
string nicnum = dr["nic"].ToString();
}
con.Close();
}
Form: I am getting data like this way
std ss = new std();
ss.get();
dataGridView1.Rows.Clear();
If I wrote like this way how to pass data into the datagridview columns? I am stuck in this area
It's easier like this:
public void FillGrid()
{
var dt = new DataTable();
var da = new SqlDataAdapter("select * from std", "server =.; initial catalog=testdb; User ID=sa; Password=123");
da.Fill(dt);
dataGridView1.DataSource = dt;
}
but if you're going to use such a low level method of database access you should consider adding a DataSet type of file to your project; visual studio will write all this code and more for you with a few mouse clicks, and it makes a good job of creating tables and adapters that are a lot easier to work with
you have made multiple mistakes. First you read data wirh dataraeader and in every iteration define two stname and nimnum variables like. So when loop ends variables are destroyed. You have to define data table and read data by dataraeader and and add them to it row by row. Or read by sqldataadapter and read it immediately and pass to datatable object.Finnaly you pass datatable as return object of function. Use this vala as datasource of datagridview property if I'm not wrong.

A data source instance has not been supplied for the data source 'DataSet2'-SSRS

This is my First report using SSRS.
I am trying to generate a Report using SSRS in asp.net.
My Need is:
I want to create a report with multiple tables (4 tables) that have relationship with one another. I have configured each individual table with accepting 1 parameter, for instance:
What I tried is:
I have created a dataset.xsd with 4 tables and given the relationship between those tables.
Then I created a report.rdlc and designed a report with four tables and drag and dropped the required field to the table and created a report parameter called ID.
The error i'm Getting is:
A data source instance has not been supplied for the data source 'DataSet2'
What I have written in cs page on button click is:
protected void BtnGo_Click(object sender, EventArgs e)
{
DataSet2TableAdapters.TB_TransReceiptTableAdapter ta = new DataSet2TableAdapters.TB_TransReceiptTableAdapter();
DataSet2.TB_TransReceiptDataTable dt = new DataSet2.TB_TransReceiptDataTable();
ta.Fill(dt,Convert.ToInt16( TxtID.Text));
//ta.Fill(dt,TxtID.Text);
ReportDataSource rds = new ReportDataSource();
rds.Name = "DataSet2";
rds.Value = dt;
ReportParameter rp = new ReportParameter("ID", TxtID.Text.ToString());
rptviewer.LocalReport.DataSources.Clear();
rptviewer.LocalReport.ReportPath = "Report1.rdlc";
rptviewer.LocalReport.SetParameters(new ReportParameter[] { rp });
rptviewer.LocalReport.DataSources.Add(rds);
rptviewer.LocalReport.Refresh();
rptviewer.Visible = true;
}
The help i seek is:
I dont know how to bind the report via code, since I have four tables that are related to one another with foreign key. Above is the code I used but it throws an error.
I would be very thankful if some one could help me to solve this issue.
Thanks in advance.
As per tgolisch instead of table i Bound dataset and passed to report it works fine.
And also instead of four separate table i created a view .It Makes my job simple
private DataTable getData()
{
DataSet dss = new DataSet();
string sql = "";
sql = "SELECT * from VW_TransReciptReport WHERE tREC_NUPKId='" + TxtID.Text + "'";
SqlDataAdapter da = new SqlDataAdapter(sql, con);
da.Fill(dss);
DataTable dt = dss.Tables[0];
return dt;
}
private void runRptViewer()
{
this.rptviewer.Reset();
ReportParameter rp = new ReportParameter("ID", TxtID.Text.ToString());
this.rptviewer.LocalReport.ReportPath = Server.MapPath("ReportReceipt.rdlc");
rptviewer.LocalReport.SetParameters(new ReportParameter[] { rp });
ReportDataSource rdsB = new ReportDataSource("DataSet1_VW_TransReciptReport", getData());
this.rptviewer.LocalReport.DataSources.Clear();
this.rptviewer.LocalReport.DataSources.Add(rdsB);
this.rptviewer.DataBind();
this.rptviewer.LocalReport.Refresh();
}

Displaying data from local SQL Server CE database in a gridview C#

I am working on a small application for personal use. It is about keeping some data readily available for me.
It just consists of a local database, functions to add, erase or modify 4 or 5 columns of data and displaying the table in a datagridview.
I have managed to add data to the table and I have managed to use a
SELECT * FROM mytable
statement to get the data and iterate through it but I want to bind the table to the datagridview.
Here is my current method of trying to bind the data:
private void button2_Click(object sender, EventArgs e)
{
string query = "SELECT * FROM myTable";
SqlCeConnection conn = new SqlCeConnection(conString);
using (SqlCeDataAdapter adap = new SqlCeDataAdapter(query, conn))
{
//the adapter will open and close the connection for you.
DataTable dat = new DataTable();
adap.Fill(dat);
dataGridView1.DataSource = dat;
}
}
When I run this code it does not throw an exception and if I change the name of the table to something that does not exists then it causes an exception telling that the table does not exists so I know that it is fetching my table. It simply is not showing it.
Any ideas?
Thanks

Initialise Table adapter manually

How would I go about initialising a table adapter properly pragmatically? Normally, I would use the table adapter that get's created for me when I drag and drop the Data Table onto my form, but have never used one in a custom class before.
Cheers!
EDIT:
I think I need to explain my scenario in more detail.
I've added a method on my datatable inside my dataset. I want to be able to call this method from inside a custom class. Therefore I'd need a valid Table Adapter to be created to allow me to do this.
Just like this:
var dt = new DataTable();
using (SqlConnection c = new SqlConnection(cString))
using (SqlDataAdapter sda = new SqlDataAdapter("SELECT ...", c))
{
sda.SelectCommand.Parameters.AddWithValue("#field1", field1);
etc...
sda.Fill(dt);
}
void FillData()
{
// 1
// Open connection
using (SqlConnection c = new SqlConnection(
Properties.Settings.Default.DataConnectionString))
{
c.Open();
// 2
// Create new DataAdapter
using (SqlDataAdapter a = new SqlDataAdapter(
"SELECT * FROM EmployeeIDs", c))
{
// 3
// Use DataAdapter to fill DataTable
DataTable t = new DataTable();
a.Fill(t);
// 4
// Render data onto the screen
// dataGridView1.DataSource = t; // <-- From your designer
}
}
}
EDIT:
Why don't you make this method in a separate class that will be called in your data table and wherever else you will need to? You will just make an instance of the class and call the public method of that class.

WinForms DataGridView - update database

I know this is a basic function of the DataGridView, but for some reason, I just can't get it to work. I just want the DataGridView on my Windows form to submit any changes made to it to the database when the user clicks the "Save" button.
I populate the DataGridView according to a function triggered by a user selection in a DropDownList as follows:
using (SqlConnection con = new SqlConnection(conString))
{
con.Open();
SqlDataAdapter ruleTableDA = new SqlDataAdapter("SELECT rule.fldFluteType AS [Flute], rule.fldKnife AS [Knife], rule.fldScore AS [Score], rule.fldLowKnife AS [Low Knife], rule.fldMatrixScore AS [Matrix Score], rule.fldMatrix AS [Matrix] FROM dbo.tblRuleTypes rule WHERE rule.fldMachine_ID = '1003'", con);
DataSet ruleTableDS = new DataSet();
ruleTableDA.Fill(ruleTableDS);
RuleTable.DataSource = ruleTableDS.Tables[0];
}
In my save function, I basically have the following (I've trimmed out some of the code around it to get to the point):
using (SqlDataAdapter ruleTableDA = new SqlDataAdapter("SELECT rule.fldFluteType AS [Flute], rule.fldKnife AS [Knife],
rule.fldScore AS [Score], rule.fldLowKnife AS [Low Knife],
rule.fldMatrixScore AS [Matrix Score], rule.fldMatrix AS [Matrix]
FROM dbo.tblRuleTypes rule WHERE rule.fldMachine_ID = '1003'", con))
{
SqlCommandBuilder commandBuilder = new SqlCommandBuilder(ruleTableDA);
DataTable dt = new DataTable();
dt = RuleTable.DataSource as DataTable;
ruleTableDA.Fill(dt);
ruleTableDA.Update(dt);
}
Okay, so I edited the code to do the following: build the commands, create a DataTable based on the DataGridView (RuleTable), fill the DataAdapter with the DataTable, and update the database. Now ruleTableDA.Update(dt) is throwing the exception "Concurrency violation: the UpdateCommand affected 0 of the expected 1 records."
I believe there are a few problems here:
The sequence to keep in mind is that when you load up your grid, it is pointed to a datatable/set already.
When you type into the grid, the changes are temporarily persisted to the data table that is bound to the grid. Therefore, you do not want to be creating a data table every time you save, because the changes that were made to the existing data table are being ignored.
Second issue is that you probably don't need to create a binding source everytime, because just like the first point, if the grid is showing data, there is already a binding source that it is bound to.
Third problem is that the SQLCommandBuilder class has methods like GetInsertCommand, GetUpdateCommand, etc. that must be used to actually get the appropriate commands.
using (SqlDataAdapter ruleTableDA = new SqlDataAdapter("SELECT rule.fldFluteType AS [Flute], rule.fldKnife AS [Knife],
rule.fldScore AS [Score], rule.fldLowKnife AS [Low Knife],
rule.fldMatrixScore AS [Matrix Score], rule.fldMatrix AS [Matrix]
FROM dbo.tblRuleTypes rule WHERE rule.fldMachine_ID = '1003'", con))
{
SqlCommandBuilder commandBuilder = new SqlCommandBuilder(ruleTableDA);
DataTable dt = new DataTable();
dt = RuleTable.DataSource as DataTable;
//ruleTableDA.Fill(dt);
ruleTableDA.Update(dt);
}
MSDN documentation states that the update/delete/insert commands are automatically set when you manually set the SelectCommand. It doesn't mention that it does the same when you construct one with a SqlDataAdapter. Try adding these lines after creating your SqlCommanduBuilder.
ruleTableDA.UpdateCommand = commandBuilder.GetUpdateCommand()
ruleTableDA.InsertCommand = commandBuilder.GetInsertCommand()
ruleTableDA.DeleteCommand = commandBuilder.GetDeleteCommand()
You may need this to get the Update Command
ruleTableDA.UpdateCommand = commandBuilder.GetUpdateCommand();

Categories