2011-07-26 4 views
10

Je suis sûr qu'il ya une raison extrêmement simple que celui-ci la ligne ne fonctionne pas, mais il a éludé la semaine dernière, donc je suis en espérant que quelqu'un d'autre remarqueront ma faute.DataAdapter.Update() ne pas mettre à jour la base de données

Je travaille sur ce projet depuis plusieurs semaines à un mois. J'ai utilisé un mélange d'ancien DataAdapter, CommandBuiler, etc. avec un codage linq à sql sur une base de données, avec plusieurs formulaires d'application Windows. Ce formulaire particulier modifie ou supprime des lignes de la base de données à l'aide d'un DataAdapter, d'un ensemble de données et d'un constructeur de commandes. Cela a bien fonctionné jusqu'à ce que je change d'ordinateur. Maintenant, l'ensemble de données est en cours de mise à jour, mais la base de données ne l'est pas.

Voici le code complet de cette forme:

private void exitToolStripMenuItem_Click(object sender, EventArgs e) 
{ 
    if (MessageBox.Show("Exit Cook Book?", "Exit?", MessageBoxButtons.OKCancel) == DialogResult.OK) 
    { 
     Application.Exit(); 
    } 
} 

private void goBackToolStripMenuItem_Click(object sender, EventArgs e) 
{ 
    AddRecipe goBack = new AddRecipe(); 

    Close(); 
    goBack.Show(); 
} 

private void helpToolStripMenuItem_Click(object sender, EventArgs e) 
{ 
    MessageBox.Show("Scan through the Cook Book to find recipes that you wish to edit or delete.", "Help!"); 
} 

SqlConnection con; 
SqlDataAdapter dataAdapt; 
DataSet dataRecipe; 
SqlCommandBuilder cb; 

int MaxRows = 0; 
int inc = 0; 


private void EditRecipe_Load(object sender, EventArgs e) 
{ 
    con = new SqlConnection(); 
    dataRecipe = new DataSet(); 

    con.ConnectionString = "Data Source=.\\SQLEXPRESS;AttachDbFilename=|DataDirectory|\\Recipes.mdf;Integrated Security=True;User Instance=True"; 

     con.Open(); 

     //MessageBox.Show("Database Open"); 

     string sql = "SELECT* From CookBookRecipes"; 
     dataAdapt = new SqlDataAdapter(sql, con); 

     dataAdapt.Fill(dataRecipe, "CookBookRecipes"); 
     NavigateRecords(); 
     MaxRows = dataRecipe.Tables["CookBookRecipes"].Rows.Count; 

     con.Close(); 
} 


private void NavigateRecords() 
{ 
    DataRow dRow = dataRecipe.Tables["CookBookRecipes"].Rows[inc]; 

    tbRName.Text = dRow.ItemArray.GetValue(0).ToString(); 
    listBox1.SelectedItem = dRow.ItemArray.GetValue(1).ToString(); 
    tbRCreate.Text = dRow.ItemArray.GetValue(2).ToString(); 
    tbRIngredient.Text = dRow.ItemArray.GetValue(3).ToString(); 
    tbRPrep.Text = dRow.ItemArray.GetValue(4).ToString(); 
    tbRCook.Text = dRow.ItemArray.GetValue(5).ToString(); 
    tbRDirections.Text = dRow.ItemArray.GetValue(6).ToString(); 
    tbRYield.Text = dRow.ItemArray.GetValue(7).ToString(); 
    textBox1.Text = dRow.ItemArray.GetValue(8).ToString(); 
} 

private void btnNext_Click(object sender, EventArgs e) 
{ 
    if (inc != MaxRows - 1) 
    { 
     inc++; 
     NavigateRecords(); 
    } 
    else 
    { 
     MessageBox.Show("That's the last recipe of your Cook Book!", "End"); 
    } 
} 

private void btnBack_Click(object sender, EventArgs e) 
{ 
    if (inc > 0) 
    { 
     inc--; 
     NavigateRecords(); 
    } 
    else 
    { 
     MessageBox.Show("This is the first recipe of your Cook Book!", "Start"); 
    } 
} 

private void btnSave_Click(object sender, EventArgs e) 
{ 
    cb = new SqlCommandBuilder(dataAdapt); 

    DataRow daRow = dataRecipe.Tables["CookBookRecipes"].Rows[inc]; 

    daRow[0] = tbRName.Text; 
    daRow[1] = listBox1.SelectedItem.ToString(); 
    daRow[2] = tbRCreate.Text; 
    daRow[3] = tbRIngredient.Text; 
    daRow[4] = tbRPrep.Text; 
    daRow[5] = tbRCook.Text; 
    daRow[6] = tbRDirections.Text; 
    daRow[7] = tbRYield.Text; 
    daRow[8] = textBox1.Text; 

    if (MessageBox.Show("You wish to save your updates?", "Save Updates?", MessageBoxButtons.OKCancel) == DialogResult.OK) 
    { 

     dataAdapt.Update(dataRecipe, "CookBookRecipes"); 

     MessageBox.Show("Recipe Updated", "Update"); 
    } 
} 

private void btnDelete_Click(object sender, EventArgs e) 
{ 
    SqlCommandBuilder cb; 
    cb = new SqlCommandBuilder(dataAdapt); 

    if (MessageBox.Show("You wish to DELETE this recipe?", "Delete?", MessageBoxButtons.OKCancel) == DialogResult.OK) 
    { 
     dataRecipe.Tables["CookBookRecipes"].Rows[inc].Delete(); 
     MaxRows--; 
     inc = 0; 
     NavigateRecords(); 

     dataAdapt.Update(dataRecipe, "CookBookRecipes"); 

     MessageBox.Show("Your Recipe has been Deleted", "Delete"); 
    } 
} 

Ceci est censé mettre à jour la table:

dataAdapt.Update(dataRecipe, "CookBookRecipes"); 

Je ne reçois pas des erreurs, mais la table de données vient de gagner » t mise à jour.

Merci d'avance pour votre aide, et laissez-moi savoir si vous avez besoin de plus amples informations.

+0

Avez-vous déjà eu une réponse à ce sujet? J'ai le même problème avec un projet que j'ai construit pour gérer mes mises à jour de Db. En l'utilisant à partir d'un projet, il échoue comme vous le constatez. En l'utilisant d'un autre, cela fonctionne bien. Donc je suis vraiment perplexe. J'ai même comparé le SqlAdapter.GetUpdateCommand(). CommandText des deux et ils sont exactement les mêmes que les éléments de données ItemArray. Cependant, je ne comprends pas vraiment tous les paramètres de la commande INSERT générée automatiquement. RowStates sont également les mêmes. Frustrant. –

Répondre

2

Qu'est-ce que la mise à jour SqlCommand pour ressembler? Je vois la commande mais je ne vois aucun SqlText, c'est ce qui vous manque.

Vous devez définir ce que .Update fait en fixant .UpdateCommand propriété sur le SqlDataAdapter

Ce lien donne une assez bonne répartition sur la façon de s'y prendre: http://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqldataadapter.updatecommand.aspx

+0

SqlText? Où pourrais-je mettre ça? – Miffed

+0

Merci. Mais comment pourrais-je utiliser cela dans mon code? – Miffed

11

Afin de mettre à jour les données sur la base de données votre SqlDataAdapter doit avoir son ensemble de propriétés InsertCommand, UpdateCommand, DeleteCommand. L'instance SqlCommandBuilder que vous avez créée contient ces commandes, mais vous devez les définir sur votre SqlDataAdapter.

Dans d'autres mondes: Quelque part entre

SqlCommandBuilder cb; 
cb = new SqlCommandBuilder(dataAdapt); 

et

dataAdapt.Update(dataRecipe, "CookBookRecipes"); 

vous devez

dataAdapt.DeleteCommand = cb.GetDeleteCommand(true); 
dataAdapt.UpdateCommand = cb.GetUpdateCommand(true); 
dataAdapt.InsertCommand = cb.GetInsertCommand(true); 
+2

recherché partout, et personne n'a mentionné liant les requêtes que le générateur de commande génère à l'adaptateur de données. Merci pour cela. – Ajibola

+1

Juste une note que si vous spécifiez le dataAdaptor lors de la création de SqlCommandBuilder vous n'avez pas besoin de définir les commandes, le SqlCommandBuilder s'enregistre comme un écouteur. [Documentation] (https://msdn.microsoft.com/fr-fr/library/w0154tsb (v = vs.110) .aspx) – nicV

0

Vous pourriez avoir besoin

DataAdapeter.AcceptChanges() 
0

J'ai eu le même problème: Rempli un nouveau Dataset avec quelques nouvelles lignes, mais rien ne se passait sur la mise à jour. J'ai utilisé le MySqlDataAdapter qui fonctionne de manière similaire.

Il s'avère que lorsque vous avez besoin de l'InsertCommand de MySqlCommandBuilder, vous devez spécifier l'attribut rowstate ajouté. Voir aussi: MSDN

0
//change this line 

DataRow daRow = dataRecipe.Tables["CookBookRecipes"].NewRow(); 

daRow[0] = tbRName.Text; 
daRow[1] = listBox1.SelectedItem.ToString(); 
daRow[2] = tbRCreate.Text; 
daRow[3] = tbRIngredient.Text; 
daRow[4] = tbRPrep.Text; 
daRow[5] = tbRCook.Text; 
daRow[6] = tbRDirections.Text; 
daRow[7] = tbRYield.Text; 
daRow[8] = textBox1.Text; 

if (MessageBox.Show("You wish to save your updates?", "Save Updates?", MessageBoxButtons.OKCancel) == DialogResult.OK) 
{ 
//add & change this too 
dataRecipe.Tables["CookBookRecipes"].Rows.Add(daRow); 
    dataAdapt.Update(dataRecipe, "CookBookRecipes"); 

    MessageBox.Show("Recipe Updated", "Update"); 
} 

}

0

Essayez la source ci-dessous.

private void btnSave_Click(object sender, EventArgs e) 
{ 
    cb = new SqlCommandBuilder(dataAdapt); 

    //Old source: DataRow daRow = dataRecipe.Tables["CookBookRecipes"].Rows[inc]; 

    //Added source code 
    DataRow daRow = dataRecipe.Tables["CookBookRecipes"].NewRow(); 

    //Added source code 
    dataRecipe.Tables["CookBookRecipes"].AddRow(daRow); 

    daRow.BeginEdit(); 
    daRow[0] = tbRName.Text; 
    daRow[1] = listBox1.SelectedItem.ToString(); 
    daRow[2] = tbRCreate.Text; 
    daRow[3] = tbRIngredient.Text; 
    daRow[4] = tbRPrep.Text; 
    daRow[5] = tbRCook.Text; 
    daRow[6] = tbRDirections.Text; 
    daRow[7] = tbRYield.Text; 
    daRow[8] = textBox1.Text; 
    daRow.EndEdit(); 

    //Reset state of rows to unchanged 
    dataRecipe.Tables["CookBookRecipes"].AcceptChanges(); 
    //Set modified. The dataAdapt will call update stored procedured 
    //for the row that has Modifed row state. 
    //You can also try SetAdded() method for new row you want to insert 
    daRow.SetModified(); 

    if (MessageBox.Show("You wish to save your updates?", "Save Updates?", MessageBoxButtons.OKCancel) == DialogResult.OK) 
    { 

     dataAdapt.Update(dataRecipe, "CookBookRecipes"); 

     MessageBox.Show("Recipe Updated", "Update"); 
    } 
} 
0

Ajout AcceptChangesDuringUpdate avant mise à jour fonctionne pour moi, par exemple:

foreach (string tableName in tableNames) 
     {    
      da = new SqlDataAdapter("SELECT * FROM " + tableName, cn); 
      cb = new SqlCommandBuilder(da); //initialise the update, insert and delete commands of da 
      da.AcceptChangesDuringUpdate = true; 
      da.Update(myDataSet, tableName);    
     } 
0

J'ai rencontré le même problème. Mon dataadapter.fill fonctionne mais dataadapter.update ne fonctionne pas. J'ai réalisé que le problème était que ma table de base de données ne contient pas de clé primaire. Après avoir modifié ma table pour inclure une colonne avec la clé primaire, dataadapter.fill fonctionne. Espérons que cela aide quelqu'un.

Questions connexes