0

データベースに新しいディスカッション スレッドを挿入するディスカッション フォーラム Web サイトの挿入関数を作成しました。機能は次のとおりです。

public int createDiscuss(Discussion dis)
    {
        query = "insert into [MyForums].[dbo].[Discussions](desid, text, date, time, replyto, uid, isPrivate) values(@id, @text, @date, @time, @replyto, @uid, @pvp)";
        string did=getDesID();
        if (did == null)
            return -1;
        try
        {
            com = new SqlCommand(query, con);
            com.Parameters.AddWithValue("@id", did); 
            com.Parameters.AddWithValue("@text", dis.gettext()); 
            com.Parameters.AddWithValue("@date", SqlDateTime.Parse(DateTime.Now.ToString())); 
            com.Parameters.AddWithValue("@time", SqlDateTime.Parse(DateTime.Now.ToString()));
            com.Parameters.AddWithValue("@replyto", dis.getreplyto());
            com.Parameters.AddWithValue("@uid", dis.getuid());
            if (dis.IsPrivate() == false)
            { com.Parameters.AddWithValue("@pvp", 1); }
            else
            { com.Parameters.AddWithValue("@pvp", 2);  }
            con.Open();
            int r=com.ExecuteNonQuery();
            if (r <= 0)
            {
                return -1;
            }
            con.Close();

        }
        catch (Exception)
        {
            return -1;
        }
        return 0;
    }

この関数は、-1 を返すよりもエラーまたは例外に遭遇した場合、呼び出し元の関数によってチェックされ、呼び出し元の関数はエラーを表示します。問題は、この挿入関数がクエリを実行していないことです。値が AddWithValue 関数に引数として適切に渡されているかどうかを確認したところ、asp.net ページで指定されたとおりにすべての値が渡されていることがわかりました。しかし、制御が com.ExecuteNonQuery() 関数になると。エラーである-1を返しています。誰かが私のコードの何が問題なのか教えてもらえますか? または、com.ExecuteNonQuery()が影響を受けた行を返さない理由を確認するにはどうすればよいですか??


この例外表示

A first chance exception of type 'System.Threading.ThreadAbortException' occurred in mscorlib.dll
An exception of type 'System.Threading.ThreadAbortException' occurred in mscorlib.dll but was not handled in user code
4

5 に答える 5

2

そうは言っても、ここでは SQL プロファイラーがあなたの味方です。生成された SQL をプロファイラーから取得し、SQL mgmt studio で実行します。答えは自明であると 99% 確信しています。そうでない場合は、プロファイラーから生成された sql で回答を更新してください。そこから取得します。

SQL プロファイラーに関するガイダンスが必要な場合は、単純な Google 検索で多くのオプションが表示されます。SQL プロファイラー検索

于 2012-04-27T16:15:57.470 に答える
2
  • finallyブロックで接続を閉じる必要があります。以前に例外が発生するcon.Close();と、接続が開いたままになります。それがここでのエラーである可能性があります(のスコープに応じてcon

  • 例外を飲み込むのではなく、ログに記録してください。その後、エラーを適切に調べることができます。ログがない場合は、ログを取得します。ただし、それまでの間、デバッガーを使用してキャッチした例外を確認してください。

  • また、接続エラーとアプリケーションの慢性的なバグを区別できるように、より具体的な例外をキャッチする必要があります。呼び出しているメソッドによってスローされる可能性が高い例外を確認します。たとえば、con.Open() はこれらをスローできます。

SqlException

InvalidOperationException

したがって、それらを最初にキャッチし、Exception最後にキャッチします。

例外のタイプに応じて、異なるエラー コードを返したり、異なるレベルの重大度でログを記録したりできます。


また、データベースに対してそのクエリを実行し、何が起こるかを確認する方法 (プロファイリングまたは単にコピー アンド ペーストを使用) を考え出します。たとえば、次の部分は正しいですか。

        com.Parameters.AddWithValue("@date",
            SqlDateTime.Parse(DateTime.Now.ToString())); 
        com.Parameters.AddWithValue("@time",
            SqlDateTime.Parse(DateTime.Now.ToString()));

@date@time同一です。データベースの値も同一で、列は両方とも文字列を期待していますか?

于 2012-04-27T17:07:40.260 に答える
1

基本的なデバッグを行う必要があります。次のようにコードをセットアップします。

catch(Exception ex)
{
  return -1;
}

戻り時にブレークポイントを設定し、例外が何であるかを確認します。

于 2012-04-27T16:14:34.477 に答える
0

int r=com.ExecuteNonQuery();おそらくコードに到達していません。con.Open();メソッドのエラーである可能性があります。

catch 内で新しい例外をスローして、実際のエラーを表示していただけますか?

于 2012-04-27T16:16:25.473 に答える
0

現在のコードの課題は、いくつかの異なるシナリオで "-1" が返されることです。

  • 例外発生
  • getDesID の結果が null です
  • INSERT ステートメントが行の挿入に失敗する

これを確認する簡単な方法の 1 つは、各障害点から異なる数値 (-2 または -3 など) を返すことです。そうすれば、コードを大幅に変更したり、デバッガーを接続したりすることなく、エラーが発生している場所を特定できます。

問題はおそらく SQL INSERT ステートメントではないようです。ステートメント自体が無効であるか、データベースの制約に違反している場合、SQL Server は例外を発生させ、例外ハンドラーによってキャッチされます。

于 2012-04-27T16:53:47.380 に答える