こんにちは、なかぜんです。Accessでサクッと作る原型は早いけど、運用が始まると「遅い」「壊れる」「誰も直せない」が顔を出しがち。現場で評価されるAccessアプリは、見た目の派手さよりも壊れない・速い・運用しやすいが揃っています。今日は私が現場で磨いてきた設計指針を、コードと具体策付きでまとめます。
1. まずは土台:バックエンド分離と接続戦略
1-1. テーブルはSQL Server/Azure SQLへ
MDB/ACCDBの共有は小規模でも破損・ロックで詰みます。バックエンドをSQL Serverに分離し、Accessはフォーム&レポートのフロントに徹させましょう。テーブルはリンクテーブルにし、更新はパススルークエリかADOで。
' ADOで明示トランザクション(SQL Server)
Dim cn As ADODB.Connection, cmd As ADODB.Command
Set cn = New ADODB.Connection
cn.Open "Provider=SQLOLEDB;Data Source=SRV01;Initial Catalog=AppDB;Integrated Security=SSPI;"
cn.BeginTrans
Set cmd = New ADODB.Command
Set cmd.ActiveConnection = cn
cmd.CommandText = "UPDATE dbo.Orders SET Status=? WHERE OrderID=?"
cmd.Parameters.Append cmd.CreateParameter(, adVarChar, adParamInput, 10, "Closed")
cmd.Parameters.Append cmd.CreateParameter(, adInteger, adParamInput, , 1024)
cmd.Execute
cn.CommitTrans
ポイント:DAOでリンクテーブル更新もOKですが、重い処理はサーバー側で完結。ストアドやパススルーでネットワーク往復を減らします。
1-2. 接続は「1フォーム=1接続」原則を避ける
フォームごとに接続を開閉すると遅延の温床。共通モジュールで接続を使い回し、エラー時のみ再確立します。
' シングルトン接続管理(簡易)
Option Compare Database
Option Explicit
Private m_cnn As ADODB.Connection
Public Function AppCnn() As ADODB.Connection
If m_cnn Is Nothing Then
Set m_cnn = New ADODB.Connection
m_cnn.Open CurrentProject.Connection ' リンクに乗る
End If
Set AppCnn = m_cnn
End Function
2. モデル設計:正規化しすぎない実務的データモデル
2-1. 第3正規形+集計のための補助列
過度な正規化はフォーム設計を複雑化。第3正規形を基準に、月次・担当者名などはビューや計算列で補助。検索キー用に非クラスタ化インデックスを適切に張るのが速度の肝。
2-2. 同時編集と排他戦略
Accessフォームは楽ですが、衝突に弱い。実運用では楽観ロック+タイムスタンプが扱いやすいです。
' 楽観ロックの衝突検知(擬似コード)
UPDATE dbo.Tasks
SET Title=@Title, UpdatedAt=SYSDATETIME()
WHERE TaskID=@TaskID AND RowVer=@RowVer;
IF @@ROWCOUNT = 0
RAISERROR('他ユーザーにより更新されました',16,1);
フォーム保存時にRowVerを渡し、0件更新なら差分表示→再読み込みの動線を用意。
3. フロント設計:速さと一貫性を両立
3-1. 名前規約とモジュール分割
frm_
フォーム、rpt_
レポート、qry_
クエリ、mdl_
モジュール、tbl_
テーブル。mdl_App
(起動・接続)、mdl_Repo
(DB操作)、mdl_Util
(共通関数)など役割で分割。
3-2. 「読み込み時に全部」は禁止
メインフォームは軽く。サブフォームのデータは必要時ロード。検索はテキスト変更で即時SQLを投げず、Enter確定 or ボタンで。
' 遅延ロードの例:検索ボタンクリック時だけ再クエリ
Private Sub btnSearch_Click()
Me.subItems.Form.Filter = BuildFilter(Me.txtKeyword, Me.cboStatus)
Me.subItems.Form.FilterOn = True
Me.subItems.Requery
End Sub
3-3. バリデーションはUI+DBの二重柵
フォーム側での必須チェックに加え、DB側にCHECK制約も置くと品質が安定します。
4. トランザクション&エラーハンドリング
現場評価を分ける最大の要素。失敗時に後片付けされるかで信頼感が変わります。
' 失敗しても状態を汚さないためのテンプレ
Public Sub DoInTx(ByVal action As String, ByVal work As String)
On Error GoTo EH
AppCnn.BeginTrans
AppCnn.Execute work
AppCnn.CommitTrans
Exit Sub
EH:
If AppCnn.Errors.Count > 0 Then AppCnn.RollbackTrans
Call LogError(action, Err.Number, Err.Description)
MsgBox "処理に失敗しました:" & action, vbExclamation
End Sub
Public Sub LogError(ByVal action As String, ByVal code As Long, ByVal msg As String)
AppCnn.Execute "INSERT INTO dbo.AppLog(Action, Code, Message, At) VALUES(" & _
Q(action) & "," & code & "," & Q(msg) & ",SYSDATETIME())"
End Sub
ログテーブルにはアクション名・ユーザー名・端末名・相関ID(GUID)を入れると調査が爆速になります。
5. レポートはバッチ化&非同期風に見せる
重い帳票はその場で生成せず、要求をキューに登録→サーバー側で生成→完了通知 or 置き場に保存、が快適。Accessではフォームで進捗を疑似表示し、完了時にファイルを開く形にします。
' 簡易キュー登録(擬似)
INSERT INTO dbo.ReportQueue(ReportName, ParamsJson, RequestedBy)
VALUES ('rpt_Sales', '{ "from":"2025-04-01","to":"2025-04-30"}', SYSTEM_USER);
6. 配布・更新の運用設計(ここが効く)
6-1. フロントはACCDE+自動配布
起動ランチャー(薄いACCDB)をショートカットにし、起動時に最新ACCDEをサーバーから自分のローカルへコピー→実行。
' ランチャー例(起動時)
Private Sub Form_Load()
Dim src As String, dst As String
src = "\\srv\release\app\Front.accde"
dst = Environ$("LOCALAPPDATA") & "\App\Front.accde"
If FileDateTime(src) > GetFileDate(dst) Then FileCopy src, dst
Application.FollowHyperlink dst
DoCmd.Quit
End Sub
6-2. バージョニングとマイグレーション
DBにSchemaVersion
テーブルを作り、起動時に不足スクリプトを順序実行。手作業での「差し替え忘れ」をなくします。
7. UI/UXの小ワザ:現場のストレスを下げる
- F2/F4/ESCなど標準キーの動作を尊重。独自ショートカットは衝突しないように。
- 重要ボタンは右下固定(保存/実行)、破壊的操作は赤+確認ダイアログ。
- 検索条件は直近値を保存し、再起動後も復元。
- 長処理はプログレスと予測時間(概算)を表示。
8. よくあるミスと回避策
- フォームのレコードソースに「SELECT *」:列追加で壊れる/帯域も無駄。列指定を徹底。
- 結合や集計をクライアント側で実行:重い処理はSQL側へ。
- 入力チェックをフォームだけに依存:DB制約もセットで。
- バックアップをファイルコピーのみ:SQLの整合バックアップ+復元手順をドキュメント化。
9. 応用ポイント:クラウドと連携して“寿命を伸ばす”
Accessを捨てるか残すかの二択ではなく、クラウドと役割分担が現実解です。参照系はPower BI、承認フローはPower Automate、外部公開はPower Apps or Web(ASP.NET等)。Accessは入力と帳票の生産性に集中させると全体が安定します。
まとめ:設計は「運用しやすさ」への投資
現場で評価されるAccessは、土台(バックエンド分離)、モデル(同時編集対策)、フロント(遅延ロードと一貫規約)、そして運用(配布・ログ・スキーマ管理)が噛み合っています。今日紹介したテンプレと方針をプロジェクトに差し込めば、壊れない・速い・運用しやすいに確実に近づきます。次の一歩は、既存プロジェクトに「接続管理」「ログ」「配布スクリプト」の三点をまず入れてみること。効果、出ますよ。
