【入門編】QueryDef実行時の「型不一致エラー」を未然に防ぐ:VBAデータ型とSQLデータ型のマッピング自動化 – Access VBA解析バイブル

スポンサーリンク

こんにちは。現場で「なぜか動かない」と悩むコードを何度も見てきたエンジニアです。

Access VBAで最も多くの開発者が挫折し、そして最も多く「逃げ道」を作ってしまうのが「SQLの組み立て」です。特に`QueryDef`を使って動的にクエリを作る際、日付や数値を文字列として結合しようとして、型不一致(Data Type Mismatch)の嵐に遭ったことはありませんか?

今日は、そんな「SQL組み立ての呪い」を解き、どんなデータ型でも安全にデータベースへ渡すための「型マッピング自動化」の奥義を伝授します。

—

なぜ「型不一致」は起きるのか?

SQLはテキストです。しかし、データベースはテキストの中に埋め込まれた値が「数値なのか、日付なのか、文字列なのか」を厳密に判別します。

多くの初心者はこう書きます。
`”WHERE ID = ” & myID`

これ自体は動きます。しかし、日付になるとどうでしょう?
`”WHERE BirthDate = ” & myDate`
これでは Access は「それは日付のつもり? それとも割り算の式?」と混乱してエラーを吐きます。SQLの世界では、日付は `#` で囲み、文字列は `’` で囲むという「お作法」があるからです。

このお作法をいちいち手書きで書くのは、プロの仕事ではありません。自動化しましょう。

—

型マッピング自動化の設計思想

「値」を「SQLに適した文字列」に変換する専用の関数(ガード関数)を作ります。この関数を通せば、どんな変数も安全なSQLのパーツに生まれ変わります。

実装コード:SQL安全化のマスターピース

この関数を標準モジュールに一つ置いておくだけで、あなたのコードは劇的に安定します。

‘ — SQLの型不一致を防ぐためのガード関数 —
Public Function ToSqlValue(val As Variant) As String
Select Case VarType(val)
Case vbNull, vbEmpty
ToSqlValue = “NULL”
Case vbString
‘ シングルクォートをエスケープして文字列化
ToSqlValue = “‘” & Replace(val, “‘”, “””) & “‘”
Case vbDate
‘ 日付は # で囲むのがAccess SQLの鉄則
ToSqlValue = “#” & Format(val, “yyyy/mm/dd hh:nn:ss”) & “#”
Case vbBoolean
‘ True/False を -1/0 に変換
ToSqlValue = IIf(val, -1, 0)
Case Else
‘ 数値はそのまま文字列化
ToSqlValue = CStr(val)
End Select
End Function

—

この関数の使い方:QueryDefでの実践

では、この関数を使って`QueryDef`を安全に実行する方法を見てみましょう。

Public Sub UpdateCustomerData(custID As Long, custName As String, birthDate As Date)
Dim db As DAO.Database
Dim qdf As DAO.QueryDef
Dim sql As String

Set db = CurrentDb

‘ SQLを組み立てる際、先ほどの関数で包むだけ!
sql = “UPDATE T_Customers SET ” & _
“CustomerName = ” & ToSqlValue(custName) & “, ” & _
“BirthDate = ” & ToSqlValue(birthDate) & ” ” & _
“WHERE ID = ” & ToSqlValue(custID)

‘ QueryDefを使って実行(デバッグ時はDebug.PrintでSQLを確認すること!)
Debug.Print sql

db.Execute sql, dbFailOnError

Set qdf = Nothing
Set db = Nothing
End Sub

ここがポイント!

1. VarType関数の活用: `VarType`を使うことで、VBAの変数が「今、何型なのか」を正確に判定しています。
2. 文字列のエスケープ: `Replace(val, “‘”, “””)` は非常に重要です。名前に「O’Reilly」のようなシングルクォートが含まれていても、これでエラーを回避できます。
3. 可読性の向上: SQLの中に `’` や `#` が散らばらないため、コードがスッキリして保守性が圧倒的に高まります。

—

最後に:なぜ「動的SQL」を極める必要があるのか

`QueryDef`を直接書き換える手法は、Accessというプラットフォームにおいて最もパフォーマンスが高く、柔軟な実装です。

「マクロの記録」や「クエリのデザインビュー」に頼る段階を卒業すると、あなたは「データそのものを自在に操るエンジニア」へと進化します。この関数を使いこなせれば、もう「型不一致」という言葉に怯えることはありません。

まずは、今のプロジェクトにあるSQL組み立て部分を、この `ToSqlValue` 関数に置き換えてみてください。驚くほどコードが頑強になるはずです。

ここをクリアすれば、Access VBAの基本はバッチリですよ。自信を持って進んでください!

タイトルとURLをコピーしました