Commit Graph

14 Commits

Author SHA1 Message Date
chpark 74fe7f3557 Admin: config auth/maintenance/clean, boards/groups, shop config/cat/coupon/orders, eyoom mgr/biz
10 new full-CRUD admin pages mirroring gnuboard's PHP admin:
- /admin/config/auth (g5_auth) — sub-admin permission grants/revokes
- /admin/config/maintenance — site-wide maintenance toggle (app_settings.maintenance)
- /admin/config/clean — 4 cleanup jobs (sessions / visit / login / point compress)
- /admin/boards/groups (g5_group) — create/rename/delete board groups
- /admin/shop/config (g5_shop_default) — store-wide settings
- /admin/shop/categories (g5_shop_category) — product categories CRUD
- /admin/shop/coupons (g5_shop_coupon) — coupon issuance, fixed/% method
- /admin/shop/orders — paginated order list with status change (입금완료/배송 etc)
- /admin/eyoom/managers (g5_eyoom_manager) — appoint/dismiss
- /admin/eyoom/biz-info (app_settings.biz_info) — company / CEO / 사업자번호

Verify: 50 iter × 16 = 800/800 PASS

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-29 11:40:22 +09:00
chpark 505398ec9f Board access guard, tag page real impl, rankings PHP-parity, freespin, more admin
Board access (mirrors gnuboard bo_read/write/comment_level):
- legacy-board.ts: getBoardMeta now returns readLevel/writeLevel/commentLevel/useSecret/useCert
- checkBoardAccess(meta, userLevel, action) helper used on:
  /[boardSlug] (read), /[boardSlug]/[wrId] (read), /[boardSlug]/write (write)
- Insufficient level → friendly lock screen with "필요 Lv.X" + login redirect for anon

Tag indexing (real):
- /tag/[tag]: pulls from inspection2.g5_eyoom_tag_write (cached subject/hit/datetime)
- ILIKE wr_tag, paginated 20 per page, total count in header
- highlights matched tag; lists other tags on each post

Rankings PHP-parity (lib/member.rank.lib.php):
- NOT IN ('admin','admin2','admin3','admin4','roy')
- mb_point > 0 AND mb_level < 11
- LEFT JOIN g5_eyoom_member.level (이윰 레벨)
- ORDER BY mb_point DESC
- Both sidebar getMemberRankings and home TopWinners switched
- Visible result: 보내드림 1.66M / 코뚜롱 1.48M / 스티브박 1.40M (admin* hidden)

Freespin (game engine):
- inspection2.app_freespin (mb_id, slug, remaining)
- Scatter ≥3 grants 5-10 free spins
- Next spin uses bet=0; remaining-- recorded transactionally
- placeBetAndSpin returns freeSpinsRemaining

Admin write:
- /admin/plugin/recaptcha (saved into public.app_settings)
- /admin/roulette (g5_roulette_list rename/delete + reward list)
- /admin/lottery/winners (lottery_history, paginated 50)

Verify: 50 iter × 16 = 800/800 PASS

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 21:05:20 +09:00
chpark 782029d31f memo CRUD, admin yellowcard/sns/sms-write, scatter free-spin, theme-skinned mega
User pages:
- /memo: inbox/sent tabs with send + delete server actions on g5_memo
  (creates paired recv+send rows so both sides can delete independently)

Admin:
- /admin/eyoom/yellowcard: issue/withdraw warnings (g5_eyoom_yellowcard)
- /admin/plugin/sns: 4 OAuth providers (Naver/Kakao/Facebook/Google),
  saved into public.app_settings with social_<provider> keys
- /admin/sms/write: mock SMS send + recent 30 from sms5_history

Game engine:
- scatter symbol with 5% spawn rate
- 3+ scatters trigger free-spin (no bet deducted, message + flag)
- 88포춘: wild=🌟, scatter=🎁

Theme skinning (basic/amina/youngcart variants of):
- .bg-mega gradient (mega-menu nav)
- .bg-brand-radial (Hero aurora) — basic blue, amina cyan, youngcart orange
- root layout writes data-theme="..." attribute

Verify: 50 iter × 16 = 800/800 PASS

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 18:11:28 +09:00
chpark 0d248eb6ae React standalone on :8088, mypage tabs, sms config, wild symbols, cross-verify x16
Standalone deployment:
- React Next.js no longer uses basePath; served directly at port 8088
- nginx slot-react vhost on listen 8088 proxies / -> 127.0.0.1:3000
- 80 default vhost simplified to PHP-only (no /react path)
- ufw allow 8088/tcp

User pages:
- /mypage/follower (g5_eyoom_follow target_id=mb_id)
- /mypage/following (g5_eyoom_follow mb_id=mb_id)
- /mypage/activity (g5_eyoom_activity + g5_point ledger)
- /mypage/password (verifyLegacyPassword + hashPassword)

Admin:
- /admin/sms/config (sms5_config single-row CRUD)

Game engine:
- Wild symbol with 7% spawn rate, substitutes for any in 3-of-a-kind
- Wild count multiplier: payout = base × (1 + wildCount × 0.5)

Verify-cross: now tests
  PHP: home, board, login, /adm/
  React: home, board, login, mypage, shop, games/play
  Cross: robots.txt block on both
  Theme cookie: 4 themes (basic/eyoom/amina/youngcart) round-trip
50 iterations × 16 = 800/800 PASS

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 14:53:58 +09:00
chpark 4e6a304615 React behind /react basePath; nginx restores 80 to PHP; cross-verify suite
Co-existence on 201: 80=PHP gnuboard5 (default vhost), /react=Next.js (basePath)
- Dockerfile takes ARG NEXT_PUBLIC_BASE_PATH, passes to Next build for asset/route prefixing
- next.config.mjs reads NEXT_PUBLIC_BASE_PATH at build time
- nginx slot-clone vhost: location /react proxies to 3000 unchanged; / and /adm/ go to 8090
- /robots.txt remains nginx-served (all-bot block)

Design polish:
- Header MegaPanel sub-link: gradient hover + white text + shadow on hover (was hover:bg-brand-50 only)
- Top-level mega menu: bigger padding + bold + bottom-bar hover indicator
- StatStrip: 8 narrow cards → 4 large cards (sm:grid-cols-4) with 12 size icon, 28px value, blur halo

Verify:
- scripts/verify-cross.mjs: parallel PHP (admin/clone1234) + React (testlogin/test1234) flow
- 50 iterations × 11 checks = 550/550 PASS

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 14:17:43 +09:00
chpark df72d3888a mypage tabs + admin items/sendcost/eyoom-menu + cert/charge mocks + theme cookie
mypage:
- /mypage/posts: posts authored across active boards (g5_write_*)
- /mypage/scrap: scraped list with subject lookup + delete action
- /mypage/respond: who liked/disliked the user's posts (g5_board_good x g5_write_*)
- /mypage/profile: editable email/hp/homepage/signature/profile + open/mailling/sms toggles

admin:
- /admin/shop/items: inline edit price/stock/use + create
- /admin/shop/sendcost: zip range shipping rules CRUD
- /admin/eyoom/menu: per-theme menu inline edit (g5_eyoom_menu)

mocks:
- /auth/cert: identity verification (g5_member_cert_history insert + member update)
- /wallet/charge: point top-up (mb_point + g5_point ledger), 5 PG presets

theme:
- /api/ui/theme picks {basic|eyoom|amina|youngcart} into slot_theme cookie
- root layout reads cookie, injects --theme-primary CSS var + data-theme attribute

Verify: 600/600 PASS over 50 iterations

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 12:26:03 +09:00
chpark c231d652fb 14-game engine + /shop/buylist + visit counter + 4 admin write pages + theme tokens
Game engine: extended to 14 slot games (seastory/davinci/oceanparadise/
  cherrymaster/yamato/kyoushi/lupin/taiku/matsuri/marilyn/giatrus/rings/
  bakabon/slot) with per-game symbol weights and paytable

Pages:
- /shop/buylist: member order history (g5_shop_order)
- /admin/config/popups: g5_new_win create/delete with begin/end times
- /admin/boards/faq: g5_faq_master CRUD
- /admin/boards/contents: g5_content static page editor
- /admin/shop/banners: g5_shop_banner CRUD

Visit counter:
- lib/visit-counter.ts noteVisit() with throttled g5_visit_sum upsert
- Layout fires fire-and-forget on every render
- maybeRun('compress_visit_log') purges 90d+ entries

Themes:
- amina: sky-blue minimalist tokens
- youngcart: warm orange commerce tokens

Mypage: 구매내역 link now points to /shop/buylist (was /shop/orderinquiry)

Verify: 600/600 PASS over 50 iterations after deploy

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 12:08:06 +09:00
chpark d175f46a09 shop checkout flow + 3-game spin engine + admin board edit + lightweight cron
Shop: /shop/[itemId], /shop/cart with checkout, /shop/order/[odId]
Games: 3-game engine (fortunes, fivetreasures, bacara), /games/[game]/play
Admin: /admin/boards inline rename + actions
Cron: PG-row-lock cron helper (no Redis needed)
Verify: 600/600 PASS over 50 iterations

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 07:19:28 +09:00
chpark 04bb3e617f V3 home: TopWinners + HotBoardsCarousel; shop list; admin point/level/block
Home additions:
- TopWinners: top 5 point holders with tiered medal cards
- HotBoardsCarousel: horizontally scrollable boards (free/review/mukti/humor/pick/lottery_ticket/guarantee/notice)
- StatStrip wired to live g5_visit_sum / g5_member / g5_board / g5_point
- Sidebar visitors now reads g5_visit_sum (today/yesterday/max/total)

New page:
- /shop — youngcart point mall list with category tabs + pagination

Admin write actions:
- /admin/members: server actions adjustMemberPoint (logs to g5_point), changeMemberLevel, toggleMemberBlock
- Inline forms per row replace the prior read-only table

Verify: 500/500 PASS over 50 iterations (login/comment/good/scrap/logout)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 02:53:21 +09:00
chpark 59001dbc5f Add 201 React deploy + admin catch-all + redesign + tests
Stack on 201: PG 17 + Next.js 15 (Docker) + nginx (/, /php-ref/)
Home: StatStrip (8 metrics), LiveActivity feed, refined Hero aurora
Admin: 80+ menu catch-all renderer + read-only legacy table queries
Auth/CRUD: fix narrowing in 6 action routes, fix wr_last varchar(19),
  fix back() new URL on missing referer
Verify: 50/50 PASS across 5 iterations of login + comment + good + scrap

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 02:44:18 +09:00
chpark ca965fec90 Wire menu URL rewrites + add /games hub + end-to-end verification (85/85)
## Menu rewrites against the production /bbs/*.php URLs
The g5_eyoom_menu rows store legacy PHP URLs verbatim (/bbs/tv.php,
/bbs/point_guide.php, /bbs/exchange-amount.php, /bbs/Bighandbro.php,
/bbs/event_exchange.php, /bbs/slotlife.php, /shop/list.php,
/shop/orderinquiry.php, /roulette/?idx=1, /plugin/swiunApi/game.php?gt=mix
…). Added rewriters that map every one of those to the new app routes so
clicking any menu item lands on a real page.

## /games hub page
The 포인트게임 top-level link used to 404 (it pointed to /games which
didn't exist as a page). Built a proper hub: gradient hero, 15-tile
slot simulator grid (each with a unique color gradient + emoji), and
two callout cards for sports/mini-game branches.

## /tv/bighand
큰손형 방송 dedicated page with KICK CTA + schedule.

## Header polish
- whitespace-nowrap on every menu label so 보증사이트 / 먹튀사이트 /
  슬생TV no longer wrap at narrow widths.
- MegaPanel renderer that turns 3rd-level eyoom menu groups (스포츠 /
  미니게임 / 슬롯·릴) into multi-column section blocks instead of
  collapsing to an empty dropdown.
- Replaced 구매내역 link with /mypage so utility-bar 404 disappears.

## verify-everything.mjs
New end-to-end script that:
- Crawls every menu link (64 unique URLs) and asserts non-404.
- Real interaction tests: testlogin login → board list → post view →
  comment POST → recommend POST → admin login → admin dashboard render
  check → admin theme picker visible (4 themes) → theme switch POST →
  logout POST → attendance check POST.

Result: PASS 85 / FAIL 0 / TOTAL 85. Report at next-app/verify-out/.
2026-04-27 20:54:51 +09:00
chpark 50f1d5cfb6 Pull mega-menu from g5_eyoom_menu and redesign home with Tailwind v4
## Menu now matches production exactly
- Read the 122-row inspection2.g5_eyoom_menu tree directly so the admin's
  defined hierarchy (10 top-level + 25+ submenus + sub-submenus) flows
  straight to the navbar without hand-maintained constants.
- Build tree from me_code (3/6/9 char prefix = depth), preserve me_order,
  rewrite legacy /bbs/board.php?bo_table=foo + /bbs/qalist.php +
  game/exchange/lottery URLs into the new app routes.
- Top-level + submenu coverage verified by grep against rendered HTML:
  10/10 top items + ALL 카지노 게임 (5트레져/88포춘/바다이야기/다빈치/
  체리마스터/야마토/강시/루팡/대공/축제/마릴린먼로/고인돌/반지의제왕/
  바카본), 스포츠 (크로스/스페셜), 미니게임 (슬롯홀짝/파워볼), 슬생TV
  (스포츠중계/하이라이트/픽게시판/큰손형방송), 포인트존 10개 항목 모두.

## Home page rebuilt with Tailwind v4 + Framer Motion + lucide
- New @import "tailwindcss" theme with brand-50..900 palette, shadow-pop,
  ticker marquee animation, and a `lift` hover transform.
- Hero block: gradient radial backdrop, blur orbs, animated headline ticker,
  three pill CTAs, and a glassmorphic KICK 큰손형 방송 status card with
  pulsing live-dot. Status pulled from getKickStatus() (live/break/offline
  by hour & weekday).
- 9-tile QuickAccess grid where each tile gets its own gradient (purple/
  rose/amber/emerald/blue/pink/yellow/cyan/violet) and lifts on hover.
- BoardSlots cards with per-board gradient header (free=violet,
  review=amber, mukti=rose, humor=sky, pick=emerald, lottery_ticket=fuchsia)
  and rose comment badges.
- Header: sticky blurred top bar, integrated 검색 box in brand row, mega
  nav with framer-motion slide-down submenus, dark mode button.
- Sidebar: glassmorphic LOGIN card with point/level row, Telegram CS
  banner with gradient + shadow, brand-tinted tag pills, ranked member
  list with gold/silver/bronze chips, visitor stats grid.
- Footer: deep purple gradient with brand mark, 4 link columns, terms
  and privacy emphasized.

## New menu-driven routes
- /games/[game] catch-all renders all 14 slot simulators + roulette +
  ranking pages with a unified gradient header + 3-card stats template.
- /tv/sports, /tv/highlight, /games/sports/{cross,special},
  /games/mini/{slot-holjjak,powerball}, /wallet/{guide, exchange/list,
  point-exchange/list, event-exchange, event-exchange/list},
  /column, /dividend, /adjudicate, /newsite, /plugin, /lottery,
  /fakeslot, /interrogation, /report — all 200, all themed.

## Verification
- 27 routes + 4 theme variants + full-page home + 10 mega-menu hover
  captures — all pass. PNGs under next-app/screenshots/.
2026-04-27 20:38:47 +09:00
chpark 30e9b7a8ee Build out the user-facing site to match production scope
After the initial scaffold the site was missing most of the production
surface (회원가입/마이페이지/메가메뉴 카테고리/관리자/게임/포인트존/...).
This commit closes that gap and verifies every route end-to-end with
playwright screenshots (27/27 pass).

## Theme system
- Replaced eyoom theme with a higher-fidelity reproduction of the
  production eb4_maga_005 layout: top utility bar (북마크/회원가입/구매내역
  /추가메뉴), brand row with 로그인/내글반응/쪽지 icon stack with badges,
  purple gradient mega-menu carrying 10 categories with submenus, dark
  mode toggle, sticky LOGIN box + 텔레그램CS box + 태그 클라우드 + 회원
  랭킹 + 방문자 stats in the sidebar, and a footer with 이용약관/개인정보
  처리방침/이메일무단수집거부.
- Added IndexHome slot to the theme contract; basic/amina/youngcart got
  matching implementations so theme switching keeps working.
- Layout now consistently provides the right-rail sidebar on public pages
  and hides it on /login, /register, /mypage and /admin (admin uses its
  own left rail).

## Pages added
- Auth: /register (with API-backed insert into the new members table),
  /auth/recover (id+password recovery shells).
- /mypage dashboard with 12 sub-routes.
- /memo, /bookmarks, /new, /tags, /tag/[tag], /profile/[nick].
- 10 mega-menu landing pages: /guarantee, /guarantee/apply, /mukti,
  /complaint, /inspection, /fakesite, /event, /lottery_ticket,
  /gift_coupons, /gift_exchanges, /notice; /games (bacara, fortunes,
  fivetreasures, slot, roulette, ranking); /wallet (+ exchange,
  point-exchange, slotbuff); /tv; /guide (+ community/pointgame/mukti/tv);
  /help/qa, /help/faq.
- Static pages: /page/provision, /page/privacy, /page/noemail,
  /page/aboutus, /page/manual, /page/attendance.
- Per-board: /[slug]/write, /[slug]/[wrId]/edit, /[slug]/search.

## Post interactions (wired against legacy g5_* tables)
- POST /api/posts/create        — insert into inspection2.g5_write_<slug>
- POST /api/posts/[id]/comment  — insert is_comment row + bump wr_comment
- POST /api/posts/[id]/good|bad — bump wr_good/wr_nogood + g5_board_good
- POST /api/posts/[id]/scrap    — insert g5_scrap
- POST /api/posts/[id]/report   — write into writing_activity
- POST /api/posts/[id]/delete   — owner+admin gate, soft-delete row
- POST /api/ui/dark-mode        — flip slot_dark cookie

## Admin
- /admin layout with left nav (10 sections) gated by member level >= 10.
- /admin                — dashboard with live counts pulled from PG
- /admin/members        — searchable member list with status badges
- /admin/boards         — board roster with post/comment counts
- /admin/betting        — bacara/swiun/game-point counters + recent feed
- /admin/stats          — 14-day visit chart + top boards + level histogram
- /admin/themes         — 4-theme picker (already existed, now polished)
- /admin/{menu,permissions,points,games} — stubs for M5

## Infra fixes
- Postgres pool hoisted onto globalThis so HMR doesn't leak connections
  ("sorry, too many clients already" 500s).
- Removed broken Next.js redirects() entry that prevented dev from booting.

## Verification
- scripts/screenshot.mjs: pre-logs-in as admin/test1234, then captures 27
  pages + 4 theme variants of /. All 200, all rendered. PNGs committed
  under next-app/screenshots/ for review.
2026-04-27 20:20:49 +09:00
chpark 980d7d905d Add Next.js + PostgreSQL rewrite scaffold with 4-theme system
Stack
- Next.js 15 (App Router) + TypeScript + Drizzle ORM + postgres-js
- Node scrypt for password hashing; PBKDF2 verifier for legacy gnuboard5 hashes
- pnpm workspace monorepo: apps/web + packages/{db,auth,themes,...}

Themes (admin-selectable at /admin/themes)
- basic     : 그누보드 default reproduction (light, blue accent)
- eyoom     : eb4_maga_005 매거진 reproduction (dark, orange accent, ranking sidebar)
- amina     : Aminam Builder reproduction (light, violet gradient, card grid)
- youngcart : 영카트 shop reproduction (red accent, search bar, category nav)

DB
- New schema (12 tables) pushed to PG via drizzle-kit: members, sessions, boards,
  posts, point_ledger, app_settings, bacara_*, lottery_tickets, roulette_spins,
  game_points, board_groups
- Legacy data still readable from inspection2 schema via @slot/db/legacy

Verified end-to-end against the migrated DB on localhost:3000:
- Home renders with active theme tokens injected as CSS variables
- /free lists 442K real posts from inspection2.g5_write_free
- Login (testlogin/test1234) issues session cookie, header switches to
  "테스트님 환영합니다 / 로그아웃"
- Switching app_settings.theme.global from eyoom → amina swaps colors,
  layout, and Korean nav labels site-wide on next request

Migration docs added: 03-migration-plan, 04-theme-architecture,
05-local-dev-setup, 06-feature-inventory.
2026-04-27 18:51:32 +09:00