I'll try to simplify my problem as much, as possible.
Feel free to comment and correct my English. Hope you can understand me.
My main question is:
Is there any simple and "automated" way, to fill a table in dataset only with rows related to data in other table?
Let's say, we have database with following schema:
Now, i'm trying to make the same thing with table "Orders", and create custom method "FillByDate". It works, but there is small problem:
DataSet1 myDataSetInstance = new DataSet1();
DataSet1TableAdapters.OrdersTableAdapter OrdersTA = new DataSet1TableAdapters.OrdersTableAdapter();
OrdersTA.FillByDate(myDataSetInstance.Orders, new DateTime(2013, 1,1), DateTime.Now);
foreach (var row in myDataSetInstance.Orders)
{
MessageBox.Show(row.Comments); // OK
MessageBox.Show(row.CustomersRow.Name); //NULL
}
Getting related row from Customers table is impossible - first i have to manually fill that table. I can see two ways to do this
Getting whole content of this table - but it will be A LOT of unneeded data
Create custom query in it's TableAdapter - something like FillByOrdersByDate(#Date1, #Date2) - it is easy, when I have only 2 tables and 1 relation, but with more tables this method will require dozens of custom queries for each TableAdapter.
I really believe, that there have to be "better" way to do this.
Couple of ways to approach this - if you are only going to read the data, you can use a join query to populate the dataset.
Alternatively, you can use a join query to populate the child table. Looking at your example, suppose you wanted to list customers and orders for all customers in a particular city. You have already written a 'FillbyCity' query for your Customers TA - you would write a similar FillbyCity Query for your Orders ta. Yes you could use a join to the customers table to do this: SELECT Orders.* FROM Orders INNER JOIN customers ON customers.customerid = orders.customerid WHERE customers.city = #city
You would then use the datarelation to link individual customers to their orders, depending on the requirements of your application.
(If perchance you have David Sceppa's 'Programming ADO.Net 2.0' this is dealt with in chapter 7)
"but with more tables this method will require dozens of custom queries for each TableAdapter." Why dozens? I'm not sure where you're going with that.
(PS your English is fine, apart from mixing up it's and its - but lots of native speakers do that too. . )
There is an obscure... don't even know what to call it - ADO.NET SQL extension, or something - a command called SHAPE, that describes the relations you're looking for and ADO.NET uses that "special" SQL to give you a dataset that nicely contains multiple related tables.
SHAPE {select * from customers}
APPEND ({select * from orders} AS rsOrders
RELATE customerid TO customerid)
It works beautifully, but I think it's old and scarcely (un)supported
MS suggest that SHAPE provider is to be depreciated and to use XML instead (sorry - lost the link, but that was back in .NET 1.1) and they were pointing towards XML. I think the FOR XML T-SQL clause is doing the trick. I haven't done it myself (yet), where I use FOR XML to populate a DataSet, but if you follow the link in an answer I left to another similar question, I think it's going to work.
Related
This past week I was tasked with moving a PHP based database to a new SQL database. There are a handful of requirements, but one of those was using ASP.Net MVC to connect to the SQL database...and I have never used ASP.Net or MVC.
I have successfully moved the database to SQL and have the foundation of the ASP site set up (after spending many hours pouring through tutorials). The issue I am having now is that one of the pages is meant to display a handful of fields (User_Name, Work_Date, Work_Description, Work_Location, etc) but the only way of grabbing all of those fields is by combining two of the tables. Furthermore, I am required to allow the user to search the combined table for any matching rows between a user inputted date range.
I have tried having a basic table set up that displays the correct fields and have implemented a search bar...but that only allows me to search by a single date, not a range. I have also tried to use GridView with its Query Builder feature to grab the data fields I needed (which worked really well), but I can't figure out how to attach textboxes/buttons to the newly made GridView. Using a single table with GridView works perfectly and using textboxes/buttons is very intuitive. I just can't seem to make the same connection with a joined view.
So I suppose my question is this: what is the best way for me to combine these two tables while also still having the ability to perform searches on the displayed data? If I could build this database from scratch I would have just made a table with the relevant data attached to it, but because this is derived from a previously made database it has 12+ years of information that I need to dump into it.
Any help would be greatly appreciated. I am kind of dead in the water here. My inexperience with these systems is getting the better of me. I could post the code that I have, but I am mainly interested in my options and then I can do the research on my own.
Thanks!
It's difficult to offer definitive answers to your questions due to the need for guesswork.
But here are some hints.
You can say WHERE datestamp >= '2017-01-01' AND datestamp < '2018-01-01' to filter all the rows in calendar year 2017. Many variations on this sort of date range filter are available.
Your first table probably has some kind of ID number on each row. Let's call it first.first_id. Your second table probably has its own id, let's call it second.second_id. And, it probably has another id that identifies a row in your first table, let's call it second.first_id. That second.first_id is called a foreign key in the second table to the first table. There can be any number of rows in your second table corresponding to your first table via this foreign key.
If this is the case you can do something like this:
SELECT first.datestamp, first.val1, first.val2, second.val1, second.val2
FROM first
JOIN second ON first.first_id = second.first_id
WHERE first.datestamp >= '2018-06-01' AND first.datestamp < '2018-07-01'
AND (first.val1 = 'some search term' OR second.val1 = 'some search term')
ORDER BY first.datestamp
This makes a virtual table by joining together your two physical tables (FROM...JOIN...).
Then it filters the rows you want from that virtual table (FROM ...).
Then it puts them in the order you want (ORDER BY...).
Finally, it chooses the columns from the virtual table you want in your result set (SELECT ...).
SQL database servers (MySQL, SQL Server, postgreSQL, Oracle and the rest) are very smart about doing this sort of thing efficiently.
I have 5 tables in database Table1, Table2 and so on [All tables have same column name or Table Definition]. I am using Entity Framework in MVC application and C#.
First creating an object of db of Database.
Getting table data as db.Table1.ToList();.
I want to do some thing like this.
list<string> TableNames = new list<string>();
db.TableNames[1].ToList();
Now I know this won't work but is there any way I can get data without hard coding the table names as my Project will deal with 100s of tables with same column names but different data.
This is a Project for a Hospital which will receive data from different locations. Lets say for location A I am expecting 100 cases a day and right now I have 10 locations. So if I combine all this data into one which means 1000 records each day in a single day therefore overtime searching through this table will become performance sensitive.
I am writing this for those who might occur into this same dilemma.....
I had reference a table through EF so the classes got generated into the Model.
Lets say I have 3 tables of same schema tbl_Loc1, tbl_Loc2 and tblLoc3.
public void getDataFromTable(string TableName)
{
using(var ctx = new DBEntities())
{
string query ="Select * from " +TableName;
var data=ctx.tbl_Loc1.SqlQuery(query);
}
}
DBEntities is Database Connection String
In ctx.tbl_Loc1.SqlQuery(query);.............. tbl_loc1 has a class in model which will help in getting data in the same format[As all tables have the same table definition]
There is a model of tbl_Loc1 in EF whereas tbl_Loc2 and tbl_Loc3 are only in Database.
Return this data as IEnumerable list
http://www.entityframeworktutorial.net/Querying-with-EDM.aspx
I echo other commenter's thoughts that you probably can handle this all in one table with a distinguishing column (and some proper indexes on the table). What you've mentioned so far only amounts to hundreds of thousands of records, something that should still perform very well.
However, in order to do what you want the way you state it, you can use reflection to examine the properties of your db object. Any property in there that is a hashset is a property that represents a table, so you can get a list of all the hashset properties, and their names (perhaps with a few tweaks regarding pluralization), which will give you your table names.
For a more sophisticated use of metadata within EF, take a look at How I can read EF DbContext metadata programmatically?.
Also, you may find that SMO is a helpful approach to this kind of thing (nothing preventing you from using it and EF).
I have four types of data's in a SQL Server Database Table: forum topic, article topic, chat topic and QnA Topic. These have same type of columns : ID, Title, Content, User,type etc. The only difference is the type column that is used to detect if the current content is forum topic(type = 0) or article topic(type = 1) and so on.
My colleagues said it will be better to store them in separate tables namely ForumTopics, Articles, Chats, QnAs. But in my view its not a good idea because the C# methods that are based on these content will be different and either I have to write multiple functions having same logic for each operation for each table or a conditional check in one function that its a forum topic(type = 0) or article topic(type = 1) or other.
Please tell me which is a better approach?
One table is better approach because it will give you flexibility in the future. You will be able to do things like the following:
Select everything for a particular user
Search something in all titles
Besides multiple tables are harder to maintain and you are right. There will be more complexity and repetition in your C# code as well with multiple tables.
Using one table is better way because it is difficult to maintain data if it is stored in separate table you have to write complex queries.
If you use multiple table you have to use joins or subquery to retrieve data which makes slow performance.
So go with a single table.
I'm consuming a 3rd-party web service that outputs a Dataset (from XML). I'd like to create a new table in my local MS Access database that contains the DataSet data.
Is there a simple way to hand-off the DataSet to a .net object and ask it to "create a table from this"?
I know that we can use different parts of ADO to extract schema, build commands, insert rows, etc. I figured there has to be a simpler way.
The only two ways I know of are to
Walk through the DataSet field by
field and generate a DDL instruction
(which is valid for MS-Access)
Add a reference to ADOX, create a new table (with columns) and append the new table to the ADOX catalog. More info here. But again you are walking throught the dataset table field by field.
I haven't provided much detail on either of these approaches since I don't think they match what you've specified.
It seems you are looking for a quicker way than either of those so I guess the answer to your question is no.
Suppose I have an ADO.NET DataTable that I was to 'persist' by saving it to a new table in a SQL Server database - is there a fast way of doing this?
I realise I could write code generating the DDL for the 'CREATE TABLE' statement by looping through the DataColumns collection and working out the right type mappings and so on ... but I'm wondering if there is an existing method to do this, or a framework someone has written?
(NB: I need to be able to handle arbitrary columns, nothing too fancy like blobs; just common column types like strings, numbers, guids and dates. The program won't know what the columns in the DataTable are until run-time so they can't be hard-coded.)
ADO.net cannot create tables in SQL Server directly, however, SMO can do this with the .Create method of the Table class. Unfortunately, there is no built-in way to use a DataTable to define an SMO Table object.
Fortunately, Nick Tompson wrote just such a DataTable-to-SMO.Table routine back in 2006. It is posted as one of the replies to this MSDN forums topic http://social.msdn.microsoft.com/forums/en-US/adodotnetdataproviders/thread/4929a0a8-0137-45f6-86e8-d11e220048c3/ (edit: I can make hyperlinks now).
Note also, the reply post that shows how to add SQLBulkCopy to it.
If the table exists, you can use SqlBulkCopy (which will accept a DataTable) to get the data into the table in the fastest possible way (much faster than via an adapter). I don't think it will create the table though. You might have to write the DDL yourself, or find some existing code to loop over the DataTable.Columns to do it.
I think this post can help
I might be easier to store your DataTable as XML. just create a table with an XML column.