claude-telegram-bot 0.2.3 → 0.2.4
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/README.ko.md +1 -1
- package/README.md +4 -2
- package/bot.mjs +35 -12
- package/package.json +1 -1
package/README.ko.md
CHANGED
|
@@ -100,7 +100,7 @@ claude-telegram-bot ~/botconfigs/myproj/config.json
|
|
|
100
100
|
| `env` | (선택) `claude` 프로세스에 넘길 환경 변수 |
|
|
101
101
|
| `schedule` | (선택) 정해진 시각에 프롬프트를 실행하는 cron 작업 — [예약 작업](#예약-작업-cron) 참고 |
|
|
102
102
|
|
|
103
|
-
`state
|
|
103
|
+
`state`와 첨부 파일은 config 파일 옆 **`.claude-bot/` 숨김 폴더**에 저장됩니다(프로젝트 격리). 구버전에서 올리면 첫 시작 때 기존 `state.json`·`attachments/`를 `.claude-bot/`로 **자동 이동**합니다(무손실). 로그는 launchd plist가 가리키는 위치 그대로입니다.
|
|
104
104
|
|
|
105
105
|
## 첫 실행
|
|
106
106
|
|
package/README.md
CHANGED
|
@@ -192,8 +192,10 @@ Edit `config.json`:
|
|
|
192
192
|
| `env` | (optional) Extra environment variables passed to the `claude` process |
|
|
193
193
|
| `schedule` | (optional) Cron jobs that run a prompt on a timer — see [Scheduled tasks](#scheduled-tasks-cron) |
|
|
194
194
|
|
|
195
|
-
State
|
|
196
|
-
projects stay isolated.
|
|
195
|
+
State and downloaded attachments live in a hidden **`.claude-bot/`** folder next to the config
|
|
196
|
+
file, so projects stay isolated. Upgrading from an older version **auto-moves** an existing
|
|
197
|
+
`state.json` / `attachments/` into `.claude-bot/` on first start (no data loss). Logs stay wherever
|
|
198
|
+
your launchd plist points them.
|
|
197
199
|
|
|
198
200
|
### Usage details
|
|
199
201
|
|
package/bot.mjs
CHANGED
|
@@ -14,7 +14,7 @@
|
|
|
14
14
|
// 자동 판별하고, cfg.lang 을 주면 그 언어로 고정함. 콘솔/CLI 출력은 영어 단일.
|
|
15
15
|
|
|
16
16
|
import { basename, dirname, join } from "node:path";
|
|
17
|
-
import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs";
|
|
17
|
+
import { existsSync, mkdirSync, readFileSync, renameSync, writeFileSync } from "node:fs";
|
|
18
18
|
|
|
19
19
|
import dns from "node:dns";
|
|
20
20
|
import { fileURLToPath } from "node:url";
|
|
@@ -73,13 +73,33 @@ Requires: the claude CLI installed and authenticated on the host.`);
|
|
|
73
73
|
// isolated. Falls back to ./config.json for the single-project setup.
|
|
74
74
|
const CONFIG_PATH = process.argv[2] || process.env.BOT_CONFIG || join(HERE, "config.json");
|
|
75
75
|
const DATA_DIR = dirname(CONFIG_PATH);
|
|
76
|
-
// state
|
|
77
|
-
// config
|
|
76
|
+
// 데이터(state·attachments)는 config 폴더 아래 숨김 폴더 .claude-bot/ 에 모은다.
|
|
77
|
+
// state 파일명은 config 이름에서 파생 → 여러 페르소나 config 가 한 .claude-bot/ 를 공유해도 안 섞임
|
|
78
|
+
// (config.json → state.json, 그 외 foo.json → foo.state.json).
|
|
78
79
|
const stateBase = basename(CONFIG_PATH, ".json");
|
|
79
|
-
const
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
);
|
|
80
|
+
const stateFile = stateBase === "config" ? "state.json" : `${stateBase}.state.json`;
|
|
81
|
+
const BOT_DIR = join(DATA_DIR, ".claude-bot");
|
|
82
|
+
const STATE_PATH = join(BOT_DIR, stateFile);
|
|
83
|
+
const ATTACH_DIR = join(BOT_DIR, "attachments");
|
|
84
|
+
const LEGACY_STATE_PATH = join(DATA_DIR, stateFile); // 구버전(루트 직하) 호환
|
|
85
|
+
const LEGACY_ATTACH_DIR = join(DATA_DIR, "attachments");
|
|
86
|
+
|
|
87
|
+
// 구버전에서 올라온 경우, 루트 직하 데이터를 .claude-bot/ 로 1회 이동(무손실, 실패 시 기존 경로 폴백).
|
|
88
|
+
function migrateData() {
|
|
89
|
+
try {
|
|
90
|
+
mkdirSync(BOT_DIR, { recursive: true });
|
|
91
|
+
if (!existsSync(STATE_PATH) && existsSync(LEGACY_STATE_PATH)) {
|
|
92
|
+
renameSync(LEGACY_STATE_PATH, STATE_PATH);
|
|
93
|
+
console.log(`Migrated state → ${STATE_PATH}`);
|
|
94
|
+
}
|
|
95
|
+
if (!existsSync(ATTACH_DIR) && existsSync(LEGACY_ATTACH_DIR)) {
|
|
96
|
+
renameSync(LEGACY_ATTACH_DIR, ATTACH_DIR);
|
|
97
|
+
console.log(`Migrated attachments → ${ATTACH_DIR}`);
|
|
98
|
+
}
|
|
99
|
+
} catch (e) {
|
|
100
|
+
console.error("Data migration skipped:", e.message);
|
|
101
|
+
}
|
|
102
|
+
}
|
|
83
103
|
|
|
84
104
|
if (!existsSync(CONFIG_PATH)) {
|
|
85
105
|
console.error(
|
|
@@ -224,11 +244,13 @@ const COMMANDS = {
|
|
|
224
244
|
|
|
225
245
|
// ── 상태 (세션 이어가기용) ────────────────────────────────────────────────
|
|
226
246
|
function loadState() {
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
247
|
+
// 새 경로(.claude-bot/) 우선, 없으면 구버전 루트 경로로 폴백(이주 실패 시 안전망).
|
|
248
|
+
for (const p of [STATE_PATH, LEGACY_STATE_PATH]) {
|
|
249
|
+
try {
|
|
250
|
+
return JSON.parse(readFileSync(p, "utf8"));
|
|
251
|
+
} catch {}
|
|
231
252
|
}
|
|
253
|
+
return {};
|
|
232
254
|
}
|
|
233
255
|
function saveState(s) {
|
|
234
256
|
try {
|
|
@@ -237,6 +259,7 @@ function saveState(s) {
|
|
|
237
259
|
console.error("Failed to save state", e);
|
|
238
260
|
}
|
|
239
261
|
}
|
|
262
|
+
migrateData(); // 루트 직하 → .claude-bot/ 1회 이주(있으면) 후 state 로드
|
|
240
263
|
let state = loadState(); // { sessionId?, cron?: [{ id, cron, prompt, label? }], restartNotify? }
|
|
241
264
|
|
|
242
265
|
// ── 텔레그램 헬퍼 ─────────────────────────────────────────────────────────
|
|
@@ -616,7 +639,7 @@ async function downloadAttachment(att) {
|
|
|
616
639
|
const r = await fetch(`https://api.telegram.org/file/bot${cfg.token}/${filePath}`);
|
|
617
640
|
if (!r.ok) throw new Error(`download failed ${r.status}`);
|
|
618
641
|
const buf = Buffer.from(await r.arrayBuffer());
|
|
619
|
-
const dir =
|
|
642
|
+
const dir = ATTACH_DIR;
|
|
620
643
|
mkdirSync(dir, { recursive: true });
|
|
621
644
|
const ext = filePath.includes(".") ? filePath.slice(filePath.lastIndexOf(".")) : "";
|
|
622
645
|
const name = att.name || `tg-${att.fileId.slice(-10)}${ext}`;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "claude-telegram-bot",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.4",
|
|
4
4
|
"description": "Drive Claude Code from Telegram — messages run headless `claude -p` in a project dir and replies come back to the chat. Zero dependencies.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|