refactori api

This commit is contained in:
Nicolò Boschi 2025-11-13 13:51:42 +01:00
parent c82fff949b
commit 28e28d51c4
59 changed files with 1394 additions and 822 deletions

View file

@ -19,6 +19,7 @@ cd ..
This regenerates Python and TypeScript clients from `openapi.json`.
**Note:** Your `pyproject.toml` and `package.json` are preserved - only code is regenerated.
### 3. Commit Everything
@ -34,8 +35,94 @@ git commit -m "Update OpenAPI spec and regenerate clients"
```
This will:
- Update versions in all core components
- Update version to `0.0.6` in **all** components (core, clients, CLI, UI, Helm)
- Commit changes
- Create and push tag `v0.0.6`
- Trigger GitHub Actions (builds Python package, Rust CLI, Docker images, Helm chart)
---
## After GitHub Actions Complete
### Publish Python Client to PyPI
```bash
cd memora-clients/python
uv build
uv publish
```
### Publish TypeScript Client to NPM
```bash
cd memora-clients/typescript
npm install
npm run build
npm publish --access public
```
---
## Pre-Release Checklist
- [ ] Tests passing: `cd memora && uv run pytest tests`
- [ ] No uncommitted changes: `git status`
- [ ] On `main` branch
---
## Versioning
**Semantic Versioning: `MAJOR.MINOR.PATCH`**
- **PATCH** (0.0.6): Bug fixes, no API changes
- **MINOR** (0.1.0): New features, backward compatible
- **MAJOR** (1.0.0): Breaking changes
**All components use the same version** - coordinated releases for simplicity.
---
## Troubleshooting
**Tag already exists:**
```bash
git tag -d v0.0.6
git push origin :refs/tags/v0.0.6
```
**Working directory not clean:**
```bash
git status
# Commit or stash changes first
```
**GitHub Actions failed:**
- Check: https://github.com/nicoloboschi/memora/actions
- Re-run failed jobs or fix and release new patch version
**Rollback:**
```bash
git tag -d v0.0.6
git push origin :refs/tags/v0.0.6
git revert HEAD
git push
```
---
## Quick Reference
```bash
# Full release workflow
uv sync
cd memora-dev && uv run generate-openapi && cd ..
./scripts/generate-clients.sh
git add openapi.json memora-clients/
git commit -m "Update OpenAPI spec and regenerate clients"
./scripts/release.sh 0.0.6
# After GH Actions complete:
cd memora-clients/python && uv build && uv publish
cd ../typescript && npm run build && npm publish --access public
```

View file

@ -15,7 +15,6 @@ pub struct ApiError {
pub struct SearchRequest {
pub query: String,
pub fact_type: Vec<String>,
pub agent_id: String,
pub thinking_budget: i32,
pub max_tokens: i32,
pub trace: bool,
@ -50,7 +49,6 @@ pub struct TraceInfo {
#[derive(Debug, Serialize)]
pub struct ThinkRequest {
pub query: String,
pub agent_id: String,
pub thinking_budget: i32,
#[serde(skip_serializing_if = "Option::is_none")]
pub context: Option<String>,
@ -71,7 +69,6 @@ pub struct MemoryItem {
#[derive(Debug, Serialize)]
pub struct BatchMemoryRequest {
pub agent_id: String,
pub items: Vec<MemoryItem>,
pub document_id: Option<String>,
}
@ -134,6 +131,62 @@ pub struct BackgroundResponse {
pub personality: Option<PersonalityTraits>,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct AgentStats {
pub agent_id: String,
pub total_nodes: i32,
pub total_links: i32,
pub total_documents: i32,
pub pending_operations: i32,
pub failed_operations: i32,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct Document {
pub document_id: String,
pub agent_id: String,
pub created_at: String,
pub num_units: i32,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct DocumentDetails {
pub document_id: String,
pub agent_id: String,
pub text: String,
pub created_at: String,
pub num_units: i32,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct DocumentsResponse {
pub documents: Vec<Document>,
pub total: i32,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct Operation {
pub id: String,
pub task_type: String,
pub items_count: i32,
pub document_id: Option<String>,
pub created_at: String,
pub status: String,
pub error_message: Option<String>,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct OperationsResponse {
pub agent_id: String,
pub operations: Vec<Operation>,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct DeleteResponse {
pub success: bool,
pub message: String,
}
pub struct ApiClient {
client: Client,
base_url: String,
@ -149,8 +202,8 @@ impl ApiClient {
Ok(ApiClient { client, base_url })
}
pub fn search(&self, request: SearchRequest, verbose: bool) -> Result<SearchResponse> {
let url = format!("{}/api/search", self.base_url);
pub fn search(&self, agent_id: &str, request: SearchRequest, verbose: bool) -> Result<SearchResponse> {
let url = format!("{}/api/v1/agents/{}/memories/search", self.base_url, agent_id);
let request_body = serde_json::to_string_pretty(&request).unwrap_or_default();
if verbose {
@ -188,8 +241,8 @@ impl ApiClient {
Ok(result)
}
pub fn think(&self, request: ThinkRequest, verbose: bool) -> Result<ThinkResponse> {
let url = format!("{}/api/think", self.base_url);
pub fn think(&self, agent_id: &str, request: ThinkRequest, verbose: bool) -> Result<ThinkResponse> {
let url = format!("{}/api/v1/agents/{}/think", self.base_url, agent_id);
if verbose {
eprintln!("Request URL: {}", url);
@ -226,13 +279,17 @@ impl ApiClient {
Ok(result)
}
pub fn put_memories(&self, request: BatchMemoryRequest, async_mode: bool, verbose: bool) -> Result<BatchMemoryResponse> {
pub fn put_memories(&self, agent_id: &str, request: BatchMemoryRequest, async_mode: bool, verbose: bool) -> Result<BatchMemoryResponse> {
let endpoint = if async_mode {
"batch_async"
"async"
} else {
"batch"
""
};
let url = if async_mode {
format!("{}/api/v1/agents/{}/memories/{}", self.base_url, agent_id, endpoint)
} else {
format!("{}/api/v1/agents/{}/memories", self.base_url, agent_id)
};
let url = format!("{}/api/memories/{}", self.base_url, endpoint);
if verbose {
eprintln!("Request URL: {}", url);
@ -270,7 +327,7 @@ impl ApiClient {
}
pub fn list_agents(&self, verbose: bool) -> Result<Vec<Agent>> {
let url = format!("{}/api/agents", self.base_url);
let url = format!("{}/api/v1/agents", self.base_url);
if verbose {
eprintln!("Request URL: {}", url);
@ -314,7 +371,7 @@ impl ApiClient {
}
pub fn get_profile(&self, agent_id: &str, verbose: bool) -> Result<AgentProfile> {
let url = format!("{}/api/agents/{}/profile", self.base_url, agent_id);
let url = format!("{}/api/v1/agents/{}/profile", self.base_url, agent_id);
if verbose {
eprintln!("Request URL: {}", url);
@ -360,7 +417,7 @@ impl ApiClient {
bias_strength: f32,
verbose: bool,
) -> Result<AgentProfile> {
let url = format!("{}/api/agents/{}/profile", self.base_url, agent_id);
let url = format!("{}/api/v1/agents/{}/profile", self.base_url, agent_id);
let request = UpdatePersonalityRequest {
personality: PersonalityTraits {
openness,
@ -408,7 +465,7 @@ impl ApiClient {
}
pub fn add_background(&self, agent_id: &str, content: &str, update_personality: bool, verbose: bool) -> Result<BackgroundResponse> {
let url = format!("{}/api/agents/{}/background", self.base_url, agent_id);
let url = format!("{}/api/v1/agents/{}/background", self.base_url, agent_id);
let request = AddBackgroundRequest {
content: content.to_string(),
update_personality,
@ -448,4 +505,236 @@ impl ApiClient {
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
pub fn get_stats(&self, agent_id: &str, verbose: bool) -> Result<AgentStats> {
let url = format!("{}/api/v1/agents/{}/stats", self.base_url, agent_id);
if verbose {
eprintln!("Request URL: {}", url);
}
let response = self
.client
.get(&url)
.timeout(Duration::from_secs(30))
.send()?;
let status = response.status();
if verbose {
eprintln!("Response status: {}", status);
}
if !status.is_success() {
let error_body = response.text().unwrap_or_default();
if verbose {
eprintln!("Error response body:\n{}", error_body);
}
anyhow::bail!("API returned error status {}: {}", status, error_body);
}
let response_text = response.text()?;
if verbose {
eprintln!("Response body:\n{}", response_text);
}
let result: AgentStats = serde_json::from_str(&response_text)
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
pub fn list_documents(&self, agent_id: &str, q: Option<&str>, limit: Option<i32>, offset: Option<i32>, verbose: bool) -> Result<DocumentsResponse> {
let mut url = format!("{}/api/v1/agents/{}/documents", self.base_url, agent_id);
let mut params = vec![];
if let Some(query) = q {
params.push(format!("q={}", query));
}
if let Some(l) = limit {
params.push(format!("limit={}", l));
}
if let Some(o) = offset {
params.push(format!("offset={}", o));
}
if !params.is_empty() {
url.push('?');
url.push_str(&params.join("&"));
}
if verbose {
eprintln!("Request URL: {}", url);
}
let response = self
.client
.get(&url)
.timeout(Duration::from_secs(30))
.send()?;
let status = response.status();
if verbose {
eprintln!("Response status: {}", status);
}
if !status.is_success() {
let error_body = response.text().unwrap_or_default();
if verbose {
eprintln!("Error response body:\n{}", error_body);
}
anyhow::bail!("API returned error status {}: {}", status, error_body);
}
let response_text = response.text()?;
if verbose {
eprintln!("Response body:\n{}", response_text);
}
let result: DocumentsResponse = serde_json::from_str(&response_text)
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
pub fn get_document(&self, agent_id: &str, document_id: &str, verbose: bool) -> Result<DocumentDetails> {
let url = format!("{}/api/v1/agents/{}/documents/{}", self.base_url, agent_id, document_id);
if verbose {
eprintln!("Request URL: {}", url);
}
let response = self
.client
.get(&url)
.timeout(Duration::from_secs(30))
.send()?;
let status = response.status();
if verbose {
eprintln!("Response status: {}", status);
}
if !status.is_success() {
let error_body = response.text().unwrap_or_default();
if verbose {
eprintln!("Error response body:\n{}", error_body);
}
anyhow::bail!("API returned error status {}: {}", status, error_body);
}
let response_text = response.text()?;
if verbose {
eprintln!("Response body:\n{}", response_text);
}
let result: DocumentDetails = serde_json::from_str(&response_text)
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
pub fn list_operations(&self, agent_id: &str, verbose: bool) -> Result<OperationsResponse> {
let url = format!("{}/api/v1/agents/{}/operations", self.base_url, agent_id);
if verbose {
eprintln!("Request URL: {}", url);
}
let response = self
.client
.get(&url)
.timeout(Duration::from_secs(30))
.send()?;
let status = response.status();
if verbose {
eprintln!("Response status: {}", status);
}
if !status.is_success() {
let error_body = response.text().unwrap_or_default();
if verbose {
eprintln!("Error response body:\n{}", error_body);
}
anyhow::bail!("API returned error status {}: {}", status, error_body);
}
let response_text = response.text()?;
if verbose {
eprintln!("Response body:\n{}", response_text);
}
let result: OperationsResponse = serde_json::from_str(&response_text)
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
pub fn cancel_operation(&self, agent_id: &str, operation_id: &str, verbose: bool) -> Result<DeleteResponse> {
let url = format!("{}/api/v1/agents/{}/operations/{}", self.base_url, agent_id, operation_id);
if verbose {
eprintln!("Request URL: {}", url);
}
let response = self
.client
.delete(&url)
.timeout(Duration::from_secs(30))
.send()?;
let status = response.status();
if verbose {
eprintln!("Response status: {}", status);
}
if !status.is_success() {
let error_body = response.text().unwrap_or_default();
if verbose {
eprintln!("Error response body:\n{}", error_body);
}
anyhow::bail!("API returned error status {}: {}", status, error_body);
}
let response_text = response.text()?;
if verbose {
eprintln!("Response body:\n{}", response_text);
}
let result: DeleteResponse = serde_json::from_str(&response_text)
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
pub fn delete_memory(&self, agent_id: &str, unit_id: &str, verbose: bool) -> Result<DeleteResponse> {
let url = format!("{}/api/v1/agents/{}/memories/{}", self.base_url, agent_id, unit_id);
if verbose {
eprintln!("Request URL: {}", url);
}
let response = self
.client
.delete(&url)
.timeout(Duration::from_secs(30))
.send()?;
let status = response.status();
if verbose {
eprintln!("Response status: {}", status);
}
if !status.is_success() {
let error_body = response.text().unwrap_or_default();
if verbose {
eprintln!("Error response body:\n{}", error_body);
}
anyhow::bail!("API returned error status {}: {}", status, error_body);
}
let response_text = response.text()?;
if verbose {
eprintln!("Response body:\n{}", response_text);
}
let result: DeleteResponse = serde_json::from_str(&response_text)
.with_context(|| format!("Failed to parse API response. Response was: {}", response_text))?;
Ok(result)
}
}

View file

@ -180,6 +180,63 @@ enum Commands {
#[arg(long)]
no_update_personality: bool,
},
/// Get memory statistics for an agent
Stats {
/// Agent ID to get stats for
agent_id: String,
},
/// List documents for an agent
Documents {
/// Agent ID to list documents for
agent_id: String,
/// Search query to filter documents
#[arg(short = 'q', long)]
query: Option<String>,
/// Maximum number of results
#[arg(short = 'l', long, default_value = "100")]
limit: i32,
/// Offset for pagination
#[arg(short = 's', long, default_value = "0")]
offset: i32,
},
/// Get a specific document by ID
Document {
/// Agent ID
agent_id: String,
/// Document ID to retrieve
document_id: String,
},
/// List async operations for an agent
Operations {
/// Agent ID to list operations for
agent_id: String,
},
/// Cancel a pending async operation
CancelOperation {
/// Agent ID
agent_id: String,
/// Operation ID to cancel
operation_id: String,
},
/// Delete a memory unit
DeleteMemory {
/// Agent ID
agent_id: String,
/// Memory unit ID to delete
unit_id: String,
},
}
fn main() {
@ -227,13 +284,12 @@ fn run() -> Result<()> {
let request = SearchRequest {
query,
fact_type,
agent_id,
thinking_budget: budget,
max_tokens,
trace,
};
let response = client.search(request, verbose);
let response = client.search(&agent_id, request, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
@ -266,12 +322,11 @@ fn run() -> Result<()> {
let request = ThinkRequest {
query,
agent_id,
thinking_budget: budget,
context,
};
let response = client.think(request, verbose);
let response = client.think(&agent_id, request, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
@ -311,12 +366,11 @@ fn run() -> Result<()> {
};
let request = BatchMemoryRequest {
agent_id,
items: vec![item],
document_id: Some(doc_id.clone()),
};
let response = client.put_memories(request, r#async, verbose);
let response = client.put_memories(&agent_id, request, r#async, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
@ -425,11 +479,10 @@ fn run() -> Result<()> {
};
let request = BatchMemoryRequest {
agent_id,
items,
document_id,
};
let response = client.put_memories(request, r#async, verbose);
let response = client.put_memories(&agent_id, request, r#async, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
@ -622,6 +675,201 @@ fn run() -> Result<()> {
Err(e) => Err(e)
}
}
Commands::Stats { agent_id } => {
let spinner = if output_format == OutputFormat::Pretty {
Some(ui::create_spinner("Fetching statistics..."))
} else {
None
};
let response = client.get_stats(&agent_id, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
}
match response {
Ok(stats) => {
if output_format == OutputFormat::Pretty {
ui::print_info(&format!("Statistics for agent '{}':", agent_id));
println!(" Total Nodes: {}", stats.total_nodes);
println!(" Total Links: {}", stats.total_links);
println!(" Total Documents: {}", stats.total_documents);
println!(" Pending Operations: {}", stats.pending_operations);
println!(" Failed Operations: {}", stats.failed_operations);
} else {
output::print_output(&stats, output_format)?;
}
Ok(())
}
Err(e) => Err(e)
}
}
Commands::Documents { agent_id, query, limit, offset } => {
let spinner = if output_format == OutputFormat::Pretty {
Some(ui::create_spinner("Fetching documents..."))
} else {
None
};
let response = client.list_documents(&agent_id, query.as_deref(), Some(limit), Some(offset), verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
}
match response {
Ok(docs_response) => {
if output_format == OutputFormat::Pretty {
ui::print_info(&format!("Documents for agent '{}' (total: {})", agent_id, docs_response.total));
for doc in &docs_response.documents {
println!("\n Document ID: {}", doc.document_id);
println!(" Created: {}", doc.created_at);
println!(" Units: {}", doc.num_units);
}
} else {
output::print_output(&docs_response, output_format)?;
}
Ok(())
}
Err(e) => Err(e)
}
}
Commands::Document { agent_id, document_id } => {
let spinner = if output_format == OutputFormat::Pretty {
Some(ui::create_spinner("Fetching document..."))
} else {
None
};
let response = client.get_document(&agent_id, &document_id, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
}
match response {
Ok(doc) => {
if output_format == OutputFormat::Pretty {
ui::print_info(&format!("Document: {}", doc.document_id));
println!(" Agent ID: {}", doc.agent_id);
println!(" Created: {}", doc.created_at);
println!(" Units: {}", doc.num_units);
println!("\n Text:\n{}", doc.text);
} else {
output::print_output(&doc, output_format)?;
}
Ok(())
}
Err(e) => Err(e)
}
}
Commands::Operations { agent_id } => {
let spinner = if output_format == OutputFormat::Pretty {
Some(ui::create_spinner("Fetching operations..."))
} else {
None
};
let response = client.list_operations(&agent_id, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
}
match response {
Ok(ops_response) => {
if output_format == OutputFormat::Pretty {
ui::print_info(&format!("Operations for agent '{}':", agent_id));
if ops_response.operations.is_empty() {
println!(" No operations found.");
} else {
for op in &ops_response.operations {
println!("\n Operation ID: {}", op.id);
println!(" Type: {}", op.task_type);
println!(" Status: {}", op.status);
println!(" Items: {}", op.items_count);
if let Some(doc_id) = &op.document_id {
println!(" Document ID: {}", doc_id);
}
println!(" Created: {}", op.created_at);
if let Some(error) = &op.error_message {
println!(" Error: {}", error);
}
}
}
} else {
output::print_output(&ops_response, output_format)?;
}
Ok(())
}
Err(e) => Err(e)
}
}
Commands::CancelOperation { agent_id, operation_id } => {
let spinner = if output_format == OutputFormat::Pretty {
Some(ui::create_spinner("Cancelling operation..."))
} else {
None
};
let response = client.cancel_operation(&agent_id, &operation_id, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
}
match response {
Ok(result) => {
if output_format == OutputFormat::Pretty {
if result.success {
ui::print_success(&result.message);
} else {
ui::print_error(&result.message);
}
} else {
output::print_output(&result, output_format)?;
}
Ok(())
}
Err(e) => Err(e)
}
}
Commands::DeleteMemory { agent_id, unit_id } => {
let spinner = if output_format == OutputFormat::Pretty {
Some(ui::create_spinner("Deleting memory unit..."))
} else {
None
};
let response = client.delete_memory(&agent_id, &unit_id, verbose);
if let Some(sp) = spinner {
sp.finish_and_clear();
}
match response {
Ok(result) => {
if output_format == OutputFormat::Pretty {
if result.success {
ui::print_success(&result.message);
} else {
ui::print_error(&result.message);
}
} else {
output::print_output(&result, output_format)?;
}
Ok(())
}
Err(e) => Err(e)
}
}
};
// Handle API errors with nice messages

View file

@ -20,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "post",
"url": f"/api/agents/{agent_id}/background",
"url": f"/api/v1/agents/{agent_id}/background",
}
_kwargs["json"] = body.to_dict()

View file

@ -12,7 +12,7 @@ from ...types import Response
def _get_kwargs() -> dict[str, Any]:
_kwargs: dict[str, Any] = {
"method": "get",
"url": "/api/agents",
"url": "/api/v1/agents",
}
return _kwargs

View file

@ -20,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "put",
"url": f"/api/agents/{agent_id}",
"url": f"/api/v1/agents/{agent_id}",
}
_kwargs["json"] = body.to_dict()

View file

@ -15,7 +15,7 @@ def _get_kwargs(
) -> dict[str, Any]:
_kwargs: dict[str, Any] = {
"method": "get",
"url": f"/api/agents/{agent_id}/profile",
"url": f"/api/v1/agents/{agent_id}/profile",
}
return _kwargs

View file

@ -14,7 +14,7 @@ def _get_kwargs(
) -> dict[str, Any]:
_kwargs: dict[str, Any] = {
"method": "get",
"url": f"/api/stats/{agent_id}",
"url": f"/api/v1/agents/{agent_id}/stats",
}
return _kwargs

View file

@ -20,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "put",
"url": f"/api/agents/{agent_id}/profile",
"url": f"/api/v1/agents/{agent_id}/profile",
}
_kwargs["json"] = body.to_dict()

View file

@ -7,24 +7,16 @@ from ... import errors
from ...client import AuthenticatedClient, Client
from ...models.document_response import DocumentResponse
from ...models.http_validation_error import HTTPValidationError
from ...types import UNSET, Response
from ...types import Response
def _get_kwargs(
document_id: str,
*,
agent_id: str,
document_id: str,
) -> dict[str, Any]:
params: dict[str, Any] = {}
params["agent_id"] = agent_id
params = {k: v for k, v in params.items() if v is not UNSET and v is not None}
_kwargs: dict[str, Any] = {
"method": "get",
"url": f"/api/documents/{document_id}",
"params": params,
"url": f"/api/v1/agents/{agent_id}/documents/{document_id}",
}
return _kwargs
@ -61,18 +53,18 @@ def _build_response(
def sync_detailed(
agent_id: str,
document_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
) -> Response[DocumentResponse | HTTPValidationError]:
"""Get document details
Get a specific document including its original text
Args:
document_id (str):
agent_id (str):
document_id (str):
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -83,8 +75,8 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
document_id=document_id,
agent_id=agent_id,
document_id=document_id,
)
response = client.get_httpx_client().request(
@ -95,18 +87,18 @@ def sync_detailed(
def sync(
agent_id: str,
document_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
) -> DocumentResponse | HTTPValidationError | None:
"""Get document details
Get a specific document including its original text
Args:
document_id (str):
agent_id (str):
document_id (str):
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -117,25 +109,25 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
document_id=document_id,
client=client,
agent_id=agent_id,
).parsed
async def asyncio_detailed(
agent_id: str,
document_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
) -> Response[DocumentResponse | HTTPValidationError]:
"""Get document details
Get a specific document including its original text
Args:
document_id (str):
agent_id (str):
document_id (str):
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -146,8 +138,8 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
document_id=document_id,
agent_id=agent_id,
document_id=document_id,
)
response = await client.get_async_httpx_client().request(**kwargs)
@ -156,18 +148,18 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
document_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
) -> DocumentResponse | HTTPValidationError | None:
"""Get document details
Get a specific document including its original text
Args:
document_id (str):
agent_id (str):
document_id (str):
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -179,8 +171,8 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
document_id=document_id,
client=client,
agent_id=agent_id,
)
).parsed

View file

@ -11,16 +11,14 @@ from ...types import UNSET, Response, Unset
def _get_kwargs(
*,
agent_id: str,
*,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
offset: int | Unset = 0,
) -> dict[str, Any]:
params: dict[str, Any] = {}
params["agent_id"] = agent_id
json_q: None | str | Unset
if isinstance(q, Unset):
json_q = UNSET
@ -36,7 +34,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "get",
"url": "/api/documents",
"url": f"/api/v1/agents/{agent_id}/documents",
"params": params,
}
@ -74,9 +72,9 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
offset: int | Unset = 0,
@ -115,9 +113,9 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
offset: int | Unset = 0,
@ -142,8 +140,8 @@ def sync(
"""
return sync_detailed(
client=client,
agent_id=agent_id,
client=client,
q=q,
limit=limit,
offset=offset,
@ -151,9 +149,9 @@ def sync(
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
offset: int | Unset = 0,
@ -190,9 +188,9 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: str,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
offset: int | Unset = 0,
@ -218,8 +216,8 @@ async def asyncio(
return (
await asyncio_detailed(
client=client,
agent_id=agent_id,
client=client,
q=q,
limit=limit,
offset=offset,

View file

@ -12,6 +12,7 @@ from ...types import Response
def _get_kwargs(
agent_id: str,
*,
body: BatchPutRequest,
) -> dict[str, Any]:
@ -19,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "post",
"url": "/api/memories/batch",
"url": f"/api/v1/agents/{agent_id}/memories",
}
_kwargs["json"] = body.to_dict()
@ -61,6 +62,7 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -87,10 +89,10 @@ def sync_detailed(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -101,6 +103,7 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -112,6 +115,7 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -138,10 +142,10 @@ def sync(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -152,12 +156,14 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
client=client,
body=body,
).parsed
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -184,10 +190,10 @@ async def asyncio_detailed(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -198,6 +204,7 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -207,6 +214,7 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -233,10 +241,10 @@ async def asyncio(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -248,6 +256,7 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
client=client,
body=body,
)

View file

@ -12,6 +12,7 @@ from ...types import Response
def _get_kwargs(
agent_id: str,
*,
body: BatchPutRequest,
) -> dict[str, Any]:
@ -19,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "post",
"url": "/api/memories/batch_async",
"url": f"/api/v1/agents/{agent_id}/memories/async",
}
_kwargs["json"] = body.to_dict()
@ -61,6 +62,7 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -90,10 +92,10 @@ def sync_detailed(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -104,6 +106,7 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -115,6 +118,7 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -144,10 +148,10 @@ def sync(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -158,12 +162,14 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
client=client,
body=body,
).parsed
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -193,10 +199,10 @@ async def asyncio_detailed(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -207,6 +213,7 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -216,6 +223,7 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: BatchPutRequest,
@ -245,10 +253,10 @@ async def asyncio(
be deleted before creating new ones (upsert behavior).
Args:
body (BatchPutRequest): Request model for batch put endpoint. Example: {'agent_id':
'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at
Google', 'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date':
'2024-01-15T10:00:00Z'}]}.
agent_id (str):
body (BatchPutRequest): Request model for batch put endpoint. Example: {'document_id':
'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -260,6 +268,7 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
client=client,
body=body,
)

View file

@ -10,11 +10,12 @@ from ...types import Response
def _get_kwargs(
agent_id: str,
operation_id: str,
) -> dict[str, Any]:
_kwargs: dict[str, Any] = {
"method": "delete",
"url": f"/api/operations/{operation_id}",
"url": f"/api/v1/agents/{agent_id}/operations/{operation_id}",
}
return _kwargs
@ -50,6 +51,7 @@ def _build_response(
def sync_detailed(
agent_id: str,
operation_id: str,
*,
client: AuthenticatedClient | Client,
@ -59,6 +61,7 @@ def sync_detailed(
Cancel a pending async operation by removing it from the queue
Args:
agent_id (str):
operation_id (str):
Raises:
@ -70,6 +73,7 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
operation_id=operation_id,
)
@ -81,6 +85,7 @@ def sync_detailed(
def sync(
agent_id: str,
operation_id: str,
*,
client: AuthenticatedClient | Client,
@ -90,6 +95,7 @@ def sync(
Cancel a pending async operation by removing it from the queue
Args:
agent_id (str):
operation_id (str):
Raises:
@ -101,12 +107,14 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
operation_id=operation_id,
client=client,
).parsed
async def asyncio_detailed(
agent_id: str,
operation_id: str,
*,
client: AuthenticatedClient | Client,
@ -116,6 +124,7 @@ async def asyncio_detailed(
Cancel a pending async operation by removing it from the queue
Args:
agent_id (str):
operation_id (str):
Raises:
@ -127,6 +136,7 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
operation_id=operation_id,
)
@ -136,6 +146,7 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
operation_id: str,
*,
client: AuthenticatedClient | Client,
@ -145,6 +156,7 @@ async def asyncio(
Cancel a pending async operation by removing it from the queue
Args:
agent_id (str):
operation_id (str):
Raises:
@ -157,6 +169,7 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
operation_id=operation_id,
client=client,
)

View file

@ -10,11 +10,12 @@ from ...types import Response
def _get_kwargs(
agent_id: str,
unit_id: str,
) -> dict[str, Any]:
_kwargs: dict[str, Any] = {
"method": "delete",
"url": f"/api/memory/{unit_id}",
"url": f"/api/v1/agents/{agent_id}/memories/{unit_id}",
}
return _kwargs
@ -50,6 +51,7 @@ def _build_response(
def sync_detailed(
agent_id: str,
unit_id: str,
*,
client: AuthenticatedClient | Client,
@ -59,6 +61,7 @@ def sync_detailed(
Delete a single memory unit and all its associated links (temporal, semantic, and entity links)
Args:
agent_id (str):
unit_id (str):
Raises:
@ -70,6 +73,7 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
unit_id=unit_id,
)
@ -81,6 +85,7 @@ def sync_detailed(
def sync(
agent_id: str,
unit_id: str,
*,
client: AuthenticatedClient | Client,
@ -90,6 +95,7 @@ def sync(
Delete a single memory unit and all its associated links (temporal, semantic, and entity links)
Args:
agent_id (str):
unit_id (str):
Raises:
@ -101,12 +107,14 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
unit_id=unit_id,
client=client,
).parsed
async def asyncio_detailed(
agent_id: str,
unit_id: str,
*,
client: AuthenticatedClient | Client,
@ -116,6 +124,7 @@ async def asyncio_detailed(
Delete a single memory unit and all its associated links (temporal, semantic, and entity links)
Args:
agent_id (str):
unit_id (str):
Raises:
@ -127,6 +136,7 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
unit_id=unit_id,
)
@ -136,6 +146,7 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
unit_id: str,
*,
client: AuthenticatedClient | Client,
@ -145,6 +156,7 @@ async def asyncio(
Delete a single memory unit and all its associated links (temporal, semantic, and entity links)
Args:
agent_id (str):
unit_id (str):
Raises:
@ -157,6 +169,7 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
unit_id=unit_id,
client=client,
)

View file

@ -11,8 +11,8 @@ from ...types import UNSET, Response, Unset
def _get_kwargs(
agent_id: str,
*,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
@ -20,13 +20,6 @@ def _get_kwargs(
) -> dict[str, Any]:
params: dict[str, Any] = {}
json_agent_id: None | str | Unset
if isinstance(agent_id, Unset):
json_agent_id = UNSET
else:
json_agent_id = agent_id
params["agent_id"] = json_agent_id
json_fact_type: None | str | Unset
if isinstance(fact_type, Unset):
json_fact_type = UNSET
@ -49,7 +42,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "get",
"url": "/api/list",
"url": f"/api/v1/agents/{agent_id}/memories/list",
"params": params,
}
@ -87,9 +80,9 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
@ -97,11 +90,10 @@ def sync_detailed(
) -> Response[HTTPValidationError | ListMemoryUnitsResponse]:
"""List memory units
List memory units with pagination and optional full-text search. Supports filtering by agent_id and
fact_type.
List memory units with pagination and optional full-text search. Supports filtering by fact_type.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
q (None | str | Unset):
limit (int | Unset): Default: 100.
@ -131,9 +123,9 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
@ -141,11 +133,10 @@ def sync(
) -> HTTPValidationError | ListMemoryUnitsResponse | None:
"""List memory units
List memory units with pagination and optional full-text search. Supports filtering by agent_id and
fact_type.
List memory units with pagination and optional full-text search. Supports filtering by fact_type.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
q (None | str | Unset):
limit (int | Unset): Default: 100.
@ -160,8 +151,8 @@ def sync(
"""
return sync_detailed(
client=client,
agent_id=agent_id,
client=client,
fact_type=fact_type,
q=q,
limit=limit,
@ -170,9 +161,9 @@ def sync(
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
@ -180,11 +171,10 @@ async def asyncio_detailed(
) -> Response[HTTPValidationError | ListMemoryUnitsResponse]:
"""List memory units
List memory units with pagination and optional full-text search. Supports filtering by agent_id and
fact_type.
List memory units with pagination and optional full-text search. Supports filtering by fact_type.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
q (None | str | Unset):
limit (int | Unset): Default: 100.
@ -212,9 +202,9 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
q: None | str | Unset = UNSET,
limit: int | Unset = 100,
@ -222,11 +212,10 @@ async def asyncio(
) -> HTTPValidationError | ListMemoryUnitsResponse | None:
"""List memory units
List memory units with pagination and optional full-text search. Supports filtering by agent_id and
fact_type.
List memory units with pagination and optional full-text search. Supports filtering by fact_type.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
q (None | str | Unset):
limit (int | Unset): Default: 100.
@ -242,8 +231,8 @@ async def asyncio(
return (
await asyncio_detailed(
client=client,
agent_id=agent_id,
client=client,
fact_type=fact_type,
q=q,
limit=limit,

View file

@ -14,7 +14,7 @@ def _get_kwargs(
) -> dict[str, Any]:
_kwargs: dict[str, Any] = {
"method": "get",
"url": f"/api/operations/{agent_id}",
"url": f"/api/v1/agents/{agent_id}/operations",
}
return _kwargs

View file

@ -12,6 +12,7 @@ from ...types import Response
def _get_kwargs(
agent_id: str,
*,
body: SearchRequest,
) -> dict[str, Any]:
@ -19,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "post",
"url": "/api/search",
"url": f"/api/v1/agents/{agent_id}/memories/search",
}
_kwargs["json"] = body.to_dict()
@ -61,6 +62,7 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: SearchRequest,
@ -69,16 +71,17 @@ def sync_detailed(
Search memory using semantic similarity and spreading activation.
The fact_type parameter is required and must be one of:
The fact_type parameter is optional and must be one of:
- 'world': General knowledge about people, places, events, and things that happen
- 'agent': Memories about what the AI agent did, actions taken, and tasks performed
- 'opinion': The agent's formed beliefs, perspectives, and viewpoints
Args:
body (SearchRequest): Request model for search endpoint. Example: {'agent_id': 'user123',
'fact_type': ['world', 'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about
machine learning?', 'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic',
'thinking_budget': 100, 'trace': True}.
agent_id (str):
body (SearchRequest): Request model for search endpoint. Example: {'fact_type': ['world',
'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about machine learning?',
'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic', 'thinking_budget': 100,
'trace': True}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -89,6 +92,7 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -100,6 +104,7 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: SearchRequest,
@ -108,16 +113,17 @@ def sync(
Search memory using semantic similarity and spreading activation.
The fact_type parameter is required and must be one of:
The fact_type parameter is optional and must be one of:
- 'world': General knowledge about people, places, events, and things that happen
- 'agent': Memories about what the AI agent did, actions taken, and tasks performed
- 'opinion': The agent's formed beliefs, perspectives, and viewpoints
Args:
body (SearchRequest): Request model for search endpoint. Example: {'agent_id': 'user123',
'fact_type': ['world', 'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about
machine learning?', 'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic',
'thinking_budget': 100, 'trace': True}.
agent_id (str):
body (SearchRequest): Request model for search endpoint. Example: {'fact_type': ['world',
'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about machine learning?',
'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic', 'thinking_budget': 100,
'trace': True}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -128,12 +134,14 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
client=client,
body=body,
).parsed
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: SearchRequest,
@ -142,16 +150,17 @@ async def asyncio_detailed(
Search memory using semantic similarity and spreading activation.
The fact_type parameter is required and must be one of:
The fact_type parameter is optional and must be one of:
- 'world': General knowledge about people, places, events, and things that happen
- 'agent': Memories about what the AI agent did, actions taken, and tasks performed
- 'opinion': The agent's formed beliefs, perspectives, and viewpoints
Args:
body (SearchRequest): Request model for search endpoint. Example: {'agent_id': 'user123',
'fact_type': ['world', 'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about
machine learning?', 'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic',
'thinking_budget': 100, 'trace': True}.
agent_id (str):
body (SearchRequest): Request model for search endpoint. Example: {'fact_type': ['world',
'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about machine learning?',
'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic', 'thinking_budget': 100,
'trace': True}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -162,6 +171,7 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -171,6 +181,7 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: SearchRequest,
@ -179,16 +190,17 @@ async def asyncio(
Search memory using semantic similarity and spreading activation.
The fact_type parameter is required and must be one of:
The fact_type parameter is optional and must be one of:
- 'world': General knowledge about people, places, events, and things that happen
- 'agent': Memories about what the AI agent did, actions taken, and tasks performed
- 'opinion': The agent's formed beliefs, perspectives, and viewpoints
Args:
body (SearchRequest): Request model for search endpoint. Example: {'agent_id': 'user123',
'fact_type': ['world', 'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about
machine learning?', 'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic',
'thinking_budget': 100, 'trace': True}.
agent_id (str):
body (SearchRequest): Request model for search endpoint. Example: {'fact_type': ['world',
'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about machine learning?',
'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic', 'thinking_budget': 100,
'trace': True}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -200,6 +212,7 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
client=client,
body=body,
)

View file

@ -1 +0,0 @@
"""Contains endpoint functions for accessing the API"""

View file

@ -12,6 +12,7 @@ from ...types import Response
def _get_kwargs(
agent_id: str,
*,
body: ThinkRequest,
) -> dict[str, Any]:
@ -19,7 +20,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "post",
"url": "/api/think",
"url": f"/api/v1/agents/{agent_id}/think",
}
_kwargs["json"] = body.to_dict()
@ -61,6 +62,7 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: ThinkRequest,
@ -78,9 +80,10 @@ def sync_detailed(
6. Returns plain text answer, the facts used, and new opinions
Args:
body (ThinkRequest): Request model for think endpoint. Example: {'agent_id': 'user123',
'context': 'This is for a research paper on AI ethics', 'query': 'What do you think about
artificial intelligence?', 'thinking_budget': 50}.
agent_id (str):
body (ThinkRequest): Request model for think endpoint. Example: {'context': 'This is for a
research paper on AI ethics', 'query': 'What do you think about artificial intelligence?',
'thinking_budget': 50}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -91,6 +94,7 @@ def sync_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -102,6 +106,7 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: ThinkRequest,
@ -119,9 +124,10 @@ def sync(
6. Returns plain text answer, the facts used, and new opinions
Args:
body (ThinkRequest): Request model for think endpoint. Example: {'agent_id': 'user123',
'context': 'This is for a research paper on AI ethics', 'query': 'What do you think about
artificial intelligence?', 'thinking_budget': 50}.
agent_id (str):
body (ThinkRequest): Request model for think endpoint. Example: {'context': 'This is for a
research paper on AI ethics', 'query': 'What do you think about artificial intelligence?',
'thinking_budget': 50}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -132,12 +138,14 @@ def sync(
"""
return sync_detailed(
agent_id=agent_id,
client=client,
body=body,
).parsed
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: ThinkRequest,
@ -155,9 +163,10 @@ async def asyncio_detailed(
6. Returns plain text answer, the facts used, and new opinions
Args:
body (ThinkRequest): Request model for think endpoint. Example: {'agent_id': 'user123',
'context': 'This is for a research paper on AI ethics', 'query': 'What do you think about
artificial intelligence?', 'thinking_budget': 50}.
agent_id (str):
body (ThinkRequest): Request model for think endpoint. Example: {'context': 'This is for a
research paper on AI ethics', 'query': 'What do you think about artificial intelligence?',
'thinking_budget': 50}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -168,6 +177,7 @@ async def asyncio_detailed(
"""
kwargs = _get_kwargs(
agent_id=agent_id,
body=body,
)
@ -177,6 +187,7 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
body: ThinkRequest,
@ -194,9 +205,10 @@ async def asyncio(
6. Returns plain text answer, the facts used, and new opinions
Args:
body (ThinkRequest): Request model for think endpoint. Example: {'agent_id': 'user123',
'context': 'This is for a research paper on AI ethics', 'query': 'What do you think about
artificial intelligence?', 'thinking_budget': 50}.
agent_id (str):
body (ThinkRequest): Request model for think endpoint. Example: {'context': 'This is for a
research paper on AI ethics', 'query': 'What do you think about artificial intelligence?',
'thinking_budget': 50}.
Raises:
errors.UnexpectedStatus: If the server returns an undocumented status code and Client.raise_on_unexpected_status is True.
@ -208,6 +220,7 @@ async def asyncio(
return (
await asyncio_detailed(
agent_id=agent_id,
client=client,
body=body,
)

View file

@ -1 +0,0 @@
"""Contains endpoint functions for accessing the API"""

View file

@ -11,19 +11,12 @@ from ...types import UNSET, Response, Unset
def _get_kwargs(
agent_id: str,
*,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
) -> dict[str, Any]:
params: dict[str, Any] = {}
json_agent_id: None | str | Unset
if isinstance(agent_id, Unset):
json_agent_id = UNSET
else:
json_agent_id = agent_id
params["agent_id"] = json_agent_id
json_fact_type: None | str | Unset
if isinstance(fact_type, Unset):
json_fact_type = UNSET
@ -35,7 +28,7 @@ def _get_kwargs(
_kwargs: dict[str, Any] = {
"method": "get",
"url": "/api/graph",
"url": f"/api/v1/agents/{agent_id}/graph",
"params": params,
}
@ -73,18 +66,18 @@ def _build_response(
def sync_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
) -> Response[GraphDataResponse | HTTPValidationError]:
"""Get memory graph data
Retrieve graph data for visualization, optionally filtered by agent_id and fact_type
(world/agent/opinion). Limited to 1000 most recent items.
Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion).
Limited to 1000 most recent items.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
Raises:
@ -108,18 +101,18 @@ def sync_detailed(
def sync(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
) -> GraphDataResponse | HTTPValidationError | None:
"""Get memory graph data
Retrieve graph data for visualization, optionally filtered by agent_id and fact_type
(world/agent/opinion). Limited to 1000 most recent items.
Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion).
Limited to 1000 most recent items.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
Raises:
@ -131,25 +124,25 @@ def sync(
"""
return sync_detailed(
client=client,
agent_id=agent_id,
client=client,
fact_type=fact_type,
).parsed
async def asyncio_detailed(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
) -> Response[GraphDataResponse | HTTPValidationError]:
"""Get memory graph data
Retrieve graph data for visualization, optionally filtered by agent_id and fact_type
(world/agent/opinion). Limited to 1000 most recent items.
Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion).
Limited to 1000 most recent items.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
Raises:
@ -171,18 +164,18 @@ async def asyncio_detailed(
async def asyncio(
agent_id: str,
*,
client: AuthenticatedClient | Client,
agent_id: None | str | Unset = UNSET,
fact_type: None | str | Unset = UNSET,
) -> GraphDataResponse | HTTPValidationError | None:
"""Get memory graph data
Retrieve graph data for visualization, optionally filtered by agent_id and fact_type
(world/agent/opinion). Limited to 1000 most recent items.
Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion).
Limited to 1000 most recent items.
Args:
agent_id (None | str | Unset):
agent_id (str):
fact_type (None | str | Unset):
Raises:
@ -195,8 +188,8 @@ async def asyncio(
return (
await asyncio_detailed(
client=client,
agent_id=agent_id,
client=client,
fact_type=fact_type,
)
).parsed

View file

@ -4,7 +4,6 @@ from .add_background_request import AddBackgroundRequest
from .agent_list_item import AgentListItem
from .agent_list_response import AgentListResponse
from .agent_profile_response import AgentProfileResponse
from .agents_response import AgentsResponse
from .background_response import BackgroundResponse
from .batch_put_async_response import BatchPutAsyncResponse
from .batch_put_request import BatchPutRequest
@ -37,7 +36,6 @@ __all__ = (
"AgentListItem",
"AgentListResponse",
"AgentProfileResponse",
"AgentsResponse",
"BackgroundResponse",
"BatchPutAsyncResponse",
"BatchPutRequest",

View file

@ -1,65 +0,0 @@
from __future__ import annotations
from collections.abc import Mapping
from typing import Any, TypeVar, cast
from attrs import define as _attrs_define
from attrs import field as _attrs_field
T = TypeVar("T", bound="AgentsResponse")
@_attrs_define
class AgentsResponse:
"""Response model for agents list endpoint.
Example:
{'agents': ['user123', 'agent_alice', 'agent_bob']}
Attributes:
agents (list[str]):
"""
agents: list[str]
additional_properties: dict[str, Any] = _attrs_field(init=False, factory=dict)
def to_dict(self) -> dict[str, Any]:
agents = self.agents
field_dict: dict[str, Any] = {}
field_dict.update(self.additional_properties)
field_dict.update(
{
"agents": agents,
}
)
return field_dict
@classmethod
def from_dict(cls: type[T], src_dict: Mapping[str, Any]) -> T:
d = dict(src_dict)
agents = cast(list[str], d.pop("agents"))
agents_response = cls(
agents=agents,
)
agents_response.additional_properties = d
return agents_response
@property
def additional_keys(self) -> list[str]:
return list(self.additional_properties.keys())
def __getitem__(self, key: str) -> Any:
return self.additional_properties[key]
def __setitem__(self, key: str, value: Any) -> None:
self.additional_properties[key] = value
def __delitem__(self, key: str) -> None:
del self.additional_properties[key]
def __contains__(self, key: str) -> bool:
return key in self.additional_properties

View file

@ -20,23 +20,19 @@ class BatchPutRequest:
"""Request model for batch put endpoint.
Example:
{'agent_id': 'user123', 'document_id': 'conversation_123', 'items': [{'content': 'Alice works at Google',
'context': 'work'}, {'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}
{'document_id': 'conversation_123', 'items': [{'content': 'Alice works at Google', 'context': 'work'},
{'content': 'Bob went hiking yesterday', 'event_date': '2024-01-15T10:00:00Z'}]}
Attributes:
agent_id (str):
items (list[MemoryItem]):
document_id (None | str | Unset):
"""
agent_id: str
items: list[MemoryItem]
document_id: None | str | Unset = UNSET
additional_properties: dict[str, Any] = _attrs_field(init=False, factory=dict)
def to_dict(self) -> dict[str, Any]:
agent_id = self.agent_id
items = []
for items_item_data in self.items:
items_item = items_item_data.to_dict()
@ -52,7 +48,6 @@ class BatchPutRequest:
field_dict.update(self.additional_properties)
field_dict.update(
{
"agent_id": agent_id,
"items": items,
}
)
@ -66,8 +61,6 @@ class BatchPutRequest:
from ..models.memory_item import MemoryItem
d = dict(src_dict)
agent_id = d.pop("agent_id")
items = []
_items = d.pop("items")
for items_item_data in _items:
@ -85,7 +78,6 @@ class BatchPutRequest:
document_id = _parse_document_id(d.pop("document_id", UNSET))
batch_put_request = cls(
agent_id=agent_id,
items=items,
document_id=document_id,
)

View file

@ -16,14 +16,12 @@ class SearchRequest:
"""Request model for search endpoint.
Example:
{'agent_id': 'user123', 'fact_type': ['world', 'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about
machine learning?', 'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic', 'thinking_budget': 100,
'trace': True}
{'fact_type': ['world', 'agent'], 'max_tokens': 4096, 'query': 'What did Alice say about machine learning?',
'question_date': '2023-05-30T23:40:00', 'reranker': 'heuristic', 'thinking_budget': 100, 'trace': True}
Attributes:
query (str):
fact_type (list[str] | None | Unset):
agent_id (str | Unset): Default: 'default'.
thinking_budget (int | Unset): Default: 100.
max_tokens (int | Unset): Default: 4096.
reranker (str | Unset): Default: 'heuristic'.
@ -33,7 +31,6 @@ class SearchRequest:
query: str
fact_type: list[str] | None | Unset = UNSET
agent_id: str | Unset = "default"
thinking_budget: int | Unset = 100
max_tokens: int | Unset = 4096
reranker: str | Unset = "heuristic"
@ -53,8 +50,6 @@ class SearchRequest:
else:
fact_type = self.fact_type
agent_id = self.agent_id
thinking_budget = self.thinking_budget
max_tokens = self.max_tokens
@ -78,8 +73,6 @@ class SearchRequest:
)
if fact_type is not UNSET:
field_dict["fact_type"] = fact_type
if agent_id is not UNSET:
field_dict["agent_id"] = agent_id
if thinking_budget is not UNSET:
field_dict["thinking_budget"] = thinking_budget
if max_tokens is not UNSET:
@ -115,8 +108,6 @@ class SearchRequest:
fact_type = _parse_fact_type(d.pop("fact_type", UNSET))
agent_id = d.pop("agent_id", UNSET)
thinking_budget = d.pop("thinking_budget", UNSET)
max_tokens = d.pop("max_tokens", UNSET)
@ -137,7 +128,6 @@ class SearchRequest:
search_request = cls(
query=query,
fact_type=fact_type,
agent_id=agent_id,
thinking_budget=thinking_budget,
max_tokens=max_tokens,
reranker=reranker,

View file

@ -16,18 +16,16 @@ class ThinkRequest:
"""Request model for think endpoint.
Example:
{'agent_id': 'user123', 'context': 'This is for a research paper on AI ethics', 'query': 'What do you think
about artificial intelligence?', 'thinking_budget': 50}
{'context': 'This is for a research paper on AI ethics', 'query': 'What do you think about artificial
intelligence?', 'thinking_budget': 50}
Attributes:
query (str):
agent_id (str | Unset): Default: 'default'.
thinking_budget (int | Unset): Default: 50.
context (None | str | Unset):
"""
query: str
agent_id: str | Unset = "default"
thinking_budget: int | Unset = 50
context: None | str | Unset = UNSET
additional_properties: dict[str, Any] = _attrs_field(init=False, factory=dict)
@ -35,8 +33,6 @@ class ThinkRequest:
def to_dict(self) -> dict[str, Any]:
query = self.query
agent_id = self.agent_id
thinking_budget = self.thinking_budget
context: None | str | Unset
@ -52,8 +48,6 @@ class ThinkRequest:
"query": query,
}
)
if agent_id is not UNSET:
field_dict["agent_id"] = agent_id
if thinking_budget is not UNSET:
field_dict["thinking_budget"] = thinking_budget
if context is not UNSET:
@ -66,8 +60,6 @@ class ThinkRequest:
d = dict(src_dict)
query = d.pop("query")
agent_id = d.pop("agent_id", UNSET)
thinking_budget = d.pop("thinking_budget", UNSET)
def _parse_context(data: object) -> None | str | Unset:
@ -81,7 +73,6 @@ class ThinkRequest:
think_request = cls(
query=query,
agent_id=agent_id,
thinking_budget=thinking_budget,
context=context,
)

View file

@ -11,7 +11,6 @@ export type { AddBackgroundRequest } from './models/AddBackgroundRequest';
export type { AgentListItem } from './models/AgentListItem';
export type { AgentListResponse } from './models/AgentListResponse';
export type { AgentProfileResponse } from './models/AgentProfileResponse';
export type { AgentsResponse } from './models/AgentsResponse';
export type { BackgroundResponse } from './models/BackgroundResponse';
export type { BatchPutAsyncResponse } from './models/BatchPutAsyncResponse';
export type { BatchPutRequest } from './models/BatchPutRequest';
@ -33,10 +32,8 @@ export type { ThinkResponse } from './models/ThinkResponse';
export type { UpdatePersonalityRequest } from './models/UpdatePersonalityRequest';
export type { ValidationError } from './models/ValidationError';
export { AgentProfileService } from './services/AgentProfileService';
export { AgentManagementService } from './services/AgentManagementService';
export { DocumentsService } from './services/DocumentsService';
export { MemoryStatisticsService } from './services/MemoryStatisticsService';
export { MemoryStorageService } from './services/MemoryStorageService';
export { MemoryOperationsService } from './services/MemoryOperationsService';
export { ReasoningService } from './services/ReasoningService';
export { SearchService } from './services/SearchService';
export { VisualizationService } from './services/VisualizationService';

View file

@ -1,11 +0,0 @@
/* generated using openapi-typescript-codegen -- do not edit */
/* istanbul ignore file */
/* tslint:disable */
/* eslint-disable */
/**
* Response model for agents list endpoint.
*/
export type AgentsResponse = {
agents: Array<string>;
};

View file

@ -7,7 +7,6 @@ import type { MemoryItem } from './MemoryItem';
* Request model for batch put endpoint.
*/
export type BatchPutRequest = {
agent_id: string;
items: Array<MemoryItem>;
document_id?: (string | null);
};

View file

@ -8,7 +8,6 @@
export type SearchRequest = {
query: string;
fact_type?: (Array<string> | null);
agent_id?: string;
thinking_budget?: number;
max_tokens?: number;
reranker?: string;

View file

@ -7,7 +7,6 @@
*/
export type ThinkRequest = {
query: string;
agent_id?: string;
thinking_budget?: number;
context?: (string | null);
};

View file

@ -11,17 +11,39 @@ import type { UpdatePersonalityRequest } from '../models/UpdatePersonalityReques
import type { CancelablePromise } from '../core/CancelablePromise';
import { OpenAPI } from '../core/OpenAPI';
import { request as __request } from '../core/request';
export class AgentProfileService {
export class AgentManagementService {
/**
* List all agents
* Get a list of all agents with their profiles
* @returns AgentListResponse Successful Response
* @throws ApiError
*/
public static apiListAgentsApiAgentsGet(): CancelablePromise<AgentListResponse> {
public static apiAgentsApiV1AgentsGet(): CancelablePromise<AgentListResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/agents',
url: '/api/v1/agents',
});
}
/**
* Get memory statistics for an agent
* Get statistics about nodes and links for a specific agent
* @returns any Successful Response
* @throws ApiError
*/
public static apiStatsApiV1AgentsAgentIdStatsGet({
agentId,
}: {
agentId: string,
}): CancelablePromise<any> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/v1/agents/{agent_id}/stats',
path: {
'agent_id': agentId,
},
errors: {
422: `Validation Error`,
},
});
}
/**
@ -30,14 +52,14 @@ export class AgentProfileService {
* @returns AgentProfileResponse Successful Response
* @throws ApiError
*/
public static apiGetAgentProfileApiAgentsAgentIdProfileGet({
public static apiGetAgentProfileApiV1AgentsAgentIdProfileGet({
agentId,
}: {
agentId: string,
}): CancelablePromise<AgentProfileResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/agents/{agent_id}/profile',
url: '/api/v1/agents/{agent_id}/profile',
path: {
'agent_id': agentId,
},
@ -52,7 +74,7 @@ export class AgentProfileService {
* @returns AgentProfileResponse Successful Response
* @throws ApiError
*/
public static apiUpdateAgentPersonalityApiAgentsAgentIdProfilePut({
public static apiUpdateAgentPersonalityApiV1AgentsAgentIdProfilePut({
agentId,
requestBody,
}: {
@ -61,7 +83,7 @@ export class AgentProfileService {
}): CancelablePromise<AgentProfileResponse> {
return __request(OpenAPI, {
method: 'PUT',
url: '/api/agents/{agent_id}/profile',
url: '/api/v1/agents/{agent_id}/profile',
path: {
'agent_id': agentId,
},
@ -78,7 +100,7 @@ export class AgentProfileService {
* @returns BackgroundResponse Successful Response
* @throws ApiError
*/
public static apiAddAgentBackgroundApiAgentsAgentIdBackgroundPost({
public static apiAddAgentBackgroundApiV1AgentsAgentIdBackgroundPost({
agentId,
requestBody,
}: {
@ -87,7 +109,7 @@ export class AgentProfileService {
}): CancelablePromise<BackgroundResponse> {
return __request(OpenAPI, {
method: 'POST',
url: '/api/agents/{agent_id}/background',
url: '/api/v1/agents/{agent_id}/background',
path: {
'agent_id': agentId,
},
@ -104,7 +126,7 @@ export class AgentProfileService {
* @returns AgentProfileResponse Successful Response
* @throws ApiError
*/
public static apiCreateOrUpdateAgentApiAgentsAgentIdPut({
public static apiCreateOrUpdateAgentApiV1AgentsAgentIdPut({
agentId,
requestBody,
}: {
@ -113,7 +135,7 @@ export class AgentProfileService {
}): CancelablePromise<AgentProfileResponse> {
return __request(OpenAPI, {
method: 'PUT',
url: '/api/agents/{agent_id}',
url: '/api/v1/agents/{agent_id}',
path: {
'agent_id': agentId,
},

View file

@ -14,7 +14,7 @@ export class DocumentsService {
* @returns ListDocumentsResponse Successful Response
* @throws ApiError
*/
public static apiListDocumentsApiDocumentsGet({
public static apiListDocumentsApiV1AgentsAgentIdDocumentsGet({
agentId,
q,
limit = 100,
@ -27,9 +27,11 @@ export class DocumentsService {
}): CancelablePromise<ListDocumentsResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/documents',
query: {
url: '/api/v1/agents/{agent_id}/documents',
path: {
'agent_id': agentId,
},
query: {
'q': q,
'limit': limit,
'offset': offset,
@ -45,21 +47,19 @@ export class DocumentsService {
* @returns DocumentResponse Successful Response
* @throws ApiError
*/
public static apiGetDocumentApiDocumentsDocumentIdGet({
documentId,
public static apiGetDocumentApiV1AgentsAgentIdDocumentsDocumentIdGet({
agentId,
documentId,
}: {
documentId: string,
agentId: string,
documentId: string,
}): CancelablePromise<DocumentResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/documents/{document_id}',
url: '/api/v1/agents/{agent_id}/documents/{document_id}',
path: {
'document_id': documentId,
},
query: {
'agent_id': agentId,
'document_id': documentId,
},
errors: {
422: `Validation Error`,

View file

@ -5,10 +5,80 @@
import type { BatchPutAsyncResponse } from '../models/BatchPutAsyncResponse';
import type { BatchPutRequest } from '../models/BatchPutRequest';
import type { BatchPutResponse } from '../models/BatchPutResponse';
import type { ListMemoryUnitsResponse } from '../models/ListMemoryUnitsResponse';
import type { SearchRequest } from '../models/SearchRequest';
import type { SearchResponse } from '../models/SearchResponse';
import type { CancelablePromise } from '../core/CancelablePromise';
import { OpenAPI } from '../core/OpenAPI';
import { request as __request } from '../core/request';
export class MemoryStorageService {
export class MemoryOperationsService {
/**
* List memory units
* List memory units with pagination and optional full-text search. Supports filtering by fact_type.
* @returns ListMemoryUnitsResponse Successful Response
* @throws ApiError
*/
public static apiListApiV1AgentsAgentIdMemoriesListGet({
agentId,
factType,
q,
limit = 100,
offset,
}: {
agentId: string,
factType?: (string | null),
q?: (string | null),
limit?: number,
offset?: number,
}): CancelablePromise<ListMemoryUnitsResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/v1/agents/{agent_id}/memories/list',
path: {
'agent_id': agentId,
},
query: {
'fact_type': factType,
'q': q,
'limit': limit,
'offset': offset,
},
errors: {
422: `Validation Error`,
},
});
}
/**
* Search memory
* Search memory using semantic similarity and spreading activation.
*
* The fact_type parameter is optional and must be one of:
* - 'world': General knowledge about people, places, events, and things that happen
* - 'agent': Memories about what the AI agent did, actions taken, and tasks performed
* - 'opinion': The agent's formed beliefs, perspectives, and viewpoints
* @returns SearchResponse Successful Response
* @throws ApiError
*/
public static apiSearchApiV1AgentsAgentIdMemoriesSearchPost({
agentId,
requestBody,
}: {
agentId: string,
requestBody: SearchRequest,
}): CancelablePromise<SearchResponse> {
return __request(OpenAPI, {
method: 'POST',
url: '/api/v1/agents/{agent_id}/memories/search',
path: {
'agent_id': agentId,
},
body: requestBody,
mediaType: 'application/json',
errors: {
422: `Validation Error`,
},
});
}
/**
* Store multiple memories
* Store multiple memory items in batch with automatic fact extraction.
@ -31,14 +101,19 @@ export class MemoryStorageService {
* @returns BatchPutResponse Successful Response
* @throws ApiError
*/
public static apiBatchPutApiMemoriesBatchPost({
public static apiBatchPutApiV1AgentsAgentIdMemoriesPost({
agentId,
requestBody,
}: {
agentId: string,
requestBody: BatchPutRequest,
}): CancelablePromise<BatchPutResponse> {
return __request(OpenAPI, {
method: 'POST',
url: '/api/memories/batch',
url: '/api/v1/agents/{agent_id}/memories',
path: {
'agent_id': agentId,
},
body: requestBody,
mediaType: 'application/json',
errors: {
@ -71,14 +146,19 @@ export class MemoryStorageService {
* @returns BatchPutAsyncResponse Successful Response
* @throws ApiError
*/
public static apiBatchPutAsyncApiMemoriesBatchAsyncPost({
public static apiBatchPutAsyncApiV1AgentsAgentIdMemoriesAsyncPost({
agentId,
requestBody,
}: {
agentId: string,
requestBody: BatchPutRequest,
}): CancelablePromise<BatchPutAsyncResponse> {
return __request(OpenAPI, {
method: 'POST',
url: '/api/memories/batch_async',
url: '/api/v1/agents/{agent_id}/memories/async',
path: {
'agent_id': agentId,
},
body: requestBody,
mediaType: 'application/json',
errors: {
@ -92,14 +172,14 @@ export class MemoryStorageService {
* @returns any Successful Response
* @throws ApiError
*/
public static apiListOperationsApiOperationsAgentIdGet({
public static apiListOperationsApiV1AgentsAgentIdOperationsGet({
agentId,
}: {
agentId: string,
}): CancelablePromise<any> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/operations/{agent_id}',
url: '/api/v1/agents/{agent_id}/operations',
path: {
'agent_id': agentId,
},
@ -114,15 +194,18 @@ export class MemoryStorageService {
* @returns any Successful Response
* @throws ApiError
*/
public static apiCancelOperationApiOperationsOperationIdDelete({
public static apiCancelOperationApiV1AgentsAgentIdOperationsOperationIdDelete({
agentId,
operationId,
}: {
agentId: string,
operationId: string,
}): CancelablePromise<any> {
return __request(OpenAPI, {
method: 'DELETE',
url: '/api/operations/{operation_id}',
url: '/api/v1/agents/{agent_id}/operations/{operation_id}',
path: {
'agent_id': agentId,
'operation_id': operationId,
},
errors: {
@ -136,15 +219,18 @@ export class MemoryStorageService {
* @returns any Successful Response
* @throws ApiError
*/
public static apiDeleteMemoryUnitApiMemoryUnitIdDelete({
public static apiDeleteMemoryUnitApiV1AgentsAgentIdMemoriesUnitIdDelete({
agentId,
unitId,
}: {
agentId: string,
unitId: string,
}): CancelablePromise<any> {
return __request(OpenAPI, {
method: 'DELETE',
url: '/api/memory/{unit_id}',
url: '/api/v1/agents/{agent_id}/memories/{unit_id}',
path: {
'agent_id': agentId,
'unit_id': unitId,
},
errors: {

View file

@ -1,31 +0,0 @@
/* generated using openapi-typescript-codegen -- do not edit */
/* istanbul ignore file */
/* tslint:disable */
/* eslint-disable */
import type { CancelablePromise } from '../core/CancelablePromise';
import { OpenAPI } from '../core/OpenAPI';
import { request as __request } from '../core/request';
export class MemoryStatisticsService {
/**
* Get memory statistics for an agent
* Get statistics about nodes and links for a specific agent
* @returns any Successful Response
* @throws ApiError
*/
public static apiStatsApiStatsAgentIdGet({
agentId,
}: {
agentId: string,
}): CancelablePromise<any> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/stats/{agent_id}',
path: {
'agent_id': agentId,
},
errors: {
422: `Validation Error`,
},
});
}
}

View file

@ -22,14 +22,19 @@ export class ReasoningService {
* @returns ThinkResponse Successful Response
* @throws ApiError
*/
public static apiThinkApiThinkPost({
public static apiThinkApiV1AgentsAgentIdThinkPost({
agentId,
requestBody,
}: {
agentId: string,
requestBody: ThinkRequest,
}): CancelablePromise<ThinkResponse> {
return __request(OpenAPI, {
method: 'POST',
url: '/api/think',
url: '/api/v1/agents/{agent_id}/think',
path: {
'agent_id': agentId,
},
body: requestBody,
mediaType: 'application/json',
errors: {

View file

@ -1,37 +0,0 @@
/* generated using openapi-typescript-codegen -- do not edit */
/* istanbul ignore file */
/* tslint:disable */
/* eslint-disable */
import type { SearchRequest } from '../models/SearchRequest';
import type { SearchResponse } from '../models/SearchResponse';
import type { CancelablePromise } from '../core/CancelablePromise';
import { OpenAPI } from '../core/OpenAPI';
import { request as __request } from '../core/request';
export class SearchService {
/**
* Search memory
* Search memory using semantic similarity and spreading activation.
*
* The fact_type parameter is required and must be one of:
* - 'world': General knowledge about people, places, events, and things that happen
* - 'agent': Memories about what the AI agent did, actions taken, and tasks performed
* - 'opinion': The agent's formed beliefs, perspectives, and viewpoints
* @returns SearchResponse Successful Response
* @throws ApiError
*/
public static apiSearchApiSearchPost({
requestBody,
}: {
requestBody: SearchRequest,
}): CancelablePromise<SearchResponse> {
return __request(OpenAPI, {
method: 'POST',
url: '/api/search',
body: requestBody,
mediaType: 'application/json',
errors: {
422: `Validation Error`,
},
});
}
}

View file

@ -3,64 +3,31 @@
/* tslint:disable */
/* eslint-disable */
import type { GraphDataResponse } from '../models/GraphDataResponse';
import type { ListMemoryUnitsResponse } from '../models/ListMemoryUnitsResponse';
import type { CancelablePromise } from '../core/CancelablePromise';
import { OpenAPI } from '../core/OpenAPI';
import { request as __request } from '../core/request';
export class VisualizationService {
/**
* Get memory graph data
* Retrieve graph data for visualization, optionally filtered by agent_id and fact_type (world/agent/opinion). Limited to 1000 most recent items.
* Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion). Limited to 1000 most recent items.
* @returns GraphDataResponse Successful Response
* @throws ApiError
*/
public static apiGraphApiGraphGet({
public static apiGraphApiV1AgentsAgentIdGraphGet({
agentId,
factType,
}: {
agentId?: (string | null),
agentId: string,
factType?: (string | null),
}): CancelablePromise<GraphDataResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/graph',
query: {
url: '/api/v1/agents/{agent_id}/graph',
path: {
'agent_id': agentId,
'fact_type': factType,
},
errors: {
422: `Validation Error`,
},
});
}
/**
* List memory units
* List memory units with pagination and optional full-text search. Supports filtering by agent_id and fact_type.
* @returns ListMemoryUnitsResponse Successful Response
* @throws ApiError
*/
public static apiListApiListGet({
agentId,
factType,
q,
limit = 100,
offset,
}: {
agentId?: (string | null),
factType?: (string | null),
q?: (string | null),
limit?: number,
offset?: number,
}): CancelablePromise<ListMemoryUnitsResponse> {
return __request(OpenAPI, {
method: 'GET',
url: '/api/list',
query: {
'agent_id': agentId,
'fact_type': factType,
'q': q,
'limit': limit,
'offset': offset,
},
errors: {
422: `Validation Error`,

View file

@ -4,7 +4,7 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function GET() {
try {
const response = await fetch(`${DATAPLANE_URL}/api/agents`);
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents`);
const data = await response.json();
return NextResponse.json(data, { status: response.status });
} catch (error) {

View file

@ -9,10 +9,17 @@ export async function GET(
try {
const { documentId } = await params;
const searchParams = request.nextUrl.searchParams;
const queryString = searchParams.toString();
const agentId = searchParams.get('agent_id');
if (!agentId) {
return NextResponse.json(
{ error: 'agent_id is required' },
{ status: 400 }
);
}
const response = await fetch(
`${DATAPLANE_URL}/api/documents/${documentId}?${queryString}`
`${DATAPLANE_URL}/api/v1/agents/${agentId}/documents/${documentId}`
);
const data = await response.json();
return NextResponse.json(data, { status: response.status });

View file

@ -5,9 +5,22 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function GET(request: NextRequest) {
try {
const searchParams = request.nextUrl.searchParams;
const queryString = searchParams.toString();
const agentId = searchParams.get('agent_id');
const response = await fetch(`${DATAPLANE_URL}/api/documents?${queryString}`);
if (!agentId) {
return NextResponse.json(
{ error: 'agent_id is required' },
{ status: 400 }
);
}
// Remove agent_id from query params and rebuild query string
const newSearchParams = new URLSearchParams(searchParams);
newSearchParams.delete('agent_id');
const queryString = newSearchParams.toString();
const url = `${DATAPLANE_URL}/api/v1/agents/${agentId}/documents${queryString ? `?${queryString}` : ''}`;
const response = await fetch(url);
const data = await response.json();
return NextResponse.json(data, { status: response.status });
} catch (error) {

View file

@ -5,9 +5,22 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function GET(request: NextRequest) {
try {
const searchParams = request.nextUrl.searchParams;
const queryString = searchParams.toString();
const agentId = searchParams.get('agent_id');
const response = await fetch(`${DATAPLANE_URL}/api/graph?${queryString}`);
if (!agentId) {
return NextResponse.json(
{ error: 'agent_id is required' },
{ status: 400 }
);
}
// Remove agent_id from query params and rebuild query string
const newSearchParams = new URLSearchParams(searchParams);
newSearchParams.delete('agent_id');
const queryString = newSearchParams.toString();
const url = `${DATAPLANE_URL}/api/v1/agents/${agentId}/graph${queryString ? `?${queryString}` : ''}`;
const response = await fetch(url);
const data = await response.json();
return NextResponse.json(data, { status: response.status });
} catch (error) {

View file

@ -5,9 +5,22 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function GET(request: NextRequest) {
try {
const searchParams = request.nextUrl.searchParams;
const queryString = searchParams.toString();
const agentId = searchParams.get('agent_id');
const response = await fetch(`${DATAPLANE_URL}/api/list?${queryString}`);
if (!agentId) {
return NextResponse.json(
{ error: 'agent_id is required' },
{ status: 400 }
);
}
// Remove agent_id from query params and rebuild query string
const newSearchParams = new URLSearchParams(searchParams);
newSearchParams.delete('agent_id');
const queryString = newSearchParams.toString();
const url = `${DATAPLANE_URL}/api/v1/agents/${agentId}/memories/list${queryString ? `?${queryString}` : ''}`;
const response = await fetch(url);
const data = await response.json();
return NextResponse.json(data, { status: response.status });
} catch (error) {

View file

@ -5,13 +5,24 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function POST(request: NextRequest) {
try {
const body = await request.json();
const agentId = body.agent_id;
const response = await fetch(`${DATAPLANE_URL}/api/memories/batch`, {
if (!agentId) {
return NextResponse.json(
{ error: 'agent_id is required' },
{ status: 400 }
);
}
// Remove agent_id from body as it's now in the path
const { agent_id, ...bodyWithoutAgentId } = body;
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents/${agentId}/memories`, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(body),
body: JSON.stringify(bodyWithoutAgentId),
});
const data = await response.json();

View file

@ -5,13 +5,24 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function POST(request: NextRequest) {
try {
const body = await request.json();
const agentId = body.agent_id;
const response = await fetch(`${DATAPLANE_URL}/api/memories/batch_async`, {
if (!agentId) {
return NextResponse.json(
{ error: 'agent_id is required' },
{ status: 400 }
);
}
// Remove agent_id from body as it's now in the path
const { agent_id, ...bodyWithoutAgentId } = body;
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents/${agentId}/memories/async`, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(body),
body: JSON.stringify(bodyWithoutAgentId),
});
const data = await response.json();

View file

@ -8,7 +8,7 @@ export async function GET(
) {
try {
const { agentId } = await params;
const response = await fetch(`${DATAPLANE_URL}/api/operations/${agentId}`);
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents/${agentId}/operations`);
const data = await response.json();
return NextResponse.json(data, { status: response.status });
} catch (error) {

View file

@ -5,13 +5,17 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function POST(request: NextRequest) {
try {
const body = await request.json();
const agentId = body.agent_id || 'default';
const response = await fetch(`${DATAPLANE_URL}/api/search`, {
// Remove agent_id from body as it's now in the path
const { agent_id, ...bodyWithoutAgentId } = body;
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents/${agentId}/memories/search`, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(body),
body: JSON.stringify(bodyWithoutAgentId),
});
const data = await response.json();

View file

@ -8,7 +8,7 @@ export async function GET(
) {
try {
const { agentId } = await params;
const response = await fetch(`${DATAPLANE_URL}/api/stats/${agentId}`);
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents/${agentId}/stats`);
const data = await response.json();
return NextResponse.json(data, { status: response.status });
} catch (error) {

View file

@ -5,13 +5,17 @@ const DATAPLANE_URL = process.env.MEMORA_CP_DATAPLANE_API_URL || 'http://localho
export async function POST(request: NextRequest) {
try {
const body = await request.json();
const agentId = body.agent_id || 'default';
const response = await fetch(`${DATAPLANE_URL}/api/think`, {
// Remove agent_id from body as it's now in the path
const { agent_id, ...bodyWithoutAgentId } = body;
const response = await fetch(`${DATAPLANE_URL}/api/v1/agents/${agentId}/think`, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(body),
body: JSON.stringify(bodyWithoutAgentId),
});
const data = await response.json();

View file

@ -30,18 +30,16 @@ export class DataplaneClient {
async search(params: {
query: string;
fact_type: ('world' | 'agent' | 'opinion')[];
agent_id?: string;
agent_id: string;
thinking_budget?: number;
max_tokens?: number;
reranker?: string;
trace?: boolean;
}) {
return this.fetchApi('/api/search', {
const { agent_id, ...body } = params;
return this.fetchApi(`/api/v1/agents/${agent_id}/memories/search`, {
method: 'POST',
body: JSON.stringify({
agent_id: params.agent_id || 'default',
...params,
}),
body: JSON.stringify(body),
});
}
@ -50,15 +48,13 @@ export class DataplaneClient {
*/
async think(params: {
query: string;
agent_id?: string;
agent_id: string;
thinking_budget?: number;
}) {
return this.fetchApi('/api/think', {
const { agent_id, ...body } = params;
return this.fetchApi(`/api/v1/agents/${agent_id}/think`, {
method: 'POST',
body: JSON.stringify({
agent_id: params.agent_id || 'default',
...params,
}),
body: JSON.stringify(body),
});
}
@ -74,9 +70,10 @@ export class DataplaneClient {
}>;
document_id?: string;
}) {
return this.fetchApi('/api/memories/batch', {
const { agent_id, ...body } = params;
return this.fetchApi(`/api/v1/agents/${agent_id}/memories`, {
method: 'POST',
body: JSON.stringify(params),
body: JSON.stringify(body),
});
}
@ -93,9 +90,10 @@ export class DataplaneClient {
}>;
document_id?: string;
}) {
return this.fetchApi('/api/memories/batch_async', {
const { agent_id, ...body } = params;
return this.fetchApi(`/api/v1/agents/${agent_id}/memories/async`, {
method: 'POST',
body: JSON.stringify(params),
body: JSON.stringify(body),
});
}
@ -103,68 +101,65 @@ export class DataplaneClient {
* List all agents
*/
async listAgents() {
return this.fetchApi<{ agents: string[] }>('/api/agents', { cache: 'no-store' });
return this.fetchApi<{ agents: any[] }>('/api/v1/agents', { cache: 'no-store' });
}
/**
* Get agent statistics
*/
async getAgentStats(agentId: string) {
return this.fetchApi(`/api/stats/${agentId}`);
return this.fetchApi(`/api/v1/agents/${agentId}/stats`);
}
/**
* Get graph data for visualization
*/
async getGraphData(params?: {
agent_id?: string;
async getGraphData(params: {
agent_id: string;
fact_type?: string;
}) {
const queryParams = new URLSearchParams();
if (params?.agent_id) queryParams.append('agent_id', params.agent_id);
if (params?.fact_type) queryParams.append('fact_type', params.fact_type);
if (params.fact_type) queryParams.append('fact_type', params.fact_type);
const path = `/api/graph${queryParams.toString() ? `?${queryParams}` : ''}`;
const path = `/api/v1/agents/${params.agent_id}/graph${queryParams.toString() ? `?${queryParams}` : ''}`;
return this.fetchApi(path);
}
/**
* List memory units
*/
async listMemoryUnits(params?: {
agent_id?: string;
async listMemoryUnits(params: {
agent_id: string;
fact_type?: string;
q?: string;
limit?: number;
offset?: number;
}) {
const queryParams = new URLSearchParams();
if (params?.agent_id) queryParams.append('agent_id', params.agent_id);
if (params?.fact_type) queryParams.append('fact_type', params.fact_type);
if (params?.q) queryParams.append('q', params.q);
if (params?.limit) queryParams.append('limit', params.limit.toString());
if (params?.offset) queryParams.append('offset', params.offset.toString());
if (params.fact_type) queryParams.append('fact_type', params.fact_type);
if (params.q) queryParams.append('q', params.q);
if (params.limit) queryParams.append('limit', params.limit.toString());
if (params.offset) queryParams.append('offset', params.offset.toString());
const path = `/api/list${queryParams.toString() ? `?${queryParams}` : ''}`;
const path = `/api/v1/agents/${params.agent_id}/memories/list${queryParams.toString() ? `?${queryParams}` : ''}`;
return this.fetchApi(path);
}
/**
* List documents
*/
async listDocuments(params?: {
agent_id?: string;
async listDocuments(params: {
agent_id: string;
q?: string;
limit?: number;
offset?: number;
}) {
const queryParams = new URLSearchParams();
if (params?.agent_id) queryParams.append('agent_id', params.agent_id);
if (params?.q) queryParams.append('q', params.q);
if (params?.limit) queryParams.append('limit', params.limit.toString());
if (params?.offset) queryParams.append('offset', params.offset.toString());
if (params.q) queryParams.append('q', params.q);
if (params.limit) queryParams.append('limit', params.limit.toString());
if (params.offset) queryParams.append('offset', params.offset.toString());
const path = `/api/documents${queryParams.toString() ? `?${queryParams}` : ''}`;
const path = `/api/v1/agents/${params.agent_id}/documents${queryParams.toString() ? `?${queryParams}` : ''}`;
return this.fetchApi(path);
}
@ -172,22 +167,21 @@ export class DataplaneClient {
* Get document by ID
*/
async getDocument(documentId: string, agentId: string) {
const queryParams = new URLSearchParams({ agent_id: agentId });
return this.fetchApi(`/api/documents/${documentId}?${queryParams}`);
return this.fetchApi(`/api/v1/agents/${agentId}/documents/${documentId}`);
}
/**
* List async operations for an agent
*/
async listOperations(agentId: string) {
return this.fetchApi(`/api/operations/${agentId}`);
return this.fetchApi(`/api/v1/agents/${agentId}/operations`);
}
/**
* Cancel a pending async operation
*/
async cancelOperation(operationId: string) {
return this.fetchApi(`/api/operations/${operationId}`, {
async cancelOperation(agentId: string, operationId: string) {
return this.fetchApi(`/api/v1/agents/${agentId}/operations/${operationId}`, {
method: 'DELETE',
});
}
@ -195,8 +189,8 @@ export class DataplaneClient {
/**
* Delete a memory unit
*/
async deleteMemoryUnit(unitId: string) {
return this.fetchApi(`/api/memory/${unitId}`, {
async deleteMemoryUnit(agentId: string, unitId: string) {
return this.fetchApi(`/api/v1/agents/${agentId}/memories/${unitId}`, {
method: 'DELETE',
});
}

View file

@ -1,61 +0,0 @@
"""
Quick script to fix corrupted background data for ea_marcus agent.
The background field contains JSON instead of plain text.
"""
import asyncio
import json
import os
from memora import TemporalSemanticMemory
async def fix_background(agent_id: str):
"""Fix background by extracting text from JSON string."""
# Initialize memory system from environment variables
memory = TemporalSemanticMemory()
try:
# Get current profile
profile = await memory.get_agent_profile(agent_id)
background = profile["background"]
print(f"Current background for {agent_id}:")
print(f" {background[:200]}")
print()
# Check if it's corrupted (contains JSON)
if background.strip().startswith("{"):
print("Background appears to be corrupted JSON. Attempting to extract text...")
try:
# Try to parse as JSON
data = json.loads(background)
if "background" in data:
clean_background = data["background"]
print(f"Extracted text: {clean_background}")
# Update with clean background (without personality inference to preserve current traits)
await memory.merge_agent_background(
agent_id,
clean_background,
update_personality=False
)
print(f"✓ Fixed background for {agent_id}")
else:
print("✗ JSON doesn't have 'background' key")
except json.JSONDecodeError:
print("✗ Failed to parse as JSON")
else:
print("Background looks fine - no corruption detected")
finally:
await memory.close()
async def main():
agent_id = "ea_marcus"
print(f"Fixing background for agent: {agent_id}")
print("=" * 60)
await fix_background(agent_id)
if __name__ == "__main__":
asyncio.run(main())

View file

@ -22,7 +22,6 @@ class SearchRequest(BaseModel):
"""Request model for search endpoint."""
query: str
fact_type: Optional[List[str]] = None # List of fact types to search (defaults to all if not specified)
agent_id: str = "default"
thinking_budget: int = 100
max_tokens: int = 4096
reranker: str = "heuristic"
@ -34,7 +33,6 @@ class SearchRequest(BaseModel):
"example": {
"query": "What did Alice say about machine learning?",
"fact_type": ["world", "agent"],
"agent_id": "user123",
"thinking_budget": 100,
"max_tokens": 4096,
"reranker": "heuristic",
@ -112,14 +110,12 @@ class MemoryItem(BaseModel):
class BatchPutRequest(BaseModel):
"""Request model for batch put endpoint."""
agent_id: str
items: List[MemoryItem]
document_id: Optional[str] = None
class Config:
json_schema_extra = {
"example": {
"agent_id": "user123",
"items": [
{
"content": "Alice works at Google",
@ -180,7 +176,6 @@ class BatchPutAsyncResponse(BaseModel):
class ThinkRequest(BaseModel):
"""Request model for think endpoint."""
query: str
agent_id: str = "default"
thinking_budget: int = 50
context: Optional[str] = None
@ -188,7 +183,6 @@ class ThinkRequest(BaseModel):
json_schema_extra = {
"example": {
"query": "What do you think about artificial intelligence?",
"agent_id": "user123",
"thinking_budget": 50,
"context": "This is for a research paper on AI ethics"
}
@ -588,36 +582,36 @@ def _register_routes(app: FastAPI):
@app.get(
"/api/graph",
"/api/v1/agents/{agent_id}/graph",
response_model=GraphDataResponse,
tags=["Visualization"],
summary="Get memory graph data",
description="Retrieve graph data for visualization, optionally filtered by agent_id and fact_type (world/agent/opinion). Limited to 1000 most recent items."
description="Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion). Limited to 1000 most recent items."
)
async def api_graph(
agent_id: Optional[str] = None,
agent_id: str,
fact_type: Optional[str] = None
):
"""Get graph data from database, optionally filtered by agent_id and fact_type."""
"""Get graph data from database, filtered by agent_id and optionally by fact_type."""
try:
data = await app.state.memory.get_graph_data(agent_id, fact_type)
return data
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/graph: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/graph: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/list",
"/api/v1/agents/{agent_id}/memories/list",
response_model=ListMemoryUnitsResponse,
tags=["Visualization"],
tags=["Memory Operations"],
summary="List memory units",
description="List memory units with pagination and optional full-text search. Supports filtering by agent_id and fact_type."
description="List memory units with pagination and optional full-text search. Supports filtering by fact_type."
)
async def api_list(
agent_id: Optional[str] = None,
agent_id: str,
fact_type: Optional[str] = None,
q: Optional[str] = None,
limit: int = 100,
@ -627,7 +621,7 @@ def _register_routes(app: FastAPI):
List memory units for table view with optional full-text search.
Args:
agent_id: Filter by agent ID
agent_id: Agent ID (from path)
fact_type: Filter by fact type (world, agent, opinion)
q: Search query for full-text search (searches text and context)
limit: Maximum number of results (default: 100)
@ -645,25 +639,25 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/list: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/memories/list: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.post(
"/api/search",
"/api/v1/agents/{agent_id}/memories/search",
response_model=SearchResponse,
tags=["Search"],
tags=["Memory Operations"],
summary="Search memory",
description="""
Search memory using semantic similarity and spreading activation.
The fact_type parameter is required and must be one of:
The fact_type parameter is optional and must be one of:
- 'world': General knowledge about people, places, events, and things that happen
- 'agent': Memories about what the AI agent did, actions taken, and tasks performed
- 'opinion': The agent's formed beliefs, perspectives, and viewpoints
"""
)
async def api_search(request: SearchRequest):
async def api_search(agent_id: str, request: SearchRequest):
"""Run a search and return results with trace."""
try:
# Validate fact_type(s)
@ -693,7 +687,7 @@ def _register_routes(app: FastAPI):
# Run search with tracing
core_result = await app.state.memory.search_async(
agent_id=request.agent_id,
agent_id=agent_id,
query=request.query,
thinking_budget=request.thinking_budget,
max_tokens=request.max_tokens,
@ -724,12 +718,12 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/search: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/memories/search: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.post(
"/api/think",
"/api/v1/agents/{agent_id}/think",
response_model=ThinkResponse,
tags=["Reasoning"],
summary="Think and generate answer",
@ -745,11 +739,11 @@ def _register_routes(app: FastAPI):
6. Returns plain text answer, the facts used, and new opinions
"""
)
async def api_think(request: ThinkRequest):
async def api_think(agent_id: str, request: ThinkRequest):
try:
# Use the memory system's think_async method
core_result = await app.state.memory.think_async(
agent_id=request.agent_id,
agent_id=agent_id,
query=request.query,
thinking_budget=request.thinking_budget,
context=request.context
@ -776,31 +770,31 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/think: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/think: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/agents",
response_model=AgentsResponse,
tags=["Management"],
"/api/v1/agents",
response_model=AgentListResponse,
tags=["Agent Management"],
summary="List all agents",
description="Get a list of all agent IDs that have stored memories in the system"
description="Get a list of all agents with their profiles"
)
async def api_agents():
"""Get list of available agents from database."""
"""Get list of all agents with their profiles."""
try:
agent_list = await app.state.memory.list_agents()
return AgentsResponse(agents=agent_list)
agents = await app.state.memory.list_agents()
return AgentListResponse(agents=agents)
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/agents: {error_detail}")
print(f"Error in /api/v1/agents: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/stats/{agent_id}",
tags=["Memory Statistics"],
"/api/v1/agents/{agent_id}/stats",
tags=["Agent Management"],
summary="Get memory statistics for an agent",
description="Get statistics about nodes and links for a specific agent"
)
@ -878,11 +872,11 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/stats/{agent_id}: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/stats: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/documents",
"/api/v1/agents/{agent_id}/documents",
response_model=ListDocumentsResponse,
tags=["Documents"],
summary="List documents",
@ -898,7 +892,7 @@ def _register_routes(app: FastAPI):
List documents for an agent with optional search.
Args:
agent_id: Agent ID (required)
agent_id: Agent ID (from path)
q: Search query (searches document ID and metadata)
limit: Maximum number of results (default: 100)
offset: Offset for pagination (default: 0)
@ -914,27 +908,27 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/documents: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/documents: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/documents/{document_id}",
"/api/v1/agents/{agent_id}/documents/{document_id}",
response_model=DocumentResponse,
tags=["Documents"],
summary="Get document details",
description="Get a specific document including its original text"
)
async def api_get_document(
document_id: str,
agent_id: str
agent_id: str,
document_id: str
):
"""
Get a specific document with its original text.
Args:
document_id: Document ID
agent_id: Agent ID (required as query parameter)
agent_id: Agent ID (from path)
document_id: Document ID (from path)
"""
try:
document = await app.state.memory.get_document(document_id, agent_id)
@ -946,14 +940,14 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/documents/{document_id}: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/documents/{document_id}: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.post(
"/api/memories/batch",
"/api/v1/agents/{agent_id}/memories",
response_model=BatchPutResponse,
tags=["Memory Storage"],
tags=["Memory Operations"],
summary="Store multiple memories",
description="""
Store multiple memory items in batch with automatic fact extraction.
@ -975,7 +969,7 @@ def _register_routes(app: FastAPI):
Note: If document_id is provided and already exists, the old document and its memory units will be deleted before creating new ones (upsert behavior).
"""
)
async def api_batch_put(request: BatchPutRequest):
async def api_batch_put(agent_id: str, request: BatchPutRequest):
try:
# Prepare contents for put_batch_async
contents = []
@ -989,7 +983,7 @@ def _register_routes(app: FastAPI):
# Call put_batch_async
result = await app.state.memory.put_batch_async(
agent_id=request.agent_id,
agent_id=agent_id,
contents=contents,
document_id=request.document_id
)
@ -998,21 +992,21 @@ def _register_routes(app: FastAPI):
return BatchPutResponse(
success=True,
message=f"Successfully stored {len(contents)} memory items",
agent_id=request.agent_id,
agent_id=agent_id,
document_id=request.document_id,
items_count=len(contents)
)
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/memories/batch: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/memories: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.post(
"/api/memories/batch_async",
"/api/v1/agents/{agent_id}/memories/async",
response_model=BatchPutAsyncResponse,
tags=["Memory Storage"],
tags=["Memory Operations"],
summary="Store multiple memories asynchronously",
description="""
Store multiple memory items in batch asynchronously using the task backend.
@ -1037,7 +1031,7 @@ def _register_routes(app: FastAPI):
Note: If document_id is provided and already exists, the old document and its memory units will be deleted before creating new ones (upsert behavior).
"""
)
async def api_batch_put_async(request: BatchPutRequest):
async def api_batch_put_async(agent_id: str, request: BatchPutRequest):
try:
# Prepare contents for put_batch_async
contents = []
@ -1061,7 +1055,7 @@ def _register_routes(app: FastAPI):
VALUES ($1, $2, $3, $4, $5)
""",
operation_id,
request.agent_id,
agent_id,
'batch_put',
len(contents),
request.document_id
@ -1071,17 +1065,17 @@ def _register_routes(app: FastAPI):
await app.state.memory._task_backend.submit_task({
'type': 'batch_put',
'operation_id': str(operation_id),
'agent_id': request.agent_id,
'agent_id': agent_id,
'contents': contents,
'document_id': request.document_id
})
logging.info(f"Batch put task queued for agent_id={request.agent_id}, {len(contents)} items, operation_id={operation_id}")
logging.info(f"Batch put task queued for agent_id={agent_id}, {len(contents)} items, operation_id={operation_id}")
return BatchPutAsyncResponse(
success=True,
message=f"Batch put task queued for background processing ({len(contents)} items)",
agent_id=request.agent_id,
agent_id=agent_id,
document_id=request.document_id,
items_count=len(contents),
queued=True
@ -1089,13 +1083,13 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/memories/batch_async: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/memories/async: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/operations/{agent_id}",
tags=["Memory Storage"],
"/api/v1/agents/{agent_id}/operations",
tags=["Memory Operations"],
summary="List async operations",
description="Get a list of all async operations (pending and failed) for a specific agent, including error messages for failed operations"
)
@ -1133,17 +1127,17 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/operations/{agent_id}: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/operations: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.delete(
"/api/operations/{operation_id}",
tags=["Memory Storage"],
"/api/v1/agents/{agent_id}/operations/{operation_id}",
tags=["Memory Operations"],
summary="Cancel a pending async operation",
description="Cancel a pending async operation by removing it from the queue"
)
async def api_cancel_operation(operation_id: str):
async def api_cancel_operation(agent_id: str, operation_id: str):
"""Cancel a pending async operation."""
try:
# Validate UUID format
@ -1154,14 +1148,15 @@ def _register_routes(app: FastAPI):
pool = await app.state.memory._get_pool()
async with pool.acquire() as conn:
# Check if operation exists
# Check if operation exists and belongs to this agent
result = await conn.fetchrow(
"SELECT agent_id FROM async_operations WHERE id = $1",
op_uuid
"SELECT agent_id FROM async_operations WHERE id = $1 AND agent_id = $2",
op_uuid,
agent_id
)
if not result:
raise HTTPException(status_code=404, detail=f"Operation {operation_id} not found")
raise HTTPException(status_code=404, detail=f"Operation {operation_id} not found for agent {agent_id}")
# Delete the operation
await conn.execute(
@ -1173,7 +1168,7 @@ def _register_routes(app: FastAPI):
"success": True,
"message": f"Operation {operation_id} cancelled",
"operation_id": operation_id,
"agent_id": result['agent_id']
"agent_id": agent_id
}
except HTTPException:
@ -1181,17 +1176,17 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/operations/{operation_id}: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/operations/{operation_id}: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.delete(
"/api/memory/{unit_id}",
tags=["Memory Storage"],
"/api/v1/agents/{agent_id}/memories/{unit_id}",
tags=["Memory Operations"],
summary="Delete a memory unit",
description="Delete a single memory unit and all its associated links (temporal, semantic, and entity links)"
)
async def api_delete_memory_unit(unit_id: str):
async def api_delete_memory_unit(agent_id: str, unit_id: str):
"""Delete a memory unit and all its links."""
try:
result = await app.state.memory.delete_memory_unit(unit_id)
@ -1205,35 +1200,16 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/memory/{unit_id}: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/memories/{unit_id}: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
# Agent Profile Endpoints
@app.get(
"/api/agents",
response_model=AgentListResponse,
tags=["Agent Profile"],
summary="List all agents",
description="Get a list of all agents with their profiles"
)
async def api_list_agents():
"""List all agents with their profiles."""
try:
agents = await app.state.memory.list_agents()
return AgentListResponse(agents=agents)
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/agents: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.get(
"/api/agents/{agent_id}/profile",
"/api/v1/agents/{agent_id}/profile",
response_model=AgentProfileResponse,
tags=["Agent Profile"],
tags=["Agent Management"],
summary="Get agent profile",
description="Get personality traits and background for an agent. Auto-creates agent with defaults if not exists."
)
@ -1249,14 +1225,14 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/agents/{agent_id}/profile: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/profile: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.put(
"/api/agents/{agent_id}/profile",
"/api/v1/agents/{agent_id}/profile",
response_model=AgentProfileResponse,
tags=["Agent Profile"],
tags=["Agent Management"],
summary="Update agent personality",
description="Update agent's Big Five personality traits and bias strength"
)
@ -1282,14 +1258,14 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/agents/{agent_id}/profile: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/profile: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.post(
"/api/agents/{agent_id}/background",
"/api/v1/agents/{agent_id}/background",
response_model=BackgroundResponse,
tags=["Agent Profile"],
tags=["Agent Management"],
summary="Add/merge agent background",
description="Add new background information or merge with existing. LLM intelligently resolves conflicts, normalizes to first person, and optionally infers personality traits."
)
@ -1313,14 +1289,14 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/agents/{agent_id}/background: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}/background: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))
@app.put(
"/api/agents/{agent_id}",
"/api/v1/agents/{agent_id}",
response_model=AgentProfileResponse,
tags=["Agent Profile"],
tags=["Agent Management"],
summary="Create or update agent",
description="Create a new agent or update existing agent with personality and background. Auto-fills missing fields with defaults."
)
@ -1367,5 +1343,5 @@ def _register_routes(app: FastAPI):
except Exception as e:
import traceback
error_detail = f"{str(e)}\n\nTraceback:\n{traceback.format_exc()}"
print(f"Error in /api/agents/{agent_id}: {error_detail}")
print(f"Error in /api/v1/agents/{agent_id}: {error_detail}")
raise HTTPException(status_code=500, detail=str(e))

View file

@ -74,7 +74,6 @@ class RemoteMemoryClient:
# Make API request
request_data = {
"agent_id": agent_id,
"items": items
}
@ -82,7 +81,7 @@ class RemoteMemoryClient:
request_data["document_id"] = document_id
response = await self.client.post(
f"{self.base_url}/api/memories/batch_async",
f"{self.base_url}/api/v1/agents/{agent_id}/memories/async",
json=request_data
)
response.raise_for_status()
@ -114,7 +113,6 @@ class RemoteMemoryClient:
Tuple of (results, trace)
"""
request_data = {
"agent_id": agent_id,
"query": query,
"thinking_budget": thinking_budget,
"max_tokens": max_tokens,
@ -126,7 +124,7 @@ class RemoteMemoryClient:
request_data["fact_type"] = fact_type
response = await self.client.post(
f"{self.base_url}/api/search",
f"{self.base_url}/api/v1/agents/{agent_id}/memories/search",
json=request_data
)
response.raise_for_status()
@ -154,7 +152,6 @@ class RemoteMemoryClient:
Dict with 'text', 'based_on', and 'new_opinions' keys
"""
request_data = {
"agent_id": agent_id,
"query": query,
"thinking_budget": thinking_budget
}
@ -163,7 +160,7 @@ class RemoteMemoryClient:
request_data["context"] = context
response = await self.client.post(
f"{self.base_url}/api/think",
f"{self.base_url}/api/v1/agents/{agent_id}/think",
json=request_data
)
response.raise_for_status()
@ -193,7 +190,7 @@ class RemoteMemoryClient:
Returns:
List of agent IDs
"""
response = await self.client.get(f"{self.base_url}/api/agents")
response = await self.client.get(f"{self.base_url}/api/v1/agents")
response.raise_for_status()
result = response.json()
return result.get("agents", [])
@ -208,7 +205,7 @@ class RemoteMemoryClient:
Returns:
Dict with statistics including total_nodes, total_links, and pending_operations
"""
response = await self.client.get(f"{self.base_url}/api/stats/{agent_id}")
response = await self.client.get(f"{self.base_url}/api/v1/agents/{agent_id}/stats")
response.raise_for_status()
return response.json()

View file

@ -153,6 +153,3 @@ async def test_think_without_prior_context(memory):
assert result.text, "Should return some answer"
assert result.based_on, "Should return based_on structure"
if __name__ == "__main__":
pytest.main([__file__, "-v", "-s"])

View file

@ -13,28 +13,21 @@
"version": "1.0.0"
},
"paths": {
"/api/graph": {
"/api/v1/agents/{agent_id}/graph": {
"get": {
"tags": [
"Visualization"
],
"summary": "Get memory graph data",
"description": "Retrieve graph data for visualization, optionally filtered by agent_id and fact_type (world/agent/opinion). Limited to 1000 most recent items.",
"operationId": "api_graph_api_graph_get",
"description": "Retrieve graph data for visualization, optionally filtered by fact_type (world/agent/opinion). Limited to 1000 most recent items.",
"operationId": "api_graph_api_v1_agents__agent_id__graph_get",
"parameters": [
{
"name": "agent_id",
"in": "query",
"required": false,
"in": "path",
"required": true,
"schema": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"type": "string",
"title": "Agent Id"
}
},
@ -79,28 +72,21 @@
}
}
},
"/api/list": {
"/api/v1/agents/{agent_id}/memories/list": {
"get": {
"tags": [
"Visualization"
"Memory Operations"
],
"summary": "List memory units",
"description": "List memory units with pagination and optional full-text search. Supports filtering by agent_id and fact_type.",
"operationId": "api_list_api_list_get",
"description": "List memory units with pagination and optional full-text search. Supports filtering by fact_type.",
"operationId": "api_list_api_v1_agents__agent_id__memories_list_get",
"parameters": [
{
"name": "agent_id",
"in": "query",
"required": false,
"in": "path",
"required": true,
"schema": {
"anyOf": [
{
"type": "string"
},
{
"type": "null"
}
],
"type": "string",
"title": "Agent Id"
}
},
@ -181,23 +167,34 @@
}
}
},
"/api/search": {
"/api/v1/agents/{agent_id}/memories/search": {
"post": {
"tags": [
"Search"
"Memory Operations"
],
"summary": "Search memory",
"description": "Search memory using semantic similarity and spreading activation.\n\n The fact_type parameter is required and must be one of:\n - 'world': General knowledge about people, places, events, and things that happen\n - 'agent': Memories about what the AI agent did, actions taken, and tasks performed\n - 'opinion': The agent's formed beliefs, perspectives, and viewpoints",
"operationId": "api_search_api_search_post",
"description": "Search memory using semantic similarity and spreading activation.\n\n The fact_type parameter is optional and must be one of:\n - 'world': General knowledge about people, places, events, and things that happen\n - 'agent': Memories about what the AI agent did, actions taken, and tasks performed\n - 'opinion': The agent's formed beliefs, perspectives, and viewpoints",
"operationId": "api_search_api_v1_agents__agent_id__memories_search_post",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SearchRequest"
}
}
},
"required": true
}
},
"responses": {
"200": {
@ -223,23 +220,34 @@
}
}
},
"/api/think": {
"/api/v1/agents/{agent_id}/think": {
"post": {
"tags": [
"Reasoning"
],
"summary": "Think and generate answer",
"description": "Think and formulate an answer using agent identity, world facts, and opinions.\n\n This endpoint:\n 1. Retrieves agent facts (agent's identity)\n 2. Retrieves world facts relevant to the query\n 3. Retrieves existing opinions (agent's perspectives)\n 4. Uses LLM to formulate a contextual answer\n 5. Extracts and stores any new opinions formed\n 6. Returns plain text answer, the facts used, and new opinions",
"operationId": "api_think_api_think_post",
"operationId": "api_think_api_v1_agents__agent_id__think_post",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ThinkRequest"
}
}
},
"required": true
}
},
"responses": {
"200": {
@ -265,14 +273,14 @@
}
}
},
"/api/agents": {
"/api/v1/agents": {
"get": {
"tags": [
"Agent Profile"
"Agent Management"
],
"summary": "List all agents",
"description": "Get a list of all agents with their profiles",
"operationId": "api_list_agents_api_agents_get",
"operationId": "api_agents_api_v1_agents_get",
"responses": {
"200": {
"description": "Successful Response",
@ -287,14 +295,14 @@
}
}
},
"/api/stats/{agent_id}": {
"/api/v1/agents/{agent_id}/stats": {
"get": {
"tags": [
"Memory Statistics"
"Agent Management"
],
"summary": "Get memory statistics for an agent",
"description": "Get statistics about nodes and links for a specific agent",
"operationId": "api_stats_api_stats__agent_id__get",
"operationId": "api_stats_api_v1_agents__agent_id__stats_get",
"parameters": [
{
"name": "agent_id",
@ -328,18 +336,18 @@
}
}
},
"/api/documents": {
"/api/v1/agents/{agent_id}/documents": {
"get": {
"tags": [
"Documents"
],
"summary": "List documents",
"description": "List documents with pagination and optional search. Documents are the source content from which memory units are extracted.",
"operationId": "api_list_documents_api_documents_get",
"operationId": "api_list_documents_api_v1_agents__agent_id__documents_get",
"parameters": [
{
"name": "agent_id",
"in": "query",
"in": "path",
"required": true,
"schema": {
"type": "string",
@ -407,15 +415,24 @@
}
}
},
"/api/documents/{document_id}": {
"/api/v1/agents/{agent_id}/documents/{document_id}": {
"get": {
"tags": [
"Documents"
],
"summary": "Get document details",
"description": "Get a specific document including its original text",
"operationId": "api_get_document_api_documents__document_id__get",
"operationId": "api_get_document_api_v1_agents__agent_id__documents__document_id__get",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
},
{
"name": "document_id",
"in": "path",
@ -424,15 +441,6 @@
"type": "string",
"title": "Document Id"
}
},
{
"name": "agent_id",
"in": "query",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
}
],
"responses": {
@ -459,23 +467,34 @@
}
}
},
"/api/memories/batch": {
"/api/v1/agents/{agent_id}/memories": {
"post": {
"tags": [
"Memory Storage"
"Memory Operations"
],
"summary": "Store multiple memories",
"description": "Store multiple memory items in batch with automatic fact extraction.\n\n Features:\n - Efficient batch processing\n - Automatic fact extraction from natural language\n - Entity recognition and linking\n - Document tracking with automatic upsert (when document_id is provided)\n - Temporal and semantic linking\n\n The system automatically:\n 1. Extracts semantic facts from the content\n 2. Generates embeddings\n 3. Deduplicates similar facts\n 4. Creates temporal, semantic, and entity links\n 5. Tracks document metadata\n\n Note: If document_id is provided and already exists, the old document and its memory units will be deleted before creating new ones (upsert behavior).",
"operationId": "api_batch_put_api_memories_batch_post",
"operationId": "api_batch_put_api_v1_agents__agent_id__memories_post",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/BatchPutRequest"
}
}
},
"required": true
}
},
"responses": {
"200": {
@ -501,23 +520,34 @@
}
}
},
"/api/memories/batch_async": {
"/api/v1/agents/{agent_id}/memories/async": {
"post": {
"tags": [
"Memory Storage"
"Memory Operations"
],
"summary": "Store multiple memories asynchronously",
"description": "Store multiple memory items in batch asynchronously using the task backend.\n\n This endpoint returns immediately after queuing the task, without waiting for completion.\n The actual processing happens in the background.\n\n Features:\n - Immediate response (non-blocking)\n - Background processing via task queue\n - Efficient batch processing\n - Automatic fact extraction from natural language\n - Entity recognition and linking\n - Document tracking with automatic upsert (when document_id is provided)\n - Temporal and semantic linking\n\n The system automatically:\n 1. Queues the batch put task\n 2. Returns immediately with success=True, queued=True\n 3. Processes in background: extracts facts, generates embeddings, creates links\n\n Note: If document_id is provided and already exists, the old document and its memory units will be deleted before creating new ones (upsert behavior).",
"operationId": "api_batch_put_async_api_memories_batch_async_post",
"operationId": "api_batch_put_async_api_v1_agents__agent_id__memories_async_post",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/BatchPutRequest"
}
}
},
"required": true
}
},
"responses": {
"200": {
@ -543,14 +573,14 @@
}
}
},
"/api/operations/{agent_id}": {
"/api/v1/agents/{agent_id}/operations": {
"get": {
"tags": [
"Memory Storage"
"Memory Operations"
],
"summary": "List async operations",
"description": "Get a list of all async operations (pending and failed) for a specific agent, including error messages for failed operations",
"operationId": "api_list_operations_api_operations__agent_id__get",
"operationId": "api_list_operations_api_v1_agents__agent_id__operations_get",
"parameters": [
{
"name": "agent_id",
@ -584,15 +614,24 @@
}
}
},
"/api/operations/{operation_id}": {
"/api/v1/agents/{agent_id}/operations/{operation_id}": {
"delete": {
"tags": [
"Memory Storage"
"Memory Operations"
],
"summary": "Cancel a pending async operation",
"description": "Cancel a pending async operation by removing it from the queue",
"operationId": "api_cancel_operation_api_operations__operation_id__delete",
"operationId": "api_cancel_operation_api_v1_agents__agent_id__operations__operation_id__delete",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
},
{
"name": "operation_id",
"in": "path",
@ -625,15 +664,24 @@
}
}
},
"/api/memory/{unit_id}": {
"/api/v1/agents/{agent_id}/memories/{unit_id}": {
"delete": {
"tags": [
"Memory Storage"
"Memory Operations"
],
"summary": "Delete a memory unit",
"description": "Delete a single memory unit and all its associated links (temporal, semantic, and entity links)",
"operationId": "api_delete_memory_unit_api_memory__unit_id__delete",
"operationId": "api_delete_memory_unit_api_v1_agents__agent_id__memories__unit_id__delete",
"parameters": [
{
"name": "agent_id",
"in": "path",
"required": true,
"schema": {
"type": "string",
"title": "Agent Id"
}
},
{
"name": "unit_id",
"in": "path",
@ -666,14 +714,14 @@
}
}
},
"/api/agents/{agent_id}/profile": {
"/api/v1/agents/{agent_id}/profile": {
"get": {
"tags": [
"Agent Profile"
"Agent Management"
],
"summary": "Get agent profile",
"description": "Get personality traits and background for an agent. Auto-creates agent with defaults if not exists.",
"operationId": "api_get_agent_profile_api_agents__agent_id__profile_get",
"operationId": "api_get_agent_profile_api_v1_agents__agent_id__profile_get",
"parameters": [
{
"name": "agent_id",
@ -710,11 +758,11 @@
},
"put": {
"tags": [
"Agent Profile"
"Agent Management"
],
"summary": "Update agent personality",
"description": "Update agent's Big Five personality traits and bias strength",
"operationId": "api_update_agent_personality_api_agents__agent_id__profile_put",
"operationId": "api_update_agent_personality_api_v1_agents__agent_id__profile_put",
"parameters": [
{
"name": "agent_id",
@ -760,14 +808,14 @@
}
}
},
"/api/agents/{agent_id}/background": {
"/api/v1/agents/{agent_id}/background": {
"post": {
"tags": [
"Agent Profile"
"Agent Management"
],
"summary": "Add/merge agent background",
"description": "Add new background information or merge with existing. LLM intelligently resolves conflicts, normalizes to first person, and optionally infers personality traits.",
"operationId": "api_add_agent_background_api_agents__agent_id__background_post",
"operationId": "api_add_agent_background_api_v1_agents__agent_id__background_post",
"parameters": [
{
"name": "agent_id",
@ -813,14 +861,14 @@
}
}
},
"/api/agents/{agent_id}": {
"/api/v1/agents/{agent_id}": {
"put": {
"tags": [
"Agent Profile"
"Agent Management"
],
"summary": "Create or update agent",
"description": "Create a new agent or update existing agent with personality and background. Auto-fills missing fields with defaults.",
"operationId": "api_create_or_update_agent_api_agents__agent_id__put",
"operationId": "api_create_or_update_agent_api_v1_agents__agent_id__put",
"parameters": [
{
"name": "agent_id",
@ -1009,30 +1057,6 @@
}
}
},
"AgentsResponse": {
"properties": {
"agents": {
"items": {
"type": "string"
},
"type": "array",
"title": "Agents"
}
},
"type": "object",
"required": [
"agents"
],
"title": "AgentsResponse",
"description": "Response model for agents list endpoint.",
"example": {
"agents": [
"user123",
"agent_alice",
"agent_bob"
]
}
},
"BackgroundResponse": {
"properties": {
"background": {
@ -1123,10 +1147,6 @@
},
"BatchPutRequest": {
"properties": {
"agent_id": {
"type": "string",
"title": "Agent Id"
},
"items": {
"items": {
"$ref": "#/components/schemas/MemoryItem"
@ -1148,13 +1168,11 @@
},
"type": "object",
"required": [
"agent_id",
"items"
],
"title": "BatchPutRequest",
"description": "Request model for batch put endpoint.",
"example": {
"agent_id": "user123",
"document_id": "conversation_123",
"items": [
{
@ -1624,11 +1642,6 @@
],
"title": "Fact Type"
},
"agent_id": {
"type": "string",
"title": "Agent Id",
"default": "default"
},
"thinking_budget": {
"type": "integer",
"title": "Thinking Budget",
@ -1668,7 +1681,6 @@
"title": "SearchRequest",
"description": "Request model for search endpoint.",
"example": {
"agent_id": "user123",
"fact_type": [
"world",
"agent"
@ -1879,11 +1891,6 @@
"type": "string",
"title": "Query"
},
"agent_id": {
"type": "string",
"title": "Agent Id",
"default": "default"
},
"thinking_budget": {
"type": "integer",
"title": "Thinking Budget",
@ -1908,7 +1915,6 @@
"title": "ThinkRequest",
"description": "Request model for think endpoint.",
"example": {
"agent_id": "user123",
"context": "This is for a research paper on AI ethics",
"query": "What do you think about artificial intelligence?",
"thinking_budget": 50

View file

@ -108,6 +108,26 @@ else
print_warn "File $CONTROL_PLANE_PKG not found, skipping"
fi
# Update Python API client
PYTHON_CLIENT_PKG="memora-clients/python/pyproject.toml"
if [ -f "$PYTHON_CLIENT_PKG" ]; then
print_info "Updating $PYTHON_CLIENT_PKG"
sed -i.bak "s/^version = \".*\"/version = \"$VERSION\"/" "$PYTHON_CLIENT_PKG"
rm "${PYTHON_CLIENT_PKG}.bak"
else
print_warn "File $PYTHON_CLIENT_PKG not found, skipping"
fi
# Update TypeScript API client
TYPESCRIPT_CLIENT_PKG="memora-clients/typescript/package.json"
if [ -f "$TYPESCRIPT_CLIENT_PKG" ]; then
print_info "Updating $TYPESCRIPT_CLIENT_PKG"
sed -i.bak "s/\"version\": \".*\"/\"version\": \"$VERSION\"/" "$TYPESCRIPT_CLIENT_PKG"
rm "${TYPESCRIPT_CLIENT_PKG}.bak"
else
print_warn "File $TYPESCRIPT_CLIENT_PKG not found, skipping"
fi
# Show changes
print_info "Changes to be committed:"
git diff
@ -129,6 +149,8 @@ git commit -m "Release v$VERSION
- Update version to $VERSION in all components
- Python packages: memora, memora-dev, memora-dev/benchmarks
- Python client: memora-clients/python
- TypeScript client: memora-clients/typescript
- Rust CLI: memora-cli
- Control Plane: memora-control-plane
- Helm chart"