create-entity-server 0.0.25 → 0.0.27

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (80) hide show
  1. package/package.json +1 -1
  2. package/template/.env.example +38 -0
  3. package/template/configs/auth/cors.json +15 -0
  4. package/template/configs/auth/identity.json +27 -0
  5. package/template/configs/auth/jwt.json +12 -0
  6. package/template/configs/{oauth.json → auth/oauth.json} +7 -4
  7. package/template/configs/auth/password.json +33 -0
  8. package/template/configs/auth/privacy_policy.json +28 -0
  9. package/template/configs/{security.json → auth/security.json} +4 -2
  10. package/template/configs/auth/two_factor.json +12 -0
  11. package/template/configs/database.json +0 -159
  12. package/template/configs/database.json.example +186 -0
  13. package/template/configs/extensions/backup.json +46 -0
  14. package/template/configs/extensions/pg.json +37 -0
  15. package/template/configs/extensions/storage.json +148 -0
  16. package/template/configs/extensions/tax-invoice.json +59 -0
  17. package/template/configs/keys/.gitkeep +0 -0
  18. package/template/configs/keys/apns.p8.example +7 -0
  19. package/template/configs/keys/firebase.pem.example +7 -0
  20. package/template/configs/notification/alimtalk.json +75 -0
  21. package/template/configs/{push.json → notification/push.json} +1 -2
  22. package/template/configs/notification/sms.json +54 -0
  23. package/template/configs/notification/smtp.json +43 -0
  24. package/template/configs/server.json +2 -0
  25. package/template/entities/README.md +20 -23
  26. package/template/entities/System/Auth/account.json +17 -1
  27. package/template/entities/System/Auth/account_audit.json +23 -0
  28. package/template/entities/System/Auth/account_device.json +63 -0
  29. package/template/entities/System/Auth/account_login_log.json +54 -0
  30. package/template/entities/System/Auth/account_oauth.json +45 -0
  31. package/template/entities/System/Auth/api_keys.json +1 -1
  32. package/template/entities/System/Auth/identity_verification.json +95 -0
  33. package/template/entities/System/Auth/license.json +1 -1
  34. package/template/entities/System/Auth/password_history.json +20 -0
  35. package/template/entities/System/Auth/rbac_roles.json +1 -1
  36. package/template/entities/System/Backup/backup_log.json +62 -0
  37. package/template/entities/System/Email/smtp_log.json +83 -0
  38. package/template/entities/System/Email/smtp_msg.json +104 -0
  39. package/template/entities/System/Notification/alimtalk_log.json +45 -0
  40. package/template/entities/System/Notification/alimtalk_msg.json +39 -0
  41. package/template/entities/System/Notification/friendtalk_log.json +48 -0
  42. package/template/entities/System/Notification/friendtalk_msg.json +63 -0
  43. package/template/entities/System/Notification/sms_log.json +26 -0
  44. package/template/entities/System/Notification/sms_msg.json +52 -0
  45. package/template/entities/System/Notification/sms_verification.json +40 -0
  46. package/template/entities/System/Payment/pg_cancel.json +45 -0
  47. package/template/entities/System/Payment/pg_order.json +88 -0
  48. package/template/entities/System/Payment/pg_webhook_log.json +37 -0
  49. package/template/entities/System/Push/push_log.json +71 -0
  50. package/template/entities/System/Push/push_msg.json +55 -0
  51. package/template/entities/System/Storage/file_backup_log.json +46 -0
  52. package/template/entities/System/Storage/file_download_log.json +41 -0
  53. package/template/entities/System/Storage/file_meta.json +59 -0
  54. package/template/entities/System/system_audit_log.json +2 -1
  55. package/template/entities/company.json +1 -1
  56. package/template/entities/{product.json → goods.json} +6 -10
  57. package/template/entities/todo.json +1 -1
  58. package/template/samples/entities/README.md +2 -2
  59. package/template/scripts/generate-env-keys.sh +16 -0
  60. package/template/templates/email/account/dormancy_warning.html +20 -0
  61. package/template/templates/email/account/password_expiry_warning.html +21 -0
  62. package/template/templates/email/auth/2fa_disabled.html +23 -0
  63. package/template/templates/email/auth/2fa_recovery_regenerated.html +31 -0
  64. package/template/templates/email/auth/2fa_setup_complete.html +43 -0
  65. package/template/templates/email/auth/email_verification.html +18 -0
  66. package/template/templates/email/auth/force_reset.html +18 -0
  67. package/template/templates/email/auth/password_reset.html +19 -0
  68. package/template/templates/email/auth/verification.html +15 -0
  69. package/template/templates/email/auth/verification_link.html +25 -0
  70. package/template/templates/email/auth/welcome.html +18 -0
  71. package/template/templates/email/backup/backup_completed.html +35 -0
  72. package/template/templates/email/backup/backup_failed.html +27 -0
  73. package/template/templates/email/backup/backup_partial.html +31 -0
  74. package/template/templates/email/layout.html +47 -0
  75. package/template/templates/email/order/order_confirmation.html +30 -0
  76. package/template/templates/email/storage/storage_quota_exceeded.html +37 -0
  77. package/template/templates/email/storage/storage_quota_warning.html +37 -0
  78. package/template/configs/cors.json +0 -7
  79. package/template/configs/jwt.json +0 -8
  80. package/template/entities/Account/account_audit.json +0 -16
@@ -0,0 +1,37 @@
1
+ {
2
+ "enabled": false,
3
+ "default": "toss_payments",
4
+ "webhook_secret": "${PG_WEBHOOK_SECRET}",
5
+ "order_id_prefix": "ORD",
6
+ "success_url": "/payment/success",
7
+ "fail_url": "/payment/fail",
8
+ "webhook_url": "/v1/pg/webhook",
9
+ "amount_limit": {
10
+ "min": 100,
11
+ "max": 10000000
12
+ },
13
+ "workers": 2,
14
+ "providers": [
15
+ {
16
+ "driver": "toss_payments",
17
+ "client_key": "${TOSS_CLIENT_KEY}",
18
+ "secret_key": "${TOSS_SECRET_KEY}",
19
+ "api_url": "https://api.tosspayments.com",
20
+ "api_version": "2022-11-16"
21
+ },
22
+ {
23
+ "_comment": "NHN KCP (Phase 2)",
24
+ "driver": "kcp",
25
+ "site_cd": "${KCP_SITE_CD}",
26
+ "secret_key": "${KCP_SECRET_KEY}",
27
+ "api_url": "https://api.pay.kcp.co.kr"
28
+ },
29
+ {
30
+ "_comment": "KG 이니시스 (Phase 2)",
31
+ "driver": "inicis",
32
+ "store_id": "${INICIS_STORE_ID}",
33
+ "sign_key": "${INICIS_SIGN_KEY}",
34
+ "api_url": "https://api.inicis.com"
35
+ }
36
+ ]
37
+ }
@@ -0,0 +1,148 @@
1
+ {
2
+ "enabled": true,
3
+ "default": "local-main",
4
+ "max_file_size_mb": 20,
5
+ "storages": {
6
+ "local-main": {
7
+ "driver": "local",
8
+ "root": "./uploads"
9
+ },
10
+
11
+ "s3-aws": {
12
+ "driver": "s3",
13
+ "bucket": "my-entity-files",
14
+ "region": "ap-northeast-2",
15
+ "access_key": "${AWS_ACCESS_KEY_ID}",
16
+ "secret_key": "${AWS_SECRET_ACCESS_KEY}",
17
+ "prefix": "entity-files"
18
+ },
19
+
20
+ "s3-r2": {
21
+ "driver": "s3",
22
+ "bucket": "my-files",
23
+ "region": "auto",
24
+ "endpoint": "https://${CF_ACCOUNT_ID}.r2.cloudflarestorage.com",
25
+ "access_key": "${R2_ACCESS_KEY}",
26
+ "secret_key": "${R2_SECRET_KEY}",
27
+ "prefix": "",
28
+ "_comment": "Cloudflare R2 (S3 호환) — 이그레스 무료"
29
+ },
30
+
31
+ "s3-b2": {
32
+ "driver": "s3",
33
+ "bucket": "my-files",
34
+ "region": "us-west-004",
35
+ "endpoint": "https://s3.us-west-004.backblazeb2.com",
36
+ "access_key": "${B2_KEY_ID}",
37
+ "secret_key": "${B2_APP_KEY}",
38
+ "_comment": "Backblaze B2 (S3 호환) — S3 대비 1/4 가격"
39
+ },
40
+
41
+ "s3-wasabi": {
42
+ "driver": "s3",
43
+ "bucket": "my-files",
44
+ "region": "ap-northeast-2",
45
+ "endpoint": "https://s3.ap-northeast-2.wasabisys.com",
46
+ "access_key": "${WASABI_ACCESS_KEY}",
47
+ "secret_key": "${WASABI_SECRET_KEY}",
48
+ "_comment": "Wasabi (S3 호환) — 저가 hot storage"
49
+ },
50
+
51
+ "s3-do-spaces": {
52
+ "driver": "s3",
53
+ "bucket": "my-files",
54
+ "region": "sgp1",
55
+ "endpoint": "https://sgp1.digitaloceanspaces.com",
56
+ "access_key": "${DO_SPACES_KEY}",
57
+ "secret_key": "${DO_SPACES_SECRET}",
58
+ "_comment": "DigitalOcean Spaces (S3 호환)"
59
+ },
60
+
61
+ "s3-minio": {
62
+ "driver": "s3",
63
+ "bucket": "entity-files",
64
+ "region": "us-east-1",
65
+ "endpoint": "http://minio.internal:9000",
66
+ "access_key": "minioadmin",
67
+ "secret_key": "minioadmin",
68
+ "_comment": "MinIO (S3 호환) — 자체 호스팅"
69
+ },
70
+
71
+ "s3-ncloud": {
72
+ "driver": "s3",
73
+ "bucket": "my-files",
74
+ "region": "kr-standard",
75
+ "endpoint": "https://kr.object.ncloudstorage.com",
76
+ "access_key": "${NCLOUD_ACCESS_KEY}",
77
+ "secret_key": "${NCLOUD_SECRET_KEY}",
78
+ "_comment": "Naver Cloud Object Storage (S3 호환)"
79
+ },
80
+
81
+ "azure-example": {
82
+ "driver": "azure",
83
+ "container": "files",
84
+ "account_name": "${AZURE_STORAGE_ACCOUNT}",
85
+ "account_key": "${AZURE_STORAGE_KEY}",
86
+ "prefix": "entity-files"
87
+ },
88
+
89
+ "gcs-example": {
90
+ "driver": "gcs",
91
+ "bucket": "my-entity-files",
92
+ "credentials_file": "./configs/keys/gcp-sa.json",
93
+ "prefix": "entity-files",
94
+ "_comment": "GKE/Cloud Run에서는 credentials_file 불필요 (Workload Identity)"
95
+ },
96
+
97
+ "sftp-example": {
98
+ "driver": "sftp",
99
+ "host": "nas.company.com",
100
+ "port": 22,
101
+ "user": "backup",
102
+ "private_key_file": "./configs/keys/backup_rsa",
103
+ "root": "/volume1/entity-files",
104
+ "_comment": "NAS/온프레미스 서버 연동"
105
+ },
106
+
107
+ "swift-kt": {
108
+ "driver": "swift",
109
+ "auth_url": "https://ssproxy.ucloudbiz.olleh.com/identity/v3",
110
+ "container": "my-files",
111
+ "user": "${KT_USER}",
112
+ "password": "${KT_PASSWORD}",
113
+ "tenant_name": "${KT_TENANT}",
114
+ "domain_name": "Default",
115
+ "region": "kr1",
116
+ "_comment": "KT Cloud Storage (OpenStack Swift)"
117
+ }
118
+ },
119
+ "thumbnail": {
120
+ "enabled": true,
121
+ "auto_orient": true,
122
+ "sizes": {
123
+ "sm": {
124
+ "width": 160,
125
+ "height": 160
126
+ },
127
+ "md": {
128
+ "width": 480,
129
+ "height": 480
130
+ },
131
+ "lg": {
132
+ "width": 1024,
133
+ "height": 1024
134
+ }
135
+ },
136
+ "quality": 85
137
+ },
138
+ "quota": {
139
+ "default_limit_gb": 0,
140
+ "threshold_percent": 80,
141
+ "notify": ["log", "smtp"]
142
+ },
143
+ "gc": {
144
+ "enabled": true,
145
+ "orphan_threshold_hours": 24,
146
+ "cron": "0 3 * * *"
147
+ }
148
+ }
@@ -0,0 +1,59 @@
1
+ {
2
+ "enabled": true,
3
+ "default": "barobill",
4
+ "workers": 2,
5
+ "queue_size": 100,
6
+ "dispatch_interval_sec": 10,
7
+ "max_retries": 3,
8
+ "providers": [
9
+ {
10
+ "driver": "barobill",
11
+ "cert_key": "${TAXINVOICE_CERT_KEY}",
12
+ "corp_num": "${TAXINVOICE_CORP_NUM}",
13
+ "user_id": "${TAXINVOICE_USER_ID}",
14
+ "api_endpoint": "https://barobill.co.kr/TAPI/TaxInvoiceService.asmx",
15
+ "timeout_sec": 30
16
+ },
17
+ {
18
+ "driver": "popbill",
19
+ "link_id": "${TAXINVOICE_LINK_ID}",
20
+ "secret_key": "${TAXINVOICE_SECRET_KEY}",
21
+ "corp_num": "${TAXINVOICE_CORP_NUM}",
22
+ "api_endpoint": "https://taxinvoice.linkhub.co.kr",
23
+ "timeout_sec": 30
24
+ },
25
+ {
26
+ "driver": "bolta",
27
+ "api_key": "${TAXINVOICE_API_KEY}",
28
+ "customer_key": "${TAXINVOICE_CUSTOMER_KEY}",
29
+ "api_endpoint": "https://xapi.bolta.io/v1",
30
+ "timeout_sec": 30
31
+ },
32
+ {
33
+ "driver": "smartbill",
34
+ "api_key": "${TAXINVOICE_API_KEY}",
35
+ "corp_num": "${TAXINVOICE_CORP_NUM}",
36
+ "api_endpoint": "https://nxapi.smartbill.co.kr",
37
+ "timeout_sec": 30
38
+ },
39
+ {
40
+ "driver": "esero",
41
+ "corp_num": "${TAXINVOICE_CORP_NUM}",
42
+ "cert_path": "/run/secrets/esero_cert.pfx",
43
+ "cert_pass": "${TAXINVOICE_CERT_PASS}",
44
+ "api_endpoint": "https://esero.go.kr/api/v1",
45
+ "timeout_sec": 60
46
+ }
47
+ ],
48
+ "nts": {
49
+ "taxation_option": 1,
50
+ "taxation_add_tax_allow": 0,
51
+ "tax_exemption_option": 1,
52
+ "tax_exemption_add_tax_allow": 0
53
+ },
54
+ "notify": ["log", "smtp", "alimtalk"],
55
+ "sync": {
56
+ "state_sync_interval_min": 10,
57
+ "max_list_days": 200
58
+ }
59
+ }
File without changes
@@ -0,0 +1,7 @@
1
+ -----BEGIN PRIVATE KEY-----
2
+ (샘플) Apple Developer Console → Certificates, Identifiers & Profiles
3
+ → Keys → "+" 버튼으로 APNs 키 생성 후 다운로드한 .p8 파일 내용을 여기에 붙여넣으세요.
4
+
5
+ 실제 키는 아래와 같은 형식입니다:
6
+ MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQg...
7
+ -----END PRIVATE KEY-----
@@ -0,0 +1,7 @@
1
+ -----BEGIN PRIVATE KEY-----
2
+ (샘플) Firebase Console → 프로젝트 설정 → 서비스 계정 → 새 비공개 키 생성
3
+ 으로 다운로드한 JSON 파일의 private_key 값을 여기에 붙여넣으세요.
4
+
5
+ 실제 키는 아래와 같은 형식입니다:
6
+ MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQC...
7
+ -----END PRIVATE KEY-----
@@ -0,0 +1,75 @@
1
+ {
2
+ "_comment": "알림톡(Kakao Alimtalk) 설정 예시 — 4개 프로바이더 전체 구성",
3
+ "enabled": false,
4
+ "default": "aligo",
5
+ "sender_key": "YOUR_KAKAO_SENDER_KEY",
6
+ "workers": 2,
7
+ "dispatch_interval_sec": 5,
8
+ "queue_size": 200,
9
+ "max_retries": 3,
10
+ "fallback": {
11
+ "enabled": true,
12
+ "sender": "01012345678",
13
+ "type": "sms"
14
+ },
15
+ "template_cache_ttl_sec": 300,
16
+ "providers": {
17
+ "aligo": {
18
+ "driver": "aligo",
19
+ "api_key": "YOUR_ALIGO_API_KEY",
20
+ "user_id": "YOUR_ALIGO_USER_ID",
21
+ "sender_key": "YOUR_KAKAO_SENDER_KEY"
22
+ },
23
+ "solapi": {
24
+ "driver": "solapi",
25
+ "api_key": "YOUR_SOLAPI_API_KEY",
26
+ "api_secret": "YOUR_SOLAPI_API_SECRET",
27
+ "pf_id": "YOUR_SOLAPI_PF_ID",
28
+ "sender_key": "YOUR_KAKAO_SENDER_KEY"
29
+ },
30
+ "ppurio": {
31
+ "driver": "ppurio",
32
+ "account": "YOUR_PPURIO_ACCOUNT",
33
+ "api_key": "YOUR_PPURIO_API_KEY",
34
+ "sender_key": "YOUR_KAKAO_SENDER_KEY"
35
+ },
36
+ "nhn": {
37
+ "driver": "nhn_cloud",
38
+ "app_key": "YOUR_NHN_APP_KEY",
39
+ "secret_key": "YOUR_NHN_SECRET_KEY",
40
+ "sender_key": "YOUR_KAKAO_SENDER_KEY"
41
+ }
42
+ },
43
+ "templates": [
44
+ {
45
+ "code": "AUTH_001",
46
+ "description": "인증번호 발송",
47
+ "variables": ["code", "minutes"],
48
+ "fallback_sms": true
49
+ },
50
+ {
51
+ "code": "ORDER_001",
52
+ "description": "주문 접수 확인",
53
+ "variables": ["name", "order_no", "amount"],
54
+ "fallback_sms": true
55
+ },
56
+ {
57
+ "code": "DELIVERY_001",
58
+ "description": "배송 시작 알림",
59
+ "variables": ["name", "tracking_no", "courier"],
60
+ "fallback_sms": true
61
+ },
62
+ {
63
+ "code": "PAYMENT_001",
64
+ "description": "결제 완료",
65
+ "variables": ["name", "amount", "method"],
66
+ "fallback_sms": false
67
+ },
68
+ {
69
+ "code": "NOTICE_001",
70
+ "description": "일반 공지",
71
+ "variables": ["title", "content"],
72
+ "fallback_sms": false
73
+ }
74
+ ]
75
+ }
@@ -2,7 +2,7 @@
2
2
  "workers": 2,
3
3
  "queue_size": 500,
4
4
  "fcm": {
5
- "enabled": true,
5
+ "enabled": false,
6
6
  "type": "service_account",
7
7
  "project_id": "your-firebase-project-id",
8
8
  "private_key_id": "abc123def456...",
@@ -16,7 +16,6 @@
16
16
  },
17
17
  "apns": {
18
18
  "enabled": false,
19
- "_comment": "APNs 직접 전송 (미구현 - 예약)",
20
19
  "key_file": "./configs/keys/apns.p8",
21
20
  "key_id": "ABCDE12345",
22
21
  "team_id": "FGHIJ67890",
@@ -0,0 +1,54 @@
1
+ {
2
+ "enabled": true,
3
+ "default": "aligo",
4
+ "sender": "01012345678",
5
+ "workers": 2,
6
+ "queue_size": 200,
7
+ "dispatch_interval_sec": 5,
8
+ "max_retries": 3,
9
+ "auto_lms": true,
10
+ "lms_threshold_bytes": 80,
11
+ "providers": {
12
+ "aligo": {
13
+ "driver": "aligo",
14
+ "api_key": "${ALIGO_API_KEY}",
15
+ "user_id": "${ALIGO_USER_ID}",
16
+ "sender": "01012345678"
17
+ },
18
+ "solapi": {
19
+ "driver": "solapi",
20
+ "api_key": "${SOLAPI_API_KEY}",
21
+ "api_secret": "${SOLAPI_API_SECRET}",
22
+ "sender": "01012345678"
23
+ },
24
+ "ppurio": {
25
+ "driver": "ppurio",
26
+ "account": "${PPURIO_ACCOUNT}",
27
+ "api_key": "${PPURIO_API_KEY}",
28
+ "sender": "01012345678"
29
+ },
30
+ "nhn": {
31
+ "driver": "nhn_cloud",
32
+ "app_key": "${NHN_SMS_APP_KEY}",
33
+ "secret_key": "${NHN_SMS_SECRET_KEY}",
34
+ "sender": "01012345678"
35
+ },
36
+ "aws": {
37
+ "driver": "aws_sns",
38
+ "region": "ap-northeast-2",
39
+ "access_key": "${AWS_ACCESS_KEY}",
40
+ "secret_key": "${AWS_SECRET_KEY}"
41
+ }
42
+ },
43
+ "rate_limit": {
44
+ "per_number_per_minute": 5,
45
+ "per_minute": 60,
46
+ "per_hour": 500
47
+ },
48
+ "verification": {
49
+ "code_length": 6,
50
+ "ttl_sec": 180,
51
+ "max_attempts": 5,
52
+ "cooldown_sec": 60
53
+ }
54
+ }
@@ -0,0 +1,43 @@
1
+ {
2
+ "enabled": false,
3
+ "default": "main",
4
+ "workers": 2,
5
+ "queue_size": 200,
6
+ "dispatch_interval_sec": 5,
7
+ "max_retries": 3,
8
+
9
+ "providers": {
10
+ "main": {
11
+ "host": "smtp.gmail.com",
12
+ "port": 587,
13
+ "username": "${SMTP_USERNAME}",
14
+ "password": "${SMTP_PASSWORD}",
15
+ "from": "noreply@example.com",
16
+ "from_name": "My Service",
17
+ "encryption": "starttls",
18
+ "auth": "plain",
19
+ "timeout_sec": 30,
20
+ "max_connections": 5
21
+ },
22
+ "transactional": {
23
+ "host": "smtp.sendgrid.net",
24
+ "port": 465,
25
+ "username": "apikey",
26
+ "password": "${SENDGRID_API_KEY}",
27
+ "from": "alerts@example.com",
28
+ "from_name": "My Service Alerts",
29
+ "encryption": "ssl",
30
+ "auth": "plain"
31
+ }
32
+ },
33
+
34
+ "templates": {
35
+ "dir": "./configs/templates/email",
36
+ "default_layout": "layout.html"
37
+ },
38
+
39
+ "rate_limit": {
40
+ "per_minute": 0,
41
+ "per_hour": 0
42
+ }
43
+ }
@@ -1,7 +1,9 @@
1
1
  {
2
2
  "namespace": "entity-prod",
3
+ "public_url": "https://api.example.com",
3
4
  "default_email_domain": "example.com",
4
5
  "language": "ko",
6
+ "timezone": "Asia/Seoul",
5
7
  "environment": "production",
6
8
  "port": 47200,
7
9
  "enable_auto_schema_sync": true,
@@ -4,26 +4,25 @@
4
4
 
5
5
  ## 예제 엔티티 목록
6
6
 
7
- | 파일 | 설명 | 주요 특징 |
8
- | -------------------------------------------------------------------------- | -------------- | ------------------------------------------------------------------------- |
9
- | [todo.json](#1-todojson) | 할 일 목록 | 기본 인덱스, 해시 필드 |
10
- | [product.json](#2-productjson) | 제품 관리 | 유니크 제약, reset_defaults 시딩 |
11
- | [examples/Auth/account.json](#3-examplesauthaccountjson) | 사용자 관리 | rbac_role, 인증 훅 / **JWT 사용 시 필수** |
12
- | [examples/Auth/rbac_roles.json](#4-examplesauthrbac_rolesjson) | RBAC 역할 정의 | permissions 포함 5개 역할, reset-all 시 자동 시딩 / **RBAC 사용 시 필수** |
13
- | [examples/Auth/api_keys.json](#5-examplesauthauthapi_keysjson) | API 키 관리 | HMAC 인증 키, 역할 연결, user_seq 연결 / **HMAC 사용 시 필수** |
14
- | [license.json](#6-licensejson) | 라이선스 관리 | 계약/만료일, 유니크 제약, 자동 시딩 |
15
- | [company.json](#7-companyjson) | 회사 정보 | license_scope, 사업자번호 해시, 캐시 |
16
- | [examples/Account/account_audit.json](#8-examplesaccountaccount_auditjson) | 감사 로그 | INSERT 전용, 훅으로 자동 기록 |
7
+ | 파일 | 설명 | 주요 특징 |
8
+ | -------------------------------------------------------------- | -------------- | ------------------------------------------------------------------------- |
9
+ | [todo.json](#1-todojson) | 할 일 목록 | 기본 인덱스, 해시 필드 |
10
+ | [goods.json](#2-goodsjson) | 상품 관리 | 유니크 제약, reset_defaults 시딩 |
11
+ | [examples/Auth/account.json](#3-examplesauthaccountjson) | 사용자 관리 | rbac_role, 인증 훅 / **JWT 사용 시 필수** |
12
+ | [examples/Auth/rbac_roles.json](#4-examplesauthrbac_rolesjson) | RBAC 역할 정의 | permissions 포함 5개 역할, reset-all 시 자동 시딩 / **RBAC 사용 시 필수** |
13
+ | [examples/Auth/api_keys.json](#5-examplesauthauthapi_keysjson) | API 키 관리 | HMAC 인증 키, 역할 연결, user_seq 연결 / **HMAC 사용 시 필수** |
14
+ | [license.json](#6-licensejson) | 라이선스 관리 | 계약/만료일, 유니크 제약, 자동 시딩 |
15
+ | [company.json](#7-companyjson) | 회사 정보 | license_scope, 사업자번호 해시, 캐시 |
17
16
 
18
17
  ## 문서 바로가기
19
18
 
20
- | 섹션 | 내용 |
21
- | ------------------------------------------------------------ | ----------------------------------------- |
22
- | [포함된 예제](#포함된-예제) | 각 예제 파일 상세 설명 |
23
- | [엔티티 설정 규칙](#엔티티-설정-규칙) | 자동 추론 필드, Types, index 형식, 복합키 |
24
- | [훅 (Hooks)](#훅-hooks) | SQL 훅, Entity 훅, 실행 시점, 템플릿 변수 |
25
- | [라이선스 스코프](#라이선스-스코프란) | 멀티테넌트 / 단일 시스템 모드 |
26
- | [Entity Config Guide](../../docs/ops/entity-config-guide.md) | 전체 엔티티 설정 레퍼런스 |
19
+ | 섹션 | 내용 |
20
+ | -------------------------------------------------------------------- | ----------------------------------------- |
21
+ | [포함된 예제](#포함된-예제) | 각 예제 파일 상세 설명 |
22
+ | [엔티티 설정 규칙](#엔티티-설정-규칙) | 자동 추론 필드, Types, index 형식, 복합키 |
23
+ | [훅 (Hooks)](#훅-hooks) | SQL 훅, Entity 훅, 실행 시점, 템플릿 변수 |
24
+ | [라이선스 스코프](#라이선스-스코프란) | 멀티테넌트 / 단일 시스템 모드 |
25
+ | [Entity Config Guide](../../docs/guides/data/entity-config-guide.md) | 전체 엔티티 설정 레퍼런스 |
27
26
 
28
27
  ---
29
28
 
@@ -38,7 +37,7 @@
38
37
  - 기본 인덱스 필드 (`title`, `status`, `created_time`)
39
38
  - 해시 필드 (`user_id`) - 암호화되어 저장
40
39
 
41
- ### 2. product.json
40
+ ### 2. goods.json
42
41
 
43
42
  제품 관리 엔티티
44
43
 
@@ -50,7 +49,7 @@
50
49
 
51
50
  ### 3. examples/Auth/account.json
52
51
 
53
- 사용자 관리 엔티티 (`entities/examples/Auth/` 에 위치 → 배포 시 `dist/entities/System/Auth/account.json`)
52
+ 사용자 관리 엔티티 (`entities-example/Auth/` 에 위치 → 배포 시 `dist/entities/System/Auth/account.json`)
54
53
 
55
54
  > **⚠️ JWT 인증을 사용하려면 필수입니다.**
56
55
  > HMAC 인증만 사용하는 경우에는 필요하지 않습니다.
@@ -68,7 +67,7 @@
68
67
 
69
68
  ### 4. examples/Auth/rbac_roles.json
70
69
 
71
- RBAC 역할 정의 엔티티 (`entities/examples/Auth/` 에 위치 → 배포 시 `dist/entities/System/Auth/rbac_roles.json`)
70
+ RBAC 역할 정의 엔티티 (`entities-example/Auth/` 에 위치 → 배포 시 `dist/entities/System/Auth/rbac_roles.json`)
72
71
 
73
72
  > **⚠️ RBAC 인증을 사용하려면 필수입니다.**
74
73
  > `reset-all` 실행 시 `reset_defaults`의 5개 역할이 자동 시딩됩니다.
@@ -84,7 +83,7 @@ RBAC 역할 정의 엔티티 (`entities/examples/Auth/` 에 위치 → 배포
84
83
 
85
84
  ### 5. examples/Auth/api_keys.json
86
85
 
87
- API 키 관리 엔티티 (`entities/examples/Auth/` 에 위치 → 배포 시 `dist/entities/System/Auth/api_keys.json`)
86
+ API 키 관리 엔티티 (`entities-example/Auth/` 에 위치 → 배포 시 `dist/entities/System/Auth/api_keys.json`)
88
87
 
89
88
  > **⚠️ HMAC 인증을 사용하려면 필수입니다.**
90
89
  > `reset-all` 실행 시 admin 역할의 API 키 1개가 자동 생성되며 `key_value`와 `hmac_secret`이 출력됩니다.
@@ -130,8 +129,6 @@ API_KEY=<admin-key> ./scripts/api-keys.sh delete 3
130
129
  - 해시 필드 (`tax_id`) - 사업자번호 암호화
131
130
  - 캐시 활성화 (TTL 300초)
132
131
 
133
- ### 8. examples/Account/account_audit.json
134
-
135
132
  사용자 감사 로그 엔티티
136
133
 
137
134
  **특징**:
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "account",
3
- "description": "JWT 로그인/인증 계정 예제",
3
+ "description": "JWT 로그인/인증 계정 예제. 사용자 환경에 맞게 index·fields를 자유롭게 확장할 수 있습니다.",
4
4
  "index": {
5
5
  "user_seq": {
6
6
  "comment": "사용자번호"
@@ -41,6 +41,22 @@
41
41
  "params": ["${new.seq}", "INSERT", "${new.email}"],
42
42
  "async": false
43
43
  }
44
+ ],
45
+ "after_update": [
46
+ {
47
+ "type": "sql",
48
+ "query": "INSERT INTO account_audit (account_seq, action, email, created_time) VALUES (?, ?, ?, NOW())",
49
+ "params": ["${new.seq}", "UPDATE", "${new.email}"],
50
+ "async": false
51
+ }
52
+ ],
53
+ "after_delete": [
54
+ {
55
+ "type": "sql",
56
+ "query": "INSERT INTO account_audit (account_seq, action, email, created_time) VALUES (?, ?, ?, NOW())",
57
+ "params": ["${old.seq}", "DELETE", "${old.email}"],
58
+ "async": false
59
+ }
44
60
  ]
45
61
  }
46
62
  }
@@ -0,0 +1,23 @@
1
+ {
2
+ "name": "account_audit",
3
+ "description": "account 감사 로그. account.json 훅(after_insert/after_update/after_delete)에 의해 자동 기록됩니다. 사용자 환경에 맞게 index·fields를 자유롭게 확장할 수 있습니다.",
4
+ "hard_delete": true,
5
+ "read_only": true,
6
+ "compress": true,
7
+ "index": {
8
+ "account_seq": {
9
+ "comment": "계정 seq (JWT 인증 시 account.seq 참조. HMAC은 nullable)",
10
+ "type": "bigint",
11
+ "nullable": true
12
+ },
13
+ "action": {
14
+ "comment": "작업 유형 (after_insert → INSERT, after_update → UPDATE, after_delete → DELETE)",
15
+ "type": ["INSERT", "UPDATE", "DELETE"],
16
+ "required": true
17
+ },
18
+ "email": {
19
+ "comment": "작업 대상 계정 이메일",
20
+ "nullable": true
21
+ }
22
+ }
23
+ }