使用OracleDataAdapter将Datatable插入Oracle

时间:2018-02-20 12:58:27

标签: c# oracle11g

我需要将DataGridView中的特定行插入Oracle DB表。我所做的是为OracleDataAdapter设置InsertCommand,创建一个具有相同列名的新的空DataTable,并用它填充OracleDataAdapter。然后我循环遍历DataGridView中的行,将所需的行添加到DataTable然后调用da.Update()方法 - 但它不起作用,我得“值不能为null。参数名称:命令”同一行的错误 - da.Fill() ...这是我所描述的代码:

private OracleDataAdapter da = new OracleDataAdapter();
private void Inicialize_adapter()
{
    OracleConnection conn = new OracleConnection(conn_string);
    conn.Open();

    OracleCommand insert = new OracleCommand("Myschema.InsertToTable", conn);

    insert.Parameters.Add("ID_IN", OracleDbType.Decimal, 4, "ID");
    insert.Parameters.Add("ID_FK_IN", OracleDbType.Decimal, 4, "ID_FK");
    insert.Parameters.Add("SERIAL_IN", OracleDbType.Decimal, 4, "SERIAL_NO");

    da.InsertCommand = insert;
    da.MissingSchemaAction = MissingSchemaAction.AddWithKey;
    conn.Close();
}

我的ButtonSave_Click中的代码:

...

Inicialize_adapter();

DataTable dt_Test = new DataTable();
DataColumn dc = new DataColumn("ID", typeof(int));
dt_Test.Columns.Add(dc);

dc = new DataColumn("ID_FK", typeof(int));
dt_Test.Columns.Add(dc);

dc = new DataColumn("SERIAL_NO", typeof(int));
dt_Test.Columns.Add(dc);

var sequence = New_id(1); // this get's me next sequence in DB
int increase_seq = 0;

foreach (DataGridViewRow row in MyDGV.Rows)
{
    if (row.Cells[0].Value == "Added")
    {
       DataRow newRow = dt_Test.NewRow();

       newRow[0] = sequence+increase_seq;
       newRow[1] = 2";
       newRow[2] = row.Cells[1].Value;

       dt_Test.Rows.Add(newRow.ItemArray);
       ++increase_seq;
     }
 }
 //Fill Adapter -error here
 da.Fill(dt_Test);

 da.Update(dt_Test);

  ...

我也尝试了其他选项,比如数组绑定,但这并没有产生好的结果,所以我希望我能以这种方式工作,因为它更简单。有人知道我的代码中有什么问题吗?提前感谢您的帮助!!

1 个答案:

答案 0 :(得分:1)

<强>更新

首先:要从DataGridView获取选定的行,您可以这样做:

    foreach (DataGridViewRow dr in MyDGV.Rows)
    {
        if (dr.Selected)
        {
            //Add to DataTable
        }
    }

    //Or even easier:

    foreach (DataGridViewRow row in MyDGV.SelectedRows)
    {
        //Add to DataTable
    }

另一部分是da.Fill()/ da.Update()。我不确定&#34; Myschema.InsertToTable&#34;是一个存储过程(我没有多少经验),但我正在假设它。以下是关于如何使用存储过程将DataTable插入Oracle数据库的一些想法:OracleDataAdapter

所以现在我希望我做对了,你可以解决你的问题(:

旧回答:

据我所知,这似乎是你试图插入一个DataRow,其中列数多于你填充的列数(Column-Name:command),而你的DataBase不接受该DataColumn的空值。因此,您需要更改DataBase以允许该列上的空值,或者在插入之前为该列赋值:

foreach (DataGridViewRow row in MyDGV.Rows){
if (row.Cells[0].Value == "Added")
{
   DataRow newRow = dt_Test.NewRow();

   newRow[0] = sequence+increase_seq;
   newRow[1] = 2";
   newRow[2] = row.Cells[1].Value;
   newRow["command"] = "someValue";

   dt_Test.Rows.Add(newRow.ItemArray);
   ++increase_seq;
 }

}

您是否尝试过使用DataBinding?在我看来,这应该会让事情变得更加轻松。

修改

好的,我弄错了。也许你的命令是错误的,但是当我们用Databinding查看它时它应该可行。这是Tutorial

您需要的是DB-Connection,DataAdapter以及DataSet和BindingSource。

您已经拥有DataAdapter(OracleDataAdapter da)和Connection(OracleConnection conn),但您没有正确使用它。

  1. 初始化DB-Connection

    OracleConnection conn = new OracleConnection(conn_string);

  2. 初始化DataAdapter

    string Query =&#34; SELECT * FROM YourTable&#34 ;; OracleDataAdapter da = new OracleDataAdapter(Query,conn);

  3. 填充数据集

    DataSet ds; da.Fill(ds,&#34; Tablename&#34;);

  4. 将数据绑定到BindingSource

    BindingSource bs = new BindingSource(ds,&#34; Tablename&#34;);

  5. 现在您可以填充DataGridView

    DataGridView dgv; dgv.DataSource = bs;

  6. 之后,您可以使用Data,在DataGridView等中编辑它们。在和中您可以生成Insertcommands等并更新数据(更改数据,新数据,无论您想要什么)。

    bs.EndEdit();
    
    OracleCommandBuilder ocb = new OracleCommandBuilder(da);
    da.UpdateCommand = ocb.GetUpdateCommand(true);
    da.InsertCommand = ocb.GetInsertCommand(true);
    da.DeleteCommand = ocb.GetDeleteCommand(true);
    
    da.Update(ds, "Tablename");
    

    这只是一个简短的概述,您需要更详细地查看它,即制作&#34; bs.EndEdit()&#34;&#34; bs.EndEdit()&#34;在执行da.Update()之前,所以进行了更改。

    我希望这会对你有所帮助。

    <强> EDIT2:

    这是一个更好的可查看代码,我也使用SQLConnection等进行此操作(因此可能需要更改一些调用)但是它与Oracle相同(前一段时间):

    string Query = "SELECT * FROM YourTable"; 
    DataSet ds;  
    OracleConnection conn;
    OracleDataAdapter da; 
    BindingSource bs;
    DataGridView dgv = new DataGridView();
    
    private void GetDataAndFillDataGridView()
    {
        conn = new OracleConnection(conn_string);
        OracleDataAdapter da = new OracleDataAdapter(Query, conn);
        da.Fill(ds, "Tablename");
        bs = new BindingSource(ds, "Tablename");
        dgv.DataSource = bs;
    }
    
    private void buttonSave_Click(object sender, EventArgs e)
    {
        bs.EndEdit();
    
        OracleCommandBuilder ocb = new OracleCommandBuilder(da);
        da.UpdateCommand = ocb.GetUpdateCommand(true);
        da.InsertCommand = ocb.GetInsertCommand(true);
        da.DeleteCommand = ocb.GetDeleteCommand(true);
    
        da.Update(ds, "Tablename");
    }