devark-cli 0.1.0 → 0.1.2
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/dist/checksums.sha256 +2 -2
- package/dist/index.js +119 -23
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/checksums.sha256
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
df64dc39f16af067e894ac8145ecc1cd692b008f0863974d06e7424ae803f123 index.js
|
|
2
|
+
2207035473e531a8eee7f5ffb2b3928f94c4768b0c6993cf31e09a60b7a26e28 index.js.map
|
|
3
3
|
137b0f6da8ab3a82dd96e536c9de1c0162f51d5450895af16e935906975671a8 report-template.html
|
package/dist/index.js
CHANGED
|
@@ -2481,7 +2481,7 @@ var require_package = __commonJS({
|
|
|
2481
2481
|
"package.json"(exports2, module2) {
|
|
2482
2482
|
module2.exports = {
|
|
2483
2483
|
name: "devark-cli",
|
|
2484
|
-
version: "0.1.
|
|
2484
|
+
version: "0.1.2",
|
|
2485
2485
|
description: "DevArk - Developer Productivity CLI",
|
|
2486
2486
|
bin: {
|
|
2487
2487
|
devark: "./bin/devark.js"
|
|
@@ -3060,6 +3060,25 @@ var init_api_client = __esm({
|
|
|
3060
3060
|
}
|
|
3061
3061
|
return response.data;
|
|
3062
3062
|
}
|
|
3063
|
+
/**
|
|
3064
|
+
* Get the timestamp of the user's most recent session for incremental sync.
|
|
3065
|
+
* @returns Last session timestamp (ISO string) and ID, or null if no sessions exist
|
|
3066
|
+
*/
|
|
3067
|
+
async getLastSessionDate() {
|
|
3068
|
+
var _a;
|
|
3069
|
+
try {
|
|
3070
|
+
const response = await this.client.get("/api/sessions/last");
|
|
3071
|
+
return {
|
|
3072
|
+
lastSessionTimestamp: response.data.lastSessionTimestamp || null,
|
|
3073
|
+
lastSessionId: response.data.lastSessionId || null
|
|
3074
|
+
};
|
|
3075
|
+
} catch (error) {
|
|
3076
|
+
if (((_a = error.response) == null ? void 0 : _a.status) === 404) {
|
|
3077
|
+
return { lastSessionTimestamp: null, lastSessionId: null };
|
|
3078
|
+
}
|
|
3079
|
+
throw error;
|
|
3080
|
+
}
|
|
3081
|
+
}
|
|
3063
3082
|
getBaseUrl() {
|
|
3064
3083
|
return this.client.defaults.baseURL || "http://localhost:3000";
|
|
3065
3084
|
}
|
|
@@ -4010,10 +4029,14 @@ var init_send_orchestrator = __esm({
|
|
|
4010
4029
|
return this.readSelectedSessions(options.selectedSessions);
|
|
4011
4030
|
}
|
|
4012
4031
|
if (options.all) {
|
|
4013
|
-
const
|
|
4032
|
+
const serverSince = await this.getServerLastSessionDate();
|
|
4033
|
+
if (serverSince) {
|
|
4034
|
+
logger.debug(`Using server timestamp for incremental sync: ${serverSince.toISOString()}`);
|
|
4035
|
+
}
|
|
4036
|
+
const sessions2 = await readClaudeSessions({ since: serverSince });
|
|
4014
4037
|
return sessions2;
|
|
4015
4038
|
}
|
|
4016
|
-
const sinceDate = this.
|
|
4039
|
+
const sinceDate = await this.determineSinceDateWithServerFallback(options);
|
|
4017
4040
|
if (options.claudeProjectDir && options.claudeProjectDir.trim() !== "") {
|
|
4018
4041
|
return this.loadProjectSessions(options.claudeProjectDir, sinceDate);
|
|
4019
4042
|
}
|
|
@@ -4036,6 +4059,34 @@ var init_send_orchestrator = __esm({
|
|
|
4036
4059
|
}
|
|
4037
4060
|
return void 0;
|
|
4038
4061
|
}
|
|
4062
|
+
/**
|
|
4063
|
+
* Get the server's last session timestamp for incremental sync.
|
|
4064
|
+
* Returns undefined on error to allow fallback to local sync state.
|
|
4065
|
+
*/
|
|
4066
|
+
async getServerLastSessionDate() {
|
|
4067
|
+
try {
|
|
4068
|
+
const result = await apiClient.getLastSessionDate();
|
|
4069
|
+
if (result.lastSessionTimestamp) {
|
|
4070
|
+
return new Date(result.lastSessionTimestamp);
|
|
4071
|
+
}
|
|
4072
|
+
return void 0;
|
|
4073
|
+
} catch (error) {
|
|
4074
|
+
logger.warn(`Failed to get server last session date, falling back to local sync: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
4075
|
+
return void 0;
|
|
4076
|
+
}
|
|
4077
|
+
}
|
|
4078
|
+
/**
|
|
4079
|
+
* Determine since date with server-side incremental sync fallback.
|
|
4080
|
+
* First tries server timestamp, then falls back to local sync state.
|
|
4081
|
+
*/
|
|
4082
|
+
async determineSinceDateWithServerFallback(options) {
|
|
4083
|
+
const serverSince = await this.getServerLastSessionDate();
|
|
4084
|
+
if (serverSince) {
|
|
4085
|
+
logger.debug(`Using server timestamp for incremental sync: ${serverSince.toISOString()}`);
|
|
4086
|
+
return serverSince;
|
|
4087
|
+
}
|
|
4088
|
+
return this.determineSinceDate(options);
|
|
4089
|
+
}
|
|
4039
4090
|
async loadProjectSessions(claudeProjectDir, sinceDate) {
|
|
4040
4091
|
const dirName = parseProjectName(claudeProjectDir);
|
|
4041
4092
|
const project = await analyzeProject(claudeProjectDir, dirName);
|
|
@@ -11422,6 +11473,20 @@ var manual_sync_menu_exports = {};
|
|
|
11422
11473
|
__export(manual_sync_menu_exports, {
|
|
11423
11474
|
showManualSyncMenu: () => showManualSyncMenu
|
|
11424
11475
|
});
|
|
11476
|
+
async function getServerLastSessionDate() {
|
|
11477
|
+
try {
|
|
11478
|
+
if (!await isAuthenticated()) {
|
|
11479
|
+
return void 0;
|
|
11480
|
+
}
|
|
11481
|
+
const result = await apiClient.getLastSessionDate();
|
|
11482
|
+
if (result.lastSessionTimestamp) {
|
|
11483
|
+
return new Date(result.lastSessionTimestamp);
|
|
11484
|
+
}
|
|
11485
|
+
return void 0;
|
|
11486
|
+
} catch {
|
|
11487
|
+
return void 0;
|
|
11488
|
+
}
|
|
11489
|
+
}
|
|
11425
11490
|
async function showManualSyncMenu() {
|
|
11426
11491
|
console.log("");
|
|
11427
11492
|
console.log(colors.primary("Manual sync to cloud"));
|
|
@@ -11562,22 +11627,39 @@ async function showManualSyncMenu() {
|
|
|
11562
11627
|
}
|
|
11563
11628
|
}
|
|
11564
11629
|
case "all": {
|
|
11565
|
-
const
|
|
11566
|
-
|
|
11567
|
-
|
|
11568
|
-
|
|
11569
|
-
|
|
11570
|
-
{
|
|
11571
|
-
|
|
11572
|
-
|
|
11573
|
-
|
|
11574
|
-
|
|
11630
|
+
const spinner = createSpinner("Calculating sessions to sync...").start();
|
|
11631
|
+
try {
|
|
11632
|
+
const serverSince = await getServerLastSessionDate();
|
|
11633
|
+
const sessions = await readClaudeSessions({ since: serverSince });
|
|
11634
|
+
const validSessions = sessions.filter((s) => s.duration >= 240);
|
|
11635
|
+
const projectPaths = new Set(validSessions.map((s) => {
|
|
11636
|
+
var _a;
|
|
11637
|
+
return (_a = s.sourceFile) == null ? void 0 : _a.claudeProjectPath;
|
|
11638
|
+
}).filter(Boolean));
|
|
11639
|
+
spinner.stop();
|
|
11640
|
+
console.log("");
|
|
11641
|
+
if (serverSince) {
|
|
11642
|
+
console.log(colors.info(`This will sync ${validSessions.length} new sessions from ${projectPaths.size} projects`));
|
|
11643
|
+
console.log(colors.subdued(`(Sessions since ${serverSince.toLocaleDateString()})`));
|
|
11644
|
+
} else {
|
|
11645
|
+
console.log(colors.info(`This will sync ${validSessions.length} sessions from ${projectPaths.size} projects.`));
|
|
11575
11646
|
}
|
|
11576
|
-
|
|
11577
|
-
|
|
11647
|
+
const { confirm } = await import_inquirer14.default.prompt([
|
|
11648
|
+
{
|
|
11649
|
+
type: "confirm",
|
|
11650
|
+
name: "confirm",
|
|
11651
|
+
message: `Continue with syncing ${validSessions.length} sessions?`,
|
|
11652
|
+
default: true
|
|
11653
|
+
}
|
|
11654
|
+
]);
|
|
11655
|
+
if (!confirm) {
|
|
11656
|
+
return { type: "cancel" };
|
|
11657
|
+
}
|
|
11658
|
+
return { type: "all" };
|
|
11659
|
+
} catch (error) {
|
|
11660
|
+
spinner.fail(colors.error("Failed to calculate sessions"));
|
|
11578
11661
|
return { type: "cancel" };
|
|
11579
11662
|
}
|
|
11580
|
-
return { type: "all" };
|
|
11581
11663
|
}
|
|
11582
11664
|
default:
|
|
11583
11665
|
return { type: "cancel" };
|
|
@@ -11595,6 +11677,8 @@ var init_manual_sync_menu = __esm({
|
|
|
11595
11677
|
init_claude();
|
|
11596
11678
|
init_project_display();
|
|
11597
11679
|
init_ui();
|
|
11680
|
+
init_api_client();
|
|
11681
|
+
init_token();
|
|
11598
11682
|
}
|
|
11599
11683
|
});
|
|
11600
11684
|
|
|
@@ -15608,7 +15692,7 @@ function createSection(title, content, options) {
|
|
|
15608
15692
|
lines.push(color(chars.bl + chars.h.repeat(width - 2) + chars.br));
|
|
15609
15693
|
return lines.join("\n");
|
|
15610
15694
|
}
|
|
15611
|
-
function createCloudStatusSection(status2) {
|
|
15695
|
+
function createCloudStatusSection(status2, serverLastSessionDate) {
|
|
15612
15696
|
const content = [];
|
|
15613
15697
|
const connectionIcon = status2.connected ? icons.success : icons.error;
|
|
15614
15698
|
const connectionColor = status2.connected ? colors.success : colors.error;
|
|
@@ -15636,12 +15720,13 @@ function createCloudStatusSection(status2) {
|
|
|
15636
15720
|
let syncColor = colors.primary;
|
|
15637
15721
|
let syncText = "Never synced";
|
|
15638
15722
|
let syncProject = "";
|
|
15639
|
-
|
|
15640
|
-
|
|
15723
|
+
const lastSyncDate = serverLastSessionDate || status2.lastSync;
|
|
15724
|
+
if (lastSyncDate) {
|
|
15725
|
+
const timeSince = (/* @__PURE__ */ new Date()).getTime() - lastSyncDate.getTime();
|
|
15641
15726
|
const minutes = Math.floor(timeSince / 6e4);
|
|
15642
15727
|
const hours = Math.floor(minutes / 60);
|
|
15643
15728
|
const days = Math.floor(hours / 24);
|
|
15644
|
-
if (status2.lastSyncProject) {
|
|
15729
|
+
if (!serverLastSessionDate && status2.lastSyncProject) {
|
|
15645
15730
|
syncProject = `${status2.lastSyncProject} `;
|
|
15646
15731
|
}
|
|
15647
15732
|
if (days > 0) {
|
|
@@ -15722,9 +15807,9 @@ function createLocalEngineSection(engine) {
|
|
|
15722
15807
|
color: sectionColor
|
|
15723
15808
|
});
|
|
15724
15809
|
}
|
|
15725
|
-
async function createStatusDashboard(cloud, local) {
|
|
15810
|
+
async function createStatusDashboard(cloud, local, serverLastSessionDate) {
|
|
15726
15811
|
const sections = [];
|
|
15727
|
-
sections.push(createCloudStatusSection(cloud));
|
|
15812
|
+
sections.push(createCloudStatusSection(cloud, serverLastSessionDate));
|
|
15728
15813
|
sections.push("");
|
|
15729
15814
|
sections.push(createLocalEngineSection(local));
|
|
15730
15815
|
return sections.join("\n");
|
|
@@ -16135,7 +16220,18 @@ async function showMainMenu(state, packageUpdateInfo2) {
|
|
|
16135
16220
|
statusLineStatus: state.statusLineStatus,
|
|
16136
16221
|
configPath: "~/.claude/config"
|
|
16137
16222
|
};
|
|
16138
|
-
|
|
16223
|
+
let serverLastSessionDate;
|
|
16224
|
+
if (state.hasAuth) {
|
|
16225
|
+
try {
|
|
16226
|
+
const { apiClient: apiClient2 } = await Promise.resolve().then(() => (init_api_client(), api_client_exports));
|
|
16227
|
+
const result = await apiClient2.getLastSessionDate();
|
|
16228
|
+
if (result.lastSessionTimestamp) {
|
|
16229
|
+
serverLastSessionDate = new Date(result.lastSessionTimestamp);
|
|
16230
|
+
}
|
|
16231
|
+
} catch {
|
|
16232
|
+
}
|
|
16233
|
+
}
|
|
16234
|
+
console.log(await createStatusDashboard(cloudStatus, localEngine, serverLastSessionDate));
|
|
16139
16235
|
console.log("");
|
|
16140
16236
|
const context = {
|
|
16141
16237
|
state: state.state,
|