diff --git a/.github/workflows/release-dmg.yml b/.github/workflows/release-dmg.yml new file mode 100644 index 0000000..7f6788a --- /dev/null +++ b/.github/workflows/release-dmg.yml @@ -0,0 +1,48 @@ +# Tag push (v*) → Release 빌드, UDZO DMG 업로드, GitHub Release 생성 + +name: Release (DMG) + +on: + push: + tags: + - "v*" + +permissions: + contents: write + +jobs: + release: + runs-on: macos-14 + steps: + - name: Check out repository + uses: actions/checkout@v4 + + - name: Build kkamppak.app (unsigned) + run: | + set -euo pipefail + PROJ="apps/kkamppak/kkamppak.xcodeproj" + xcodebuild -project "$PROJ" -scheme kkamppak -configuration Release -destination 'platform=macOS' CODE_SIGNING_ALLOWED=NO build + APP=$(find ~/Library/Developer/Xcode/DerivedData -path '*/Build/Products/Release/kkamppak.app' -print -quit) + test -n "$APP" -a -d "$APP" + echo "BUILT_APP=$APP" >> "$GITHUB_ENV" + + - name: Create DMG + run: | + set -euo pipefail + VOL="kkamppak" + DMG="kkamppak-${{ github.ref_name }}.dmg" + hdiutil create -volname "$VOL" -srcfolder "$BUILT_APP" -ov -format UDZO "$GITHUB_WORKSPACE/$DMG" + ls -la "$GITHUB_WORKSPACE/$DMG" + + - name: Publish GitHub Release + uses: softprops/action-gh-release@v2 + with: + files: kkamppak-${{ github.ref_name }}.dmg + generate_release_notes: true + fail_on_unmatched_files: true + body: | + **kkamppak** macOS 빌드 (서명·공증 없음). DMG 안의 `kkamppak.app`을 응용 프로그램 폴더로 옮긴 뒤 실행하세요. + + 자세한 설치·보안 안내: [README](https://github.com/${{ github.repository }}/blob/main/README.md) + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} diff --git a/PLANS.md b/PLANS.md index 79b6dbb..3321973 100644 --- a/PLANS.md +++ b/PLANS.md @@ -8,9 +8,9 @@ ### Release artifacts -- **Outcome:** GitHub Releases에 `.app` zip 업로드 (또는 CI 아티팩트를 릴리스에 붙이기). README **방법 B**와 맞출 것. +- **Outcome:** `v*` 태그 푸시 시 Actions가 **UDZO DMG** 빌드 후 GitHub Release 자동 생성 (`.github/workflows/release-dmg.yml`). PR·main용 zip 아티팩트는 `build-macos.yml`. - **Why this is accepted:** 사용자가 소스 빌드 없이 받을 수 있게. -- **Preconditions:** 태그·릴리스 노트; (선택) Developer ID 서명 시 GitHub secret 연동. +- **Preconditions:** 시맨틱 버전 태그 예: `v1.0.0`; (선택) Developer ID 서명 시 워크플로 확장. - **Related ids:** — ### 문서·검증 @@ -27,8 +27,7 @@ ### Near term -- **Initiative:** 첫 GitHub Release 게시 (unsigned zip이라도) + README와 동기화 -- **Initiative:** (선택) Release 워크플로로 태그 시 자동 zip 첨부 +- **Initiative:** 첫 `v*` 태그 푸시로 DMG 릴리즈 확인 ### Mid term diff --git a/README.en.md b/README.en.md index 3cbcd9a..8aa00bb 100644 --- a/README.en.md +++ b/README.en.md @@ -19,9 +19,16 @@ Repo operating model: [REPO.md](REPO.md). Product summary: [SPEC.md](SPEC.md). 3. On **first launch**, enter your admin password once (installs helper script, LaunchDaemon, and a narrow `sudoers` rule). 4. After that, pick a mode without typing your password again. -**Option B — release binary (when published)** +**Option B — release DMG (GitHub Actions)** -If **[Releases](https://github.com/devuterian/kkamppak/releases)** has a zip or other artifact, download it and install the same way. If nothing is there yet, use **Option A**. +Download **`kkamppak-vX.Y.Z.dmg`** from **[Releases](https://github.com/devuterian/kkamppak/releases)**. Pushing a `v*` tag triggers a workflow that builds the DMG and publishes the release: + +```bash +git tag v1.0.0 +git push origin v1.0.0 +``` + +Drag **kkamppak.app** from the DMG to **Applications**, then follow **Option A** for first-run install. If no release exists yet, use **Option A**. **If macOS blocks the app:** unsigned or ad-hoc builds may need **Right-click → Open** once, or approval under **System Settings → Privacy & Security**. This project assumes **no Notarization** is required by design. diff --git a/README.md b/README.md index 802c3e2..8bd4580 100644 --- a/README.md +++ b/README.md @@ -19,9 +19,16 @@ 3. **첫 실행**에서 관리자 암호를 한 번 입력해요. (도구 스크립트·LaunchDaemon·`sudoers` 한 줄이 깔려요.) 4. 그다음부터는 암호 없이 모드만 고르면 돼요. -**방법 B — 릴리즈 바이너리 (있을 때)** +**방법 B — 릴리즈 DMG (GitHub Actions)** -[Releases](https://github.com/devuterian/kkamppak/releases)에 올라온 **zip 등**이 있으면 받아서 같은 방식으로 Applications에 넣고 실행하면 됩니다. 아직 없으면 **방법 A**를 쓰면 돼요. +[Releases](https://github.com/devuterian/kkamppak/releases)에서 **`kkamppak-vX.Y.Z.dmg`** 를 받으면 됩니다. (저장소에 `v*` 태그를 푸시하면 Actions가 DMG를 만들고 릴리즈를 올립니다.) + +```bash +git tag v1.0.0 +git push origin v1.0.0 +``` + +DMG 안의 **kkamppak.app**을 응용 프로그램으로 옮긴 뒤 **방법 A**와 같이 첫 실행·설치를 진행하면 돼요. 릴리즈가 아직 없으면 **방법 A**를 쓰면 됩니다. **보안 경고가 뜨면:** 직접 빌드하거나 서명이 없으면 **우클릭 → 열기**로 한 번 실행하거나, **시스템 설정 → 개인 정보 보호 및 보안**에서 허용해 주면 돼요. 이 프로젝트는 기획상 **공증(Notarization) 없이** 배포해도 된다고 가정해요. diff --git a/STATUS.md b/STATUS.md index 6e90c3b..aac3237 100644 --- a/STATUS.md +++ b/STATUS.md @@ -2,15 +2,15 @@ ## Snapshot -- **Last updated:** 2026-04-10 +- **Last updated:** 2026-04-11 - **Overall posture:** `active` -- **Current focus:** 문서·CI 빌드로 설치 경로 정리; 릴리스는 운영자가 GitHub에서 게시하면 README 방법 B와 연결 +- **Current focus:** `v*` 태그 푸시 시 Actions가 DMG 빌드·GitHub Release 자동화 (`release-dmg.yml`) - **Highest-priority blocker:** 없음 (커밋은 provenance trailer 또는 명시적 migration/bootstrap 예외) - **Related decisions:** — ## Current state summary -Xcode 프로젝트는 `apps/kkamppak/kkamppak.xcodeproj`에 있으며, Swift 앱이 `pmset` 기반 스크립트로 전원 프리셋을 적용한다. 저장소 루트는 SPEC/STATUS/PLANS/INBOX·skills·records·커밋 검사를 포함한다. PR·`main`에 대해 **서명 없는** macOS 빌드 워크플로가 `.github/workflows/build-macos.yml`에 있다. +Xcode 프로젝트는 `apps/kkamppak/kkamppak.xcodeproj`에 있으며, Swift 앱이 `pmset` 기반 스크립트로 전원 프리셋을 적용한다. 저장소 루트는 SPEC/STATUS/PLANS/INBOX·skills·records·커밋 검사를 포함한다. **서명 없는** macOS CI: `build-macos.yml`(PR·main zip 아티팩트), `release-dmg.yml`(`v*` 태그 → DMG + Release). ## Active phases or tracks @@ -28,5 +28,5 @@ Xcode 프로젝트는 `apps/kkamppak/kkamppak.xcodeproj`에 있으며, Swift 앱 ## Immediate next steps -- 운영자: [Releases](https://github.com/devuterian/kkamppak/releases)에 zip 첫 업로드 시 README **방법 B** 문구와 실제 링크 맞추기 +- 운영자: `git tag v1.0.0 && git push origin v1.0.0` 로 첫 DMG 릴리즈 확인 - 로컬 개발: `./scripts/install-hooks.sh`로 커밋 훅 켜 두기 (`CONTRIBUTING.md`) diff --git a/docs/build.md b/docs/build.md index b1c723e..f0a0692 100644 --- a/docs/build.md +++ b/docs/build.md @@ -13,6 +13,17 @@ 로컬에서 zip으로 묶을 때는 Release 산출물 폴더에서 예를 들어 `zip -r kkamppak.app.zip kkamppak.app` 을 실행하면 됩니다. +## GitHub에서 DMG 릴리즈 + +`v` 로 시작하는 태그를 푸시하면 Actions가 Release용 DMG를 만들고 [GitHub Releases](https://github.com/devuterian/kkamppak/releases)에 올립니다. + +```bash +git tag v1.0.0 +git push origin v1.0.0 +``` + +워크플로: `.github/workflows/release-dmg.yml` (서명·공증 없음). + ## 산출물 - 빌드 결과: Xcode가 지정한 DerivedData 경로의 `kkamppak.app` diff --git a/records/agent-worklogs/LOG-20260409-001-repo-remodel.md b/records/agent-worklogs/LOG-20260409-001-repo-remodel.md index 659a098..a23740e 100644 --- a/records/agent-worklogs/LOG-20260409-001-repo-remodel.md +++ b/records/agent-worklogs/LOG-20260409-001-repo-remodel.md @@ -27,3 +27,8 @@ Recorded by agent: cursor-background - `SPEC.md`에 전원 프리셋·LaunchDaemon 역할 명시. - `PLANS.md`·`STATUS.md` 갱신(AppIcon은 보류 섹션). - `.github/workflows/build-macos.yml` — PR·main용 서명 없는 Xcode 빌드 + zip 아티팩트. + +## Follow-up — release DMG + +- `.github/workflows/release-dmg.yml`: `v*` 태그 푸시 시 `hdiutil` UDZO DMG + `softprops/action-gh-release` 로 GitHub Release 자동 생성. +- README·README.en·`docs/build.md`·`PLANS.md`·`STATUS.md` 반영.