Add biome config and update plugin source + dependencies
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
34
biome.json
Normal file
34
biome.json
Normal file
@@ -0,0 +1,34 @@
|
|||||||
|
{
|
||||||
|
"$schema": "https://biomejs.dev/schemas/2.4.11/schema.json",
|
||||||
|
"vcs": {
|
||||||
|
"enabled": true,
|
||||||
|
"clientKind": "git",
|
||||||
|
"useIgnoreFile": true
|
||||||
|
},
|
||||||
|
"files": {
|
||||||
|
"includes": ["**", "!!**/dist"]
|
||||||
|
},
|
||||||
|
"formatter": {
|
||||||
|
"enabled": true,
|
||||||
|
"indentStyle": "tab"
|
||||||
|
},
|
||||||
|
"linter": {
|
||||||
|
"enabled": true,
|
||||||
|
"rules": {
|
||||||
|
"recommended": true
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"javascript": {
|
||||||
|
"formatter": {
|
||||||
|
"quoteStyle": "double"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"assist": {
|
||||||
|
"enabled": true,
|
||||||
|
"actions": {
|
||||||
|
"source": {
|
||||||
|
"organizeImports": "on"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
164
package-lock.json
generated
164
package-lock.json
generated
@@ -11,10 +11,174 @@
|
|||||||
"@paperclipai/plugin-sdk": "^2026.325.0"
|
"@paperclipai/plugin-sdk": "^2026.325.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
"@biomejs/biome": "2.4.11",
|
||||||
"@types/node": "^25.5.0",
|
"@types/node": "^25.5.0",
|
||||||
"typescript": "^6.0.2"
|
"typescript": "^6.0.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@biomejs/biome": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/biome/-/biome-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-nWxHX8tf3Opb/qRgZpBbsTOqOodkbrkJ7S+JxJAruxOReaDPPmPuLBAGQ8vigyUgo0QBB+oQltNEAvalLcjggA==",
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"bin": {
|
||||||
|
"biome": "bin/biome"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"type": "opencollective",
|
||||||
|
"url": "https://opencollective.com/biome"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@biomejs/cli-darwin-arm64": "2.4.11",
|
||||||
|
"@biomejs/cli-darwin-x64": "2.4.11",
|
||||||
|
"@biomejs/cli-linux-arm64": "2.4.11",
|
||||||
|
"@biomejs/cli-linux-arm64-musl": "2.4.11",
|
||||||
|
"@biomejs/cli-linux-x64": "2.4.11",
|
||||||
|
"@biomejs/cli-linux-x64-musl": "2.4.11",
|
||||||
|
"@biomejs/cli-win32-arm64": "2.4.11",
|
||||||
|
"@biomejs/cli-win32-x64": "2.4.11"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-darwin-arm64": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-arm64/-/cli-darwin-arm64-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-wOt+ed+L2dgZanWyL6i29qlXMc088N11optzpo10peayObBaAshbTcxKUchzEMp9QSY8rh5h6VfAFE3WTS1rqg==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"darwin"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-darwin-x64": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-x64/-/cli-darwin-x64-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-gZ6zR8XmZlExfi/Pz/PffmdpWOQ8Qhy7oBztgkR8/ylSRyLwfRPSadmiVCV8WQ8PoJ2MWUy2fgID9zmtgUUJmw==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"darwin"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-linux-arm64": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64/-/cli-linux-arm64-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-avdJaEElXrKceK0va9FkJ4P5ci3N01TGkc6ni3P8l3BElqbOz42Wg2IyX3gbh0ZLEd4HVKEIrmuVu/AMuSeFFA==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-linux-arm64-musl": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64-musl/-/cli-linux-arm64-musl-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-+Sbo1OAmlegtdwqFE8iOxFIWLh1B3OEgsuZfBpyyN/kWuqZ8dx9ZEes6zVnDMo+zRHF2wLynRVhoQmV7ohxl2Q==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-linux-x64": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64/-/cli-linux-x64-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-TagWV0iomp5LnEnxWFg4nQO+e52Fow349vaX0Q/PIcX6Zhk4GGBgp3qqZ8PVkpC+cuehRctMf3+6+FgQ8jCEFQ==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-linux-x64-musl": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64-musl/-/cli-linux-x64-musl-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-bexd2IklK7ZgPhrz6jXzpIL6dEAH9MlJU1xGTrypx+FICxrXUp4CqtwfiuoDKse+UlgAlWtzML3jrMqeEAHEhA==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-win32-arm64": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-win32-arm64/-/cli-win32-arm64-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-RJhaTnY8byzxDt4bDVb7AFPHkPcjOPK3xBip4ZRTrN3TEfyhjLRm3r3mqknqydgVTB74XG8l4jMLwEACEeihVg==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"win32"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@biomejs/cli-win32-x64": {
|
||||||
|
"version": "2.4.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/@biomejs/cli-win32-x64/-/cli-win32-x64-2.4.11.tgz",
|
||||||
|
"integrity": "sha512-A8D3JM/00C2KQgUV3oj8Ba15EHEYwebAGCy5Sf9GAjr5Y3+kJIYOiESoqRDeuRZueuMdCsbLZIUqmPhpYXJE9A==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"dev": true,
|
||||||
|
"license": "MIT OR Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"win32"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.21.3"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/@paperclipai/plugin-sdk": {
|
"node_modules/@paperclipai/plugin-sdk": {
|
||||||
"version": "2026.325.0",
|
"version": "2026.325.0",
|
||||||
"resolved": "https://registry.npmjs.org/@paperclipai/plugin-sdk/-/plugin-sdk-2026.325.0.tgz",
|
"resolved": "https://registry.npmjs.org/@paperclipai/plugin-sdk/-/plugin-sdk-2026.325.0.tgz",
|
||||||
|
|||||||
11
package.json
11
package.json
@@ -8,13 +8,18 @@
|
|||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"build": "tsc",
|
"build": "tsc",
|
||||||
"dev": "paperclip-plugin-dev-server"
|
"dev": "paperclip-plugin-dev-server",
|
||||||
|
"format": "biome format --write src/",
|
||||||
|
"format:check": "biome format src/",
|
||||||
|
"biome": "biome check src/",
|
||||||
|
"biome:fix": "biome check --write src/"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@paperclipai/plugin-sdk": "^2026.325.0"
|
"@paperclipai/plugin-sdk": "^2026.325.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"typescript": "^6.0.2",
|
"@biomejs/biome": "2.4.11",
|
||||||
"@types/node": "^25.5.0"
|
"@types/node": "^25.5.0",
|
||||||
|
"typescript": "^6.0.2"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
373
src/legal-api.ts
373
src/legal-api.ts
@@ -3,227 +3,260 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
export class LegalApi {
|
export class LegalApi {
|
||||||
constructor(private baseUrl: string) {}
|
constructor(private baseUrl: string) {}
|
||||||
|
|
||||||
private async request<T>(path: string, init?: RequestInit): Promise<T> {
|
private async request<T>(path: string, init?: RequestInit): Promise<T> {
|
||||||
const res = await fetch(`${this.baseUrl}${path}`, {
|
const res = await fetch(`${this.baseUrl}${path}`, {
|
||||||
...init,
|
...init,
|
||||||
headers: {
|
headers: {
|
||||||
"Content-Type": "application/json",
|
"Content-Type": "application/json",
|
||||||
...init?.headers,
|
...init?.headers,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
if (!res.ok) {
|
if (!res.ok) {
|
||||||
const text = await res.text();
|
const text = await res.text();
|
||||||
throw new Error(`Legal API ${res.status}: ${text}`);
|
throw new Error(`Legal API ${res.status}: ${text}`);
|
||||||
}
|
}
|
||||||
return res.json() as Promise<T>;
|
return res.json() as Promise<T>;
|
||||||
}
|
}
|
||||||
|
|
||||||
async listCases(): Promise<CaseSummary[]> {
|
async listCases(): Promise<CaseSummary[]> {
|
||||||
return this.request("/api/cases");
|
return this.request("/api/cases");
|
||||||
}
|
}
|
||||||
|
|
||||||
async getCase(caseNumber: string): Promise<CaseDetails> {
|
async getCase(caseNumber: string): Promise<CaseDetails> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/details`);
|
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/details`);
|
||||||
}
|
}
|
||||||
|
|
||||||
async createCase(data: CaseCreateInput): Promise<CaseDetails> {
|
async createCase(data: CaseCreateInput): Promise<CaseDetails> {
|
||||||
return this.request("/api/cases/create", {
|
return this.request("/api/cases/create", {
|
||||||
method: "POST",
|
method: "POST",
|
||||||
body: JSON.stringify(data),
|
body: JSON.stringify(data),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateCase(caseNumber: string, data: CaseUpdateInput): Promise<CaseDetails> {
|
async updateCase(
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}`, {
|
caseNumber: string,
|
||||||
method: "PUT",
|
data: CaseUpdateInput,
|
||||||
body: JSON.stringify(data),
|
): Promise<CaseDetails> {
|
||||||
});
|
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}`, {
|
||||||
}
|
method: "PUT",
|
||||||
|
body: JSON.stringify(data),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
async getCaseStatus(caseNumber: string): Promise<WorkflowStatus> {
|
async getCaseStatus(caseNumber: string): Promise<WorkflowStatus> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/status`);
|
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/status`);
|
||||||
}
|
}
|
||||||
|
|
||||||
async search(query: string, limit = 10, sectionType = ""): Promise<SearchResult[]> {
|
async search(
|
||||||
const params = new URLSearchParams({ query, limit: String(limit) });
|
query: string,
|
||||||
if (sectionType) params.set("section_type", sectionType);
|
limit = 10,
|
||||||
return this.request(`/api/search?${params}`);
|
sectionType = "",
|
||||||
}
|
): Promise<SearchResult[]> {
|
||||||
|
const params = new URLSearchParams({ query, limit: String(limit) });
|
||||||
|
if (sectionType) params.set("section_type", sectionType);
|
||||||
|
return this.request(`/api/search?${params}`);
|
||||||
|
}
|
||||||
|
|
||||||
async searchCase(caseNumber: string, query: string, limit = 10): Promise<SearchResult[]> {
|
async searchCase(
|
||||||
const params = new URLSearchParams({ query, limit: String(limit) });
|
caseNumber: string,
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/search?${params}`);
|
query: string,
|
||||||
}
|
limit = 10,
|
||||||
|
): Promise<SearchResult[]> {
|
||||||
|
const params = new URLSearchParams({ query, limit: String(limit) });
|
||||||
|
return this.request(
|
||||||
|
`/api/cases/${encodeURIComponent(caseNumber)}/search?${params}`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
async getTemplate(caseNumber: string): Promise<{ template: string }> {
|
async getTemplate(caseNumber: string): Promise<{ template: string }> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/template`);
|
return this.request(
|
||||||
}
|
`/api/cases/${encodeURIComponent(caseNumber)}/template`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
async getProcessingStatus(): Promise<ProcessingStatus> {
|
async getProcessingStatus(): Promise<ProcessingStatus> {
|
||||||
return this.request("/api/processing-status");
|
return this.request("/api/processing-status");
|
||||||
}
|
}
|
||||||
|
|
||||||
async health(): Promise<{ status: string }> {
|
async health(): Promise<{ status: string }> {
|
||||||
return this.request("/health");
|
return this.request("/health");
|
||||||
}
|
}
|
||||||
|
|
||||||
// ── New methods for expanded workflow ──
|
// ── New methods for expanded workflow ──
|
||||||
|
|
||||||
async listDocuments(caseNumber: string): Promise<DocumentInfo[]> {
|
async listDocuments(caseNumber: string): Promise<DocumentInfo[]> {
|
||||||
const details = await this.getCase(caseNumber);
|
const details = await this.getCase(caseNumber);
|
||||||
return details.documents || [];
|
return details.documents || [];
|
||||||
}
|
}
|
||||||
|
|
||||||
async getDocumentText(docId: string): Promise<string> {
|
async getDocumentText(docId: string): Promise<string> {
|
||||||
return this.request(`/api/documents/${docId}/text`);
|
return this.request(`/api/documents/${docId}/text`);
|
||||||
}
|
}
|
||||||
|
|
||||||
async findSimilarCases(caseNumber: string): Promise<SearchResult[]> {
|
async findSimilarCases(caseNumber: string): Promise<SearchResult[]> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/search?query=similar&limit=5`);
|
return this.request(
|
||||||
}
|
`/api/cases/${encodeURIComponent(caseNumber)}/search?query=similar&limit=5`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
async setOutcome(caseNumber: string, outcome: string, reasoning?: string): Promise<{ status: string }> {
|
async setOutcome(
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/outcome`, {
|
caseNumber: string,
|
||||||
method: "POST",
|
outcome: string,
|
||||||
body: JSON.stringify({ outcome, reasoning: reasoning || "" }),
|
reasoning?: string,
|
||||||
});
|
): Promise<{ status: string }> {
|
||||||
}
|
return this.request(
|
||||||
|
`/api/cases/${encodeURIComponent(caseNumber)}/outcome`,
|
||||||
|
{
|
||||||
|
method: "POST",
|
||||||
|
body: JSON.stringify({ outcome, reasoning: reasoning || "" }),
|
||||||
|
},
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
async getClaims(caseNumber: string): Promise<ClaimsResponse> {
|
async getClaims(caseNumber: string): Promise<ClaimsResponse> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/claims`);
|
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/claims`);
|
||||||
}
|
}
|
||||||
|
|
||||||
async setDirection(caseNumber: string, directionDoc: Record<string, unknown>): Promise<{ status: string }> {
|
async setDirection(
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/direction`, {
|
caseNumber: string,
|
||||||
method: "POST",
|
directionDoc: Record<string, unknown>,
|
||||||
body: JSON.stringify({ direction_doc: directionDoc }),
|
): Promise<{ status: string }> {
|
||||||
});
|
return this.request(
|
||||||
}
|
`/api/cases/${encodeURIComponent(caseNumber)}/direction`,
|
||||||
|
{
|
||||||
|
method: "POST",
|
||||||
|
body: JSON.stringify({ direction_doc: directionDoc }),
|
||||||
|
},
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
async runQA(caseNumber: string): Promise<QAResponse> {
|
async runQA(caseNumber: string): Promise<QAResponse> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/qa`, {
|
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/qa`, {
|
||||||
method: "POST",
|
method: "POST",
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
async triggerLearning(caseNumber: string): Promise<{ status: string }> {
|
async triggerLearning(caseNumber: string): Promise<{ status: string }> {
|
||||||
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/learn`, {
|
return this.request(`/api/cases/${encodeURIComponent(caseNumber)}/learn`, {
|
||||||
method: "POST",
|
method: "POST",
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
async getStyleGuide(): Promise<string> {
|
async getStyleGuide(): Promise<string> {
|
||||||
// Return static style guide reference
|
// Return static style guide reference
|
||||||
return "ראה skill-legal-decision/SKILL.md — מדריך סגנון מלא של דפנה תמיר";
|
return "ראה skill-legal-decision/SKILL.md — מדריך סגנון מלא של דפנה תמיר";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Types
|
// Types
|
||||||
|
|
||||||
export interface CaseSummary {
|
export interface CaseSummary {
|
||||||
case_number: string;
|
case_number: string;
|
||||||
title: string;
|
title: string;
|
||||||
status: string;
|
status: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CaseDetails {
|
export interface CaseDetails {
|
||||||
id: string;
|
id: string;
|
||||||
case_number: string;
|
case_number: string;
|
||||||
title: string;
|
title: string;
|
||||||
status: string;
|
status: string;
|
||||||
appellants: string[];
|
appellants: string[];
|
||||||
respondents: string[];
|
respondents: string[];
|
||||||
subject: string;
|
subject: string;
|
||||||
property_address: string;
|
property_address: string;
|
||||||
expected_outcome: string;
|
expected_outcome: string;
|
||||||
documents?: DocumentInfo[];
|
documents?: DocumentInfo[];
|
||||||
[key: string]: unknown;
|
[key: string]: unknown;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CaseCreateInput {
|
export interface CaseCreateInput {
|
||||||
case_number: string;
|
case_number: string;
|
||||||
title: string;
|
title: string;
|
||||||
appellants?: string[];
|
appellants?: string[];
|
||||||
respondents?: string[];
|
respondents?: string[];
|
||||||
subject?: string;
|
subject?: string;
|
||||||
property_address?: string;
|
property_address?: string;
|
||||||
permit_number?: string;
|
permit_number?: string;
|
||||||
committee_type?: string;
|
committee_type?: string;
|
||||||
hearing_date?: string;
|
hearing_date?: string;
|
||||||
notes?: string;
|
notes?: string;
|
||||||
expected_outcome?: string;
|
expected_outcome?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CaseUpdateInput {
|
export interface CaseUpdateInput {
|
||||||
status?: string;
|
status?: string;
|
||||||
title?: string;
|
title?: string;
|
||||||
subject?: string;
|
subject?: string;
|
||||||
notes?: string;
|
notes?: string;
|
||||||
hearing_date?: string;
|
hearing_date?: string;
|
||||||
decision_date?: string;
|
decision_date?: string;
|
||||||
tags?: string[];
|
tags?: string[];
|
||||||
expected_outcome?: string;
|
expected_outcome?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface DocumentInfo {
|
export interface DocumentInfo {
|
||||||
id: string;
|
id: string;
|
||||||
title: string;
|
title: string;
|
||||||
doc_type: string;
|
doc_type: string;
|
||||||
extraction_status: string;
|
extraction_status: string;
|
||||||
page_count?: number;
|
page_count?: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface WorkflowStatus {
|
export interface WorkflowStatus {
|
||||||
case_number: string;
|
case_number: string;
|
||||||
title: string;
|
title: string;
|
||||||
status: string;
|
status: string;
|
||||||
documents: Array<{
|
documents: Array<{
|
||||||
title: string;
|
title: string;
|
||||||
type: string;
|
type: string;
|
||||||
extraction: string;
|
extraction: string;
|
||||||
chunks: number;
|
chunks: number;
|
||||||
pages?: number;
|
pages?: number;
|
||||||
}>;
|
}>;
|
||||||
total_documents: number;
|
total_documents: number;
|
||||||
total_chunks: number;
|
total_chunks: number;
|
||||||
has_draft: boolean;
|
has_draft: boolean;
|
||||||
draft_size_bytes: number;
|
draft_size_bytes: number;
|
||||||
next_steps: string[];
|
next_steps: string[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SearchResult {
|
export interface SearchResult {
|
||||||
score: number;
|
score: number;
|
||||||
case_number?: string;
|
case_number?: string;
|
||||||
document: string;
|
document: string;
|
||||||
section: string;
|
section: string;
|
||||||
page: number;
|
page: number;
|
||||||
content: string;
|
content: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ProcessingStatus {
|
export interface ProcessingStatus {
|
||||||
cases: number;
|
cases: number;
|
||||||
documents: number;
|
documents: number;
|
||||||
pending_processing: number;
|
pending_processing: number;
|
||||||
chunks: number;
|
chunks: number;
|
||||||
style_corpus_entries: number;
|
style_corpus_entries: number;
|
||||||
style_patterns: number;
|
style_patterns: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ClaimsResponse {
|
export interface ClaimsResponse {
|
||||||
case_number: string;
|
case_number: string;
|
||||||
claims: Record<string, Array<{ party_role: string; claim_text: string; claim_index: number }>>;
|
claims: Record<
|
||||||
total: number;
|
string,
|
||||||
|
Array<{ party_role: string; claim_text: string; claim_index: number }>
|
||||||
|
>;
|
||||||
|
total: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface QAResponse {
|
export interface QAResponse {
|
||||||
passed: boolean;
|
passed: boolean;
|
||||||
checks: Array<{
|
checks: Array<{
|
||||||
check_name: string;
|
check_name: string;
|
||||||
passed: boolean;
|
passed: boolean;
|
||||||
severity: string;
|
severity: string;
|
||||||
details: string;
|
details: string;
|
||||||
}>;
|
}>;
|
||||||
status: string;
|
status: string;
|
||||||
}
|
}
|
||||||
|
|||||||
309
src/manifest.ts
309
src/manifest.ts
@@ -1,152 +1,161 @@
|
|||||||
export default {
|
export default {
|
||||||
id: "marcusgroup.legal-ai",
|
id: "marcusgroup.legal-ai",
|
||||||
apiVersion: 1,
|
apiVersion: 1,
|
||||||
version: "0.1.0",
|
version: "0.1.0",
|
||||||
displayName: "Ezer Mishpati - Legal AI",
|
displayName: "Ezer Mishpati - Legal AI",
|
||||||
description:
|
description:
|
||||||
"Integration with legal decision drafting system — case management, semantic search, and workflow tracking",
|
"Integration with legal decision drafting system — case management, semantic search, and workflow tracking",
|
||||||
author: "Marcus Group",
|
author: "Marcus Group",
|
||||||
categories: ["connector"] as const,
|
categories: ["connector"] as const,
|
||||||
capabilities: [
|
capabilities: [
|
||||||
"events.subscribe",
|
"events.subscribe",
|
||||||
"issues.read",
|
"issues.read",
|
||||||
"issues.create",
|
"issues.create",
|
||||||
"issues.update",
|
"issues.update",
|
||||||
"issue.comments.create",
|
"issue.comments.create",
|
||||||
"agent.tools.register",
|
"agent.tools.register",
|
||||||
"http.outbound",
|
"http.outbound",
|
||||||
"plugin.state.read",
|
"plugin.state.read",
|
||||||
"plugin.state.write",
|
"plugin.state.write",
|
||||||
"jobs.schedule",
|
"jobs.schedule",
|
||||||
"activity.log.write",
|
"activity.log.write",
|
||||||
"companies.read",
|
"companies.read",
|
||||||
"projects.read",
|
"projects.read",
|
||||||
] as const,
|
] as const,
|
||||||
entrypoints: {
|
entrypoints: {
|
||||||
worker: "dist/worker.js",
|
worker: "dist/worker.js",
|
||||||
},
|
},
|
||||||
instanceConfigSchema: {
|
instanceConfigSchema: {
|
||||||
type: "object" as const,
|
type: "object" as const,
|
||||||
properties: {
|
properties: {
|
||||||
legalApiBaseUrl: {
|
legalApiBaseUrl: {
|
||||||
type: "string" as const,
|
type: "string" as const,
|
||||||
default: "http://localhost:8085",
|
default: "http://localhost:8085",
|
||||||
description: "Base URL for the Ezer Mishpati API",
|
description: "Base URL for the Ezer Mishpati API",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
tools: [
|
tools: [
|
||||||
{
|
{
|
||||||
toolKey: "legal_case_list",
|
toolKey: "legal_case_list",
|
||||||
name: "legal_case_list",
|
name: "legal_case_list",
|
||||||
displayName: "List Legal Cases",
|
displayName: "List Legal Cases",
|
||||||
description: "List all appeal cases in the legal system",
|
description: "List all appeal cases in the legal system",
|
||||||
parametersSchema: { type: "object" as const, properties: {} },
|
parametersSchema: { type: "object" as const, properties: {} },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
toolKey: "legal_case_get",
|
toolKey: "legal_case_get",
|
||||||
name: "legal_case_get",
|
name: "legal_case_get",
|
||||||
displayName: "Get Legal Case Details",
|
displayName: "Get Legal Case Details",
|
||||||
description: "Get full details of a legal case including documents",
|
description: "Get full details of a legal case including documents",
|
||||||
parametersSchema: {
|
parametersSchema: {
|
||||||
type: "object" as const,
|
type: "object" as const,
|
||||||
properties: {
|
properties: {
|
||||||
case_number: { type: "string" as const, description: "Case number" },
|
case_number: { type: "string" as const, description: "Case number" },
|
||||||
},
|
},
|
||||||
required: ["case_number"],
|
required: ["case_number"],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
toolKey: "legal_case_create",
|
toolKey: "legal_case_create",
|
||||||
name: "legal_case_create",
|
name: "legal_case_create",
|
||||||
displayName: "Create Legal Case",
|
displayName: "Create Legal Case",
|
||||||
description: "Create a new appeal case with linked Paperclip issue",
|
description: "Create a new appeal case with linked Paperclip issue",
|
||||||
parametersSchema: {
|
parametersSchema: {
|
||||||
type: "object" as const,
|
type: "object" as const,
|
||||||
properties: {
|
properties: {
|
||||||
case_number: { type: "string" as const },
|
case_number: { type: "string" as const },
|
||||||
title: { type: "string" as const },
|
title: { type: "string" as const },
|
||||||
appellants: { type: "array" as const, items: { type: "string" as const } },
|
appellants: {
|
||||||
respondents: { type: "array" as const, items: { type: "string" as const } },
|
type: "array" as const,
|
||||||
subject: { type: "string" as const },
|
items: { type: "string" as const },
|
||||||
property_address: { type: "string" as const },
|
},
|
||||||
expected_outcome: { type: "string" as const },
|
respondents: {
|
||||||
},
|
type: "array" as const,
|
||||||
required: ["case_number", "title"],
|
items: { type: "string" as const },
|
||||||
},
|
},
|
||||||
},
|
subject: { type: "string" as const },
|
||||||
{
|
property_address: { type: "string" as const },
|
||||||
toolKey: "legal_case_update",
|
expected_outcome: { type: "string" as const },
|
||||||
name: "legal_case_update",
|
},
|
||||||
displayName: "Update Legal Case",
|
required: ["case_number", "title"],
|
||||||
description: "Update a legal case status, title, or outcome",
|
},
|
||||||
parametersSchema: {
|
},
|
||||||
type: "object" as const,
|
{
|
||||||
properties: {
|
toolKey: "legal_case_update",
|
||||||
case_number: { type: "string" as const },
|
name: "legal_case_update",
|
||||||
status: { type: "string" as const },
|
displayName: "Update Legal Case",
|
||||||
title: { type: "string" as const },
|
description: "Update a legal case status, title, or outcome",
|
||||||
expected_outcome: { type: "string" as const },
|
parametersSchema: {
|
||||||
},
|
type: "object" as const,
|
||||||
required: ["case_number"],
|
properties: {
|
||||||
},
|
case_number: { type: "string" as const },
|
||||||
},
|
status: { type: "string" as const },
|
||||||
{
|
title: { type: "string" as const },
|
||||||
toolKey: "legal_case_status",
|
expected_outcome: { type: "string" as const },
|
||||||
name: "legal_case_status",
|
},
|
||||||
displayName: "Get Case Workflow Status",
|
required: ["case_number"],
|
||||||
description: "Get full workflow status: documents, drafts, next steps",
|
},
|
||||||
parametersSchema: {
|
},
|
||||||
type: "object" as const,
|
{
|
||||||
properties: {
|
toolKey: "legal_case_status",
|
||||||
case_number: { type: "string" as const },
|
name: "legal_case_status",
|
||||||
},
|
displayName: "Get Case Workflow Status",
|
||||||
required: ["case_number"],
|
description: "Get full workflow status: documents, drafts, next steps",
|
||||||
},
|
parametersSchema: {
|
||||||
},
|
type: "object" as const,
|
||||||
{
|
properties: {
|
||||||
toolKey: "legal_search",
|
case_number: { type: "string" as const },
|
||||||
name: "legal_search",
|
},
|
||||||
displayName: "Search Legal Precedents",
|
required: ["case_number"],
|
||||||
description: "Semantic RAG search across previous decisions",
|
},
|
||||||
parametersSchema: {
|
},
|
||||||
type: "object" as const,
|
{
|
||||||
properties: {
|
toolKey: "legal_search",
|
||||||
query: { type: "string" as const, description: "Search query in Hebrew" },
|
name: "legal_search",
|
||||||
limit: { type: "number" as const },
|
displayName: "Search Legal Precedents",
|
||||||
section_type: { type: "string" as const },
|
description: "Semantic RAG search across previous decisions",
|
||||||
},
|
parametersSchema: {
|
||||||
required: ["query"],
|
type: "object" as const,
|
||||||
},
|
properties: {
|
||||||
},
|
query: {
|
||||||
{
|
type: "string" as const,
|
||||||
toolKey: "legal_case_template",
|
description: "Search query in Hebrew",
|
||||||
name: "legal_case_template",
|
},
|
||||||
displayName: "Get Decision Template",
|
limit: { type: "number" as const },
|
||||||
description: "Get outcome-aware decision template for 12-block structure",
|
section_type: { type: "string" as const },
|
||||||
parametersSchema: {
|
},
|
||||||
type: "object" as const,
|
required: ["query"],
|
||||||
properties: {
|
},
|
||||||
case_number: { type: "string" as const },
|
},
|
||||||
},
|
{
|
||||||
required: ["case_number"],
|
toolKey: "legal_case_template",
|
||||||
},
|
name: "legal_case_template",
|
||||||
},
|
displayName: "Get Decision Template",
|
||||||
{
|
description: "Get outcome-aware decision template for 12-block structure",
|
||||||
toolKey: "legal_processing_status",
|
parametersSchema: {
|
||||||
name: "legal_processing_status",
|
type: "object" as const,
|
||||||
displayName: "Get Processing Status",
|
properties: {
|
||||||
description: "Get overall system processing status",
|
case_number: { type: "string" as const },
|
||||||
parametersSchema: { type: "object" as const, properties: {} },
|
},
|
||||||
},
|
required: ["case_number"],
|
||||||
],
|
},
|
||||||
jobs: [
|
},
|
||||||
{
|
{
|
||||||
jobKey: "sync-case-status",
|
toolKey: "legal_processing_status",
|
||||||
displayName: "Sync Legal Case Status",
|
name: "legal_processing_status",
|
||||||
description:
|
displayName: "Get Processing Status",
|
||||||
"Polls legal-ai for case status changes and updates Paperclip issues",
|
description: "Get overall system processing status",
|
||||||
schedule: "*/15 * * * *",
|
parametersSchema: { type: "object" as const, properties: {} },
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
jobs: [
|
||||||
|
{
|
||||||
|
jobKey: "sync-case-status",
|
||||||
|
displayName: "Sync Legal Case Status",
|
||||||
|
description:
|
||||||
|
"Polls legal-ai for case status changes and updates Paperclip issues",
|
||||||
|
schedule: "*/15 * * * *",
|
||||||
|
},
|
||||||
|
],
|
||||||
};
|
};
|
||||||
|
|||||||
1125
src/worker.ts
1125
src/worker.ts
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user