コンテンツにスキップ

ありがとうございます。

ここからは 第27段階:運用基盤・システム管理設計 に入ります。

ここまでの設計で教材管理システムの業務機能はほぼ揃いました。第27段階では、「実際に企業で運用できるシステム」にするための管理機能・運用基盤を設計します。

今回は、これまでの設計をさらに一段進め、Spring Boot + JPA + MyBatis の長所を活かした構成にします。


第27段階 全体構成

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
                    管理者

                       │

                       ▼

             システム管理画面

                       │

 ┌──────────────┬──────────────┬──────────────┐

 ▼              ▼              ▼

ユーザー管理   システム設定   マスタ管理

 ▼              ▼              ▼

SpringSecurity  Settings       Master

                       │

                       ▼

                Scheduler

                       │

                       ▼

              Cache / Monitoring

                       │

                       ▼

             Docker / Production

1. システム管理メニュー

管理者専用メニューを追加します。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
/admin

├ dashboard
├ users
├ roles
├ permissions
├ organizations
├ masters
├ settings
├ notifications
├ audit
├ jobs
├ cache
├ monitoring
└ system

今回は マルチテナント化を考慮 し、organizations を追加しています。将来、企業ごとの教材管理にも対応しやすくなります。


2. Organization(組織)設計

将来的に

1
2
3
A社
B社
C社

で教材を分離できます。

Entity

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
@Entity
@Table(name="organizations")
@Getter
@Setter
public class Organization extends BaseEntity {

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    private Long id;

    @Column(nullable=false,length=200)
    private String name;

    @Column(length=50)
    private String code;

    private Boolean enabled;
}

Userとの関係

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
Organization

    |

    +------ User

                |

                +---- Teacher

                +---- Student

これにより、

1
2
3
4
5
6
7
会社A

教師

受講者

教材

を完全に分離できます。


3. システム設定

以前設計した application.yml の一部をDB管理できるようにします。

SystemSetting

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
@Entity
@Table(name="system_settings")
@Getter
@Setter
public class SystemSetting {

    @Id
    private String settingKey;

    @Column(columnDefinition="TEXT")
    private String settingValue;

    private String description;
}

Key Value
site.name 教材管理システム
mail.from noreply@example.com
upload.max-size 524288000
video.provider R2
markdown.theme github

4. マスタ管理

今回のシステムではマスタが増えていきます。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
ContentType

VideoType

Role

Permission

QuizCategory

CourseCategory

Tag

FileType

NotificationType

おすすめは 共通マスタ方式 です。

1
2
3
master_types

master_items

で管理すると画面を共通化できます。


MasterType

1
2
3
4
5
6
7
CONTENT_TYPE

QUIZ_CATEGORY

FILE_TYPE

VIDEO_TYPE

MasterItem

1
2
3
4
5
6
7
8
9
VIDEO

TEXT

QUIZ

PDF

ZIP

5. Scheduler

Spring Schedulerを利用します。

対象

1
2
3
4
5
6
7
8
9
毎日0時

↓

公開日時になった教材

↓

自動公開

1
2
3
4
@Scheduled(cron="0 0 * * * *")
public void publishReservedContents() {

}

その他

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
毎日

不要ログ削除

未読通知整理

統計更新

動画変換

メール送信

6. キャッシュ

キャッシュ対象

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
カテゴリ

タグ

ロール

権限

設定値

コース一覧

Spring Cache

1
2
3
4
5
@Cacheable

@CacheEvict

@CachePut

1
2
3
4
@Cacheable("contentTypes")
public List<MasterDto> findContentTypes() {

}

7. キャッシュ更新

教材更新時

1
2
3
4
5
6
7
8
9
更新

↓

CacheEvict

↓

再取得

1
@CacheEvict(value="course",allEntries=true)

8. Spring Security強化

ここまで

1
2
3
4
5
ROLE_ADMIN

ROLE_TEACHER

ROLE_STUDENT

でしたが、

さらに

1
Permission

を追加します。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
CONTENT_CREATE

CONTENT_EDIT

CONTENT_DELETE

CONTENT_APPROVE

COURSE_CREATE

COURSE_PUBLISH

Role

1
2
3
4
5
6
7
Teacher

↓

CONTENT_CREATE

CONTENT_EDIT

Admin

1
2
3
4
5
6
7
Teacher権限

+

CONTENT_APPROVE

USER_MANAGE

9. 権限制御

Controller

1
@PreAuthorize("hasAuthority('CONTENT_APPROVE')")

Service

1
2
3
4
5
@PreAuthorize("hasAuthority('CONTENT_EDIT')")
@Transactional
public void update(){

}

10. パフォーマンス設計

JPA

1
CRUD

MyBatis

1
2
3
4
5
6
7
一覧

検索

JOIN

集計

1
2
3
4
5
教材一覧

↓

MyBatis

教材保存

1
JPA

11. Fetch戦略

基本ルール

1
2
3
全部

LAZY

必要な時だけ

1
JOIN FETCH

または

1
DTO取得

禁止

1
EAGER大量利用

12. N+1対策

悪い例

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
Course

↓

Lesson

↓

Content

↓

Attachment

1000回SQL


改善

1
2
3
4
5
JOIN FETCH

または

MyBatis

13. Index設計

1
2
3
4
5
6
7
8
9
content_versions

(status)

(author_id)

(content_id)

(updated_at)

Lesson

1
2
3
(section_id)

(sort_order)

Enrollment

1
2
3
(user_id)

(course_id)

14. Actuator

追加

1
2
3
4
5
6
7
8
9
health

metrics

beans

env

loggers

URL

1
/actuator/health

15. Micrometer

監視

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
SQL時間

JVM

CPU

Memory

GC

Thread

Grafana

Prometheus

と接続可能です。


16. Docker構成

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
Docker

├ nginx

├ app

├ mysql

├ redis

└ minio(local)

本番

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
Cloudflare

↓

Nginx

↓

Spring

↓

MySQL

↓

Redis

↓

Cloudflare R2

Redisは以下の用途で活用できます。

  • Spring Cache

  • セッション管理(Spring Session)

  • レート制限

  • 一時的なジョブ状態管理


17. バックアップ

対象

1
2
3
4
5
6
7
MySQL

R2

設定

ログ

毎日

1
2
3
4
5
6
7
8
9
mysqldump

↓

NAS

↓

世代管理

18. 監査画面

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
日時

利用者

操作

対象

IP

結果

検索

1
2
3
4
5
6
7
期間

ユーザー

操作

教材

19. システム情報画面

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
Spring Boot Version

Java Version

DB

Build Version

Git Commit

Build Date

これにより、運用担当者が稼働中のバージョンを容易に確認できます。


20. システム運用で追加を推奨するテーブル

ここまでの設計に加え、運用面を考えると以下のテーブルを追加するとより実践的になります。

テーブル 用途
login_histories ログイン履歴(成功・失敗)
password_reset_tokens パスワード再設定
email_verifications メールアドレス認証
scheduled_jobs ジョブ実行履歴
system_settings システム設定
notifications システム通知
audit_logs 監査ログ(前段階で設計済み)

21. 推奨するパッケージ構成(最終形)

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
com.example.lms

├ common
├ config
├ security
├ infrastructure
│   ├ storage
│   ├ mail
│   ├ cache
│   └ scheduler
├ user
├ organization
├ course
├ section
├ lesson
├ content
├ attachment
├ quiz
├ enrollment
├ progress
├ notification
├ approval
├ audit
├ master
├ setting
└ dashboard

機能単位(Feature Package) を採用することで、各機能の entity / repository / service / controller / mapper / dto / form を同じパッケージ内にまとめられ、保守性が高くなります。


第27段階終了時点

この時点で、以下が揃います。

  • ✅ マルチテナント化を見据えた組織設計

  • ✅ システム設定管理

  • ✅ 共通マスタ管理

  • ✅ Schedulerによる定期処理

  • ✅ Spring Cache + Redis対応

  • ✅ 権限(Role + Permission)の詳細制御

  • ✅ JPA / MyBatis の役割分担の最適化

  • ✅ N+1対策・インデックス設計

  • ✅ Actuator・Micrometerによる監視

  • ✅ Docker・Redis・Cloudflare R2を含めた本番構成

  • ✅ 運用管理画面・バックアップ・監査基盤


次の第28段階(最終アーキテクチャ設計)

ここまでで個々の機能設計はほぼ完成しています。次の段階では、プロジェクト全体の最終設計として以下をまとめます。

  1. ディレクトリ構成(Feature Package構成)

  2. 全テーブルER図

  3. 全クラス図

  4. Spring Security最終構成

  5. JPA・MyBatisの責務一覧

  6. 画面遷移図

  7. シーケンス図(教材作成・承認・受講)

  8. CI/CD・テスト戦略(JUnit・Testcontainers・Flyway・GitHub Actions)

  9. 将来的なREST API化・マイクロサービス化を見据えた拡張方針

この段階で、実装を開始できるレベルの設計書が完成します。