fix: improve droid provider with context isolation and message parsing
Changes: - Add context isolation using --cwd flag to prevent project context leakage - Fix message content parsing to support both string and array formats - Add debug logging for troubleshooting - Create isolated temporary working directory for each service instance This prevents Droid from seeing the current project directory and mentioning it in responses, providing a cleaner API experience. Tested: ✅ Context isolation verified - Droid reports empty temp directory ✅ Message parsing works with OpenAI format ✅ API responses no longer mention project context
This commit is contained in:
parent
66b6363ad4
commit
e91aaa02e5
1 changed files with 35 additions and 9 deletions
|
|
@ -1,4 +1,7 @@
|
||||||
import { spawn } from 'child_process';
|
import { spawn } from 'child_process';
|
||||||
|
import { mkdtempSync } from 'fs';
|
||||||
|
import { tmpdir } from 'os';
|
||||||
|
import { join } from 'path';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Droid (Factory.ai) API Service
|
* Droid (Factory.ai) API Service
|
||||||
|
|
@ -13,6 +16,10 @@ export class DroidApiService {
|
||||||
this.config = config;
|
this.config = config;
|
||||||
this.isInitialized = false;
|
this.isInitialized = false;
|
||||||
this.droidCommand = config.DROID_COMMAND || 'droid';
|
this.droidCommand = config.DROID_COMMAND || 'droid';
|
||||||
|
|
||||||
|
// Create isolated working directory to prevent context leakage
|
||||||
|
this.isolatedWorkDir = mkdtempSync(join(tmpdir(), 'droid-isolated-'));
|
||||||
|
console.log('[Droid] Created isolated working directory:', this.isolatedWorkDir);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -75,14 +82,21 @@ export class DroidApiService {
|
||||||
*/
|
*/
|
||||||
messagesToPrompt(messages) {
|
messagesToPrompt(messages) {
|
||||||
return messages.map(msg => {
|
return messages.map(msg => {
|
||||||
if (msg.role === 'user') {
|
// Handle both string and array content formats
|
||||||
return msg.content;
|
let content = msg.content;
|
||||||
} else if (msg.role === 'assistant') {
|
if (Array.isArray(content)) {
|
||||||
return `Assistant: ${msg.content}`;
|
// Extract text from content blocks
|
||||||
} else if (msg.role === 'system') {
|
content = content.map(block => block.text || '').join('');
|
||||||
return `System: ${msg.content}`;
|
|
||||||
}
|
}
|
||||||
return msg.content;
|
|
||||||
|
if (msg.role === 'user') {
|
||||||
|
return content;
|
||||||
|
} else if (msg.role === 'assistant') {
|
||||||
|
return `Assistant: ${content}`;
|
||||||
|
} else if (msg.role === 'system') {
|
||||||
|
return `System: ${content}`;
|
||||||
|
}
|
||||||
|
return content;
|
||||||
}).join('\n\n');
|
}).join('\n\n');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -99,7 +113,14 @@ export class DroidApiService {
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const prompt = this.messagesToPrompt(requestBody.messages);
|
const prompt = this.messagesToPrompt(requestBody.messages);
|
||||||
const output = await this.executeDroidCommand(['exec', '--skip-permissions-unsafe', prompt]);
|
console.log('[Droid DEBUG] Sending prompt to droid exec:', prompt);
|
||||||
|
console.log('[Droid DEBUG] Isolated working directory:', this.isolatedWorkDir);
|
||||||
|
const output = await this.executeDroidCommand([
|
||||||
|
'exec',
|
||||||
|
'--skip-permissions-unsafe',
|
||||||
|
'--cwd', this.isolatedWorkDir,
|
||||||
|
prompt
|
||||||
|
]);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
id: `msg_${Date.now()}`,
|
id: `msg_${Date.now()}`,
|
||||||
|
|
@ -151,7 +172,12 @@ export class DroidApiService {
|
||||||
content_block: { type: 'text', text: '' }
|
content_block: { type: 'text', text: '' }
|
||||||
};
|
};
|
||||||
|
|
||||||
const droid = spawn(this.droidCommand, ['exec', '--skip-permissions-unsafe', prompt]);
|
const droid = spawn(this.droidCommand, [
|
||||||
|
'exec',
|
||||||
|
'--skip-permissions-unsafe',
|
||||||
|
'--cwd', this.isolatedWorkDir,
|
||||||
|
prompt
|
||||||
|
]);
|
||||||
|
|
||||||
let buffer = '';
|
let buffer = '';
|
||||||
for await (const chunk of droid.stdout) {
|
for await (const chunk of droid.stdout) {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue