Skip to main content
ThinkEx provides a comprehensive set of AI tools that enable the assistant to interact with your workspace, search the web, process files, and more.

Tool Factory

Tools are created using the createChatTools factory function:
import { createChatTools } from "@/lib/ai/tools";

const tools = createChatTools({
  workspaceId: "uuid",
  userId: "uuid",
  activeFolderId: "uuid",
  threadId: "uuid",
  clientTools: {}, // Frontend tools
  enableDeepResearch: false,
});

Workspace Tools

createNote

Create a new note card in the workspace.
title
string
required
The title of the note card
content
string
required
The markdown body content. DO NOT repeat title in content. Start with subheadings/text.
sources
array
Optional sources from web search or deep research
Example Usage:
await createNote({
  title: "Photosynthesis Overview",
  content: "## Process\n\nPhotosynthesis converts light energy...",
  sources: [{
    title: "Biology Textbook",
    url: "https://example.com/biology",
  }]
});

updateNote

Update an existing note with targeted edits or full rewrite.
noteName
string
required
The name of the note to update (fuzzy matched)
oldString
string
required
Text to find. Use '' for full rewrite. For targeted edit: exact text from readWorkspace Content section.
newString
string
required
Replacement text (entire note if oldString is empty)
replaceAll
boolean
default:false
Replace every occurrence of oldString; use for renaming or changing repeated text
title
string
New title for the note. If not provided, existing title is preserved.
Example Usage:
// Full rewrite
await updateNote({
  noteName: "My Note",
  oldString: "",
  newString: "# New Content\n\nCompletely new note body..."
});

// Targeted edit
await updateNote({
  noteName: "My Note",
  oldString: "old section content",
  newString: "updated section content"
});

deleteItem

Permanently delete a card/note from the workspace by name.
itemName
string
required
Item name or virtual path (e.g., pdfs/Report.pdf) to delete

selectCards

Select cards by their titles and add them to conversation context.
cardTitles
array
required
Array of card titles to search for and select
Response:
success
boolean
Whether the operation succeeded
addedCount
number
Number of cards successfully selected
message
string
Descriptive message about the selection result

Flashcard Tools

createFlashcards

Create a new flashcard deck.
title
string
The title of the flashcard deck (defaults to ‘Flashcard Deck’ if not provided)
cards
array
required
Array of flashcard objects, each with ‘front’ and ‘back’ properties (minimum 1 card)
Example Usage:
await createFlashcards({
  title: "Spanish Vocabulary",
  cards: [
    { front: "Hello", back: "Hola" },
    { front: "Goodbye", back: "Adiós" },
    { front: "Thank you", back: "Gracias" },
  ]
});

updateFlashcards

Add more flashcards to an existing flashcard deck and/or update its title.
deckName
string
required
The name or ID of the flashcard deck to update
cards
array
Array of flashcard objects to add
title
string
New title for the flashcard deck

Quiz Tools

createQuiz

Create an interactive quiz. Extract topic from user message. Use selected cards as context if available.
topic
string
The topic or specific focus instructions for the quiz - extract from user’s message
contextContent
string
Content from selected cards in system context if available
questionCount
number
default:5
The specific number of questions requested by the user (1-50)
sourceCardIds
array
IDs of source cards
sourceCardNames
array
Names of source cards
Example Usage:
await createQuiz({
  topic: "Linear Algebra Basics",
  questionCount: 10,
});

updateQuiz

Update quiz title and/or add more questions. Can use new topic, selected cards, or general knowledge.
quizName
string
required
The name of the quiz to update (fuzzy matched)
title
string
New title for the quiz
topic
string
New topic for questions
contextContent
string
Content from newly selected cards in system context
questionCount
number
Number of questions to add (1-50)

Search & Code Tools

webSearch

Search the web for current information using Google Search with grounding.
query
string
required
The search query to look up on the web (1-500 characters)
Response:
text
string
Synthesized search results with summary and key findings
sources
array
Array of source objects with title and url
groundingMetadata
object
Google grounding metadata with chunks
Example Usage:
const result = await webSearch({
  query: "latest developments in quantum computing 2024"
});

executeCode

Execute Python code for calculations, data processing, algorithms, or mathematical computations.
task
string
required
Description of the task to solve with code
Example Usage:
await executeCode({
  task: "Calculate the fibonacci sequence up to n=20"
});

searchWorkspace

Grep-like text search across workspace content (notes, flashcards, PDFs, quizzes, audio transcripts).
pattern
string
required
Search pattern (plain text or regex) — the term/phrase to find in workspace content
include
string
Filter by item type, e.g., "note", "flashcard", "pdf"
path
string
Virtual path prefix to scope search, e.g., "Physics/" for items under Physics folder
Example Usage:
await searchWorkspace({
  pattern: "photosynthesis",
  include: "note",
  path: "Biology/"
});

readWorkspace

Read content of a workspace item (note, flashcard deck, PDF summary, quiz) by path or name.
path
string
Virtual path (e.g., Physics/notes/Thermodynamics.md) — unambiguous when duplicates exist
itemName
string
Name for fuzzy match — use when path unknown
lineStart
number
default:1
1-based line number to start from. Use with limit for pagination.
limit
number
default:500
Max lines to return (max 2000). Use with lineStart for pagination.
pageStart
number
For PDFs only: 1-indexed start page (e.g., 5 for page 5)
pageEnd
number
For PDFs only: 1-indexed end page inclusive (e.g., 10 for pages 5–10)
Example Usage:
// Read note
await readWorkspace({
  itemName: "My Study Notes"
});

// Read specific PDF pages
await readWorkspace({
  path: "pdfs/Textbook.pdf",
  pageStart: 10,
  pageEnd: 15
});

File & URL Processing Tools

processFiles

Process and analyze files including PDFs, images, documents, and videos.
urls
array
Array of file/video URLs to process (Supabase storage URLs or YouTube URLs)
fileNames
array
Workspace item names or virtual paths (e.g., "Annual Report" or "pdfs/Annual Report.pdf")
pdfImageRefs
array
Images from PDFs — map placeholder names to base64 for analysis
forceReprocess
boolean
default:false
Set to true to bypass cached PDF content and re-analyze the file
Supported File Types:
  • PDFs: Extracted via Azure Document AI OCR (cached after first extraction)
  • Images: JPEG, PNG, GIF, WebP, SVG
  • Videos: YouTube URLs (native Gemini support)
  • Documents: DOC, DOCX, TXT
Example Usage:
// Process workspace files
await processFiles({
  fileNames: ["Research Paper", "Lecture Slides"]
});

// Process external URLs
await processFiles({
  urls: [
    "https://storage.supabase.co/...",
    "https://youtube.com/watch?v=..."
  ]
});

// Extract image from PDF
await processFiles({
  pdfImageRefs: [{
    pdfName: "Syllabus",
    imageId: "img-0.jpeg"
  }]
});

processUrls

Analyze web pages using Google’s URL Context API.
jsonInput
string
required
JSON string containing an object with ‘urls’ (array of web URLs).Example: '{"urls": ["https://example.com"]}'
Features:
  • Extracts content from regular web URLs (http/https)
  • Supports up to 20 URLs per request
  • Automatically falls back between scraping methods
  • Returns analyzed content with sources
Example Usage:
await processUrls({
  jsonInput: JSON.stringify({
    urls: [
      "https://en.wikipedia.org/wiki/Machine_learning",
      "https://blog.example.com/ai-trends"
    ]
  })
});

YouTube Tools

searchYoutube

Search for YouTube videos.
query
string
required
The search query for YouTube videos
Response:
success
boolean
Whether the search succeeded
videos
array
Array of video objects with id, title, thumbnail, etc.

addYoutubeVideo

Add a YouTube video to the workspace.
videoId
string
required
The YouTube Video ID (not the full URL)
title
string
required
The title of the video
Example Usage:
await addYoutubeVideo({
  videoId: "dQw4w9WgXcQ",
  title: "Introduction to Neural Networks"
});

Tool Context

All workspace tools receive a shared context:
export interface WorkspaceToolContext {
  workspaceId: string | null;    // Current workspace UUID
  userId: string | null;          // Authenticated user UUID
  activeFolderId?: string;        // Active folder UUID
  threadId?: string | null;       // Conversation thread UUID
}
This context provides:
  • Security: Ensures user has access to workspace
  • Scoping: Operations limited to current workspace
  • Context: Tools can reference active folder for new items

Error Handling

All tools return consistent error structures:
{
  success: false,
  message: "Descriptive error message",
  // Additional context fields
}
Common error scenarios:
  • Item not found: Suggests available items or paths
  • No workspace context: User must be in a workspace
  • Permission denied: User lacks access to workspace
  • Invalid input: Validation error with requirements

Build docs developers (and LLMs) love