質問

Here is my code:

private void UpdatePlatypus(String APetPlatypus) 
{
    oracleConnectionMainForm.Open();
    OracleCommand ocmd = new OracleCommand();
    ocmd.Connection = oracleConnectionMainForm;
    try 
    {
        ocmd.CommandText = @"<Update SQL statement that contains one parameter, like so: "WHERE DUCKBILLEDPLATYPUS = :PLATYPUS">)";
        ocmd.Parameters.Add("PLATYPUS", APetPlatypus);
        ocmd.ExecuteNonQuery();
    } 
    catch (Exception e) 
    {
        MessageBox.Show(String.Format("UpdatePlatypus failed with message {0}", e.Message));
    } 
    finally 
    {
        oracleConnectionMainForm.Close();
    }
    MessageBox.Show(String.Format("UpdatePlatypus to {0} succeeded", APetPlatypus));
}

In Toad, this SQL works fine -- I simply replace ":PLATYPUS" with the value "Phineas" in the Toad SQL editor, and the records are, indeed, updated, as the "27 records affected" message and a subsequent SQL Select that returns the updated records shows.

But in my C# app, it hangs on the call to ExecuteNonQuery()...I never see any of the messages - neither that the Update failed, nor that it succeeded - it simply hangs there, floating about in space like a smurf ball on the moon.

UPDATE

I copied some old Update code for dotConnect for Oracle that worked, but it still does the same thing (hangs on the call to ExecuteNonQuery()

private void UpdatePlatypus(String APetPlatypus) {

    OracleCommand ocmd;

    oracleConnectionMainForm.Open();
    String update = @"<same update sql as above>";
    ocmd = new OracleCommand(update, oracleConnectionMainForm);
    ocmd.CommandType = CommandType.Text;
    try {
        OracleParameter p_DuckbilledPlatypus =
        new OracleParameter("DIVISION", OracleDbType.NVarChar, ParameterDirection.Input);
        p_DuckbilledPlatypus.Value = APetPlatypus;
        ocmd.Parameters.Add(p_DuckbilledPlatypus);
        using (var transaction = oracleConnectionMainForm.BeginTransaction()) {
            try {
                ocmd.Transaction = transaction;
                ocmd.ExecuteNonQuery();
                transaction.Commit();
            } catch (Exception ex) {
                transaction.Rollback();
                throw;
            }
        }
    } catch (Exception e) {
        MessageBox.Show(String.Format("UpdatePlatypus failed with message {0}", e.Message));
    } finally {
        oracleConnectionMainForm.Close();
    }
    MessageBox.Show(String.Format("UpdatePlatypus to {0} succeeded", APetPlatypus));
}

ANOTHER UPDATE

Is it possible that the SQL statement can be too confusing for whatever it is that parses it, even though it is valid SQL?

Again, this query runs fine in Toad, but it is quite complex: it contains TWO nested Select statements, like so:

Update <tableName> 
Set <col = value> 
where <col> in 
(select bla from bla where bla = :Platypus) 
and (bla is null or bla)
and bla in (select distinct bla from bla 
where bla = bla and bla is not null)

YET ANOTHER UPDATE

If I simplify the query by replacing the sub-selects with parameters (that are supplied via the results returned from those atmoic SQL select statements) it runs (and almost instantaneously, at that).

So, I guess the nested subselects were too much for whatever it is that parses the Update statement...

役に立ちましたか?

解決

Did you hit "commit" button in TOAD after executing your UPDATE ? It looks that it hangs simply becacuse of the lock on the updated rows.

BTW: In TOAD, menu Database -> Monitor -> Session Browser, find your "C#" or TOAD oracle sessions and look at the "Locks" tab, there are two sub-tabs "Blocking locks" and "Blocked locks". Is there any entry when your session hangs ?

他のヒント

After you ExecuteNonQuery() call ExecuteNonQuery again with CommandText COMMIT. Oracle says it documentation that it commit automatically but actually it's not. It's committing only when you close the connection.

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top