I wrote a program to import data from excel sheet to sharepoint 2007 list. Around 11000 data gets imported. I have used the below code. My query is I wanted to put "employee's display name" in "created by" column. And im providing the same in excel sheet n in the code. But after the data gets imported I see that few employees data has reflected the created by column with their names. But for few it reflects EMPID only or EMPID + name. I debug the code It takes the right string to display but i did not understand y it gives such results. Also i am running the prog on my machine n not the server, so is it bcoz of this. As I am using test server and then only will deploy to production.
Code:
protected void btnImport_Click(object sender, EventArgs e)
{
using (SPSite site = new SPSite("URL"))
{
using (SPWeb web = site.OpenWeb())
{
webapp = web.Site.WebApplication;
webapp.FormDigestSettings.Enabled = false;
SPList list = web.Lists["List name"];
string connString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=D:\\Test.xlsx;Extended Properties=Excel 12.0";
OleDbConnection oledbConn = new OleDbConnection(connString);
oledbConn.Open();
OleDbCommand cmd = new OleDbCommand("SELECT * FROM [Sheet1$]", oledbConn);//contents from sheet1 is selected
OleDbDataAdapter oleda = new OleDbDataAdapter();
oleda.SelectCommand = cmd;
DataSet ds = new DataSet();
oleda.Fill(ds, "Employees");
DataTable dt = ds.Tables["Employees"];
DataView dv = new DataView(dt);
SPSecurity.RunWithElevatedPrivileges(delegate()
{
using (SPSite elevatedSite = new SPSite("URL"))
{
elevatedRootWeb = elevatedSite.OpenWeb();
}
});
foreach (DataRowView drv in dv)
{
EMPID = drv["Emp id"].ToString();
DispName = drv["Name"].ToString();
Title = drv["Title"].ToString();
getid = new SPQuery();
getid.Query = "<Where><Eq><FieldRef Name=’EMPID’ /><Value Type='Text'>" + EMPID + "</Value></Eq></Where><OrderBy><FieldRef Name='ID'/></OrderBy>";
check = list.GetItems(getid).GetDataTable();
if (check == null)
{
try
{
elevatedRootWeb.AllowUnsafeUpdates = true;
UserItem = list.Items.Add();
UserItem["Emp id"] = EMPID;
UserItem["Title"] = Title;
test = elevatedRootWeb.EnsureUser(PSNumber).ID + ";#" + DispName;
UserItem["Author"] = test;
UserItem.Update();
list.Update();
count++;
elevatedRootWeb.AllowUnsafeUpdates = false;
using (StreamWriter w = File.AppendText("D:\\Errorlog_SP2010.txt"))
{
Log(PSNumber + "Inserted successfully", w);
w.Close();
}
}
catch (Exception ex)
{
HttpContext.Current.Response.Write("<script>alert('Exception on adding item " + ex.Message + "')</script>");
using (StreamWriter w = File.AppendText("D:\\Errorlog_SP2010.txt"))
{
Log(ex.ToString()+ PSNumber, w);
w.Close();
}
}
}
check the "_catalogs/users/simple.aspx" list to see if the user on that site has thier information stored correctly.
This is important as the Author field takes it's value from what is displayed in this list, not exactly what you set.
See this question on how to fix this.
Related
I want to create multiple CSV file for every drop down Selected value. Even-though while debugging i can notice csv is appending for different drop down value but not writing another CSV file. do not know why and where i am doing mistake.
When i remove using block, and for second time its throwing error :
The process cannot access the file 'File path' because it is being used by another process.
I believe need to store all files on server but again same issue
i have added code to solve error but no change;
if (File.Exists(filePath))
File.Delete(filePath);
Button code
protected void btnGenerate_Click(object sender, EventArgs e)
{
List<int> stopWordArray = new List<int>();
foreach (ListItem listItem in ddlDepot.Items)
{
if (listItem.Selected)
{
string FileType = ddlqoutatfileType.SelectedItem.Text;
DateTime Qotation_Date = Convert.ToDateTime(txtdate.Text).AddDays(3);
var Qotation_Date_modified = Qotation_Date.ToShortDateString();
OracleCommand CmdB = new OracleCommand("Select DEPOT_CODE, PRODUCT_CODE, TO_CHAR(TO_DATE(UPLOAD_DATE,'DD/MM/YYYY'), 'DDMMYYY') as UPLOAD_DATE , TO_CHAR(TO_DATE(SALES_DATE,'DD/MM/YYYY'), 'DDMMYYYY') as SALES_DATE, ORDER_QTY, FILE_TYPE, ROUTE_CODE from SCM_SARAS_ORDERS_vw where File_Type = '" + FileType + "' and DEPOT_CODE =" + listItem.Value + " and SALES_DATE = TO_DATE('" + Qotation_Date_modified + "' , 'DD/MM/YYYY')", con);
CmdB.CommandType = CommandType.Text;
OracleDataAdapter daB = new OracleDataAdapter();
DataTable dtB = new DataTable();
daB.SelectCommand = CmdB;
daB.Fill(dtB);
string csv = string.Empty;
foreach (DataRow row in dtB.Rows)
{
foreach (DataColumn column in dtB.Columns)
{
csv += row[column.ColumnName].ToString().Replace(",", ";") + ',';
}
csv += "\r\n";
}
string fileName = "myfile.csv";
string filePath = Server.MapPath("~/file" + fileName);
using (StreamWriter sw = new StreamWriter(filePath, false))
{
sw.Write(csv);
}
}
}
}
I am not sure what do you mean about follow problem.
#but not writing another CSV file#
in your code, obviously, you wrote same file in the loop; why do not you change it to
string fileName = "myfile"+listItem.Value+".csv";//change filename?
string filePath = Server.MapPath("~/file" + fileName);
using (StreamWriter sw = new StreamWriter(filePath, false))
{
sw.Write(csv);
}
I am trying to simply read data from my SQL Server database and input them into text fields on a webform.
I can't figure out what I'm missing but everything compiles smoothly and runs but my text fields remain empty.
protected void Page_Load(object sender, EventArgs e)
{
String index = Request.Form["indexTb"];
string constr = ConfigurationManager.ConnectionStrings["TravelLogConnectionString2"].ConnectionString;
SqlConnection con = new SqlConnection(constr);
string selectSql = "SELECT Location, Date, Message FROM EntryLogs WHERE ID='" + Convert.ToInt32(index) + "'";
SqlCommand com = new SqlCommand(selectSql, con);
try
{
con.Open();
using (SqlDataReader reader2 = com.ExecuteReader())
{
while (reader2.Read())
{
reader2.Read();
LocTb.Text = (reader2["Location"].ToString());
DateTb.Text = (reader2["Date"].ToString());
MessTb.Text = (reader2["Message"].ToString());
}
reader2.Close();
reader2.Dispose();
}
}
finally
{
con.Close();
}
}
You're calling the reader2.Read(); twice - once in the while loop, once just below:
while (reader2.Read())
{
reader2.Read(); // <=== WHY call .Read() a second time ?!?!!?!
LocTb.Text = (reader2["Location"].ToString());
DateTb.Text = (reader2["Date"].ToString());
MessTb.Text = (reader2["Message"].ToString());
}
That's both unnecessary, and could lead to no results being returned.
If your query only returns one row, the .Read() in the while loop would read that row and return it, but then the next line does another Read(), which would not return any data (since the first and only row has already been read).
Just remove that unnecessary second call to .Read() and I bet your data will begin to show up!
And to fix that glaring SQL injection - use parametrized queries! as one should always do anyway!
string selectSql = "SELECT Location, Date, Message FROM EntryLogs WHERE ID = #Id;";
SqlCommand com = new SqlCommand(selectSql, con);
com.Parameters.Add("#Id", SqlDbType.Int).Value = Convert.ToInt32(index);
try
{
con.Open();
using (SqlDataReader reader2 = com.ExecuteReader())
{
while (reader2.Read())
{
// REMOVE THIS reader2.Read();
LocTb.Text = (reader2["Location"].ToString());
DateTb.Text = (reader2["Date"].ToString());
MessTb.Text = (reader2["Message"].ToString());
}
reader2.Close();
reader2.Dispose();
}
}
finally
{
con.Close();
}
protected void Button1_Click(object sender, EventArgs e)
{
string db = "Data Source=DESKTOP-R6H3RTP;Initial Catalog=AdmitDB; Integrated Security= true;";
SqlConnection mycon = new SqlConnection(db);
mycon.Open();
String query = "select * from tblPatient where PhoneNo like '"+TextBox1.Text+"%'";
SqlCommand cmd = new SqlCommand(query, mycon);
SqlDataAdapter da = new SqlDataAdapter(cmd);
DataSet ds = new DataSet();
da.Fill(ds);
if (cmd.ExecuteNonQuery() > 0)
{
lblName.Visible = true;
lblId.Visible = true;
lblPNo.Visible = true;
lblDOB.Visible = true;
lblName.Text = "PName";
lblId.Text = "Pid";
lblPNo.Text = "PhoneNo";
lblDOB.Text = "PDOB";
}
else
{
lblNotFound.Visible = true;
}
}
i'm searching from database but just else statement executes don't know why it's not get data from database, if any kind of error then help me please
i think you don't need if (cmd.ExecuteNonQuery() > 0). the cmd executes automatically. you want to check the tables in the dataset.
// check the first table for rows.
if(ds.Tables[0].HasRows())
{
// success. now you can work with the table.
}
ExecuteNonQuery method returns the number of row that were modified by the query. Since SELECT query doesn't modify anything in the database - you get 0.
You should modify your query with a COUNT(*) function:
String query = "select COUNT(*) from tblPatient where PhoneNo like '"+TextBox1.Text+"%'";
Then you can get that value with ExecuteScalar():
if (cmd.ExecuteScalar() > 0)
I am trying to retrieve a list of the worksheets in an Excel workbook, but the collection I get back has both the sheet names and the data column id's, which seem to be called 'Defined Names' in the original xlsx xml. Can you tell me how to return only the worksheet names?
The code I'm using is along the lines of:
OleDbConnection connExcel = new OleDbConnection(#"Provider=Microsoft.ACE.OLEDB.12.0;"
+ #"Data Source=" + FilePath + ";"
+ #"Extended Properties=""Excel 8.0;HDR=Yes;""");
OleDbCommand cmdExcel = new OleDbCommand();
cmdExcel.Connection = connExcel;
connExcel.Open();
DataTable testTable = connExcel.GetSchema("Tables");
The contents of the resulting testTable collection contain entries under TABLE_NAME of:
DATA1
DATA2
DATA3
DATA4
DATA5
Sheet1$
TEST1
-TEST2
TESTHKEY
TESTKEYS
TESTVKEY
They all have a TABLE_TYPE of TABLE.
The original workbook corresponding to the above would have 1 worksheet containing 5 columns, the first row would contain a header. I'm only interested in the Sheet1$ entry. The spreadsheet is
created in Excel 2010, I'm trying to process it in an ASP.NET 4 app written in C#. Potentially, the worksheet name may have been changed so I can't guarrantee that it will always be Sheet1$.
My first thoughts were wrong so I came up with this as a workaround. The actual worksheet names returned should always end with $, so I hacked it to check for that. Messy but you get the general idea I'm sure.
OleDbConnection connExcel = new OleDbConnection(#"Provider=Microsoft.ACE.OLEDB.12.0;"
+ #"Data Source=c:\test.xlsx;"
+ #"Extended Properties=""Excel 12.0 Xml;HDR=Yes;""");
OleDbCommand cmdExcel = new OleDbCommand();
cmdExcel.Connection = connExcel;
connExcel.Open();
DataTable testTable = connExcel.GetSchema("Tables");
String[] excelSheets = new String[testTable.Rows.Count];
int i = 0;
foreach (DataRow row in testTable.Rows)
{
excelSheets[i] = row["TABLE_NAME"].ToString();
if (excelSheets[i].EndsWith("$"))
{
Console.WriteLine(excelSheets[i] = row["TABLE_NAME"].ToString());
i++;
}
else
{
i++;
}
}
Console.ReadLine();
I had a similar issue but with the exception that it showed me Sheets that didn't exist in Excel. Even though this post is a bit old now, maybe somebody finds this and finds it helpful.
My Code:
//OpenFileDialog
try
{
OpenFileDialog.InitialDirectory = Environment.GetFolderPath(Environment.SpecialFolder.Desktop);
OpenFileDialog.Filter = "XLSX Files(*.xlsx)|*.xlsx|All Files (*.*)|*.*";
OpenFileDialog.ShowDialog();
}
catch (Exception ex)
{
//some Error Message
}
//read into Combobox
try
{
OleDbConnection con = new OleDbConnection(#"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + OpenFileDialog.FileName + ";Extended Properties=Excel 12.0;");
con.Open();
DataTable dt = con.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, null);
con.Close();
this.Combobox.Items.Clear();
for (int i = 0; i < dt.Rows.Count; i++)
{
String sheetName = dt.Rows[i]["TABLE_NAME"].ToString();
sheetName = sheetName.Substring(0, sheetName.Length - 1);
//cheap Filter to filter out unneeded/wrong sheets
if (sheetName.Replace("'", " ").Replace("$", " ").TrimStart().TrimEnd().Contains("#") != true)
{
this.Combobox.Items.Add(sheetName.Replace("'", " ").Replace("$", " ").TrimStart().TrimEnd());
}
}
}
catch (Exception Ex)
{
//some Error Message
}
This might not be the best solution, but it works quite well for me.
private static string EXCEL_CONNECTIONSTRING = string.Format("Provider=Microsoft.ACE.OLEDB.12.0; data source={0}; Extended Properties=Excel 12.0;", "#{FILENAME}");
private IEnumerable<string> GetWorksheetNames(string excelFile)
{
var currentConnectionString = EXCEL_CONNECTIONSTRING.Replace("#{FILENAME}", excelFile);
using (OleDbConnection connection = new OleDbConnection(currentConnectionString))
{
OleDbCommand cmdExcel = new OleDbCommand();
cmdExcel.Connection = connection;
connection.Open();
DataTable dt = connection.GetSchema("Tables");
IEnumerable<string> excelSheets = dt.Rows.Cast<DataRow>().Select(row => row["TABLE_NAME"].ToString());
dt.Dispose();
connection.Close();
return excelSheets;
}
}
The current solution i implemented is awful!
I use a for... loop for inserting records from an ADO.NET data-table into an SQL table.
I would like to insert at once the data-table into the SQL table, without iterating...
Is that possible, or am i asking too much?
You can pass the entire DataTable as a single Table Valued Parameter and insert the entire TVP at once. The following is the example from Table-Valued Parameters in SQL Server 2008 (ADO.NET):
// Assumes connection is an open SqlConnection.
using (connection)
{
// Create a DataTable with the modified rows.
DataTable addedCategories = CategoriesDataTable.GetChanges(
DataRowState.Added);
// Define the INSERT-SELECT statement.
string sqlInsert =
"INSERT INTO dbo.Categories (CategoryID, CategoryName)"
+ " SELECT nc.CategoryID, nc.CategoryName"
+ " FROM #tvpNewCategories AS nc;"
// Configure the command and parameter.
SqlCommand insertCommand = new SqlCommand(
sqlInsert, connection);
SqlParameter tvpParam = insertCommand.Parameters.AddWithValue(
"#tvpNewCategories", addedCategories);
tvpParam.SqlDbType = SqlDbType.Structured;
tvpParam.TypeName = "dbo.CategoryTableType";
// Execute the command.
insertCommand.ExecuteNonQuery();
}
TVP are only available in SQL 2008.
I think you are looking for SQLBulkCopy.
SqlBulkCopy is the simplest solution.
using (SqlConnection dbConn = new SqlConnection(connectionString))
{
dbConn.Open();
using (SqlBulkCopy bulkCopy = new SqlBulkCopy(dbConn))
{
bulkCopy.DestinationTableName =
"dbo.MyTable";
try
{
bulkCopy.WriteToServer(myDataTable, DataRowState.Added);
}
catch (Exception ex)
{
myLogger.Error("Fail to upload session data. ", ex);
}
}
}
You can create SqlBulkCopyColumnMapping if the columns in your DataTable don't match your database table.
You can also try the following method.
private void button1_Click(object sender, EventArgs e)
{
tabevent();
DataSet ds = new DataSet();
DataTable table = new DataTable("DataFromDGV");
ds.Tables.Add(table);
foreach (DataGridViewColumn col in dataGridView1.Columns)
table.Columns.Add(col.HeaderText, typeof(string));
foreach (DataGridViewRow row in dataGridView1.Rows)
{
table.Rows.Add(row);
foreach (DataGridViewCell cell in row.Cells)
{
table.Rows[row.Index][cell.ColumnIndex] = cell.Value;
}
}
// DataTable ds1changes = ds1.Tables[0].GetChanges();
if (table != null)
{
SqlConnection dbConn = new SqlConnection(#"Data Source=wsswe;Initial Catalog=vb;User ID=sa;Password=12345");
SqlCommand dbCommand = new SqlCommand();
dbCommand.Connection = dbConn;
foreach (DataRow row in table.Rows)
{
if (row["quantity"] != null && row["amount"]!=null && row["itemname"]!=null)
{
if (row["amount"].ToString() != string.Empty)
{
dbCommand.CommandText =
"INSERT INTO Bill" +
"(Itemname,Participants,rate,Quantity,Amount)" +
"SELECT '" + Convert.ToString(row["itemname"]) + "' AS Itemname,'" + Convert.ToString(row["Partcipants"]) + "' AS Participants,'" + Convert.ToInt32(row["rate"]) + "' AS rate,'" +
Convert.ToInt32(row["quantity"]) + "' AS Quantity,'" + Convert.ToInt32(row["amount"]) + "' AS Amount";
dbCommand.Connection.Open();
dbCommand.ExecuteNonQuery();
if (dbCommand.Connection.State != ConnectionState.Closed)
{
dbCommand.Connection.Close();
}
MessageBox.Show("inserted");
}
}
}
}
}