mirror of
https://github.com/Nezumi-2711/9router.git
synced 2026-09-22 20:00:47 +00:00
Fix bug
This commit is contained in:
@@ -1,8 +1,62 @@
|
||||
import { createHash } from "crypto";
|
||||
import { BaseExecutor } from "./base.js";
|
||||
import { CODEX_DEFAULT_INSTRUCTIONS } from "../config/codexInstructions.js";
|
||||
import { PROVIDERS } from "../config/providers.js";
|
||||
import { normalizeResponsesInput } from "../translator/helpers/responsesApiHelper.js";
|
||||
|
||||
// In-memory map: hash(first assistant content) → { sessionId, lastUsed }
|
||||
const SESSION_TTL_MS = 60 * 60 * 1000; // 1 hour
|
||||
const assistantSessionMap = new Map();
|
||||
|
||||
function hashContent(text) {
|
||||
return createHash("sha256").update(text).digest("hex").slice(0, 16);
|
||||
}
|
||||
|
||||
function generateSessionId() {
|
||||
return `sess_${Date.now().toString(36)}_${Math.random().toString(36).slice(2, 9)}`;
|
||||
}
|
||||
|
||||
// Extract text content from an input item
|
||||
function extractItemText(item) {
|
||||
if (!item) return "";
|
||||
if (typeof item.content === "string") return item.content;
|
||||
if (Array.isArray(item.content)) {
|
||||
return item.content.map(c => c.text || c.output || "").filter(Boolean).join("");
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
// Resolve session_id from first assistant message in conversation history
|
||||
function resolveConversationSessionId(input) {
|
||||
if (!Array.isArray(input) || input.length === 0) return generateSessionId();
|
||||
|
||||
const firstAssistant = input.find(item => item.role === "assistant");
|
||||
if (!firstAssistant) return generateSessionId(); // Turn 1: no assistant yet
|
||||
|
||||
const text = extractItemText(firstAssistant);
|
||||
if (!text) return generateSessionId();
|
||||
|
||||
const hash = hashContent(text);
|
||||
const entry = assistantSessionMap.get(hash);
|
||||
if (entry) {
|
||||
entry.lastUsed = Date.now();
|
||||
return entry.sessionId;
|
||||
}
|
||||
|
||||
|
||||
const sessionId = generateSessionId();
|
||||
assistantSessionMap.set(hash, { sessionId, lastUsed: Date.now() });
|
||||
return sessionId;
|
||||
}
|
||||
|
||||
// Cleanup expired entries periodically
|
||||
setInterval(() => {
|
||||
const now = Date.now();
|
||||
for (const [key, entry] of assistantSessionMap) {
|
||||
if (now - entry.lastUsed > SESSION_TTL_MS) assistantSessionMap.delete(key);
|
||||
}
|
||||
}, 10 * 60 * 1000);
|
||||
|
||||
/**
|
||||
* Codex Executor - handles OpenAI Codex API (Responses API format)
|
||||
* Automatically injects default instructions if missing
|
||||
@@ -10,14 +64,16 @@ import { normalizeResponsesInput } from "../translator/helpers/responsesApiHelpe
|
||||
export class CodexExecutor extends BaseExecutor {
|
||||
constructor() {
|
||||
super("codex", PROVIDERS.codex);
|
||||
this._currentSessionId = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Override headers to add session_id per request
|
||||
* Override headers to add session_id per conversation
|
||||
* transformRequest runs BEFORE buildHeaders, sets this._currentSessionId
|
||||
*/
|
||||
buildHeaders(credentials, stream = true) {
|
||||
const headers = super.buildHeaders(credentials, stream);
|
||||
headers["session_id"] = `${Date.now()}-${Math.random().toString(36).slice(2, 11)}`;
|
||||
headers["session_id"] = this._currentSessionId || credentials?.connectionId || "default";
|
||||
return headers;
|
||||
}
|
||||
|
||||
@@ -25,6 +81,8 @@ export class CodexExecutor extends BaseExecutor {
|
||||
* Transform request before sending - inject default instructions if missing
|
||||
*/
|
||||
transformRequest(model, body, stream, credentials) {
|
||||
// Resolve conversation-stable session_id from input history
|
||||
this._currentSessionId = resolveConversationSessionId(body.input);
|
||||
// Convert string input to array format (Codex API requires input as array)
|
||||
const normalized = normalizeResponsesInput(body.input);
|
||||
if (normalized) body.input = normalized;
|
||||
|
||||
Reference in New Issue
Block a user