- - PR -
OleDbCommandBuilderが生成するSQL
1
投稿者 | 投稿内容 | ||||
---|---|---|---|---|---|
|
投稿日時: 2007-06-14 16:40
すみません。どなたか、お知恵拝借できないでしょうか?
asp.net2.0 + accessにてwebアプリ作成中です。 OleDbCommandBuilderが生成するSQLがおかしくて困っております。 列に[c_id][日付][1_no][1_memo]をもつaccessのテーブルがあり、 [c_id]を主キーにしております。ボタンクリックにより、 [c_id]にはセッションid(guid)を入れ、その他の列にはフォームの内容を入れます。 その後フォームが修正され、再度ボタンが押された時は、先のセッションidがあるかどうか調べ、あれば、そのレコードを修正する様にしたいのです。 しかし、その再度ボタンが押された時にDataAdapter.Updateにてエラーが出ます。 ================================= クエリ式 '((c_id = ?) AND ((? = 1 AND 日付 IS NULL) OR (日付 = ?)) AND ((? = 1 AND 1_no IS NULL) OR (1_no = ?)))' の 構文エラー ================================= 上記の通りOleDbCommandBuilderで生成したクエリがおかしいのですが、 SQLがなんでこんな風になるのでしょうか? テーブルは先に示した極、単純なものです。 以下は一部分かりやすく修正したソースです。 Protected Sub Btn_Keitai_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles Btn_Keitai.Click 'アダプタとコマンドの用意 Dim m_Adapter As New OleDbDataAdapter() Dim m_Command = New OleDbCommand() Dim m_Connection = New OleDbConnection() Dim SM_SQLCONNECTION_STRING_TEMPCS As String = "接続文字列" m_Connection.ConnectionString = SM_SQLCONNECTION_STRING_TEMPCS m_Command.Connection = m_Connection m_Command.CommandText = "select * from tempcs" m_Adapter.SelectCommand = m_Command 'データセットへの読み込み Dim TempCsDataSet As DataSet = New DataSet() Dim dt As DataTable = TempCsDataSet.Tables("tempcs") Dim ModifyRow As DataRow m_Adapter.MissingSchemaAction = MissingSchemaAction.AddWithKey m_Adapter.Fill(TempCsDataSet, "tempcs") '主キーがSession("TempGuid")のレコードが存在しなければ、レコード追加 '既に存在していれば、そのレコードを修正 If dt.Rows.Find(Session("TempGuid")) Is Nothing Then ModifyRow = dt.NewRow() ModifyRow("c_id") = Session("TempGuid") ModifyRow("日付") = Now() ModifyRow("1_no") = "01" ModifyRow("1_memo") = "01のメモ" dt.Rows.Add(ModifyRow) Else ModifyRow = dt.Rows.Find(Session("TempGuid")) ModifyRow("c_id") = Session("TempGuid") ModifyRow("日付") = Now() ModifyRow("1_no") = "02" ModifyRow("1_memo") = "02のメモ" End If 'コマンド生成とアップデート Dim TempCsBuilder As OleDbCommandBuilder = New OleDbCommandBuilder(m_Adapter) m_Adapter.Update(TempCsDataSet, "tempcs") End Sub | ||||
|
投稿日時: 2007-06-14 17:28
NAL-6295です。
多分、 QuotePrefixとQuoteSuffixにそれぞれ、"["と"]"を定義してあげれば、 構文エラーは回避されます。 ちなみに、オプティミスティック同時実行制御が有効な場合CommandBuilderで生成するクエリは基本的にすべての項目が変更されていない場合のみ更新するというような形に生成されます。 | ||||
|
投稿日時: 2007-06-14 18:25
NAL-6295様。ご指摘の通りで解決いたしました。
素人なもので、他のみなさんからすれば、「こんなことで。。。」 とお思いでしょうが、3日も悩んで、憂鬱な日々を送っていました。 そもそもエラーメッセージにupdate句がないのがおかしいのだと思いこんでました。 NAL-6295「様様」です。本当にありがとうございました。 | ||||
|
投稿日時: 2007-06-14 18:30
識別子の先頭に数字を使っているからとかそういう話なのかなぁ。
| ||||
|
投稿日時: 2007-06-14 20:13
一郎様。
レスありがとうございます。 DBの列名ですよね? DB、ソースともに以下の様に変更してみましたら、 1_no →no 1_memo →memo 今度は、1回目のupdateの段階で、 INSERT INTO ステートメントの構文エラーです。 というエラーになってしまいました。 益々なぞですが、NAL-6295さんご指摘の TempCsBuilder.QuotePrefix = "[" TempCsBuilder.QuoteSuffix = "]" を入れるとエラーはなくなります。 | ||||
|
投稿日時: 2007-06-15 02:40
NAL-6295です。
名前に空白や予約済みトークンなどの文字を含む(たとえば先頭が数字等)場合 PrefixとSuffixである[]で囲ってあげることで、 「ここからここまでが列名ですよ〜。」 と規定してあげることでエラーが出なくなります。 ちなみにSQLServerは[]、Oracleは""となります。 [ メッセージ編集済み 編集者: NAL-6295 編集日時 2007-06-15 02:41 ] |
1