iss_pc
inFAMOUS Second Son의 리눅스·윈도우용 네이티브 PC 포트
An online character sheet for Savage Worlds (SWADE)
README 전체를 불러오는 중입니다.
README 전문 보기 ↗Have your Savage Worlds characters with you anywhere!
A character sheet app that works offline and syncs across devices once you sign in. It is a Savage Worlds fan product under Pinnacle's Fan License: the footer carries the required notice and the Fan License logo, which must stay unaltered in size.
The browser is the source of truth. Characters live in IndexedDB and MongoDB is the sync target, so the app keeps working without a connection.
409 and the sheet asks Keep mine or Use theirs.NEXT_PUBLIC_ENABLE_SW=1 to register it under next dev after a bun run build. Otherwise next dev unregisters any worker left from an earlier production run.| Method | Path | Purpose |
|---|---|---|
GET | /api/characters?since=<ms> | Characters changed at or after the cursor |
PUT | /api/characters/:id | Versioned write: { baseVersion, deleted, data } |
GET/PUT | /api/characters/:id/portrait?rev=<rev> | Portrait bytes (JPEG, PNG or WebP), up to 2 MiB |
Every /api/characters request needs a session and an X-WCG-Store-Owner header naming the account whose local store it syncs. A missing session, or a header that doesn't match the signed-in user, answers 401. Another user's character answers 404. A store whose account was deleted answers 410, and the client wipes it.
Sign-in uses Better Auth with Google, Discord and email links. Users and sessions live in the same MongoDB. Signing in only turns sync on: the app works fully signed out, and characters made signed out can be added to an account later.
Deleting an account (account menu → Delete account…) emails a link to /delete-account, which confirms with one more click in a browser signed in to that account, offering sign-in first if needed. Confirming deletes the account's characters and portraits, then the user, sessions and linked logins. Only the deleted user's random id is kept, in deletedUsers, so the account's other devices get 410 on their next sync and wipe their local copy. Hidden account stores on a device (signed out, or another account open) are checked the same way once per app start.
Each account has its own local store (wcg-u-<userId>); signed-out characters live in wcg. Signing out hides the account's characters on that device until it signs in again.
| Variable | Purpose |
|---|---|
BETTER_AUTH_SECRET | Session signing (openssl rand -base64 32) |
BETTER_AUTH_URL | Public base URL, e.g. http://localhost:3000 |
GOOGLE_CLIENT_ID, GOOGLE_CLIENT_SECRET | Optional; Google sign-in shows only when both are set |
DISCORD_CLIENT_ID, DISCORD_CLIENT_SECRET | Optional; Discord sign-in shows only when both are set |
SMTP_URL, EMAIL_FROM | Email links over SMTP; off in production without them |
AUTH_PASSWORD=1 | Username and password accounts (no email needed) |
AUTH_PASSWORD_MIN_LENGTH | Shortest password for new accounts; default 8 |
SIGNUP_INVITE_CODE | New accounts need this code, by any sign-in method |
SIGNUP_OPEN=1 | Self-hosted only: anyone may create an account |
DATABASE_PATH | SQLite file, used when MONGODB_URI is unset; one of the two is required |
Each sign-in method is on when its settings are, and the server refuses to start in production when none is. Sign-up stays open on MongoDB; with SQLite it needs SIGNUP_INVITE_CODE or SIGNUP_OPEN=1.
Sign-in and account-deletion emails are HTML with a plain-text part, sent over SMTP, so any provider works: SMTP_URL=smtp://<login>:<key>@<host>:587 (URL-encode @ in the login as %40). EMAIL_FROM must use a domain verified with that provider. In development without SMTP_URL, sign-in links print to the server console; in production, email sign-in is off without both.
여기까지가 README 앞부분입니다. 나머지는 원문에서 읽을 수 있습니다. README 전문 보기 ↗