userfront로 리펙토링 완료
This commit is contained in:
1 parent
6d88c81217
commit
1aaa772907
154 files changed
+339
-314
No files matched your search
+2
-2
@@ -11,7 +11,7 @@ DB_PORT=5432
|
||||
CLICKHOUSE_PORT_HTTP=8123
|
||||
CLICKHOUSE_PORT_NATIVE=9000
|
||||
BACKEND_PORT=3000
|
||||
FRONTEND_PORT=5000
|
||||
USERFRONT_PORT=5000
|
||||
|
||||
# --- Database Credentials (PostgreSQL) ---
|
||||
DB_USER=baron
|
||||
@@ -47,7 +47,7 @@ ADMIN_EMAIL=admin@baron.co.kr
|
||||
ADMIN_PASSWORD=adminPasswordIsNotSimple
|
||||
|
||||
# --- URLs for Proxy/Handoff ---
|
||||
FRONTEND_URL=https://sso.hmac.kr # 프론트엔드 접속 주소 (이메일/SMS 링크 생성 시 사용)
|
||||
USERFRONT_URL=https://sso.hmac.kr # 프론트엔드 접속 주소 (이메일/SMS 링크 생성 시 사용)
|
||||
BACKEND_URL=https://sso.hmac.kr # 프론트엔드에서 참조할 백엔드 API 주소
|
||||
|
||||
# IDP_PROVIDER는 우선순위 순으로 콤마 구분 (예: Kratos/Hydra 우선, Descope 백업)
|
||||
|
||||
@@ -86,17 +86,17 @@ jobs:
|
||||
provenance: false
|
||||
sbom: false
|
||||
|
||||
- name: Temporarily update frontend nginx port
|
||||
- name: Temporarily update userfront nginx port
|
||||
run: |
|
||||
sed -i 's/listen 5000;/listen 80;/g' frontend/nginx.conf
|
||||
sed -i 's/proxy_pass http:\/\/baron_backend:3000;/proxy_pass http:\/\/baron_backend:3010;/g' frontend/nginx.conf
|
||||
sed -i 's/listen 5000;/listen 80;/g' userfront/nginx.conf
|
||||
sed -i 's/proxy_pass http:\/\/baron_backend:3000;/proxy_pass http:\/\/baron_backend:3010;/g' userfront/nginx.conf
|
||||
|
||||
- name: Build and push frontend RC image
|
||||
- name: Build and push userfront RC image
|
||||
uses: docker/build-push-action@v5
|
||||
with:
|
||||
context: ./frontend
|
||||
file: ./frontend/Dockerfile
|
||||
context: ./userfront
|
||||
file: ./userfront/Dockerfile
|
||||
push: true
|
||||
tags: ${{ vars.HARBOR_HOSTNAME }}/baron_sso/frontend:${{ steps.rc_calculator.outputs.new_rc_tag }}
|
||||
tags: ${{ vars.HARBOR_HOSTNAME }}/baron_sso/userfront:${{ steps.rc_calculator.outputs.new_rc_tag }}
|
||||
provenance: false
|
||||
sbom: false
|
||||
@@ -13,8 +13,8 @@ on:
|
||||
required: true
|
||||
type: boolean
|
||||
default: true
|
||||
run_frontend_tests:
|
||||
description: "Run frontend Flutter tests"
|
||||
run_userfront_tests:
|
||||
description: "Run userfront Flutter tests"
|
||||
required: true
|
||||
type: boolean
|
||||
default: true
|
||||
@@ -46,9 +46,9 @@ jobs:
|
||||
working-directory: backend
|
||||
args: --enable-only=gofmt,gofumpt
|
||||
|
||||
- name: Analyze Flutter frontend
|
||||
- name: Analyze Flutter userfront
|
||||
run: |
|
||||
cd frontend
|
||||
cd userfront
|
||||
flutter analyze --no-fatal-warnings --no-fatal-infos
|
||||
|
||||
backend-tests:
|
||||
@@ -85,9 +85,9 @@ jobs:
|
||||
cd backend
|
||||
go test -v ./...
|
||||
|
||||
frontend-tests:
|
||||
userfront-tests:
|
||||
needs: lint
|
||||
if: ${{ inputs.run_frontend_tests == true }}
|
||||
if: ${{ inputs.run_userfront_tests == true }}
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Checkout code
|
||||
@@ -99,11 +99,11 @@ jobs:
|
||||
channel: "stable"
|
||||
cache: true
|
||||
|
||||
- name: Run frontend tests
|
||||
- name: Run userfront tests
|
||||
run: |
|
||||
cd frontend
|
||||
cd userfront
|
||||
if [ -d test ]; then
|
||||
flutter test
|
||||
else
|
||||
echo "No frontend tests: skipping (test/ directory not found)."
|
||||
echo "No userfront tests: skipping (test/ directory not found)."
|
||||
fi
|
||||
@@ -49,12 +49,12 @@ jobs:
|
||||
--src-tls-verify=false --dest-tls-verify=false \
|
||||
"docker://${HARBOR_HOSTNAME}/baron_sso/backend:${BASE_TAG}" "docker://${HARBOR_HOSTNAME}/baron_sso/backend:${RE_TAG}"
|
||||
|
||||
# Re-tag frontend image
|
||||
echo "Re-tagging frontend image..."
|
||||
# Re-tag userfront image
|
||||
echo "Re-tagging userfront image..."
|
||||
skopeo copy --preserve-digests \
|
||||
--src-creds "${HARBOR_USER}:${HARBOR_PASSWORD}" --dest-creds "${HARBOR_USER}:${HARBOR_PASSWORD}" \
|
||||
--src-tls-verify=false --dest-tls-verify=false \
|
||||
"docker://${HARBOR_HOSTNAME}/baron_sso/frontend:${BASE_TAG}" "docker://${HARBOR_HOSTNAME}/baron_sso/frontend:${RE_TAG}"
|
||||
"docker://${HARBOR_HOSTNAME}/baron_sso/userfront:${BASE_TAG}" "docker://${HARBOR_HOSTNAME}/baron_sso/userfront:${RE_TAG}"
|
||||
|
||||
echo "final_image_tag=${RE_TAG}" >> "$GITHUB_OUTPUT"
|
||||
|
||||
@@ -67,7 +67,7 @@ jobs:
|
||||
env:
|
||||
IMAGE_TAG: ${{ steps.retag.outputs.final_image_tag }}
|
||||
BACKEND_IMAGE_NAME: ${{ vars.HARBOR_HOSTNAME }}/baron_sso/backend
|
||||
FRONTEND_IMAGE_NAME: ${{ vars.HARBOR_HOSTNAME }}/baron_sso/frontend
|
||||
USERFRONT_IMAGE_NAME: ${{ vars.HARBOR_HOSTNAME }}/baron_sso/userfront
|
||||
DEPLOY_PATH: ${{ vars.PROD_DEPLOY_PATH }}
|
||||
PROD_HOST: ${{ vars.PROD_HOST }}
|
||||
PROD_USER: ${{ vars.PROD_USER }}
|
||||
@@ -102,7 +102,7 @@ jobs:
|
||||
"CLICKHOUSE_USER=${{ vars.PROD_CLICKHOUSE_USER }}" \
|
||||
"CLICKHOUSE_PASSWORD=${{ secrets.PROD_CLICKHOUSE_PASSWORD }}" \
|
||||
"BACKEND_PORT=${{ vars.PROD_BACKEND_PORT }}" \
|
||||
"FRONTEND_PORT=${{ vars.PROD_FRONTEND_PORT }}" \
|
||||
"USERFRONT_PORT=${{ vars.PROD_USERFRONT_PORT }}" \
|
||||
"DB_USER=${{ vars.PROD_DB_USER }}" \
|
||||
"DB_PASSWORD=${{ secrets.PROD_DB_PASSWORD }}" \
|
||||
"DB_NAME=${{ vars.PROD_DB_NAME }}" \
|
||||
@@ -119,7 +119,7 @@ jobs:
|
||||
"AWS_ACCESS_KEY_ID=${{ vars.AWS_ACCESS_KEY_ID }}" \
|
||||
"AWS_SECRET_ACCESS_KEY=${{ secrets.AWS_SECRET_ACCESS_KEY }}" \
|
||||
"AWS_SES_SENDER=${{ vars.AWS_SES_SENDER }}" \
|
||||
"FRONTEND_URL=${{ vars.PROD_FRONTEND_URL }}" \
|
||||
"USERFRONT_URL=${{ vars.PROD_USERFRONT_URL }}" \
|
||||
"BACKEND_URL=${{ vars.PROD_BACKEND_URL }}" \
|
||||
> .env
|
||||
|
||||
@@ -131,7 +131,7 @@ jobs:
|
||||
echo "${HARBOR_ROBOT_KEY}" | ssh "${PROD_USER}@${PROD_HOST}" \
|
||||
"export DEPLOY_PATH='${DEPLOY_PATH}'; \
|
||||
export BACKEND_IMAGE_NAME='${BACKEND_IMAGE_NAME}'; \
|
||||
export FRONTEND_IMAGE_NAME='${FRONTEND_IMAGE_NAME}'; \
|
||||
export USERFRONT_IMAGE_NAME='${USERFRONT_IMAGE_NAME}'; \
|
||||
export IMAGE_TAG='${IMAGE_TAG}'; \
|
||||
export HARBOR_ENDPOINT='${HARBOR_ENDPOINT}'; \
|
||||
export HARBOR_ROBOT_ACCOUNT='${HARBOR_ROBOT_ACCOUNT}'; \
|
||||
|
||||
+7
-7
@@ -17,10 +17,10 @@ backend/vendor/
|
||||
backend/tmp/
|
||||
backend/.env
|
||||
|
||||
# Frontend (Flutter)
|
||||
# Note: Frontend might have its own .gitignore, but adding here just in case
|
||||
frontend/build/
|
||||
frontend/.dart_tool/
|
||||
frontend/.packages
|
||||
frontend/.pub/
|
||||
frontend/.env
|
||||
# userfront (Flutter)
|
||||
# Note: userfront might have its own .gitignore, but adding here just in case
|
||||
userfront/build/
|
||||
userfront/.dart_tool/
|
||||
userfront/.packages
|
||||
userfront/.pub/
|
||||
userfront/.env
|
||||
@@ -21,22 +21,22 @@
|
||||
- **Features**:
|
||||
- 인증용 SMS 발송 등 Ory-Stack으로 구현 어려운 부분 직접 구현
|
||||
- `POST /api/v1/audit`: 감사 로그 수집 API
|
||||
- User-Front가 바라보는 backend
|
||||
- userfront가 바라보는 backend
|
||||
|
||||
### 2. User-Front(Flutter Web/App)
|
||||
### 2. userfront(Flutter Web/App)
|
||||
- **Framework**: Flutter 3.32+
|
||||
- **Key Packages**: `flutter_riverpod`, `go_router`
|
||||
- **Features**:
|
||||
- 탭 기반 로그인 UI (비밀번호 기반 / 링크 기반 / QR 기반 등)
|
||||
|
||||
### 3. Admin-Front(Web)
|
||||
### 3. adminfront(Web)
|
||||
- **Framework**: Vite, React 19+, Shadcn/ui 등
|
||||
- **Features**:
|
||||
- 사용자 관리, 권한 부여 등 관리자 기능
|
||||
- 앱 별 사용량(호출량) 등 통계
|
||||
- 핵심 Audit 대상
|
||||
|
||||
### 4. Dev-Front(Web) - 향후 분리 예정
|
||||
### 4. devfront(Web) - 향후 분리 예정
|
||||
- **Framework**: Vite, React 19+, Shadcn/ui 등
|
||||
- **Features**:
|
||||
- RP 등록 및 관리
|
||||
@@ -55,9 +55,9 @@
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
AF[Admin Front] -->|"OIDC authorize/token (PKCE)"| HY["Hydra (OIDC 엔진)"]
|
||||
DF[Dev Front] -->|"OIDC authorize/token (PKCE)"| HY
|
||||
UF["User Front (Login/Consent UI)"] <-->|Hydra login/consent redirect| HY
|
||||
AF[adminfront] -->|"OIDC authorize/token (PKCE)"| HY["Hydra (OIDC 엔진)"]
|
||||
DF[devfront] -->|"OIDC authorize/token (PKCE)"| HY
|
||||
UF["userfront (Login/Consent UI)"] <-->|Hydra login/consent redirect| HY
|
||||
UF -->|Kratos Browser Flow| KR["Kratos (SoT: identities/traits)"]
|
||||
KR -->|subject=identity.id| HY
|
||||
HY -->|ID/Access Token| RP[Relying Party Apps]
|
||||
@@ -111,14 +111,14 @@ docker compose -f compose.infra.yaml -f compose.ory.yaml up -d
|
||||
```
|
||||
|
||||
#### 3. 애플리케이션 실행
|
||||
Frontend와 Backend 서비스를 실행합니다.
|
||||
userfront와 backend 서비스를 실행합니다.
|
||||
```bash
|
||||
docker compose -f docker-compose.yaml up -d
|
||||
```
|
||||
(또는 한번에 실행: `docker compose -f compose.infra.yaml -f compose.ory.yaml -f docker-compose.yaml up -d`)
|
||||
|
||||
- **Frontend**: http://localhost:5000 접속
|
||||
- **Backend**: http://localhost:3000 (API)
|
||||
- **userfront**: http://localhost:5000 접속
|
||||
- **backend**: http://localhost:3000 (API)
|
||||
- **ClickHouse**: http://localhost:8123
|
||||
- **Kratos Public**: http://localhost:4433
|
||||
- **Hydra Public**: http://localhost:4444
|
||||
@@ -134,9 +134,9 @@ go mod tidy
|
||||
go run cmd/server/main.go
|
||||
```
|
||||
|
||||
**Frontend:**
|
||||
**userfront:**
|
||||
```bash
|
||||
cd frontend
|
||||
cd userfront
|
||||
flutter pub get
|
||||
flutter run -d chrome
|
||||
```
|
||||
@@ -151,10 +151,10 @@ baron_sso/
|
||||
│ ├── cmd/server/ # 진입점 (Entry point)
|
||||
│ ├── internal/ # 도메인, 핸들러, 저장소(Repository)
|
||||
│ └── Dockerfile
|
||||
├── user-front/ # Flutter 애플리케이션
|
||||
├── userfront/ # Flutter 애플리케이션
|
||||
│ ├── src/ # UI 및 로직
|
||||
│ └── pubspec.yaml
|
||||
├── admin-front/ # React 기반 관리
|
||||
├── adminfront/ # React 기반 관리
|
||||
│ ├── src/ # UI 및 로직
|
||||
│ └── pubspec.yaml
|
||||
├── compose.ory-stack.yaml # DB 서비스 (Postgres, ClickHouse)
|
||||
@@ -167,6 +167,6 @@ baron_sso/
|
||||
## 📝 상태 및 로드맵 (Status & Roadmap)
|
||||
- [x] **Phase 1**: 초기 설정 및 아키텍처 설계 (완료)
|
||||
- [x] **Phase 2**: Backend Audit API 구현 (일부 완료)
|
||||
- [x] **Phase 3**: User Front 로그인 UI 인증 로직 (완료)
|
||||
- [ ] **Phase 4**: Admin Front 기능 추가 (예정)
|
||||
- [x] **Phase 3**: userfront 로그인 UI 인증 로직 (완료)
|
||||
- [ ] **Phase 4**: adminfront 기능 추가 (예정)
|
||||
- [ ] **Phase 5**: 대시보드 및 통합 런처 구현 (예정)
|
||||
+7
-7
@@ -24,7 +24,7 @@ It leverages **Descope** for secure, passwordless authentication (Enchanted Link
|
||||
|
||||
### 3. Infrastructure (Docker)
|
||||
- **Services**: `postgres`, `clickhouse` (defined in `compose.infra.yaml`)
|
||||
- **App**: `frontend`, `backend` (defined in `docker-compose.yaml`)
|
||||
- **App**: `userfront`, `backend` (defined in `docker-compose.yaml`)
|
||||
|
||||
---
|
||||
|
||||
@@ -60,13 +60,13 @@ docker compose -f compose.infra.yaml up -d
|
||||
```
|
||||
|
||||
#### 2. Start Applications
|
||||
Start the Frontend and Backend services.
|
||||
Start the userfront and backend services.
|
||||
```bash
|
||||
docker compose up
|
||||
```
|
||||
|
||||
- **Frontend**: Accessible at http://localhost:5000
|
||||
- **Backend**: API active at http://localhost:3000
|
||||
- **userfront**: Accessible at http://localhost:5000
|
||||
- **backend**: API active at http://localhost:3000
|
||||
- **ClickHouse**: http://localhost:8123
|
||||
|
||||
### Local Development (Manual)
|
||||
@@ -79,9 +79,9 @@ go mod tidy
|
||||
go run cmd/server/main.go
|
||||
```
|
||||
|
||||
**Frontend:**
|
||||
**userfront:**
|
||||
```bash
|
||||
cd frontend
|
||||
cd userfront
|
||||
flutter pub get
|
||||
flutter run -d chrome
|
||||
```
|
||||
@@ -96,7 +96,7 @@ baron_sso/
|
||||
│ ├── cmd/server/ # Entry point
|
||||
│ ├── internal/ # Domain, Handlers, Repository
|
||||
│ └── Dockerfile
|
||||
├── frontend/ # Flutter Application
|
||||
├── userfront/ # Flutter Application
|
||||
│ ├── lib/ # UI & Logic
|
||||
│ └── pubspec.yaml
|
||||
├── compose.infra.yaml # DB Services (Postgres, ClickHouse)
|
||||
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
@@ -4,7 +4,7 @@
|
||||
<meta charset="UTF-8" />
|
||||
<link rel="icon" type="image/svg+xml" href="/vite.svg" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>admin-front</title>
|
||||
<title>adminfront</title>
|
||||
</head>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
@@ -1,11 +1,11 @@
|
||||
{
|
||||
"name": "admin-front",
|
||||
"name": "adminfront",
|
||||
"version": "0.0.0",
|
||||
"lockfileVersion": 3,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "admin-front",
|
||||
"name": "adminfront",
|
||||
"version": "0.0.0",
|
||||
"dependencies": {
|
||||
"@radix-ui/react-avatar": "^1.1.4",
|
||||
@@ -1,5 +1,5 @@
|
||||
{
|
||||
"name": "admin-front",
|
||||
"name": "adminfront",
|
||||
"private": true,
|
||||
"version": "0.0.0",
|
||||
"type": "module",
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
+1
-1
@@ -54,7 +54,7 @@ function DashboardPage() {
|
||||
<div className="space-y-3 max-w-2xl">
|
||||
<div className="inline-flex items-center gap-2 rounded-full border border-[var(--color-border)] px-3 py-1 text-xs uppercase tracking-[0.2em] text-[var(--color-muted)]">
|
||||
<Sparkles size={14} />
|
||||
admin-front ready
|
||||
adminfront ready
|
||||
</div>
|
||||
<h2 className="text-3xl font-semibold leading-tight">
|
||||
Build the admin plane with{" "}
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
@@ -74,8 +74,8 @@ func main() {
|
||||
"app_env", getEnv("APP_ENV", "dev"),
|
||||
"db_port", getEnv("DB_PORT", "5532"),
|
||||
"backend_port", getEnv("BACKEND_PORT", "3000"),
|
||||
"frontend_port", getEnv("FRONTEND_PORT", "5000"),
|
||||
"frontend_url", getEnv("FRONTEND_URL", "http://sso.hmac.kr"),
|
||||
"userfront_port", getEnv("USERFRONT_PORT", "5000"),
|
||||
"userfront_url", getEnv("USERFRONT_URL", "http://sso.hmac.kr"),
|
||||
"redis_addr", getEnv("REDIS_ADDR", "redis:6379"),
|
||||
)
|
||||
|
||||
|
||||
@@ -418,7 +418,7 @@ func (h *AuthHandler) saveSignupState(key string, state *signupState, ttl time.D
|
||||
return h.RedisService.Set(key, string(data), ttl)
|
||||
}
|
||||
|
||||
// GetPasswordPolicy exposes the current Descope password policy to the frontend for dynamic validation.
|
||||
// GetPasswordPolicy exposes the current Descope password policy to the userfront for dynamic validation.
|
||||
func (h *AuthHandler) GetPasswordPolicy(c *fiber.Ctx) error {
|
||||
if h.DescopeClient == nil {
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(fiber.Map{"error": "Descope client not configured"})
|
||||
@@ -531,12 +531,12 @@ func (h *AuthHandler) InitEnchantedLink(c *fiber.Ctx) error {
|
||||
h.RedisService.Set(prefixToken+token, fmt.Sprintf(`{"pendingRef":"%s","loginId":"%s"}`, pendingRef, loginID), defaultExpiration)
|
||||
|
||||
// Generate Link
|
||||
frontendURL := os.Getenv("FRONTEND_URL")
|
||||
slog.Info("[Enchanted] Read FRONTEND_URL", "url", frontendURL)
|
||||
if frontendURL == "" {
|
||||
frontendURL = "http://sso.hmac.kr"
|
||||
userfrontURL := os.Getenv("USERFRONT_URL")
|
||||
slog.Info("[Enchanted] Read USERFRONT_URL", "url", userfrontURL)
|
||||
if userfrontURL == "" {
|
||||
userfrontURL = "http://sso.hmac.kr"
|
||||
}
|
||||
link := fmt.Sprintf("%s/verify/%s", frontendURL, token)
|
||||
link := fmt.Sprintf("%s/verify/%s", userfrontURL, token)
|
||||
|
||||
// Route based on LoginID type
|
||||
if strings.Contains(loginID, "@") {
|
||||
@@ -801,16 +801,16 @@ func (h *AuthHandler) InitiatePasswordReset(c *fiber.Ctx) error {
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(fiber.Map{"error": "Authentication service not configured"})
|
||||
}
|
||||
|
||||
frontendURL := os.Getenv("FRONTEND_URL")
|
||||
if frontendURL == "" {
|
||||
userfrontURL := os.Getenv("USERFRONT_URL")
|
||||
if userfrontURL == "" {
|
||||
ale.Status = fiber.StatusInternalServerError
|
||||
ale.LatencyMs = time.Since(startTime)
|
||||
ale.DescopeError = "FRONTEND_URL is not set"
|
||||
ale.Log(slog.LevelError, "FRONTEND_URL is not set")
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(fiber.Map{"error": "FRONTEND_URL environment variable is not set"})
|
||||
ale.DescopeError = "USERFRONT_URL is not set"
|
||||
ale.Log(slog.LevelError, "USERFRONT_URL is not set")
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(fiber.Map{"error": "USERFRONT_URL environment variable is not set"})
|
||||
}
|
||||
// [Changed] Point to Backend API for verification (which then redirects to Frontend)
|
||||
redirectURL := fmt.Sprintf("%s/api/v1/auth/password/reset/verify", frontendURL)
|
||||
redirectURL := fmt.Sprintf("%s/api/v1/auth/password/reset/verify", userfrontURL)
|
||||
ale.RedirectTo = redirectURL
|
||||
|
||||
// 내부 토큰 발급 + 우리 채널로 전송
|
||||
@@ -831,7 +831,7 @@ func (h *AuthHandler) InitiatePasswordReset(c *fiber.Ctx) error {
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(fiber.Map{"error": "Failed to store reset token"})
|
||||
}
|
||||
|
||||
resetLink := fmt.Sprintf("%s/reset-password?token=%s", frontendURL, resetToken)
|
||||
resetLink := fmt.Sprintf("%s/reset-password?token=%s", userfrontURL, resetToken)
|
||||
ale.RedirectTo = resetLink
|
||||
ale.Operation = "SendPasswordReset"
|
||||
ale.Log(slog.LevelInfo, "Initiating password reset via internal token")
|
||||
@@ -923,7 +923,7 @@ func (h *AuthHandler) VerifyPasswordResetPage(c *fiber.Ctx) error {
|
||||
}
|
||||
|
||||
// ProcessPasswordResetToken - Handles the POST request from the interstitial page.
|
||||
// Verifies the token, sets the refresh token cookie, and redirects to the frontend.
|
||||
// Verifies the token, sets the refresh token cookie, and redirects to the userfront.
|
||||
func (h *AuthHandler) ProcessPasswordResetToken(c *fiber.Ctx) error {
|
||||
startTime := time.Now()
|
||||
ale := logger.NewAuditLogEntry(c, "verify")
|
||||
@@ -960,7 +960,7 @@ func (h *AuthHandler) ProcessPasswordResetToken(c *fiber.Ctx) error {
|
||||
ale.LoginIDs["loginId_normalized"] = loginID
|
||||
|
||||
redirectURL := fmt.Sprintf("%s/reset-password?loginId=%s&token=%s",
|
||||
os.Getenv("FRONTEND_URL"),
|
||||
os.Getenv("USERFRONT_URL"),
|
||||
loginID,
|
||||
token,
|
||||
)
|
||||
@@ -968,7 +968,7 @@ func (h *AuthHandler) ProcessPasswordResetToken(c *fiber.Ctx) error {
|
||||
ale.RedirectTo = redirectURL
|
||||
ale.Status = fiber.StatusFound
|
||||
ale.LatencyMs = time.Since(startTime)
|
||||
ale.Log(slog.LevelInfo, "Token verified, redirecting to frontend")
|
||||
ale.Log(slog.LevelInfo, "Token verified, redirecting to userfront")
|
||||
|
||||
return c.Redirect(redirectURL)
|
||||
}
|
||||
@@ -1127,11 +1127,11 @@ func (h *AuthHandler) InitQRLogin(c *fiber.Ctx) error {
|
||||
pendingRef := GenerateSecureToken(16)
|
||||
|
||||
// QR 코드 페이로드를 실제 접속 가능한 URL로 변경합니다.
|
||||
frontendURL := os.Getenv("FRONTEND_URL")
|
||||
if frontendURL == "" {
|
||||
frontendURL = "https://sso.hmac.kr"
|
||||
userfrontURL := os.Getenv("USERFRONT_URL")
|
||||
if userfrontURL == "" {
|
||||
userfrontURL = "https://sso.hmac.kr"
|
||||
}
|
||||
qrPayload := fmt.Sprintf("%s/approve?ref=%s", frontendURL, pendingRef)
|
||||
qrPayload := fmt.Sprintf("%s/approve?ref=%s", userfrontURL, pendingRef)
|
||||
|
||||
slog.Info("[QR] Init", "pendingRef", pendingRef, "url", qrPayload)
|
||||
|
||||
|
||||
@@ -44,7 +44,7 @@ func NewDescopeProvider(projectID, managementKey string) *DescopeProvider {
|
||||
|
||||
return &DescopeProvider{
|
||||
Client: descopeClient,
|
||||
FrontendURL: os.Getenv("FRONTEND_URL"),
|
||||
FrontendURL: os.Getenv("USERFRONT_URL"),
|
||||
fieldMapping: mapping,
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -52,5 +52,6 @@ volumes:
|
||||
|
||||
networks:
|
||||
baron_net:
|
||||
name: baron_network
|
||||
name: baron_net
|
||||
external: true
|
||||
driver: bridge
|
||||
+1
-1
@@ -173,7 +173,7 @@ services:
|
||||
command: >
|
||||
clients create
|
||||
--endpoint http://hydra:4445
|
||||
--id admin-front
|
||||
--id adminfront
|
||||
--secret admin-secret
|
||||
--grant-types authorization_code,refresh_token
|
||||
--response-types code
|
||||
|
||||
+85
-85
@@ -1,91 +1,91 @@
|
||||
services:
|
||||
backend:
|
||||
build:
|
||||
context: ./backend
|
||||
dockerfile: Dockerfile
|
||||
container_name: baron_backend
|
||||
env_file:
|
||||
- .env
|
||||
environment:
|
||||
- APP_ENV=${APP_ENV:-development}
|
||||
- GO_ENV=${APP_ENV:-development}
|
||||
- COOKIE_SECRET=${COOKIE_SECRET}
|
||||
- JWT_SECRET=${JWT_SECRET}
|
||||
- DESCOPE_PROJECT_ID=${DESCOPE_PROJECT_ID}
|
||||
- DESCOPE_MANAGEMENT_KEY=${DESCOPE_MANAGEMENT_KEY}
|
||||
- NAVER_CLOUD_ACCESS_KEY=${NAVER_CLOUD_ACCESS_KEY}
|
||||
- NAVER_CLOUD_SECRET_KEY=${NAVER_CLOUD_SECRET_KEY}
|
||||
- NAVER_CLOUD_SERVICE_ID=${NAVER_CLOUD_SERVICE_ID}
|
||||
- NAVER_SENDER_PHONE_NUMBER=${NAVER_SENDER_PHONE_NUMBER}
|
||||
- FRONTEND_URL=${FRONTEND_URL}
|
||||
- IDP_PROVIDER=${IDP_PROVIDER:-ory,descope}
|
||||
- KRATOS_ADMIN_URL=${KRATOS_ADMIN_URL:-http://kratos:4434}
|
||||
- HYDRA_ADMIN_URL=${HYDRA_ADMIN_URL:-http://hydra:4445}
|
||||
- DB_HOST=postgres
|
||||
- CLICKHOUSE_HOST=clickhouse
|
||||
- CLICKHOUSE_PORT=${CLICKHOUSE_PORT_NATIVE:-9000}
|
||||
- CLICKHOUSE_USER=${CLICKHOUSE_USER:-baron}
|
||||
- CLICKHOUSE_PASSWORD=${CLICKHOUSE_PASSWORD:-password}
|
||||
ports:
|
||||
- "${BACKEND_PORT:-3000}:3000"
|
||||
depends_on:
|
||||
- infra_check
|
||||
networks:
|
||||
- baron_net
|
||||
- ory-net
|
||||
volumes:
|
||||
- ./backend:/app
|
||||
command: ["go", "run", "./cmd/server/main.go"]
|
||||
backend:
|
||||
build:
|
||||
context: ./backend
|
||||
dockerfile: Dockerfile
|
||||
container_name: baron_backend
|
||||
env_file:
|
||||
- .env
|
||||
environment:
|
||||
- APP_ENV=${APP_ENV:-development}
|
||||
- GO_ENV=${APP_ENV:-development}
|
||||
- COOKIE_SECRET=${COOKIE_SECRET}
|
||||
- JWT_SECRET=${JWT_SECRET}
|
||||
- DESCOPE_PROJECT_ID=${DESCOPE_PROJECT_ID}
|
||||
- DESCOPE_MANAGEMENT_KEY=${DESCOPE_MANAGEMENT_KEY}
|
||||
- NAVER_CLOUD_ACCESS_KEY=${NAVER_CLOUD_ACCESS_KEY}
|
||||
- NAVER_CLOUD_SECRET_KEY=${NAVER_CLOUD_SECRET_KEY}
|
||||
- NAVER_CLOUD_SERVICE_ID=${NAVER_CLOUD_SERVICE_ID}
|
||||
- NAVER_SENDER_PHONE_NUMBER=${NAVER_SENDER_PHONE_NUMBER}
|
||||
- USERFRONT_URL=${USERFRONT_URL}
|
||||
- IDP_PROVIDER=${IDP_PROVIDER:-ory,descope}
|
||||
- KRATOS_ADMIN_URL=${KRATOS_ADMIN_URL:-http://kratos:4434}
|
||||
- HYDRA_ADMIN_URL=${HYDRA_ADMIN_URL:-http://hydra:4445}
|
||||
- DB_HOST=postgres
|
||||
- CLICKHOUSE_HOST=clickhouse
|
||||
- CLICKHOUSE_PORT=${CLICKHOUSE_PORT_NATIVE:-9000}
|
||||
- CLICKHOUSE_USER=${CLICKHOUSE_USER:-baron}
|
||||
- CLICKHOUSE_PASSWORD=${CLICKHOUSE_PASSWORD:-password}
|
||||
ports:
|
||||
- "${BACKEND_PORT:-3000}:3000"
|
||||
depends_on:
|
||||
- infra_check
|
||||
networks:
|
||||
- baron_net
|
||||
- ory-net
|
||||
volumes:
|
||||
- ./backend:/app
|
||||
command: ["go", "run", "./cmd/server/main.go"]
|
||||
|
||||
healthcheck:
|
||||
test: ["CMD", "wget", "-qO-", "http://127.0.0.1:3000/health"]
|
||||
interval: 10s
|
||||
timeout: 5s
|
||||
retries: 3
|
||||
start_period: 10s
|
||||
healthcheck:
|
||||
test: ["CMD", "wget", "-qO-", "http://127.0.0.1:3000/health"]
|
||||
interval: 10s
|
||||
timeout: 5s
|
||||
retries: 3
|
||||
start_period: 10s
|
||||
|
||||
frontend:
|
||||
build:
|
||||
context: ./frontend
|
||||
dockerfile: Dockerfile
|
||||
container_name: baron_frontend
|
||||
env_file:
|
||||
- .env
|
||||
environment:
|
||||
- DESCOPE_PROJECT_ID=${DESCOPE_PROJECT_ID}
|
||||
- BACKEND_URL=${BACKEND_URL}
|
||||
- FRONTEND_URL=${FRONTEND_URL}
|
||||
- APP_ENV=${APP_ENV}
|
||||
ports:
|
||||
- "${FRONTEND_PORT:-5000}:5000"
|
||||
networks:
|
||||
- baron_net
|
||||
depends_on:
|
||||
backend:
|
||||
condition: service_healthy
|
||||
command: >
|
||||
/bin/sh -c "mkdir -p /usr/share/nginx/html/assets &&
|
||||
echo \"DESCOPE_PROJECT_ID=$${DESCOPE_PROJECT_ID}\" > /usr/share/nginx/html/assets/.env &&
|
||||
echo \"BACKEND_URL=$${BACKEND_URL}\" >> /usr/share/nginx/html/assets/.env &&
|
||||
echo \"FRONTEND_URL=$${FRONTEND_URL}\" >> /usr/share/nginx/html/assets/.env &&
|
||||
echo \"APP_ENV=$${APP_ENV}\" >> /usr/share/nginx/html/assets/.env &&
|
||||
cp /usr/share/nginx/html/assets/.env /usr/share/nginx/html/.env &&
|
||||
nginx -g 'daemon off;'"
|
||||
userfront:
|
||||
build:
|
||||
context: ./userfront
|
||||
dockerfile: Dockerfile
|
||||
container_name: baron_userfront
|
||||
env_file:
|
||||
- .env
|
||||
environment:
|
||||
- DESCOPE_PROJECT_ID=${DESCOPE_PROJECT_ID}
|
||||
- BACKEND_URL=${BACKEND_URL}
|
||||
- USERFRONT_URL=${USERFRONT_URL}
|
||||
- APP_ENV=${APP_ENV}
|
||||
ports:
|
||||
- "${USERFRONT_PORT:-5000}:5000"
|
||||
networks:
|
||||
- baron_net
|
||||
depends_on:
|
||||
backend:
|
||||
condition: service_healthy
|
||||
command: >
|
||||
/bin/sh -c "mkdir -p /usr/share/nginx/html/assets &&
|
||||
echo \"DESCOPE_PROJECT_ID=$${DESCOPE_PROJECT_ID}\" > /usr/share/nginx/html/assets/.env &&
|
||||
echo \"BACKEND_URL=$${BACKEND_URL}\" >> /usr/share/nginx/html/assets/.env &&
|
||||
echo \"USERFRONT_URL=$${USERFRONT_URL}\" >> /usr/share/nginx/html/assets/.env &&
|
||||
echo \"APP_ENV=$${APP_ENV}\" >> /usr/share/nginx/html/assets/.env &&
|
||||
cp /usr/share/nginx/html/assets/.env /usr/share/nginx/html/.env &&
|
||||
nginx -g 'daemon off;'"
|
||||
|
||||
# Dummy service to wait for infra network if needed,
|
||||
# but essentially we assume infra is running.
|
||||
# In a real unified stack, we might include infra here or use external links.
|
||||
# Here we attach to the same network.
|
||||
infra_check:
|
||||
image: alpine
|
||||
command: ["echo", "Infrastructure assumed running"]
|
||||
networks:
|
||||
- baron_net
|
||||
# Dummy service to wait for infra network if needed,
|
||||
# but essentially we assume infra is running.
|
||||
# In a real unified stack, we might include infra here or use external links.
|
||||
# Here we attach to the same network.
|
||||
infra_check:
|
||||
image: alpine
|
||||
command: ["echo", "Infrastructure assumed running"]
|
||||
networks:
|
||||
- baron_net
|
||||
|
||||
networks:
|
||||
baron_net:
|
||||
external: true
|
||||
name: baron_network
|
||||
ory-net:
|
||||
external: true
|
||||
name: ory-net
|
||||
baron_net:
|
||||
external: true
|
||||
name: baron_net
|
||||
ory-net:
|
||||
external: true
|
||||
name: ory-net
|
||||
+3
-3
@@ -13,10 +13,10 @@ Backend와 Frontend 애플리케이션을 각각의 Dockerfile을 사용하여
|
||||
```bash
|
||||
# Backend 이미지 빌드
|
||||
# v1.2601.1-RC1 부분은 실제 배포 버전에 맞게 수정하세요.
|
||||
docker build -t reg.hmac.kr/baron_sso/backend:v1.2601.1-RC1 -f docker/Dockerfile.backend .
|
||||
docker build -t reg.hmac.kr/baron_sso/backend:v1.2601.1-RC1 -f backend/Dockerfile .
|
||||
|
||||
# Frontend 이미지 빌드
|
||||
docker build -t reg.hmac.kr/baron_sso/frontend:v1.2601.1-RC1 -f docker/Dockerfile.frontend .
|
||||
docker build -t reg.hmac.kr/baron_sso/userfront:v1.2601.1-RC1 -f userfront/Dockerfile .
|
||||
```
|
||||
|
||||
---
|
||||
@@ -42,7 +42,7 @@ docker login reg.hmac.kr
|
||||
docker push reg.hmac.kr/baron_sso/backend:v1.2601.1-RC1
|
||||
|
||||
# Frontend 이미지 푸시
|
||||
docker push reg.hmac.kr/baron_sso/frontend:v1.2601.1-RC1
|
||||
docker push reg.hmac.kr/baron_sso/userfront:v1.2601.1-RC1
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
@@ -16,7 +16,7 @@ services:
|
||||
- CLICKHOUSE_PORT=${CLICKHOUSE_PORT_NATIVE:-9000}
|
||||
- CLICKHOUSE_USER=${CLICKHOUSE_USER:-baron}
|
||||
- CLICKHOUSE_PASSWORD=${CLICKHOUSE_PASSWORD:-password}
|
||||
- FRONTEND_URL=${FRONTEND_URL:-https://sso.hmac.kr}
|
||||
- USERFRONT_URL=${USERFRONT_URL:-https://sso.hmac.kr}
|
||||
ports:
|
||||
- "${BACKEND_PORT:-3010}:3010"
|
||||
depends_on:
|
||||
@@ -30,15 +30,15 @@ services:
|
||||
networks:
|
||||
- baron_net
|
||||
|
||||
frontend:
|
||||
image: ${FRONTEND_IMAGE_NAME}:${IMAGE_TAG}
|
||||
container_name: baron_frontend
|
||||
userfront:
|
||||
image: ${USERFRONT_IMAGE_NAME}:${IMAGE_TAG}
|
||||
container_name: baron_userfront
|
||||
restart: unless-stopped
|
||||
environment:
|
||||
- FRONTEND_URL=${FRONTEND_URL:-https://sso.hmac.kr}
|
||||
- BACKEND_URL=${FRONTEND_URL:-https://sso.hmac.kr}
|
||||
- USERFRONT_URL=${USERFRONT_URL:-https://sso.hmac.kr}
|
||||
- BACKEND_URL=${USERFRONT_URL:-https://sso.hmac.kr}
|
||||
ports:
|
||||
- "${FRONTEND_PORT:-80}:80"
|
||||
- "${USERFRONT_PORT:-80}:80"
|
||||
depends_on:
|
||||
backend:
|
||||
condition: service_healthy
|
||||
|
||||
+1
-1
@@ -35,7 +35,7 @@
|
||||
## Workspace Structure
|
||||
Root: `/home/lectom/.gemini/antigravity/scratch/baron_sso`
|
||||
- `/backend`: Go Fiber Application
|
||||
- `/frontend`: Flutter Application
|
||||
- `/userfront`: Flutter Application
|
||||
- `/docs`: Documentation (PRD, API Specs)
|
||||
|
||||
## Current Status
|
||||
|
||||
@@ -1,98 +0,0 @@
|
||||
name: frontend
|
||||
description: "A new Flutter project."
|
||||
# The following line prevents the package from being accidentally published to
|
||||
# pub.dev using `flutter pub publish`. This is preferred for private packages.
|
||||
publish_to: "none" # Remove this line if you wish to publish to pub.dev
|
||||
|
||||
# The following defines the version and build number for your application.
|
||||
# A version number is three numbers separated by dots, like 1.2.43
|
||||
# followed by an optional build number separated by a +.
|
||||
# Both the version and the builder number may be overridden in flutter
|
||||
# build by specifying --build-name and --build-number, respectively.
|
||||
# In Android, build-name is used as versionName while build-number used as versionCode.
|
||||
# Read more about Android versioning at https://developer.android.com/studio/publish/versioning
|
||||
# In iOS, build-name is used as CFBundleShortVersionString while build-number is used as CFBundleVersion.
|
||||
# Read more about iOS versioning at
|
||||
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
|
||||
# In Windows, build-name is used as the major, minor, and patch parts
|
||||
# of the product and file versions while build-number is used as the build suffix.
|
||||
version: 1.0.0+1
|
||||
|
||||
environment:
|
||||
sdk: ^3.10.4
|
||||
|
||||
# Dependencies specify other packages that your package needs in order to work.
|
||||
# To automatically upgrade your package dependencies to the latest versions
|
||||
# consider running `flutter pub upgrade --major-versions`. Alternatively,
|
||||
# dependencies can be manually updated by changing the version numbers below to
|
||||
# the latest version available on pub.dev. To see which dependencies have newer
|
||||
# versions available, run `flutter pub outdated`.
|
||||
dependencies:
|
||||
flutter:
|
||||
sdk: flutter
|
||||
|
||||
# The following adds the Cupertino Icons font to your application.
|
||||
# Use with the CupertinoIcons class for iOS style icons.
|
||||
cupertino_icons: ^1.0.8
|
||||
flutter_riverpod: ^3.0.3
|
||||
go_router: ^17.0.1
|
||||
descope: ^0.9.11
|
||||
http: ^1.6.0
|
||||
google_fonts: ^6.3.3
|
||||
flutter_dotenv: ^5.1.0
|
||||
url_launcher: ^6.3.2
|
||||
logging: ^1.2.0
|
||||
logger: ^2.0.0
|
||||
qr_flutter: ^4.1.0
|
||||
mobile_scanner: ^6.0.0
|
||||
|
||||
dev_dependencies:
|
||||
flutter_test:
|
||||
sdk: flutter
|
||||
|
||||
# The "flutter_lints" package below contains a set of recommended lints to
|
||||
# encourage good coding practices. The lint set provided by the package is
|
||||
# activated in the `analysis_options.yaml` file located at the root of your
|
||||
# package. See that file for information about deactivating specific lint
|
||||
# rules and activating additional ones.
|
||||
flutter_lints: ^6.0.0
|
||||
|
||||
# For information on the generic Dart part of this file, see the
|
||||
# following page: https://dart.dev/tools/pub/pubspec
|
||||
|
||||
# The following section is specific to Flutter packages.
|
||||
flutter:
|
||||
# The following line ensures that the Material Icons font is
|
||||
# included with your application, so that you can use the icons in
|
||||
# the material Icons class.
|
||||
uses-material-design: true
|
||||
|
||||
# To add assets to your application, add an assets section, like this:
|
||||
# assets:
|
||||
# - .env
|
||||
|
||||
# An image asset can refer to one or more resolution-specific "variants", see
|
||||
# https://flutter.dev/to/resolution-aware-images
|
||||
|
||||
# For details regarding adding assets from package dependencies, see
|
||||
# https://flutter.dev/to/asset-from-package
|
||||
|
||||
# To add custom fonts to your application, add a fonts section here,
|
||||
# in this "flutter" section. Each entry in this list should have a
|
||||
# "family" key with the font family name, and a "fonts" key with a
|
||||
# list giving the asset and other descriptors for the font. For
|
||||
# example:
|
||||
# fonts:
|
||||
# - family: Schyler
|
||||
# fonts:
|
||||
# - asset: fonts/Schyler-Regular.ttf
|
||||
# - asset: fonts/Schyler-Italic.ttf
|
||||
# style: italic
|
||||
# - family: Trajan Pro
|
||||
# fonts:
|
||||
# - asset: fonts/TrajanPro.ttf
|
||||
# - asset: fonts/TrajanPro_Bold.ttf
|
||||
# weight: 700
|
||||
#
|
||||
# For details regarding fonts from package dependencies,
|
||||
# see https://flutter.dev/to/font-from-package
|
||||
@@ -11,7 +11,7 @@ DB_PORT=5432
|
||||
CLICKHOUSE_PORT_HTTP=8123
|
||||
CLICKHOUSE_PORT_NATIVE=9000
|
||||
BACKEND_PORT=3000
|
||||
FRONTEND_PORT=5000
|
||||
USERFRONT_PORT=5000
|
||||
|
||||
# --- Database Credentials (PostgreSQL) ---
|
||||
DB_USER=baron
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
@@ -6,7 +6,7 @@ plugins {
|
||||
}
|
||||
|
||||
android {
|
||||
namespace = "kr.co.baroncs.frontend"
|
||||
namespace = "kr.co.baroncs.userfront"
|
||||
compileSdk = flutter.compileSdkVersion
|
||||
ndkVersion = flutter.ndkVersion
|
||||
|
||||
@@ -21,7 +21,7 @@ android {
|
||||
|
||||
defaultConfig {
|
||||
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
|
||||
applicationId = "kr.co.baroncs.frontend"
|
||||
applicationId = "kr.co.baroncs.userfront"
|
||||
// You can update the following values to match your application needs.
|
||||
// For more information, see: https://flutter.dev/to/review-gradle-config.
|
||||
minSdk = flutter.minSdkVersion
|
||||
File renamed without changes.
+1
-1
@@ -1,7 +1,7 @@
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<uses-permission android:name="android.permission.CAMERA"/>
|
||||
<application
|
||||
android:label="frontend"
|
||||
android:label="userfront"
|
||||
android:name="${applicationName}"
|
||||
android:icon="@mipmap/ic_launcher">
|
||||
<activity
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
package kr.co.baroncs.frontend
|
||||
package kr.co.baroncs.userfront
|
||||
|
||||
import io.flutter.embedding.android.FlutterActivity
|
||||
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
+6
-6
@@ -368,7 +368,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.frontend;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.userfront;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
|
||||
SWIFT_VERSION = 5.0;
|
||||
@@ -384,7 +384,7 @@
|
||||
CURRENT_PROJECT_VERSION = 1;
|
||||
GENERATE_INFOPLIST_FILE = YES;
|
||||
MARKETING_VERSION = 1.0;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.frontend.RunnerTests;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.userfront.RunnerTests;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||
@@ -401,7 +401,7 @@
|
||||
CURRENT_PROJECT_VERSION = 1;
|
||||
GENERATE_INFOPLIST_FILE = YES;
|
||||
MARKETING_VERSION = 1.0;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.frontend.RunnerTests;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.userfront.RunnerTests;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_VERSION = 5.0;
|
||||
TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner";
|
||||
@@ -416,7 +416,7 @@
|
||||
CURRENT_PROJECT_VERSION = 1;
|
||||
GENERATE_INFOPLIST_FILE = YES;
|
||||
MARKETING_VERSION = 1.0;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.frontend.RunnerTests;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.userfront.RunnerTests;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_VERSION = 5.0;
|
||||
TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Runner.app/$(BUNDLE_EXECUTABLE_FOLDER_PATH)/Runner";
|
||||
@@ -547,7 +547,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.frontend;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.userfront;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||
@@ -569,7 +569,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.frontend;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = kr.co.baroncs.userfront;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
|
||||
SWIFT_VERSION = 5.0;
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
Loaded 100 of 154 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user