@k2wanko/gemini-cli-sdk 0.1.2 → 0.2.1
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/agent.d.ts +11 -0
- package/dist/agent.js +33 -2
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/session.d.ts +17 -0
- package/dist/session.js +95 -0
- package/package.json +1 -1
package/dist/agent.d.ts
CHANGED
|
@@ -10,15 +10,26 @@ export interface GeminiAgentOptions {
|
|
|
10
10
|
model?: string;
|
|
11
11
|
cwd?: string;
|
|
12
12
|
debug?: boolean;
|
|
13
|
+
/** Resume a specific session by ID */
|
|
14
|
+
sessionId?: string;
|
|
15
|
+
/** Context compression threshold (0-1 fraction) */
|
|
16
|
+
compressionThreshold?: number;
|
|
13
17
|
}
|
|
14
18
|
export declare class GeminiAgent {
|
|
15
19
|
private readonly config;
|
|
16
20
|
private readonly tools;
|
|
17
21
|
private readonly skillRefs;
|
|
18
22
|
private readonly instructions;
|
|
23
|
+
private readonly resumeSessionId;
|
|
19
24
|
private instructionsLoaded;
|
|
20
25
|
constructor(options: GeminiAgentOptions);
|
|
26
|
+
/** Return the session ID assigned to this agent instance */
|
|
27
|
+
getSessionId(): string;
|
|
28
|
+
/** List available sessions for the current project */
|
|
29
|
+
listSessions(): Promise<import("./session.js").SessionInfo[]>;
|
|
21
30
|
sendStream(prompt: string, signal?: AbortSignal): AsyncGenerator<ServerGeminiStreamEvent>;
|
|
31
|
+
private initialized;
|
|
32
|
+
private ensureInitialized;
|
|
22
33
|
private initialize;
|
|
23
34
|
private resolveInstructions;
|
|
24
35
|
private buildScopedRegistry;
|
package/dist/agent.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { ActivateSkillTool, AuthType, Config, GeminiEventType, getAuthTypeFromEnv, loadSkillsFromDir, PolicyDecision, PREVIEW_GEMINI_MODEL_AUTO, scheduleAgentTools, } from "@google/gemini-cli-core";
|
|
2
2
|
import { AgentFsImpl, AgentShellImpl } from "./context.js";
|
|
3
|
+
import { listSessions, loadSession, messageRecordsToHistory, } from "./session.js";
|
|
3
4
|
import { SdkTool } from "./tool.js";
|
|
4
5
|
export { GeminiEventType };
|
|
5
6
|
export class GeminiAgent {
|
|
@@ -7,11 +8,13 @@ export class GeminiAgent {
|
|
|
7
8
|
tools;
|
|
8
9
|
skillRefs;
|
|
9
10
|
instructions;
|
|
11
|
+
resumeSessionId;
|
|
10
12
|
instructionsLoaded = false;
|
|
11
13
|
constructor(options) {
|
|
12
14
|
this.instructions = options.instructions;
|
|
13
15
|
this.tools = options.tools ?? [];
|
|
14
16
|
this.skillRefs = options.skills ?? [];
|
|
17
|
+
this.resumeSessionId = options.sessionId;
|
|
15
18
|
const cwd = options.cwd ?? process.cwd();
|
|
16
19
|
const initialMemory = typeof this.instructions === "string" ? this.instructions : "";
|
|
17
20
|
const configParams = {
|
|
@@ -29,9 +32,19 @@ export class GeminiAgent {
|
|
|
29
32
|
policyEngineConfig: {
|
|
30
33
|
defaultDecision: PolicyDecision.ALLOW,
|
|
31
34
|
},
|
|
35
|
+
compressionThreshold: options.compressionThreshold,
|
|
32
36
|
};
|
|
33
37
|
this.config = new Config(configParams);
|
|
34
38
|
}
|
|
39
|
+
/** Return the session ID assigned to this agent instance */
|
|
40
|
+
getSessionId() {
|
|
41
|
+
return this.config.getSessionId();
|
|
42
|
+
}
|
|
43
|
+
/** List available sessions for the current project */
|
|
44
|
+
async listSessions() {
|
|
45
|
+
await this.ensureInitialized();
|
|
46
|
+
return listSessions(this.config);
|
|
47
|
+
}
|
|
35
48
|
async *sendStream(prompt, signal) {
|
|
36
49
|
await this.initialize();
|
|
37
50
|
const client = this.config.getGeminiClient();
|
|
@@ -87,12 +100,30 @@ export class GeminiAgent {
|
|
|
87
100
|
// -------------------------------------------------------------------------
|
|
88
101
|
// Private helpers
|
|
89
102
|
// -------------------------------------------------------------------------
|
|
90
|
-
|
|
91
|
-
|
|
103
|
+
initialized = false;
|
|
104
|
+
async ensureInitialized() {
|
|
105
|
+
if (this.initialized)
|
|
92
106
|
return;
|
|
93
107
|
const authType = getAuthTypeFromEnv() || AuthType.COMPUTE_ADC;
|
|
94
108
|
await this.config.refreshAuth(authType);
|
|
95
109
|
await this.config.initialize();
|
|
110
|
+
this.initialized = true;
|
|
111
|
+
}
|
|
112
|
+
async initialize() {
|
|
113
|
+
if (this.config.getContentGenerator())
|
|
114
|
+
return;
|
|
115
|
+
await this.ensureInitialized();
|
|
116
|
+
// Resume previous session if requested
|
|
117
|
+
if (this.resumeSessionId) {
|
|
118
|
+
const sessions = await listSessions(this.config);
|
|
119
|
+
const target = sessions.find((s) => s.sessionId === this.resumeSessionId);
|
|
120
|
+
if (target) {
|
|
121
|
+
const resumed = await loadSession(target.filePath);
|
|
122
|
+
const history = messageRecordsToHistory(resumed.conversation.messages);
|
|
123
|
+
const client = this.config.getGeminiClient();
|
|
124
|
+
await client.resumeChat(history, resumed);
|
|
125
|
+
}
|
|
126
|
+
}
|
|
96
127
|
// Load skills from directories
|
|
97
128
|
if (this.skillRefs.length > 0) {
|
|
98
129
|
const skillManager = this.config.getSkillManager();
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { type ConversationRecord, type Config as CoreConfig, type MessageRecord, type ResumedSessionData } from "@google/gemini-cli-core";
|
|
2
|
+
import type { Content } from "@google/genai";
|
|
3
|
+
export type { ConversationRecord, MessageRecord, ResumedSessionData };
|
|
4
|
+
export interface SessionInfo {
|
|
5
|
+
sessionId: string;
|
|
6
|
+
filePath: string;
|
|
7
|
+
startTime: string;
|
|
8
|
+
lastUpdated: string;
|
|
9
|
+
messageCount: number;
|
|
10
|
+
summary?: string;
|
|
11
|
+
}
|
|
12
|
+
/** List available sessions for the current project */
|
|
13
|
+
export declare function listSessions(config: CoreConfig): Promise<SessionInfo[]>;
|
|
14
|
+
/** Load a session file into ResumedSessionData */
|
|
15
|
+
export declare function loadSession(filePath: string): Promise<ResumedSessionData>;
|
|
16
|
+
/** Convert MessageRecord[] to Content[] for API history reconstruction */
|
|
17
|
+
export declare function messageRecordsToHistory(messages: MessageRecord[]): Content[];
|
package/dist/session.js
ADDED
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
import fs from "node:fs/promises";
|
|
2
|
+
import path from "node:path";
|
|
3
|
+
import { SESSION_FILE_PREFIX, } from "@google/gemini-cli-core";
|
|
4
|
+
/** List available sessions for the current project */
|
|
5
|
+
export async function listSessions(config) {
|
|
6
|
+
const chatsDir = path.join(config.storage.getProjectTempDir(), "chats");
|
|
7
|
+
let files;
|
|
8
|
+
try {
|
|
9
|
+
files = await fs.readdir(chatsDir);
|
|
10
|
+
}
|
|
11
|
+
catch {
|
|
12
|
+
return [];
|
|
13
|
+
}
|
|
14
|
+
const sessionFiles = files
|
|
15
|
+
.filter((f) => f.startsWith(SESSION_FILE_PREFIX) && f.endsWith(".json"))
|
|
16
|
+
.sort((a, b) => b.localeCompare(a)); // newest first
|
|
17
|
+
const sessions = [];
|
|
18
|
+
for (const file of sessionFiles) {
|
|
19
|
+
try {
|
|
20
|
+
const filePath = path.join(chatsDir, file);
|
|
21
|
+
const raw = await fs.readFile(filePath, "utf-8");
|
|
22
|
+
const conv = JSON.parse(raw);
|
|
23
|
+
sessions.push({
|
|
24
|
+
sessionId: conv.sessionId,
|
|
25
|
+
filePath,
|
|
26
|
+
startTime: conv.startTime,
|
|
27
|
+
lastUpdated: conv.lastUpdated,
|
|
28
|
+
messageCount: conv.messages.length,
|
|
29
|
+
summary: conv.summary,
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
catch {
|
|
33
|
+
/* skip corrupted files */
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
return sessions;
|
|
37
|
+
}
|
|
38
|
+
/** Load a session file into ResumedSessionData */
|
|
39
|
+
export async function loadSession(filePath) {
|
|
40
|
+
const raw = await fs.readFile(filePath, "utf-8");
|
|
41
|
+
const conversation = JSON.parse(raw);
|
|
42
|
+
return { conversation, filePath };
|
|
43
|
+
}
|
|
44
|
+
/** Convert MessageRecord[] to Content[] for API history reconstruction */
|
|
45
|
+
export function messageRecordsToHistory(messages) {
|
|
46
|
+
const history = [];
|
|
47
|
+
for (const msg of messages) {
|
|
48
|
+
if (msg.type === "info" || msg.type === "error" || msg.type === "warning") {
|
|
49
|
+
continue;
|
|
50
|
+
}
|
|
51
|
+
if (msg.type === "user") {
|
|
52
|
+
const parts = normalizeParts(msg.content);
|
|
53
|
+
if (parts.length > 0)
|
|
54
|
+
history.push({ role: "user", parts });
|
|
55
|
+
}
|
|
56
|
+
if (msg.type === "gemini") {
|
|
57
|
+
const modelParts = [];
|
|
58
|
+
const contentParts = normalizeParts(msg.content);
|
|
59
|
+
modelParts.push(...contentParts);
|
|
60
|
+
if (msg.toolCalls) {
|
|
61
|
+
for (const tc of msg.toolCalls) {
|
|
62
|
+
modelParts.push({
|
|
63
|
+
functionCall: { id: tc.id, name: tc.name, args: tc.args },
|
|
64
|
+
});
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
if (modelParts.length > 0) {
|
|
68
|
+
history.push({ role: "model", parts: modelParts });
|
|
69
|
+
}
|
|
70
|
+
// Function response parts (user role)
|
|
71
|
+
if (msg.toolCalls?.some((tc) => tc.result != null)) {
|
|
72
|
+
const responseParts = [];
|
|
73
|
+
for (const tc of msg.toolCalls) {
|
|
74
|
+
if (tc.result != null) {
|
|
75
|
+
responseParts.push(...normalizeParts(tc.result));
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
if (responseParts.length > 0) {
|
|
79
|
+
history.push({ role: "user", parts: responseParts });
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
return history;
|
|
85
|
+
}
|
|
86
|
+
function normalizeParts(content) {
|
|
87
|
+
if (!content)
|
|
88
|
+
return [];
|
|
89
|
+
if (typeof content === "string")
|
|
90
|
+
return [{ text: content }];
|
|
91
|
+
if (Array.isArray(content)) {
|
|
92
|
+
return content.map((item) => typeof item === "string" ? { text: item } : item);
|
|
93
|
+
}
|
|
94
|
+
return [content];
|
|
95
|
+
}
|