careermate 0.0.5 → 0.0.7
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.
- package/AGENTS.md +13 -10
- package/INSTALL.md +16 -15
- package/README.md +24 -24
- package/THIRD_PARTY_NOTICES.md +2 -3
- package/bin/careermate.mjs +8 -1
- package/dist/career-os/README.md +12 -6
- package/dist/career-os/eop/career-description.md +139 -0
- package/dist/career-os/eop/cover-letter.md +10 -5
- package/dist/career-os/eop/fit-analysis.md +16 -6
- package/dist/career-os/eop/interview-prep.md +209 -21
- package/dist/career-os/eop/job-analysis.md +6 -4
- package/dist/career-os/eop/profile-extraction.md +5 -4
- package/dist/career-os/knowledge/cover-letter.md +5 -4
- package/dist/career-os/knowledge/fit-matching.md +8 -8
- package/dist/career-os/knowledge/human-writing.md +2 -0
- package/dist/career-os/knowledge/interview-behavioral.md +76 -8
- package/dist/career-os/knowledge/interview-technical.md +106 -4
- package/dist/career-os/knowledge/linkedin-profile.md +1 -1
- package/dist/career-os/knowledge/networking-referrals.md +1 -1
- package/dist/career-os/knowledge/offer-evaluation-decision.md +10 -10
- package/dist/career-os/knowledge/portfolio.md +3 -3
- package/dist/career-os/knowledge/verifiers/ats-compat.md +8 -4
- package/dist/career-os/knowledge/verifiers/human-voice.md +4 -2
- package/dist/career-os/knowledge/verifiers/recency-staleness.md +1 -1
- package/dist/career-os/knowledge/verifiers/responsiveness-on-target.md +2 -2
- package/dist/career-os/knowledge/verifiers/truthfulness.md +1 -1
- package/dist/doctor.mjs +692 -71
- package/dist/mcp.mjs +710 -71
- package/dist/migrate.mjs +52 -1
- package/dist/public/app.js +42 -16
- package/dist/public/i18n/en/applications.js +23 -0
- package/dist/public/i18n/en/common.js +22 -0
- package/dist/public/i18n/en/documents.js +133 -0
- package/dist/public/i18n/en/home.js +75 -0
- package/dist/public/i18n/en/interview.js +69 -0
- package/dist/public/i18n/en/jobs.js +152 -0
- package/dist/public/i18n/en/nav.js +18 -0
- package/dist/public/i18n/en/profile.js +201 -0
- package/dist/public/i18n/en/settings.js +127 -0
- package/dist/public/i18n/en/status.js +22 -0
- package/dist/public/i18n/en.js +17 -0
- package/dist/public/i18n/ko/applications.js +23 -0
- package/dist/public/i18n/ko/common.js +22 -0
- package/dist/public/i18n/ko/documents.js +133 -0
- package/dist/public/i18n/ko/home.js +63 -0
- package/dist/public/i18n/ko/interview.js +69 -0
- package/dist/public/i18n/ko/jobs.js +152 -0
- package/dist/public/i18n/ko/nav.js +18 -0
- package/dist/public/i18n/ko/profile.js +201 -0
- package/dist/public/i18n/ko/settings.js +127 -0
- package/dist/public/i18n/ko/status.js +23 -0
- package/dist/public/i18n/ko.js +18 -0
- package/dist/public/i18n.js +55 -0
- package/dist/public/index.html +1 -0
- package/dist/public/lib.js +24 -17
- package/dist/public/pages/applications.js +17 -21
- package/dist/public/pages/documents.js +153 -107
- package/dist/public/pages/home.js +88 -53
- package/dist/public/pages/interview.js +105 -51
- package/dist/public/pages/jobs.js +330 -106
- package/dist/public/pages/profile.js +157 -152
- package/dist/public/pages/settings.js +154 -102
- package/dist/public/styles.css +28 -1
- package/dist/web.mjs +495 -75
- package/docs/FAQ.md +23 -3
- package/docs/MCP_TOOLS.md +22 -13
- package/docs/START_WORKFLOW.md +3 -3
- package/docs/SUPPORTED_AI_APPS.md +13 -0
- package/docs/WORKFLOWS.md +77 -20
- package/docs/career-os/README.md +12 -6
- package/docs/career-os/eop/career-description.md +139 -0
- package/docs/career-os/eop/cover-letter.md +10 -5
- package/docs/career-os/eop/fit-analysis.md +16 -6
- package/docs/career-os/eop/interview-prep.md +209 -21
- package/docs/career-os/eop/job-analysis.md +6 -4
- package/docs/career-os/eop/profile-extraction.md +5 -4
- package/docs/career-os/knowledge/cover-letter.md +5 -4
- package/docs/career-os/knowledge/fit-matching.md +8 -8
- package/docs/career-os/knowledge/human-writing.md +2 -0
- package/docs/career-os/knowledge/interview-behavioral.md +76 -8
- package/docs/career-os/knowledge/interview-technical.md +106 -4
- package/docs/career-os/knowledge/linkedin-profile.md +1 -1
- package/docs/career-os/knowledge/networking-referrals.md +1 -1
- package/docs/career-os/knowledge/offer-evaluation-decision.md +10 -10
- package/docs/career-os/knowledge/portfolio.md +3 -3
- package/docs/career-os/knowledge/verifiers/ats-compat.md +8 -4
- package/docs/career-os/knowledge/verifiers/human-voice.md +4 -2
- package/docs/career-os/knowledge/verifiers/recency-staleness.md +1 -1
- package/docs/career-os/knowledge/verifiers/responsiveness-on-target.md +2 -2
- package/docs/career-os/knowledge/verifiers/truthfulness.md +1 -1
- package/package.json +2 -2
- package/packages/core/src/onboarding.ts +2 -1
- package/packages/core/src/services.ts +134 -17
- package/packages/core/src/summary.ts +59 -1
- package/packages/core/src/verify/lint.ts +4 -0
- package/packages/db/src/index.ts +1 -0
- package/packages/db/src/repositories.ts +0 -0
- package/packages/db/src/schema.ts +17 -0
- package/packages/exporters/src/index.ts +28 -17
- package/packages/knowledge/src/index.ts +55 -9
- package/packages/mcp-tools/src/tools.ts +250 -24
- package/packages/mcp-tools/src/update.ts +30 -15
- package/packages/parsers/src/documents.ts +12 -1
- package/packages/prompts/src/humanize.ts +46 -0
- package/packages/prompts/src/index.ts +5 -1
- package/packages/prompts/src/install.ts +4 -4
- package/packages/prompts/src/onboarding.ts +4 -4
- package/packages/prompts/src/system.ts +9 -7
- package/packages/shared/src/enums.ts +14 -4
- package/packages/shared/src/schemas.ts +41 -0
- package/packages/workflows/src/definitions.ts +45 -8
- package/scripts/init.ts +284 -13
- package/dist/site/analytics.js +0 -97
- package/dist/site/favicon.svg +0 -1
- package/dist/site/fonts/PretendardVariable.woff2 +0 -0
- package/dist/site/icon-180.png +0 -0
- package/dist/site/icon-512.png +0 -0
- package/dist/site/index.html +0 -465
- package/dist/site/landing.js +0 -163
- package/dist/site/llms-install.txt +0 -218
- package/dist/site/robots.txt +0 -4
- package/dist/site/sitemap.xml +0 -21
- package/dist/site/start.html +0 -356
- package/dist/site/style.css +0 -665
- package/dist/site/vercel.json +0 -20
package/dist/site/index.html
DELETED
|
@@ -1,465 +0,0 @@
|
|
|
1
|
-
<!DOCTYPE html>
|
|
2
|
-
<html lang="ko" data-theme="dark">
|
|
3
|
-
<head>
|
|
4
|
-
<meta charset="utf-8" />
|
|
5
|
-
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
|
6
|
-
<!-- Resolve the saved theme before first paint (default: dark) to avoid a flash. -->
|
|
7
|
-
<script>
|
|
8
|
-
(function () {
|
|
9
|
-
try {
|
|
10
|
-
var t = window.localStorage.getItem('careermate-theme') || window.localStorage.getItem('cf-theme');
|
|
11
|
-
document.documentElement.setAttribute('data-theme', t === 'light' || t === 'dark' ? t : 'dark');
|
|
12
|
-
} catch (e) { document.documentElement.setAttribute('data-theme', 'dark'); }
|
|
13
|
-
})();
|
|
14
|
-
</script>
|
|
15
|
-
<title>CareerMate — 말로 시키는 커리어 정리</title>
|
|
16
|
-
<meta name="description" content="Codex·Claude 같은 AI에게 이력서 등록, 공고 분석, 자기소개서 작성, 지원 현황 관리를 말로 시키세요. CareerMate는 결과를 이 컴퓨터 안에 정리합니다." />
|
|
17
|
-
<link rel="canonical" href="https://careermate.life/" />
|
|
18
|
-
<meta name="google-site-verification" content="MfU5uwl1RNXKklsJhXz2hPCRytjLpCjCXSa2ls5JQH0" />
|
|
19
|
-
<meta name="theme-color" content="#faf8f4" media="(prefers-color-scheme: light)" />
|
|
20
|
-
<meta name="theme-color" content="#14130f" media="(prefers-color-scheme: dark)" />
|
|
21
|
-
|
|
22
|
-
<!-- icons -->
|
|
23
|
-
<link rel="icon" href="favicon.svg" type="image/svg+xml" />
|
|
24
|
-
<link rel="apple-touch-icon" href="icon-180.png" />
|
|
25
|
-
|
|
26
|
-
<!-- Open Graph -->
|
|
27
|
-
<meta property="og:type" content="website" />
|
|
28
|
-
<meta property="og:site_name" content="CareerMate" />
|
|
29
|
-
<meta property="og:locale" content="ko_KR" />
|
|
30
|
-
<meta property="og:url" content="https://careermate.life/" />
|
|
31
|
-
<meta property="og:title" content="CareerMate — 말로 시키는 커리어 정리" />
|
|
32
|
-
<meta property="og:description" content="이력서·자기소개서·지원 현황을 이 컴퓨터 안에서 관리하세요. 분석·글쓰기는 평소 쓰던 AI가, 데이터 보관은 CareerMate가 맡습니다." />
|
|
33
|
-
<meta property="og:image" content="https://careermate.life/og.png" />
|
|
34
|
-
<meta property="og:image:width" content="1200" />
|
|
35
|
-
<meta property="og:image:height" content="630" />
|
|
36
|
-
<meta property="og:image:alt" content="CareerMate — 로컬 전용 MCP 커리어 워크스페이스" />
|
|
37
|
-
|
|
38
|
-
<!-- Twitter / X -->
|
|
39
|
-
<meta name="twitter:card" content="summary_large_image" />
|
|
40
|
-
<meta name="twitter:title" content="CareerMate — 말로 시키는 커리어 정리" />
|
|
41
|
-
<meta name="twitter:description" content="이력서·자기소개서·지원 현황을 이 컴퓨터 안에서. 데이터는 외부로 나가지 않습니다." />
|
|
42
|
-
<meta name="twitter:image" content="https://careermate.life/og.png" />
|
|
43
|
-
|
|
44
|
-
<link rel="preload" href="fonts/PretendardVariable.woff2" as="font" type="font/woff2" crossorigin />
|
|
45
|
-
<link rel="stylesheet" href="style.css" />
|
|
46
|
-
<!-- Privacy-friendly analytics for the marketing site only (never the local 127.0.0.1 app). -->
|
|
47
|
-
<script src="/analytics.js" defer></script>
|
|
48
|
-
</head>
|
|
49
|
-
<body>
|
|
50
|
-
<a class="skip-link" href="#top">본문으로 건너뛰기</a>
|
|
51
|
-
<!-- ============================================================ nav -->
|
|
52
|
-
<nav class="nav">
|
|
53
|
-
<a class="nav__brand" href="#top">
|
|
54
|
-
<span class="nav__logo" aria-hidden="true">C</span>
|
|
55
|
-
<span class="nav__name">CareerMate</span>
|
|
56
|
-
</a>
|
|
57
|
-
<div class="nav__links">
|
|
58
|
-
<a href="#how">사용 예시</a>
|
|
59
|
-
<a href="#features">할 수 있는 일</a>
|
|
60
|
-
<a href="#preview">화면</a>
|
|
61
|
-
<a href="#install">설치</a>
|
|
62
|
-
<a href="#privacy">개인정보</a>
|
|
63
|
-
</div>
|
|
64
|
-
<div class="nav__actions">
|
|
65
|
-
<a class="nav__icon" href="https://github.com/osntak/careermate" target="_blank" rel="noopener" aria-label="GitHub 저장소" title="GitHub에서 소스 보기"><svg viewBox="0 0 16 16" fill="currentColor" aria-hidden="true"><path d="M8 0C3.58 0 0 3.58 0 8c0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38 0-.19-.01-.82-.01-1.49-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38A8.013 8.013 0 0 0 16 8c0-4.42-3.58-8-8-8z"/></svg></a>
|
|
66
|
-
<button class="theme-toggle" id="theme-toggle" type="button" aria-label="다크 모드 전환" title="다크 모드 전환">
|
|
67
|
-
<svg class="i-sun" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><circle cx="12" cy="12" r="4"/><path d="M12 2v2M12 20v2M4.9 4.9l1.4 1.4M17.7 17.7l1.4 1.4M2 12h2M20 12h2M4.9 19.1l1.4-1.4M17.7 6.3l1.4-1.4"/></svg>
|
|
68
|
-
<svg class="i-moon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M21 12.8A9 9 0 1 1 11.2 3a7 7 0 0 0 9.8 9.8z"/></svg>
|
|
69
|
-
</button>
|
|
70
|
-
</div>
|
|
71
|
-
</nav>
|
|
72
|
-
|
|
73
|
-
<main id="top" tabindex="-1">
|
|
74
|
-
|
|
75
|
-
<!-- ========================================================== hero -->
|
|
76
|
-
<header class="hero">
|
|
77
|
-
<div class="hero__main">
|
|
78
|
-
<span class="pill-badge">
|
|
79
|
-
<span class="pill-badge__dot" aria-hidden="true"></span>
|
|
80
|
-
로컬 전용 · 가입 없음
|
|
81
|
-
</span>
|
|
82
|
-
<h1 class="hero__title">
|
|
83
|
-
AI에게 말하면<br />
|
|
84
|
-
커리어가 정리됩니다
|
|
85
|
-
</h1>
|
|
86
|
-
<p class="hero__lede">
|
|
87
|
-
이력서, 공고, 자기소개서, 지원 현황까지. 말하면 내 컴퓨터에 저장됩니다.
|
|
88
|
-
</p>
|
|
89
|
-
|
|
90
|
-
<ul class="trust-strip" aria-label="안심 포인트">
|
|
91
|
-
<li>내 컴퓨터에만 저장</li>
|
|
92
|
-
<li>외부 업로드 없음</li>
|
|
93
|
-
<li>별도 가입 없음</li>
|
|
94
|
-
</ul>
|
|
95
|
-
|
|
96
|
-
<div class="hero__cta">
|
|
97
|
-
<a class="btn btn--primary" href="start.html">처음 시작하기</a>
|
|
98
|
-
<a class="btn btn--ghost" href="#preview">
|
|
99
|
-
데모 보기
|
|
100
|
-
</a>
|
|
101
|
-
</div>
|
|
102
|
-
|
|
103
|
-
</div>
|
|
104
|
-
|
|
105
|
-
<aside class="hero__demo command-demo" data-command-demo aria-label="CareerMate 사용 예시">
|
|
106
|
-
<div class="command-card">
|
|
107
|
-
<div class="command-card__head">
|
|
108
|
-
<span class="command-card__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
109
|
-
<span class="command-card__title">내 AI 앱</span>
|
|
110
|
-
<span class="command-card__status" data-demo-status>문서 등록</span>
|
|
111
|
-
</div>
|
|
112
|
-
<div class="command-card__file">
|
|
113
|
-
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.9" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M14 2H7a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h10a2 2 0 0 0 2-2V7z"/><path d="M14 2v5h5"/><path d="M9 13h6"/><path d="M9 17h4"/></svg>
|
|
114
|
-
<span data-demo-file>자기소개서.pdf</span>
|
|
115
|
-
<strong data-demo-file-state>업로드됨</strong>
|
|
116
|
-
</div>
|
|
117
|
-
<div class="command-card__body">
|
|
118
|
-
<div class="command-card__bubble command-card__bubble--user">
|
|
119
|
-
<span>나</span>
|
|
120
|
-
<p data-demo-command>이 자기소개서 읽고 CareerMate에 등록해줘.</p>
|
|
121
|
-
</div>
|
|
122
|
-
<div class="command-card__bubble command-card__bubble--ai">
|
|
123
|
-
<span>AI</span>
|
|
124
|
-
<p data-demo-result>문서를 읽고 자기소개서 버전으로 저장했어요. 핵심 경험 4개도 함께 정리했습니다.</p>
|
|
125
|
-
</div>
|
|
126
|
-
</div>
|
|
127
|
-
<ol class="command-card__steps" aria-label="예시 선택">
|
|
128
|
-
<li><button class="is-active" type="button" data-demo-step="0" aria-current="true">문서</button></li>
|
|
129
|
-
<li><button type="button" data-demo-step="1">대시보드</button></li>
|
|
130
|
-
<li><button type="button" data-demo-step="2">공고</button></li>
|
|
131
|
-
<li><button type="button" data-demo-step="3">자소서</button></li>
|
|
132
|
-
<li><button type="button" data-demo-step="4">면접</button></li>
|
|
133
|
-
</ol>
|
|
134
|
-
<div class="command-card__progress" aria-hidden="true"><span></span></div>
|
|
135
|
-
</div>
|
|
136
|
-
<p class="hero__demo-note">명령어를 외우지 않아도 됩니다. 그냥 이렇게 말하면 돼요.</p>
|
|
137
|
-
</aside>
|
|
138
|
-
</header>
|
|
139
|
-
|
|
140
|
-
<!-- ========================================================== how -->
|
|
141
|
-
<section id="how" class="section">
|
|
142
|
-
<div class="section__head">
|
|
143
|
-
<h2>AI에게 시키고, CareerMate에서 확인하세요</h2>
|
|
144
|
-
<p>어려운 설정 이름을 기억할 필요 없이, 평소 대화하듯 커리어 작업을 이어가면 됩니다.</p>
|
|
145
|
-
</div>
|
|
146
|
-
<div class="cards-3">
|
|
147
|
-
<article class="feature">
|
|
148
|
-
<span class="feature__no">01</span>
|
|
149
|
-
<h3>파일을 주고 말하기</h3>
|
|
150
|
-
<p>이력서나 자기소개서를 올리고 “읽고 등록해줘”라고 말하세요.</p>
|
|
151
|
-
</article>
|
|
152
|
-
<article class="feature">
|
|
153
|
-
<span class="feature__no">02</span>
|
|
154
|
-
<h3>공고를 붙이고 분석</h3>
|
|
155
|
-
<p>채용공고 링크나 텍스트를 주면 내 경력과 맞춰 강점·보완점을 정리합니다.</p>
|
|
156
|
-
</article>
|
|
157
|
-
<article class="feature">
|
|
158
|
-
<span class="feature__no">03</span>
|
|
159
|
-
<h3>대시보드에서 확인</h3>
|
|
160
|
-
<p>자소서 버전, 지원 상태, 면접 준비 자료가 한 곳에 모입니다.</p>
|
|
161
|
-
</article>
|
|
162
|
-
</div>
|
|
163
|
-
</section>
|
|
164
|
-
|
|
165
|
-
<!-- ====================================================== features -->
|
|
166
|
-
<section id="features" class="section">
|
|
167
|
-
<div class="section__head">
|
|
168
|
-
<h2>말로 시킬 수 있는 일</h2>
|
|
169
|
-
<p>처음 정리한 경력은 다음 공고와 다음 자기소개서에도 계속 이어집니다.</p>
|
|
170
|
-
</div>
|
|
171
|
-
<div class="checks">
|
|
172
|
-
<div class="check"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M20 6 9 17l-5-5"/></svg><div><strong>이력서·자기소개서 등록</strong><span>파일을 읽고 경력·프로젝트·스킬로 정리.</span></div></div>
|
|
173
|
-
<div class="check"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M20 6 9 17l-5-5"/></svg><div><strong>채용공고 저장</strong><span>링크나 텍스트에서 회사·직무·요건 추출.</span></div></div>
|
|
174
|
-
<div class="check"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M20 6 9 17l-5-5"/></svg><div><strong>내 경력과 공고 비교</strong><span>강점, 빈칸, 강조할 키워드를 한 번에.</span></div></div>
|
|
175
|
-
<div class="check"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M20 6 9 17l-5-5"/></svg><div><strong>공고별 자기소개서</strong><span>초안과 수정본을 버전으로 쌓아 비교.</span></div></div>
|
|
176
|
-
<div class="check"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M20 6 9 17l-5-5"/></svg><div><strong>지원 현황 관리</strong><span>작성 중, 지원 완료, 서류 합격, 면접까지.</span></div></div>
|
|
177
|
-
<div class="check"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.4" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M20 6 9 17l-5-5"/></svg><div><strong>면접 준비</strong><span>예상 질문, STAR 답변, 1분 자기소개 초안.</span></div></div>
|
|
178
|
-
</div>
|
|
179
|
-
</section>
|
|
180
|
-
|
|
181
|
-
<!-- ======================================================= preview -->
|
|
182
|
-
<section id="preview" class="section">
|
|
183
|
-
<div class="section__head section__head--center">
|
|
184
|
-
<h2>내 데이터를 눈으로 확인</h2>
|
|
185
|
-
<p>지원 현황과 문서를 한 화면에서 확인하세요.</p>
|
|
186
|
-
<div class="section__cta">
|
|
187
|
-
<a class="btn btn--primary" href="demo/">데모 둘러보기 →</a>
|
|
188
|
-
</div>
|
|
189
|
-
</div>
|
|
190
|
-
|
|
191
|
-
<div class="carousel" id="dash-carousel" role="group" aria-roledescription="캐러셀" aria-label="대시보드 화면 미리보기" tabindex="0">
|
|
192
|
-
<div class="carousel__viewport">
|
|
193
|
-
<div class="carousel__track" id="carousel-track">
|
|
194
|
-
<figure class="slide">
|
|
195
|
-
<div class="browser">
|
|
196
|
-
<div class="browser__bar">
|
|
197
|
-
<span class="browser__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
198
|
-
<span class="browser__url">127.0.0.1:4319</span>
|
|
199
|
-
</div>
|
|
200
|
-
<div class="browser__body">
|
|
201
|
-
<img class="shot__img shot__img--light" src="shots/home-light.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 홈 대시보드 — 지원 파이프라인과 할 일, 최근 활동" />
|
|
202
|
-
<img class="shot__img shot__img--dark" src="shots/home-dark.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 홈 대시보드 (다크) — 지원 파이프라인과 할 일, 최근 활동" />
|
|
203
|
-
</div>
|
|
204
|
-
</div>
|
|
205
|
-
<figcaption><strong>홈</strong> — 파이프라인·할 일·활동을 한 화면에</figcaption>
|
|
206
|
-
</figure>
|
|
207
|
-
|
|
208
|
-
<figure class="slide">
|
|
209
|
-
<div class="browser">
|
|
210
|
-
<div class="browser__bar">
|
|
211
|
-
<span class="browser__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
212
|
-
<span class="browser__url">127.0.0.1:4319/#/applications</span>
|
|
213
|
-
</div>
|
|
214
|
-
<div class="browser__body">
|
|
215
|
-
<img class="shot__img shot__img--light" src="shots/applications-light.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 지원 현황 — 상태별로 정리된 지원 목록" />
|
|
216
|
-
<img class="shot__img shot__img--dark" src="shots/applications-dark.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 지원 현황 (다크) — 상태별로 정리된 지원 목록" />
|
|
217
|
-
</div>
|
|
218
|
-
</div>
|
|
219
|
-
<figcaption><strong>지원 현황</strong> — 8단계 상태별로 한눈에</figcaption>
|
|
220
|
-
</figure>
|
|
221
|
-
|
|
222
|
-
<figure class="slide">
|
|
223
|
-
<div class="browser">
|
|
224
|
-
<div class="browser__bar">
|
|
225
|
-
<span class="browser__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
226
|
-
<span class="browser__url">127.0.0.1:4319/#/jobs</span>
|
|
227
|
-
</div>
|
|
228
|
-
<div class="browser__body">
|
|
229
|
-
<img class="shot__img shot__img--light" src="shots/jobs-light.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 채용공고 — 적합도 점수와 진행 상태" />
|
|
230
|
-
<img class="shot__img shot__img--dark" src="shots/jobs-dark.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 채용공고 (다크) — 적합도 점수와 진행 상태" />
|
|
231
|
-
</div>
|
|
232
|
-
</div>
|
|
233
|
-
<figcaption><strong>채용공고</strong> — 적합도 점수와 진행 상태</figcaption>
|
|
234
|
-
</figure>
|
|
235
|
-
|
|
236
|
-
<figure class="slide">
|
|
237
|
-
<div class="browser">
|
|
238
|
-
<div class="browser__bar">
|
|
239
|
-
<span class="browser__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
240
|
-
<span class="browser__url">127.0.0.1:4319/#/documents</span>
|
|
241
|
-
</div>
|
|
242
|
-
<div class="browser__body">
|
|
243
|
-
<img class="shot__img shot__img--light" src="shots/documents-light.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 문서 — 자기소개서와 이력서를 버전과 함께 보관" />
|
|
244
|
-
<img class="shot__img shot__img--dark" src="shots/documents-dark.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 문서 (다크) — 자기소개서와 이력서를 버전과 함께 보관" />
|
|
245
|
-
</div>
|
|
246
|
-
</div>
|
|
247
|
-
<figcaption><strong>문서</strong> — 자기소개서·이력서를 버전과 함께</figcaption>
|
|
248
|
-
</figure>
|
|
249
|
-
|
|
250
|
-
<figure class="slide">
|
|
251
|
-
<div class="browser">
|
|
252
|
-
<div class="browser__bar">
|
|
253
|
-
<span class="browser__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
254
|
-
<span class="browser__url">127.0.0.1:4319/#/interview</span>
|
|
255
|
-
</div>
|
|
256
|
-
<div class="browser__body">
|
|
257
|
-
<img class="shot__img shot__img--light" src="shots/interview-light.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 면접 준비 — 예상 질문과 STAR, 1분 자기소개" />
|
|
258
|
-
<img class="shot__img shot__img--dark" src="shots/interview-dark.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 면접 준비 (다크) — 예상 질문과 STAR, 1분 자기소개" />
|
|
259
|
-
</div>
|
|
260
|
-
</div>
|
|
261
|
-
<figcaption><strong>면접 준비</strong> — 예상 질문·STAR·1분 자기소개</figcaption>
|
|
262
|
-
</figure>
|
|
263
|
-
|
|
264
|
-
<figure class="slide">
|
|
265
|
-
<div class="browser">
|
|
266
|
-
<div class="browser__bar">
|
|
267
|
-
<span class="browser__dots" aria-hidden="true"><i></i><i></i><i></i></span>
|
|
268
|
-
<span class="browser__url">127.0.0.1:4319/#/settings</span>
|
|
269
|
-
</div>
|
|
270
|
-
<div class="browser__body">
|
|
271
|
-
<img class="shot__img shot__img--light" src="shots/settings-light.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 설정 — 데이터 저장 위치와 연결 상태, 테마" />
|
|
272
|
-
<img class="shot__img shot__img--dark" src="shots/settings-dark.png" width="1360" height="940" loading="lazy" decoding="async" alt="CareerMate 설정 (다크) — 데이터 저장 위치와 연결 상태, 테마" />
|
|
273
|
-
</div>
|
|
274
|
-
</div>
|
|
275
|
-
<figcaption><strong>설정</strong> — 데이터 위치·내보내기·테마</figcaption>
|
|
276
|
-
</figure>
|
|
277
|
-
</div>
|
|
278
|
-
</div>
|
|
279
|
-
|
|
280
|
-
<button class="carousel__arrow carousel__arrow--prev" id="carousel-prev" type="button" aria-label="이전 화면">
|
|
281
|
-
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M15 18l-6-6 6-6"/></svg>
|
|
282
|
-
</button>
|
|
283
|
-
<button class="carousel__arrow carousel__arrow--next" id="carousel-next" type="button" aria-label="다음 화면">
|
|
284
|
-
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M9 18l6-6-6-6"/></svg>
|
|
285
|
-
</button>
|
|
286
|
-
</div>
|
|
287
|
-
<div class="carousel__dots" id="carousel-dots" role="tablist" aria-label="화면 선택"></div>
|
|
288
|
-
</section>
|
|
289
|
-
|
|
290
|
-
<!-- ======================================================= install -->
|
|
291
|
-
<section id="install" class="section">
|
|
292
|
-
<div class="section__head section__head--center">
|
|
293
|
-
<h2>설치는 세 단계면 충분합니다</h2>
|
|
294
|
-
<p>앱을 열고, 아래 문장을 붙여넣고, 연결됐는지만 확인하세요.</p>
|
|
295
|
-
</div>
|
|
296
|
-
|
|
297
|
-
<div class="quick-start" aria-label="빠른 설치 순서">
|
|
298
|
-
<article class="quick-start__step">
|
|
299
|
-
<span>1</span>
|
|
300
|
-
<h3>AI 앱 선택</h3>
|
|
301
|
-
<p>Claude나 Codex처럼 폴더를 열 수 있는 AI를 고릅니다.</p>
|
|
302
|
-
<a href="start.html">내게 맞는 길 보기</a>
|
|
303
|
-
</article>
|
|
304
|
-
<article class="quick-start__step">
|
|
305
|
-
<span>2</span>
|
|
306
|
-
<h3>프롬프트 붙여넣기</h3>
|
|
307
|
-
<p>아래 문장을 AI 대화창에 그대로 넣으면 설치 안내를 읽고 연결을 진행합니다.</p>
|
|
308
|
-
</article>
|
|
309
|
-
<article class="quick-start__step">
|
|
310
|
-
<span>3</span>
|
|
311
|
-
<h3>연결 확인</h3>
|
|
312
|
-
<p>앱을 다시 열고 “커리어메이트 연결됐는지 확인해줘”라고 말합니다.</p>
|
|
313
|
-
</article>
|
|
314
|
-
</div>
|
|
315
|
-
|
|
316
|
-
<p class="install-footnote install-footnote--label">AI에게 보낼 문장</p>
|
|
317
|
-
<div class="code code--install">
|
|
318
|
-
<button class="copy-btn" type="button" data-copy-target="code-prompt-quick">복사</button>
|
|
319
|
-
<pre id="code-prompt-quick">https://careermate.life/llms-install.txt 를 읽고, 그 안내대로 CareerMate를 이 폴더에 설치하고 연결해줘. 설치가 끝나면 앱 재시작 방법과 대시보드 주소(http://127.0.0.1:4319), 이력서를 등록하는 방법도 알려줘.</pre>
|
|
320
|
-
</div>
|
|
321
|
-
|
|
322
|
-
<p class="install-footnote install-footnote--label">터미널 명령어</p>
|
|
323
|
-
<div class="code code--install">
|
|
324
|
-
<button class="copy-btn" type="button" data-copy-target="code-npx-quick">복사</button>
|
|
325
|
-
<pre id="code-npx-quick">npx -y careermate init</pre>
|
|
326
|
-
</div>
|
|
327
|
-
|
|
328
|
-
<p class="install-footnote">웹·모바일 AI 앱은 내 컴퓨터의 로컬 도구를 직접 열 수 없어 연결 대상이 아닙니다.</p>
|
|
329
|
-
</section>
|
|
330
|
-
|
|
331
|
-
<!-- ======================================================= privacy -->
|
|
332
|
-
<section id="privacy" class="section">
|
|
333
|
-
<div class="privacy-card">
|
|
334
|
-
<div class="privacy-card__icon" aria-hidden="true">
|
|
335
|
-
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.7" stroke-linecap="round" stroke-linejoin="round"><path d="M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z"/><path d="M9 12l2 2 4-4"/></svg>
|
|
336
|
-
</div>
|
|
337
|
-
<div class="privacy-card__text">
|
|
338
|
-
<h2>당신의 데이터는 당신 컴퓨터를 떠나지 않습니다</h2>
|
|
339
|
-
<p>대시보드 서버는 <code>127.0.0.1</code>(이 컴퓨터)에만 바인딩되어 외부에서 접근할 수 없습니다.<br />MCP 서버가 외부로 내보내는 것은 (끌 수 있는) <strong>최신 버전 확인</strong>뿐이며, <strong>당신의 커리어 데이터는 전송하지 않습니다.</strong> 분석·글쓰기는 당신이 직접 고른 AI가 수행합니다.</p>
|
|
340
|
-
<ul class="privacy-card__list">
|
|
341
|
-
<li><strong>저장 위치</strong> <code>~/.careermate/careermate.sqlite</code></li>
|
|
342
|
-
<li><strong>내보내기</strong> 자기소개서 등을 <code>~/.careermate/exports</code>로</li>
|
|
343
|
-
<li><strong>삭제·관리</strong> 대시보드 <strong>설정(Settings)</strong>에서 직접</li>
|
|
344
|
-
</ul>
|
|
345
|
-
</div>
|
|
346
|
-
</div>
|
|
347
|
-
</section>
|
|
348
|
-
|
|
349
|
-
</main>
|
|
350
|
-
|
|
351
|
-
<footer class="foot">
|
|
352
|
-
<div class="foot__brand"><span class="nav__logo" aria-hidden="true">C</span> CareerMate</div>
|
|
353
|
-
<p>로컬에서 동작하는 MCP 기반 커리어 관리 도구. 모든 데이터는 이 컴퓨터에만 저장됩니다.</p>
|
|
354
|
-
<div class="foot__links">
|
|
355
|
-
<a href="#top">맨 위로</a>
|
|
356
|
-
<a href="#features">기능</a>
|
|
357
|
-
<a href="#install">설치</a>
|
|
358
|
-
<a href="https://github.com/osntak/careermate" target="_blank" rel="noopener">GitHub</a>
|
|
359
|
-
</div>
|
|
360
|
-
</footer>
|
|
361
|
-
|
|
362
|
-
<div class="sr-only" role="status" aria-live="polite" id="copy-status"></div>
|
|
363
|
-
|
|
364
|
-
<script src="landing.js"></script>
|
|
365
|
-
<script>
|
|
366
|
-
(function () {
|
|
367
|
-
'use strict';
|
|
368
|
-
|
|
369
|
-
// --- config tabs -------------------------------------------------
|
|
370
|
-
var tablist = document.querySelector('.tabs[role="tablist"]');
|
|
371
|
-
if (tablist) {
|
|
372
|
-
var tabs = Array.prototype.slice.call(tablist.querySelectorAll('[role="tab"]'));
|
|
373
|
-
function selectTab(tab) {
|
|
374
|
-
tabs.forEach(function (t) {
|
|
375
|
-
var sel = t === tab;
|
|
376
|
-
t.setAttribute('aria-selected', sel ? 'true' : 'false');
|
|
377
|
-
t.classList.toggle('is-active', sel);
|
|
378
|
-
t.tabIndex = sel ? 0 : -1;
|
|
379
|
-
var panel = document.getElementById(t.getAttribute('aria-controls'));
|
|
380
|
-
if (panel) {
|
|
381
|
-
panel.setAttribute('data-active', sel ? 'true' : 'false');
|
|
382
|
-
if (sel) panel.removeAttribute('hidden'); else panel.setAttribute('hidden', '');
|
|
383
|
-
}
|
|
384
|
-
});
|
|
385
|
-
}
|
|
386
|
-
tabs.forEach(function (tab, i) {
|
|
387
|
-
tab.addEventListener('click', function () { selectTab(tab); });
|
|
388
|
-
tab.addEventListener('keydown', function (e) {
|
|
389
|
-
var idx = null;
|
|
390
|
-
if (e.key === 'ArrowRight') idx = (i + 1) % tabs.length;
|
|
391
|
-
else if (e.key === 'ArrowLeft') idx = (i - 1 + tabs.length) % tabs.length;
|
|
392
|
-
else if (e.key === 'Home') idx = 0;
|
|
393
|
-
else if (e.key === 'End') idx = tabs.length - 1;
|
|
394
|
-
if (idx !== null) { e.preventDefault(); tabs[idx].focus(); selectTab(tabs[idx]); }
|
|
395
|
-
});
|
|
396
|
-
});
|
|
397
|
-
}
|
|
398
|
-
|
|
399
|
-
// --- scroll reveal (fade-up on enter) ----------------------------
|
|
400
|
-
var reduceMotion = window.matchMedia && window.matchMedia('(prefers-reduced-motion: reduce)').matches;
|
|
401
|
-
if (!reduceMotion && 'IntersectionObserver' in window) {
|
|
402
|
-
var revealEls = document.querySelectorAll('.section__head, .feature, .check, .track__head, .step, .acc, .privacy-card');
|
|
403
|
-
revealEls.forEach(function (el) { el.classList.add('reveal'); });
|
|
404
|
-
var io = new IntersectionObserver(function (entries) {
|
|
405
|
-
entries.forEach(function (e) {
|
|
406
|
-
if (e.isIntersecting) { e.target.classList.add('is-visible'); io.unobserve(e.target); }
|
|
407
|
-
});
|
|
408
|
-
}, { threshold: 0.1, rootMargin: '0px 0px -48px 0px' });
|
|
409
|
-
revealEls.forEach(function (el) { io.observe(el); });
|
|
410
|
-
}
|
|
411
|
-
|
|
412
|
-
// --- dashboard carousel (prev/next + dots + keyboard + swipe) -----
|
|
413
|
-
var carousel = document.getElementById('dash-carousel');
|
|
414
|
-
var track = document.getElementById('carousel-track');
|
|
415
|
-
if (carousel && track) {
|
|
416
|
-
var slides = Array.prototype.slice.call(track.children);
|
|
417
|
-
var prevBtn = document.getElementById('carousel-prev');
|
|
418
|
-
var nextBtn = document.getElementById('carousel-next');
|
|
419
|
-
var dotsWrap = document.getElementById('carousel-dots');
|
|
420
|
-
var idx = 0;
|
|
421
|
-
var captionOf = function (s) {
|
|
422
|
-
var f = s.querySelector('figcaption');
|
|
423
|
-
return f ? f.textContent.trim() : '';
|
|
424
|
-
};
|
|
425
|
-
var dots = slides.map(function (s, n) {
|
|
426
|
-
var b = document.createElement('button');
|
|
427
|
-
b.type = 'button'; b.className = 'carousel__dot';
|
|
428
|
-
b.setAttribute('role', 'tab');
|
|
429
|
-
b.setAttribute('aria-label', captionOf(s) || (n + 1) + '번째 화면');
|
|
430
|
-
b.addEventListener('click', function () { go(n); });
|
|
431
|
-
dotsWrap.appendChild(b);
|
|
432
|
-
return b;
|
|
433
|
-
});
|
|
434
|
-
function go(n) {
|
|
435
|
-
idx = Math.max(0, Math.min(slides.length - 1, n));
|
|
436
|
-
track.style.transform = 'translateX(' + (-idx * 100) + '%)';
|
|
437
|
-
dots.forEach(function (d, n2) {
|
|
438
|
-
var on = n2 === idx;
|
|
439
|
-
d.classList.toggle('is-active', on);
|
|
440
|
-
d.setAttribute('aria-selected', on ? 'true' : 'false');
|
|
441
|
-
});
|
|
442
|
-
slides.forEach(function (s, n2) { s.setAttribute('aria-hidden', n2 === idx ? 'false' : 'true'); });
|
|
443
|
-
if (prevBtn) prevBtn.disabled = idx === 0;
|
|
444
|
-
if (nextBtn) nextBtn.disabled = idx === slides.length - 1;
|
|
445
|
-
}
|
|
446
|
-
if (prevBtn) prevBtn.addEventListener('click', function () { go(idx - 1); });
|
|
447
|
-
if (nextBtn) nextBtn.addEventListener('click', function () { go(idx + 1); });
|
|
448
|
-
carousel.addEventListener('keydown', function (e) {
|
|
449
|
-
if (e.key === 'ArrowLeft') { e.preventDefault(); go(idx - 1); }
|
|
450
|
-
else if (e.key === 'ArrowRight') { e.preventDefault(); go(idx + 1); }
|
|
451
|
-
});
|
|
452
|
-
var x0 = null;
|
|
453
|
-
track.addEventListener('touchstart', function (e) { x0 = e.touches[0].clientX; }, { passive: true });
|
|
454
|
-
track.addEventListener('touchend', function (e) {
|
|
455
|
-
if (x0 === null) return;
|
|
456
|
-
var dx = e.changedTouches[0].clientX - x0;
|
|
457
|
-
if (Math.abs(dx) > 40) go(idx + (dx < 0 ? 1 : -1));
|
|
458
|
-
x0 = null;
|
|
459
|
-
});
|
|
460
|
-
go(0);
|
|
461
|
-
}
|
|
462
|
-
})();
|
|
463
|
-
</script>
|
|
464
|
-
</body>
|
|
465
|
-
</html>
|
package/dist/site/landing.js
DELETED
|
@@ -1,163 +0,0 @@
|
|
|
1
|
-
// Shared behavior for the CareerMate landing pages (index.html, start.html).
|
|
2
|
-
// Loaded after the DOM is parsed; wires the clipboard "copy" buttons and the theme toggle.
|
|
3
|
-
// NOTE: the pre-paint theme resolution stays INLINE in each page's <head> to avoid a flash (FOUC) --
|
|
4
|
-
// do not move that into this file.
|
|
5
|
-
(function () {
|
|
6
|
-
'use strict';
|
|
7
|
-
var status = document.getElementById('copy-status');
|
|
8
|
-
|
|
9
|
-
// --- clipboard ---------------------------------------------------
|
|
10
|
-
function legacyCopy(text) {
|
|
11
|
-
var ta = document.createElement('textarea');
|
|
12
|
-
ta.value = text; ta.setAttribute('readonly', '');
|
|
13
|
-
ta.style.position = 'absolute'; ta.style.left = '-9999px';
|
|
14
|
-
document.body.appendChild(ta); ta.select();
|
|
15
|
-
var ok = false;
|
|
16
|
-
try { ok = document.execCommand('copy'); } catch (e) { ok = false; }
|
|
17
|
-
document.body.removeChild(ta);
|
|
18
|
-
return ok;
|
|
19
|
-
}
|
|
20
|
-
function copyText(text, onok) {
|
|
21
|
-
if (navigator.clipboard && navigator.clipboard.writeText) {
|
|
22
|
-
navigator.clipboard.writeText(text).then(onok, function () { if (legacyCopy(text)) onok(); });
|
|
23
|
-
} else if (legacyCopy(text)) { onok(); }
|
|
24
|
-
}
|
|
25
|
-
document.querySelectorAll('.copy-btn').forEach(function (btn) {
|
|
26
|
-
btn.addEventListener('click', function () {
|
|
27
|
-
var src = document.getElementById(btn.getAttribute('data-copy-target'));
|
|
28
|
-
if (!src) return;
|
|
29
|
-
copyText(src.textContent || '', function () {
|
|
30
|
-
var original = btn.textContent;
|
|
31
|
-
btn.textContent = '복사됨'; btn.classList.add('copied');
|
|
32
|
-
if (status) status.textContent = '클립보드에 복사되었습니다.';
|
|
33
|
-
window.setTimeout(function () { btn.textContent = original; btn.classList.remove('copied'); }, 1600);
|
|
34
|
-
});
|
|
35
|
-
});
|
|
36
|
-
});
|
|
37
|
-
|
|
38
|
-
// --- theme toggle (persist) --------------------------------------
|
|
39
|
-
var root = document.documentElement;
|
|
40
|
-
var toggle = document.getElementById('theme-toggle');
|
|
41
|
-
function isDark() {
|
|
42
|
-
var t = root.getAttribute('data-theme');
|
|
43
|
-
if (t === 'dark') return true;
|
|
44
|
-
if (t === 'light') return false;
|
|
45
|
-
return window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches;
|
|
46
|
-
}
|
|
47
|
-
if (toggle) {
|
|
48
|
-
toggle.addEventListener('click', function () {
|
|
49
|
-
var next = isDark() ? 'light' : 'dark';
|
|
50
|
-
root.setAttribute('data-theme', next);
|
|
51
|
-
try { window.localStorage.setItem('careermate-theme', next); window.localStorage.removeItem('cf-theme'); } catch (e) {}
|
|
52
|
-
});
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
// --- hero command demo ------------------------------------------
|
|
56
|
-
var demo = document.querySelector('[data-command-demo]');
|
|
57
|
-
if (demo) {
|
|
58
|
-
var reduceMotion = window.matchMedia && window.matchMedia('(prefers-reduced-motion: reduce)').matches;
|
|
59
|
-
var scenes = [
|
|
60
|
-
{
|
|
61
|
-
status: '문서 등록',
|
|
62
|
-
file: '자기소개서.pdf',
|
|
63
|
-
fileState: '업로드됨',
|
|
64
|
-
command: '이 자기소개서 읽고 CareerMate에 등록해줘.',
|
|
65
|
-
result: '문서를 읽고 자기소개서 버전으로 저장했어요. 핵심 경험 4개도 함께 정리했습니다.'
|
|
66
|
-
},
|
|
67
|
-
{
|
|
68
|
-
status: '대시보드',
|
|
69
|
-
file: '127.0.0.1:4319',
|
|
70
|
-
fileState: '열림',
|
|
71
|
-
command: '대시보드 열어줘. 지금 지원 현황 보고 싶어.',
|
|
72
|
-
result: '대시보드를 열었어요. 작성 중 2건, 지원 완료 3건, 면접 준비 1건이 있습니다.'
|
|
73
|
-
},
|
|
74
|
-
{
|
|
75
|
-
status: '공고 분석',
|
|
76
|
-
file: 'recruit.example.com/product-designer',
|
|
77
|
-
fileState: '링크',
|
|
78
|
-
command: '이 공고 분석해서 내 경력에 맞춰줘.',
|
|
79
|
-
result: '요구 역량과 내 경험을 비교했어요. 강조하면 좋은 키워드는 협업, 실험, 정량 개선입니다.'
|
|
80
|
-
},
|
|
81
|
-
{
|
|
82
|
-
status: '자소서 초안',
|
|
83
|
-
file: 'Product Designer · A사',
|
|
84
|
-
fileState: '공고',
|
|
85
|
-
command: '이 공고용 자기소개서 초안 써줘. 너무 딱딱하지 않게.',
|
|
86
|
-
result: '공고에 맞춘 초안을 만들고 v1로 저장했어요. 첫 문단은 지원 동기가 바로 보이게 다듬었습니다.'
|
|
87
|
-
},
|
|
88
|
-
{
|
|
89
|
-
status: '면접 준비',
|
|
90
|
-
file: 'A사 · 서류 합격',
|
|
91
|
-
fileState: '상태 변경',
|
|
92
|
-
command: '서류 합격했어. 이 공고 기준으로 면접 준비해줘.',
|
|
93
|
-
result: '예상 질문 12개, STAR 답변 뼈대, 1분 자기소개 초안을 준비해 저장했습니다.'
|
|
94
|
-
}
|
|
95
|
-
];
|
|
96
|
-
var statusEl = demo.querySelector('[data-demo-status]');
|
|
97
|
-
var fileEl = demo.querySelector('[data-demo-file]');
|
|
98
|
-
var fileStateEl = demo.querySelector('[data-demo-file-state]');
|
|
99
|
-
var commandEl = demo.querySelector('[data-demo-command]');
|
|
100
|
-
var resultEl = demo.querySelector('[data-demo-result]');
|
|
101
|
-
var stepEls = Array.prototype.slice.call(demo.querySelectorAll('[data-demo-step]'));
|
|
102
|
-
var progressEl = demo.querySelector('.command-card__progress span');
|
|
103
|
-
var sceneIndex = 0;
|
|
104
|
-
var rotateTimer = null;
|
|
105
|
-
var transitionTimer = null;
|
|
106
|
-
var settleTimer = null;
|
|
107
|
-
|
|
108
|
-
function paintScene(index) {
|
|
109
|
-
var scene = scenes[index];
|
|
110
|
-
if (!scene) return;
|
|
111
|
-
if (statusEl) statusEl.textContent = scene.status;
|
|
112
|
-
if (fileEl) fileEl.textContent = scene.file;
|
|
113
|
-
if (fileStateEl) fileStateEl.textContent = scene.fileState;
|
|
114
|
-
if (commandEl) commandEl.textContent = scene.command;
|
|
115
|
-
if (resultEl) resultEl.textContent = scene.result;
|
|
116
|
-
sceneIndex = index;
|
|
117
|
-
stepEls.forEach(function (step, n) {
|
|
118
|
-
var active = n === index;
|
|
119
|
-
step.classList.toggle('is-active', active);
|
|
120
|
-
if (active) step.setAttribute('aria-current', 'true');
|
|
121
|
-
else step.removeAttribute('aria-current');
|
|
122
|
-
});
|
|
123
|
-
if (progressEl && !reduceMotion) {
|
|
124
|
-
progressEl.style.animation = 'none';
|
|
125
|
-
progressEl.offsetHeight;
|
|
126
|
-
progressEl.style.animation = '';
|
|
127
|
-
}
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
function scheduleNextScene() {
|
|
131
|
-
if (reduceMotion) return;
|
|
132
|
-
window.clearTimeout(rotateTimer);
|
|
133
|
-
rotateTimer = window.setTimeout(function () {
|
|
134
|
-
showScene((sceneIndex + 1) % scenes.length, true);
|
|
135
|
-
}, 4500);
|
|
136
|
-
}
|
|
137
|
-
|
|
138
|
-
function showScene(index, animate) {
|
|
139
|
-
if (index < 0 || index >= scenes.length) return;
|
|
140
|
-
window.clearTimeout(rotateTimer);
|
|
141
|
-
window.clearTimeout(transitionTimer);
|
|
142
|
-
window.clearTimeout(settleTimer);
|
|
143
|
-
if (!animate || index === sceneIndex) {
|
|
144
|
-
demo.classList.remove('is-changing');
|
|
145
|
-
paintScene(index);
|
|
146
|
-
scheduleNextScene();
|
|
147
|
-
return;
|
|
148
|
-
}
|
|
149
|
-
demo.classList.add('is-changing');
|
|
150
|
-
transitionTimer = window.setTimeout(function () {
|
|
151
|
-
paintScene(index);
|
|
152
|
-
settleTimer = window.setTimeout(function () { demo.classList.remove('is-changing'); }, 40);
|
|
153
|
-
scheduleNextScene();
|
|
154
|
-
}, 180);
|
|
155
|
-
}
|
|
156
|
-
|
|
157
|
-
stepEls.forEach(function (step, n) {
|
|
158
|
-
step.addEventListener('click', function () { showScene(n, true); });
|
|
159
|
-
});
|
|
160
|
-
paintScene(0);
|
|
161
|
-
scheduleNextScene();
|
|
162
|
-
}
|
|
163
|
-
})();
|