| name | Calc Support from LibreCalc AI |
|---|---|
| overview | Calc support (chat/tools) is now implemented in WriterAgent, reusing and adapting the in-process Calc UNO layer, tool set, and error detector from libre_calc_ai-1.0.2. |
| status | COMPLETE (Feb 2026) |
| todos | |
| isProject | false |
Calc support (chat/tools) is now fully integrated into WriterAgent. We have reused the following components from libre_calc_ai-1.0.2 in-process, translated and adapted for WriterAgent's architecture.
All planned modules are implemented in core/ and integrated into the Chat Sidebar and LibreOffice Menu.
- Core Calc Logic: Ported and translated
calc_bridge.py,calc_address_utils.py,calc_inspector.py,calc_sheet_analyzer.py,calc_error_detector.py, andcalc_manipulator.py. - AI Toolset:
CALC_TOOLSincore/calc_tools.py(read ranges, write formulas, format, merge, sheet management, chart creation, detect_and_explain_errors). - Dynamic Tool Loading:
panel.pydetects document type and switches betweenWRITER_TOOLSandCALC_TOOLS. - Calc Chat Context:
get_calc_context_for_chat(model, max_context, ctx)incore/document.pyprovides a summary of the active sheet and selection. Requiresctx(component context); callers pass it from the panel or MainJob so we never useuno.getComponentContext()in this path. - Robust prompt selection:
get_chat_system_prompt_for_document(model, additional_instructions)inplugin/framework/prompts.pyis the single source of truth for the chat system prompt. It returnsDEFAULT_CALC_CHAT_SYSTEM_PROMPTfor Calc andDEFAULT_CHAT_SYSTEM_PROMPTfor Writer, so Writer/Calc prompts cannot be mixed. Used bypanel.pyandmain.pyfor both sidebar and menu Chat. - Calc System Prompt:
DEFAULT_CALC_CHAT_SYSTEM_PROMPTinplugin/framework/prompts.pystates semicolon formula syntax, a 4-step workflow (understand → get state if needed → use tools → short confirmation), and tools grouped by use (READ / WRITE & FORMAT / SHEET MANAGEMENT / CHART / ERRORS). Structure inspired by libre_calc_aiprompt_templates.py(workflow, grouped tools, “do not explain—do the operation”). - Menu: "Chat with Document" for Calc in
main.py(streams response to "AI Response" sheet; uses same prompt helper andctxfor context). - Tests:
tests/test_calc_address_utils.pyandcore/calc_tests.py.
Do not use: Their socket/pipe connect() and BridgeServer/BridgeClient.
Use: The same abstraction they use when running inside LO: get document/sheet/cell from the current component context.
- Source: CalcAI/core/uno_bridge.py (lines 155–217 and helpers).
- Status: IMPLEMENTED in
core/calc_bridge.py. - How it works: Uses
XSCRIPTCONTEXTorofficehelper.bootstrap()to get the UNO context. Exposesget_active_document(),get_active_sheet(), etc.
Source: CalcAI/core/address_utils.py
- Status: IMPLEMENTED in
core/calc_address_utils.py. - Action: Pure Python address handling for A1/range parsing.
Source: CalcAI/core/cell_inspector.py
- Status: IMPLEMENTED in
core/calc_inspector.py. - Action: Ported all analytical methods and translated Turkish comments/docstrings.
Source: CalcAI/core/sheet_analyzer.py
- Status: IMPLEMENTED in
core/calc_sheet_analyzer.py. - Action: Used to build the AI context in
core/document.py:get_calc_context_for_chat().
Source: CalcAI/core/error_detector.py
- Status: IMPLEMENTED in
core/calc_error_detector.py. - Action: Full error code mapping ported and translated. Exposed as
detect_and_explain_errorstool.
Source: CalcAI/core/cell_manipulator.py
- Status: IMPLEMENTED in
core/calc_manipulator.py. - Action: Tier 1 and 2 methods implemented. Added Tier 3
create_chartsupport.
Source: CalcAI/llm/tool_definitions.py
- Status: IMPLEMENTED in
core/calc_tools.py. - Action: Defined
CALC_TOOLSandexecute_calc_tooldispatcher. Integrated withpanel.pyandmain.py.
Source: CalcAI/llm/prompt_templates.py
- Status: IMPLEMENTED in plugin/framework/prompts.py.
- Implementation:
DEFAULT_CALC_CHAT_SYSTEM_PROMPTplusget_chat_system_prompt_for_document(model, additional_instructions)so the correct prompt is chosen by document type (Calc vs Writer). The Calc prompt includes:- “Do not explain—do the operation directly using tools” and “Perform as many steps as needed in one turn when possible.”
- A 4-step WORKFLOW: understand → get state (get_sheet_summary/read_cell_range) if needed → use tools → short confirmation (mention cell/range addresses when changing).
- FORMULA SYNTAX: Semicolon (;) as argument separator; correct vs wrong examples.
- TOOLS grouped by use: READ / WRITE & FORMAT / SHEET MANAGEMENT / CHART / ERRORS (only tools we expose).
- Structure inspired by libre_calc_ai’s prompt_templates (workflow, grouped tools).
Source: interface.py _build_context_func and sheet_analyzer usage.
- Status: IMPLEMENTED in
core/document.py:get_calc_context_for_chat(model, max_context, ctx). - Shape: Builds a string with document URL, active sheet name, used range (rows × columns), column headers, current selection range, and (for small selections) selection content. Uses
SheetAnalyzer.get_sheet_summary()and selection from the controller. - Context parameter:
ctxis required (component context from panel or MainJob). Nouno.getComponentContext()in this path.get_document_context_for_chat(..., ctx=None)requiresctxwhen the document is Calc.
- Entry point: Chat from Calc uses the same sidebar/menu as Writer;
ctxcomes from the UNO component (panel or MainJob). Both passctxintoget_document_context_for_chatso the extension context is always used. - Single process: All Calc code runs in LO’s Python. No BridgeServer, BridgeClient, or subprocess.
- LlmClient: Reuse
plugin/framework/client/llm_client.py(streaming, tool-calling, reasoning). Pass CALC_TOOLS andexecute_calc_toolwhen the active document is a spreadsheet. - UI: Same sidebar (WriterAgent deck) and menu for Writer and Calc; ContextList includes
com.sun.star.sheet.SpreadsheetDocument. Response area + input + Send/Stop. No PyQt5. - Undo: Undo grouping for AI edits is out of scope for now (Writer has the same limitation).
core/
calc_address_utils.py # address_utils (from libre_calc_ai)
calc_bridge.py # thin in-process get_active_document/sheet/cell/selection
calc_inspector.py # CellInspector-style read (read_range, get_cell_details, ...)
calc_sheet_analyzer.py # get_sheet_summary, optional detect_data_regions
calc_error_detector.py # detect_and_explain_errors
calc_manipulator.py # write_formula_range, set_cell_style, merge_cells, sort_range, ...
calc_tools.py # CALC_TOOLS (schemas) + execute_calc_tool / CalcToolDispatcher
Optional: a single Calc facade module that re-exports the public API (get_calc_context, get_sheet_summary, execute_calc_tool, CALC_TOOLS) so chat_panel or a Calc panel only imports from one place.
- interface.py (script entry, subprocess launch, bridge server): Not needed; WriterAgent uses UNO service/sidebar.
- BridgeServer / BridgeClient: Not needed; everything in-process.
- PyQt5 UI (main_window, chat_widget, settings_dialog): Not needed; use LO sidebar/XDL.
- Their config (settings.json, .env, multi-provider): Keep WriterAgent config (writeragent.json, single endpoint); optional env overrides only if you want.
- event_listener.py: Only needed if you want “auto-refresh on document change”; can be added later with UNO listeners in-process.
- Status: DONE. Integrated into
main.pyandpanel.py. - Order of Implementation (Actual):
- Ported and translated core logic (
calc_bridgetocalc_manipulator). - Integrated
get_calc_context_for_chatincore/document.py. - Created
core/calc_tools.pywith schemas and dispatcher. - Updated
panel.pyfor document type detection and tool swapping. - Updated
main.pyfor menu support and response-to-sheet flow. - Added tests in
tests/test_calc_address_utils.pyandcore/calc_tests.py. - Robustness: Added
get_chat_system_prompt_for_document()inplugin/framework/prompts.py; all chat entry points use it so Writer/Calc prompt cannot be mixed. Added requiredctxparameter toget_document_context_for_chatandget_calc_context_for_chat; callers pass component context (nouno.getComponentContext()in this path). - Calc system prompt: Added
DEFAULT_CALC_CHAT_SYSTEM_PROMPTwith workflow, grouped tools, and formula syntax; structure inspired by libre_calc_aiprompt_templates.py. Based on my analysis of your Calc tool-calling API implementation incore/calc_tools.py,core/calc_bridge.py,core/calc_manipulator.py,core/calc_inspector.py,core/calc_sheet_analyzer.py,core/calc_error_detector.py, and related files, I'll summarize what's currently implemented and suggest targeted improvements to make it better, more robust, and more capable.
- Ported and translated core logic (
- Comprehensive coverage: You have a solid foundation covering most common Calc operations (reading, writing, formatting,_sheet management, charts, error detection, sorting, clearing).
- Modular architecture: Clean separation of concerns (
Bridgefor low-level UNO,Inspectorfor reading,Manipulatorfor writing,Analyzerfor structure,Detectorfor errors). - Context-aware system prompt: The
DEFAULT_CALC_CHAT_SYSTEM_PROMPTinplugin/framework/prompts.pyeffectively guides the AI to use tools properly, reminds about semicolon syntax, and structures workflow (understand → read → use tools → confirm). - Performance optimizations: Persistent HTTP connections, global shared instances for tools (avoiding recreation per call), and batch-friendly logic in many places.
- Error handling:
format_error_for_displayfor user-friendly messages, detailed error explanations inErrorDetector, and exception catching throughout. - Calc-specific context:
get_calc_context_for_chatprovides basic sheet summary (name, range, headers, selection), which is a good start for relevant context without overwhelming tokens.
Your current 11 tools cover the essentials, but expanding to more advanced operations would make the AI more powerful. Prioritized additions:
-
Data Analysis Tools:
add_auto_filter(range_str, has_header=True): Enable/disable filters on ranges (building on your existingset_auto_filterlogic inCellManipulator).start_data_pivot(range_str, target_cell): Create pivot tables with drag-and-drop configuration (target_cell for where to place the pivot).apply_conditional_formatting(range_str, rule_type, condition, style): Add color scales, icon sets, or data bars (e.g., rule_type="color_scale", condition="values_above_threshold", style={"min_color": "#FFA500"}).
-
Advanced Manipulation:
insert_columns(position, count=1)andinsert_rows(position, count=1): Already inCellManipulator, but add toCALC_TOOLSschema for AI access.delete_columns(col_letter, count=1)anddelete_rows(row_num, count=1): Also already implemented—expose them.set_column_width(col, width_mm)andset_row_height(row, height_mm): InCellManipulatorbut not exposed.auto_fit_columns(range_str): Analogous to existingauto_fit_column, but ranged.copy_paste_range(source_range, target_cell, operation="copy"|"cut"): Extend copy_range for cut/paste.import_csv(file_path, delimiter, target_cell)andexport_csv(range_str, file_path): For data import/export.
-
Validation and Advanced Formatting:
add_data_validation(range_str, type, condition): E.g., "list", "whole_number", "date" with min/max/conditions.group_rows(range_str)/ungroup_rows: For outlining collapsible groups.freeze_panes(row, col): Freeze/split panes at specific row/column.
-
Statistical/Business Analysis:
calculate_statistics(range_str): Mean, median, std dev, quartiles, etc., above your column-levelcolumn_statistics.create_custom_chart(type, data, labels, axes_customization): Extend yourcreate_chartwith more options (e.g., multi-axis, stacked).
Implementation Notes: Most of these build directly on your existing CellManipulator and CalcBridge classes. For new complex features like pivots/charts, leverage LibreOffice's API (e.g., DatabaseRange for filters/pivots, XChartDocument for advanced charting). Expose them in CALC_TOOLS with clear schemas (e.g., enum-validation for types).
-
Smarter Parameters and Defaults:
- For tools like
sort_range, add optionalorientation="rows"(default) or"columns"(sort by rows). - For
create_chart, enhance to support primary/secondary axes and custom colors. - Add response details: After
write_formula_range, include the computed result (e.g., "Total: 123.45" if it's a formula).
- For tools like
-
Composited/Batch Tools: Reduce tool-call chain length for common workflows.
create_table(range_str, headers_list, has_borders=True): Combinewrite_formula_rangefor headers,set_cell_stylefor borders,merge_cellsfor multi-column headers.format_range(range_str, preset="header"|"data"|"total"): Apply predefined style combos (e.g., header=bold+centered, total=bold+border).
-
Better Error Recovery:
- Tools should validate inputs (e.g., check if range exists before operations) and provide actionable feedback.
- Add
undo_last_tool()orrevert_range(range_str)using LibreOffice's undo API (model'sXUndoManager).
-
Richer Document Context (
get_calc_context_for_chat):- Include a small preview of data (first 5-10 rows of used range) for AI understanding—analogous to Writer's excerpts.
- Add sheet-level summary: % of empty cells, data types (numeric/text/formula ratios), last modified regions.
- Track "working memory": In the chat panel, cache last 3 operations (e.g., "Wrote formulas in A1:A5") and include in context.
-
Tool History Integration: The AI forgets intermediate steps; enhance prompts to remind the AI of multi-step plans (e.g., "Don't forget to merge headers after writing them.").
- Validation Layer: Before executing tools, validate ranges (e.g., via
SheetAnalyzer.detect_data_regions()to ensure the range is coherent). - Unsafe Operations: For destructive tools like
clear_range, require confirmation (addconfirm=Trueparameter, defaulting to True for safety). - Fallbacks: If a visual operation fails (e.g., chart creation due to no data), explain why and suggest alternatives instead of just throwing.
- Cross-Session State: Your global
_get_toolsinstances are good, but add loading/saving of sheet state for resumed sessions.
- Lazy Reading: For large ranges,
read_cell_rangeshould page results or sample (e.g., max 1000 cells; warn if truncated). - Bulk Operations: Already covered by
write_formula_range, which commits a whole range in onesetDataArraycall; prefer it over per-cell writes in loops. - Caching: Cache sheet summaries and headers for 30s to avoid redundant UNO calls in rapid tool chains.
- Sheet-Level Locking: For multi-user scenarios (rare in Calc), use
XSheetOperation.lockRange()during tool execution. - Extension Compatibility: Test with Calc add-ins (e.g., ensure your tools work alongside statistical extensions).
- Localization: Your error messages assume English; make them locale-aware if expanding.
- Prioritize and Prototype: Start with easy wins like exposing
insert_rows/columnsandset_column_width(already coded). Then pivot tables, as they're common requests. - Update
CALC_TOOLSSchema: Ensure new tools have detailed descriptions and examples in schemas for better AI usage. - Test Thoroughly: Use your existing
calc_tests.pyand add scenarios for edge cases (merged cells, weird ranges). - System Prompt Refinement: Update
DEFAULT_CALC_CHAT_SYSTEM_PROMPTto include instructions for new tools (e.g., "Use insert_rows/delete_columns for structure changes."). - Metrics and Logging: Add
agent_logcalls in new tools for debugging (e.g., log successful range operations with sizes).
Goal: Address inefficiencies in handling large datasets and multi-cell formatting. Reduces AI tool-call overhead for common tasks.
Completed/Fixed:
- Fixed
set_cell_styleto properly handle range formatting (single method now detects ranges and delegates toset_range_style). No more one-by-one AI calls for ranges. - Range number formats now apply to entire range (new
set_range_number_formatmethod). - Exposed
delete_rows,delete_columns(backend methods existed; now full tools). Insert tools removed as CSV import provides better bulk data insertion. - Added
write_formula_rangetool: Efficiently writes formulas or values to ranges. Accepts single value for entire range or array for individual cells. - Enhanced
write_formula_rangetool: Parses CSV string (e.g., "Name,Age\nAlice,30\nBob,25") and bulk-inserts into sheet starting at a cell. No file I/O required—ideal for AI-generated or pasted data. - The method handles text/number detection automatically, supports custom delimiters (',', ';', etc.), and provides error handling for malformed CSV.
- Updated
DEFAULT_CALC_CHAT_SYSTEM_PROMPTto reference new tools: "Usewrite_formula_rangefor bulk writes or bulk CSV data inserts.set_cell_styleworks on ranges (e.g. 'A1:D10') for efficient formatting."
Next Steps (Future Enhancements):
- Enhance
read_cell_rangewith paging (e.g.,max_cells: intparameter, warn if truncated) for large ranges.
Overall, your implementation is already quite capable—users can perform table creation, calculations, formatting, and charts. These enhancements would elevate it to handle complex data analysis and formatting tasks, making the AI assistant more proactive and less error-prone. If you'd like assistance implementing specific tools or testing, let me know!