Not a legal ole auth date issue while writing to datatable - c#

I have developed a web application to import Excel data into a SQL Server table using bulk copy column mapping. I used a select * from sheet query to copy the sheet data and insert into data table before writing it to table.
There are 20 columns in the sheet. The last column contains data of type datetime, string, integers and special characters. Its a mixed data type. When the application tried to copy and insert data into data table means it shows
Not a legal ole auth date
I have checked the last column values. Date value is correct only but it shows not a legal ole auth date issue.
Instead of using select * from sheet, is there any alternative approach like insert data into data table from Excel by row wise using for loop ?
Code is
OleDbConnection excelConnection1 = new OleDbConnection(excelConnectionString);
string query = string.Format("Select * from [{0}]", excelSheets[0]);
using (OleDbDataAdapter dataAdapter = new OleDbDataAdapter(query, excelConnection1))
{
dataAdapter.Fill(dt); **// issue raise when it try to fill the datatable**
}

Related

Most Efficient way of searching a List of values in an SQL Server table

I am working on a C# Win-forms Application which is connected to SQL Server Database. I have a situation where I have to parse data from an Excel sheet and search each value in all columns of a table. And at the end display the rows of table whose value matched.
Now what I am doing is
I have parsed the whole Excel sheet into DataTable
I have a stored procedure in SQL server which take a string input and search it in all column of table and return a row if any matched.
Now I pass each value of the Datatable(extracted from excel sheet) to the stored procedure for searching.
Kindly guide me whether it is an efficient way, or give me suggestion for achieving it efficiently.
You can use Table Valued parameter and than in SQL you can use cursor or loop over the passed table and search each column in SQL table. Here is a simple example.
In database create a new Tpye
CREATE TYPE [dbo].[SearchInDB] AS TABLE(
[Id] [int] NOT NULL
)
And in SP you will pass this type from C# code. Your SP will receive it like this
ALTER PROCEDURE [dbo].[YourSPNameHere]
#DataToSearch dbo.SearchInDB ReadOnly
AS
BEGIN
--Your SP logic here
END
And in your code you will create a DataTable and fill datatable with values and pass it to SP like this
DataTable dt = new DataTable();
dt.Columns.Add("Id", typeof(int));
//Add rows in datatable with values
DataRow dr = dt.NewRow();
dr["Id"] = 10;
dt.Rows.Add(dr);
//Now pass this table to SP as parameter
SqlParameter parameter = new SqlParameter();
parameter.ParameterName = "#DataToSearch";
parameter.SqlDbType = System.Data.SqlDbType.Structured;
parameter.Value = dt;
Note
I have added only one column you have to add other column if needed. To get values from parameter passed to SP you will have to use loop or use cursor. Here is a link of another example
You can use SQL Server SSIS packages , to directly import excel into database table and can search the table using loop or cursor in stored procedure

SQLite data conversion with C#

I have a text file which has the date in the format dd-month-yyyy (example, 26-Dec-2014). That data is pulled into a database. I'm using SQLite and need to convert that date format into yyyy-MM-dd. The column in SQLite for the date is TEXT format for the date. I'm using it to put the value in a datagridviewer and eventually sorting it by date. Here is some of my code in C# that has the datetimepicker value converted to yyyy.MM.dd. and then the code to
string dt1 = From_date.Value.ToString("yyyy.MM.dd");
string dt2 = To_Date.Value.ToString("yyyy.MM.dd");
string stringsqlcommand = "SELECT * from CKData";
SQLiteDataAdapter sda = new SQLiteDataAdapter(stringsqlcommand, con);
sda.Fill(dt);
CKData is the data table. Is there a convert function like for traditional SQL where you can take the column from the table and make it a different format? The reason I'm using SQLite is because it's a local database which I will occasionally need access to and it has to be able to cross platforms easily (used on different computers).

convert datetime format in excel to time format when insert into sql server

I'm trying to import excel data to sql server database. Everything work fine except one column where the format in excel is was datetime and the datatype in my database was time. It was unable to convert datetime to time when i trying to insert the data.
My code was:
OleDbCommand exclCmd = new OleDbCommand("select * from [Sheet1$]", exclConnection);
exclConnection.Open();
OleDbDataReader exclReader = exclCmd.ExecuteReader();
SqlBulkCopy sqlBulk = new SqlBulkCopy(strConnection);
sqlBulk.DestinationTableName = "test_excel";
sqlBulk.ColumnMappings.Add("col1", "col1");
sqlBulk.ColumnMappings.Add("col2", "col2");
sqlBulk.ColumnMappings.Add("col3", "col3");
sqlBulk.ColumnMappings.Add("col4", "col4");
sqlBulk.WriteToServer(exclReader);
i tried to use "select con1, col2, col3, convert(time,col4) as col4 from [Sheet1$]" bt the convert function was not workable.
Anyone can help me on these? Thanks.
if staging table is an option, you could convert Excel date to string using TEXT(col4,"dd mmmm yyyy hh:mm:ss"). once the data is in staging table, you may write appropriate SQL statement to insert into correct table.
I would use SSIS for this kind of task since that gives more control on data transformations.

C# SqlBulkCopy types mismatch

I have a DataTable which has 10 columns, and after I add some rows in it, I want to add it to the database using SqlBulkCopy.
My problem is that in the DataTable I have strings and some fields in the database are decimal and date respectively. Is there a way to convert them to the desired data types?
When programmatically adding columns to your DataTable, you can specify type:-
DataTable dt = new DataTable();
dt.Columns.Add("FieldName", typeof(System.Decimal));
These will be honored when you perform the bulk copy.
EDIT
In response to user comment.
When populating the DataRow with information, an explicit conversion is only required if the source data doesn't match the target field.
If the types are the same, you can just assign it.
e.g.
// With a decimal field, decimal target
Decimal myNum = 123;
// Works fine - assuming the Price datacolumn has been set up as a System.Decimal
row["Price"] = myNum;
Sounds like you may be creating the columns in the DataTable in code (as opposed to Filling via a DataAdapter which would set the column data types appropriately).
If that's the case, then can you not just create the DataColumns with the correct data types to start with, instead of all strings...and then ensure when you add rows to it, you convert the data into the appropriate type?
i.e. get to the point where your DataTable has the correct types and data in correctly, so SqlBulkCopy can then blast it into the DB with data already in the correct form.
was having the same problem where in I was suppose to copy data from an excel file which had strings and I wanted them to be stored in the database as double. I have pasted the code related to the question below :-
DataTable dt = new DataTable();
//Read Data from First Sheet
connExcel.Open();
cmdExcel.CommandText = "SELECT * From [" + SheetName + "] ";
oda.SelectCommand = cmdExcel;
oda.Fill(dt);
connExcel.Close();
Convert.ToDouble(dt.Columns["Product"]);
//where product(product temperature) is the a column whose datatype in the database is float and in the excel file is string.

OLEDB and C# bulk insert for Excel spreadsheet creation

I am using C# to read a SQL stored procedure, put the results of the stored procedure into a C# data table and then reading the data table row by row to build up my "Insert into....values "etc. This creates my Excel spreadsheet with the correct data. However, instead of inserting row by row, is there a way of doing a bulk insert?
Failing that I was thinking of getting the stored procedure to write the results to a permanent table and therefore is there a way of doing an "Insert into ....select from ". When I have tried this in C# the code is unable to find the SQL table name specified "Microsoft database access engine cannot find the object ", what is the correct syntax and where do you specify where/how to access the SQL table?
Thanks
Hi, that link looks like it's using Microsoft.Office.Interop.Excel;
I'm using OLEDB (which i'm now beginning to regret!). So basically i have a C# class that is called from another component. This C# class reads a sql stored procedure, puts the results into a data table. I then set up the table definition using the OLEDBcommand "Insert into ( []) values ("?"). I then define the parameters e.g. cmd.Parameters.Add(columnHeading, OleDbType.VarChar, size) etc. Then for each row i find in the data table i set the cmd.Parameters[i].value = row[i], where parameters[i] is incremented for each column in that row. I then loop round for each data row and set cmd.Parameters[i].value appropriately. As I have to set the cmd.Parameters[i].Value for each row i find in my dataset and then cmd.ExecuteNonQuery();
, this is quite time consuming. So is there a way to bulk insert the data from the data table into the OLEDB command, if not, can i insert the data by referencing a SQL table directly and doing a "insert into..select from"?
You can separate your insert statements with a semicolon and run just 1 command. For instance ...
string sql = "insert into table (col1,col2) values ('row1','row1');"
sql += "insert into table (col1,col2) values ('row2','row2');"
sql += "insert into table (col1,col2) values ('row3','row3');"
SqlConnection conn = new SqlConnection("some connection string");
SqlCommand cmd = new SqlCommand(sql, conn);
conn.Open();
conn.ExecuteNonQuery();
conn.Dispose();
cmd.Dispose();
Or something similar. You are executing all 3 queries with 1 command. This might not work with databases other than SQL Server, but will definitely work with SQL Server.

Categories