Introduction
Welcome to the Expensabl documentation! Expensabl is an expense management automation tool living right in your browser.
What is Expensabl?
Expensabl is a Chrome extension designed to automate expense management on the Navan platform. It streamlines the expense creation process by eliminating manual data entry and providing intelligent automation features.
Core Capabilities
- Automatic Token Capture: Seamlessly captures authentication tokens when you log into Navan
- Smart Templates: Create reusable templates for recurring expenses with variable substitution
- Scheduled Automation: Set up recurring expenses that create themselves automatically
- Persistent Side Panel: Always-available interface that stays open across browser tabs
- Enterprise-Ready: Built with security, reliability, and performance in mind
Architecture Overview
Expensabl follows a layered architecture with clear separation of concerns:
Chrome Extension Layer
- Service Worker: Handles background tasks, message routing, and token capture
- Content Script: Injected into Navan pages for seamless token interception
- Side Panel UI: Persistent interface for expense management
- Message Adapter: Type-safe communication between extension contexts
Features Layer
- Authentication: Secure token management with validation and refresh
- Expenses: Complete expense lifecycle management with retry logic
- Messaging: Robust message routing with handler pattern
- Templates: Sophisticated template engine with scheduling capabilities
Shared Services
- Logger: Environment-aware logging with Chrome storage integration
- Storage: Abstracted Chrome storage with transaction support
- Types: Shared TypeScript interfaces ensuring type safety
Key Benefits
For End Users
- Time Savings: Reduce expense creation time by up to 90% with templates
- Never Forget: Scheduled expenses ensure recurring costs are always captured
- Consistency: Templates ensure expenses follow company policies
- Convenience: Side panel stays open while you work
For Organizations
- Compliance: Consistent expense data following company policies
- Visibility: All expenses captured on time for better financial tracking
- Efficiency: Reduced administrative overhead for expense management
- Integration: Seamless integration with existing Navan workflows
Documentation Structure
This documentation is organized to serve different audiences:
User Guide
Step-by-step instructions for using Expensabl:
- Installation and setup
- Creating and managing expenses
- Working with templates
- Setting up schedules
Developer Guide
Technical documentation for contributors:
- Architecture deep dive
- Development environment setup
- Building and testing
- Contributing guidelines
API Reference
Detailed API documentation:
- Message API for extension communication
- Storage API for data persistence
- Expense API for Navan integration
Getting Started
For Users
- Install the extension from the Chrome Web Store
- Navigate to Navan and sign in
- Open the Expensabl side panel
- Start creating expenses with templates!
For Developers
- Clone the repository
- Install dependencies with
npm install
- Build with
npm run build:dev
- Load unpacked extension in Chrome
For detailed instructions, see the Getting Started guide.
Getting Started
This guide will help you get up and running with Expensabl quickly.
Prerequisites
For Users
- Google Chrome browser (version 119 or later)
- A Navan account with expense creation permissions
For Developers
- Node.js (v16 or higher)
- npm (v7 or higher)
- Git
Installation Options
Option 1: Chrome Web Store (Coming Soon)
- Visit the Chrome Web Store
- Search for "Expensabl"
- Click "Add to Chrome"
- Grant the required permissions
Option 2: Development Build
Clone and Install
# Clone the repository
git clone https://github.com/xtendabl/expensabl.git
cd expensabl
# Install dependencies
npm install
# Build for development (includes source maps)
npm run build:dev
# Or build for production (optimized)
npm run build
Load in Chrome
-
Open Chrome Extension Management
- Navigate to
chrome://extensions/
in your Chrome browser - Or click the puzzle icon in the toolbar → "Manage Extensions"
- Navigate to
-
Enable Developer Mode
- Toggle the "Developer mode" switch in the top right corner
-
Load the Extension
- Click "Load unpacked" button
- Navigate to your
expensabl/dist
directory - Select the folder and click "Open"
-
Verify Installation
- The extension should appear in your extensions list
- Look for the Expensabl icon in your Chrome toolbar
- If not visible, click the puzzle icon and pin Expensabl
First Time Setup
1. Sign in to Navan
- Navigate to app.navan.com
- Sign in with your corporate credentials
- The extension will automatically capture your authentication token
- You'll see a notification when the token is captured successfully
2. Open the Side Panel
There are several ways to access Expensabl:
Method 1: Extension Icon
- Click the Expensabl icon in the Chrome toolbar
- The side panel will open automatically
Method 2: Extensions Menu
- Click the Extensions puzzle icon
- Find Expensabl in the list
- Click "Open side panel"
Method 3: Chrome Menu
- Click the three-dot menu in Chrome
- Go to "More tools" → "Extensions"
- Find Expensabl and click "Open side panel"
3. Initial Configuration
When you first open Expensabl:
- Help Section: Review the built-in help guide
- Permissions: Grant any additional permissions if prompted
- Preferences: Set your default expense preferences
Creating Your First Expense
Manual Creation
- In the side panel, click "Fetch Expenses" to load your recent expenses
- Click "Create New Expense" button
- Fill in the required fields:
- Merchant name
- Amount and currency
- Date
- Category/Policy
- Description (optional)
- Click "Submit Expense"
From a Template
- Navigate to the Templates section
- Click "Apply" on any template
- Review and modify the pre-filled data
- Submit the expense
Development Workflow
If you're developing or customizing Expensabl:
Making Changes
- Edit Source Files: Make changes in the
src/
directory - Rebuild: Run
npm run build:dev
to rebuild with your changes - Reload Extension:
- Go to
chrome://extensions/
- Find Expensabl and click the refresh icon
- Or use
Cmd+R
(Mac) /Ctrl+R
(Windows/Linux) on the extensions page
- Go to
- Test Changes: Open the extension and verify your changes
Available Commands
# Development build with source maps
npm run build:dev
# Production build (optimized)
npm run build
# Watch mode (auto-rebuild on changes)
npm run watch
# Run tests
npm test
# Run tests in watch mode
npm run test:watch
# Fix linting issues
npm run lint:fix
# Fix all formatting
npm run format:fix
# Clean build artifacts
npm run clean
Debugging Tips
Background Service Worker:
- Click "Inspect views: service worker" on the extension card in
chrome://extensions/
- This opens DevTools for background script debugging
Side Panel UI:
- Right-click the extension side panel and select "Inspect"
- This opens DevTools for UI debugging
Content Scripts:
- Open DevTools on any Navan page
- Content script logs appear in the page's console
Troubleshooting
Extension Not Loading
- Ensure you're in Developer Mode
- Check that the
dist/
folder exists and containsmanifest.json
- Try rebuilding with
npm run build:dev
Token Not Captured
- Make sure you're signed into Navan
- Refresh the Navan page after installing the extension
- Check the service worker console for errors
Side Panel Not Opening
- Ensure Chrome version is 119 or later
- Try unpinning and re-pinning the extension
- Restart Chrome if necessary
Next Steps
Now that you have Expensabl running:
- Learn about creating templates for recurring expenses
- Set up scheduled expenses for automation
- Understand authentication and token management
- Explore advanced configuration options
For developers:
- Review the Architecture Overview
- Understand the Project Structure
- Follow the Contributing Guidelines
Installation
Core Activities
This guide explains the three core activities that power Expensabl: Token Interception, Expense Creation, and Scheduled Execution.
Quick Reference
Activity | Trigger | Key Components | Chrome APIs Used |
---|---|---|---|
Token Interception | User login to Navan | Content Script, Service Worker | webRequest, storage |
Expense Creation | Template selection/Manual entry | UI Components, Expense Service | storage, runtime |
Scheduled Execution | Chrome alarms | Scheduler, Template Service | alarms, storage, notifications |
Activity | Prerequisites | Data Flow | Storage Output |
---|---|---|---|
Token Interception | Active Navan session | HTTP Headers → Content Script → Service Worker | Encrypted auth token |
Expense Creation | Valid auth token, Template data | UI → Message Router → API → Storage | Expense record, Template usage stats |
Scheduled Execution | Active template with schedule | Alarm → Service Worker → API | Execution history, Created expense |
Token Interception
The extension automatically captures authentication tokens when users log into Navan, eliminating the need for manual credential entry. This foundational activity enables all other features by establishing secure API access.
How It Works
- Content Script Monitoring: The content script monitors network requests on Navan domains
- Multiple Capture Strategies: Uses various techniques to ensure reliable token capture
- Secure Storage: Tokens are encrypted and stored in Chrome's local storage
- Automatic Validation: Validates captured tokens before storage
Token Capture Flow
graph LR
A[User Login] --> B[Navan Auth]
B --> C[API Call with Token]
C --> D[Content Script Intercepts]
D --> E[Token Captured Message]
E --> F[Service Worker]
F --> G[Encrypted Token]
G --> H[Storage]
Implementation Details
The token capture system employs a multi-layered approach:
- Network Interception: Monitors fetch and XMLHttpRequest calls
- Header Extraction: Captures Authorization headers from API requests
- Validation: Ensures token format is correct before storage
- Refresh Detection: Automatically updates stored tokens when refreshed
Security Considerations
- Tokens are never logged or exposed in console
- All tokens are encrypted before storage
- Token scope is limited to expense operations
- Automatic cleanup of expired tokens
Expenses and Templates
The expense and template system forms the core of user interaction, enabling both one-time expense creation and reusable template management.
Bi-directional Workflow
Users can:
- Create expenses from templates: Apply saved templates to quickly create new expenses
- Convert expenses to templates: Save any expense as a template for future use
Template Features
Template Storage
- Essential expense information without transaction-specific details
- Usage statistics and execution history tracking
- Support for variable substitution (e.g.,
{month}
,{year}
) - 5-template limit per user for optimal performance
Template Management
- Create: Save new templates from scratch or existing expenses
- Edit: In-place editing with validation
- Apply: Generate expenses with pre-filled data
- Delete: Remove unused templates with confirmation
Real-World Use Cases
Weekly Team Lunch Template
Name: "Friday Team Lunch"
Merchant: "Local Bistro"
Amount: $125.00
Category: "Meals - Team"
Schedule: Weekly (Fridays)
Notes: "Weekly team building lunch"
Monthly Software Subscription
Name: "Design Software License"
Merchant: "Adobe Creative Cloud"
Amount: $52.99
Category: "Software - Subscription"
Schedule: Monthly (1st of month)
Project: "Marketing Dept"
Client Entertainment Template
Name: "Client Dinner Template"
Merchant: "[To be filled]"
Amount: $200.00
Category: "Entertainment - Client"
Schedule: Manual (no automation)
Notes: "Standard client dinner budget"
Template Data Lifecycle
- Creation: User defines template parameters
- Storage: Template saved to Chrome sync storage
- Usage: Template applied to create expenses
- Updates: Usage count and last-used timestamp updated
- Sync: Templates synchronized across devices
Scheduled Executions
Scheduled executions transform manual expense entry into an automated workflow, leveraging Chrome's alarm API to create expenses at predetermined intervals.
Supported Schedule Types
- Daily: Every day at a specific time
- Weekly: Specific day(s) of the week
- Monthly: Specific day of the month
- Custom: User-defined intervals
Scheduling Timeline Example
gantt
title Template Execution Timeline
dateFormat YYYY-MM-DD
axisFormat %b %d
section Daily Template
Parking (9 AM) :active, d1, 2025-01-06, 1d
Parking (9 AM) :active, d2, 2025-01-07, 1d
Parking (9 AM) :active, d3, 2025-01-08, 1d
Parking (9 AM) :active, d4, 2025-01-09, 1d
Parking (9 AM) :active, d5, 2025-01-10, 1d
section Weekly Template
Team Lunch (Fri) :active, w1, 2025-01-10, 1d
Team Lunch (Fri) :active, w2, 2025-01-17, 1d
section Monthly Template
Software (1st) :active, m1, 2025-01-01, 1d
Software (1st) :active, m2, 2025-02-01, 1d
Chrome Alarm Configuration
The scheduling engine:
- Calculates optimal execution times based on user timezone
- Persists across browser restarts
- Monitors execution history for failure detection
- Supports pause/resume functionality
Execution Process
- Alarm Trigger: Chrome alarm fires at scheduled time
- Template Retrieval: Fetch template data from storage
- Variable Substitution: Replace placeholders with current values
- Expense Creation: Submit expense via API
- History Update: Log execution result
- Next Schedule: Calculate and set next execution time
Error Handling
- Retry Logic: Automatic retry on network failures
- Notification: User notified of persistent failures
- Fallback: Manual intervention option for critical expenses
- Recovery: Automatic recovery after connection restored
Real-World Scheduling Examples
Daily Parking Expense
Template: "Office Parking"
Amount: $15.00
Schedule: Daily (Weekdays only)
Time: 9:00 AM
Auto-submit: Yes
Note: Automatically creates parking expenses for work days
Bi-weekly Client Dinner
Template: "Client Entertainment - Dinner"
Amount: $250.00
Schedule: Every 2 weeks (Thursday)
Time: 6:00 PM
Auto-submit: No (requires receipt)
Note: Reminder for regular client relationship building
Integration Points
Service Worker
- Central hub for all background operations
- Manages alarms and scheduled executions
- Handles API communication
- Processes messages between contexts
Content Script
- Injected into Navan pages
- Monitors for authentication tokens
- Minimal footprint for performance
Side Panel UI
- User interface for all interactions
- Real-time updates via message passing
- Template and schedule management
- Expense review and submission
Best Practices
For Token Management
- Let the extension handle token capture automatically
- Don't manually enter tokens
- Sign out and back in if token issues occur
For Templates
- Use descriptive names for easy identification
- Include variable placeholders for dynamic content
- Review and update templates periodically
- Delete unused templates to stay under the limit
For Scheduling
- Set schedules based on your timezone
- Use appropriate frequencies for expense types
- Monitor execution history regularly
- Pause schedules during vacations or breaks
Troubleshooting
Token Not Captured
- Ensure you're signed into Navan
- Refresh the page after extension installation
- Check service worker logs for errors
- Try signing out and back in
Template Not Saving
- Check template limit (max 5)
- Verify all required fields are filled
- Ensure Chrome sync is enabled
- Check storage quota in Chrome
Schedule Not Executing
- Verify Chrome is running at scheduled time
- Check alarm permissions in manifest
- Review execution history for errors
- Ensure template is not paused
Configuration
Usage
Authentication
Creating Expenses
Templates
Scheduling
Architecture Overview
Project Structure
This guide provides a comprehensive overview of the Expensabl project structure, explaining how different components fit together to create a cohesive Chrome extension.
Directory Overview
expensabl/
├── src/ # Source code
│ ├── chrome/ # Chrome extension layer
│ ├── features/ # Core business logic
│ └── shared/ # Shared services and utilities
├── public/ # Static assets
├── docs/ # Documentation
├── dist/ # Build output (generated)
├── tests/ # Test files
└── [config files] # Configuration files
Chrome Extension Layer (src/chrome/
)
The Chrome extension layer serves as the primary interface between users and the expense management system. It handles all UI rendering, user interactions, and communication with Chrome's extension APIs.
Directory | Purpose | How It Fits Into The System |
---|---|---|
components/ | Reusable UI components | Provides the building blocks for the extension's user interface, implementing a component-based architecture that ensures consistent look and feel across all views. These components handle user interactions and communicate with the background service worker through the messaging system. |
domains/expenses/ | Expense-specific UI domain | Acts as the presentation layer for expense management, maintaining local UI state and orchestrating the display of expense data. It bridges the gap between raw expense data from the features layer and the visual components users interact with. |
shared/ | Shared UI services | Provides critical infrastructure for UI operations including state management for reactive updates and a messaging facade that abstracts Chrome's extension messaging API. This layer ensures UI components can communicate with background services without knowing implementation details. |
builders/ | UI content builders | Dynamically generates UI content based on user context and application state, reducing the need for static templates. This approach allows for more flexible and maintainable UI generation, particularly for help content and dynamic forms. |
Root files | Extension entry points | These files serve as the primary integration points with Chrome's extension APIs. The service worker handles background tasks and API calls, the content script injects functionality into web pages, and the sidepanel provides the main user interface for expense management. |
Key Files in Chrome Layer
- service-worker.ts: Background script handling message routing and token capture
- content.ts: Injected into Navan pages for token interception
- sidepanel.ts: Main UI entry point for the side panel
- message-adapter.ts: Type-safe messaging wrapper
Features - Core Business Logic (src/features/
)
The features directory implements Domain-Driven Design principles, organizing code by business capability rather than technical layers. Each subdomain encapsulates its complete business logic, making the system more maintainable and scalable.
Directory | Purpose | How It Fits Into The System |
---|---|---|
auth/ | Authentication management | Manages the complete authentication lifecycle including token storage, validation, and refresh. It ensures secure access to the expense API and maintains user sessions across browser restarts, acting as the gatekeeper for all authenticated operations. |
expenses/ | Expense domain logic | The heart of the application's business logic, handling all expense-related operations from creation to submission. It includes sophisticated data transformation layers, retry mechanisms for network failures, and maintains consistency between local and remote expense data. |
messaging/ | Message routing system | Implements a robust message-based architecture that enables communication between different extension contexts (content script, service worker, sidepanel). It uses a handler pattern with type safety to ensure reliable command execution and response handling across the extension. |
templates/ | Template management | Enables expense automation through reusable templates with sophisticated scheduling capabilities. This module handles complex time calculations, validates scheduling rules, and integrates with the expense creation system to automatically generate expenses based on user-defined patterns. |
Feature Module Structure
Each feature module typically contains:
- types.ts: TypeScript interfaces and types
- service.ts: Business logic implementation
- repository.ts: Data access layer
- handlers/: Message handlers for the module
- utils.ts: Helper functions specific to the feature
Shared Services (src/shared/
)
The shared services layer provides cross-cutting concerns and utilities used throughout the application. These services abstract complex operations and provide consistent interfaces for common functionality.
Directory | Purpose | How It Fits Into The System |
---|---|---|
services/logger/ | Logging infrastructure | Provides environment-aware logging that adapts between development and production modes. It integrates with Chrome's storage API to persist logs for debugging while respecting performance constraints, making it easier to diagnose issues in production. |
services/storage/ | Storage abstraction | Abstracts Chrome's storage APIs behind a consistent interface, supporting both synchronous and asynchronous operations. It includes transaction support for atomic updates and caching mechanisms to improve performance while maintaining data consistency. |
types/ | Common type definitions | Establishes the contract between different parts of the system through shared TypeScript interfaces. This ensures type safety across module boundaries and makes refactoring safer by catching breaking changes at compile time. |
Shared Service Patterns
- Singleton Pattern: Services export pre-configured instances
- Adapter Pattern: Abstract Chrome APIs behind consistent interfaces
- Factory Pattern: Create context-specific service instances
Public Assets (public/
)
Contains all static resources required by the Chrome extension, including visual assets and the manifest that defines the extension's capabilities.
Directory/File | Purpose | How It Fits Into The System |
---|---|---|
icons/ | Extension icons | Provides visual identity for the extension across different Chrome UI surfaces, following Google's design guidelines for extensions. Multiple sizes ensure crisp display on various screen densities. |
manifest.json | Chrome extension manifest | Defines the extension's capabilities, permissions, and integration points with Chrome. This configuration determines what APIs the extension can access and how it appears to users in the Chrome Web Store and browser UI. |
Manifest V3 Permissions
Key permissions required:
- storage: Store user data and preferences
- tabs: Access tab information
- activeTab: Interact with active tab
- sidePanel: Display side panel UI
- webRequest: Monitor network requests
- notifications: Show system notifications
- alarms: Schedule recurring tasks
- host permission:
https://app.navan.com/*
Documentation (docs/
)
Project documentation that helps maintain consistency and knowledge sharing across the development team.
Content | Purpose | How It Fits Into The System |
---|---|---|
src/ | Source documentation | Contains the mdBook source files including guides, API references, and architectural documentation. These files are compiled into the static documentation site. |
book/ | Built documentation | The compiled static site generated from the source files. This can be served locally or deployed to GitHub Pages for easy access by team members and users. |
Configuration Files
Root-level configuration files that define how the project is built, tested, and maintained.
File | Purpose | How It Fits Into The System |
---|---|---|
webpack.config.js | Build configuration | Orchestrates the build process, handling TypeScript compilation, code splitting for different extension contexts, and optimization for production. It ensures the extension loads quickly while maintaining development ergonomics. |
jest.config.js | Test configuration | Configures the testing environment to work with Chrome extension APIs and TypeScript. It sets up mocks for browser APIs and ensures tests run in an environment that closely matches the extension's runtime. |
tsconfig.json | TypeScript configuration | Defines compilation rules and module resolution strategies that enable clean imports and strong type checking. The path aliases defined here improve code organization and make imports more maintainable. |
package.json | Dependencies and scripts | Central configuration for the project's dependencies and automation scripts. It defines the project's external dependencies carefully chosen for bundle size and compatibility with the extension environment. |
Build Output (dist/
)
Generated during the build process, this directory contains:
- manifest.json: Processed extension manifest
- service-worker.js: Bundled background script
- content.js: Bundled content script
- sidepanel.html: Side panel HTML entry
- sidepanel.js: Bundled side panel code
- assets/: Icons and other static resources
Development Patterns
Message Flow
graph LR
A[User Action] --> B[UI Component]
B --> C[Message]
C --> D[Router]
D --> E[Handler]
E --> F[Service]
F --> G[Storage/API]
G --> H[Response]
H --> I[UI Update]
Data Flow
graph LR
A[Navan API] --> B[Token Capture]
B --> C[Storage]
C --> D[Template/Expense Service]
D --> E[UI]
E --> F[User Action]
F --> G[Chrome Sync]
G --> C
Module Dependencies
- UI layer depends on features and shared services
- Features depend on shared services
- Shared services have no dependencies on other layers
- All layers use shared types
Best Practices
Code Organization
- Keep related code together in feature modules
- Use index.ts files for clean exports
- Separate types from implementation
- Follow consistent naming conventions
Dependency Management
- Minimize external dependencies
- Use path aliases for clean imports
- Avoid circular dependencies
- Keep bundle size small
Testing Structure
- Mirror source structure in tests
- Unit tests next to source files
- Integration tests in separate directory
- Mock Chrome APIs consistently
Documentation
- Keep docs close to code
- Update docs with code changes
- Use JSDoc for complex functions
- Maintain architectural decision records
Development Setup
Building and Testing
Contributing
Message API
Storage API
Expense API
JSON Data Structures Reference
This document provides a comprehensive reference for all JSON data structures used in the Expensabl Chrome extension, with examples of actual objects and their relationships.
Table of Contents
- Expense Data Structures
- Template Data Structures
- Authentication Structures
- Message Types
- Storage Structures
- Error Structures
Expense Data Structures
ExpenseCreatePayload - Request to Create New Expense
{
"merchant": "Office Depot",
"amount": 45.99,
"currency": "USD",
"date": "2025-08-01",
"policy": "OFFICE_SUPPLIES",
"description": "Printer paper and pens for Q3",
"project": "Marketing-2025",
"customFields": {
"costCenter": "MKT-100",
"clientCode": "INTERNAL"
}
}
Expense - Full Expense Object
{
"uuid": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"dateCreated": "2025-08-01T14:30:00.000Z",
"dateModified": "2025-08-01T14:45:00.000Z",
"dateSubmitted": null,
"dateApproved": null,
"status": "DRAFT",
"source": "MANUAL",
"user": {
"uuid": "user-123",
"email": "user@company.com",
"givenName": "John",
"familyName": "Doe",
"fullName": "John Doe"
},
"merchant": {
"uuid": "merchant-456",
"name": "Office Depot",
"category": "office_supplies_and_stationery",
"categoryGroup": "OFFICE_SUPPLIES",
"logo": "https://example.com/logos/office-depot.png"
},
"amount": 45.99,
"currency": "USD",
"accountAmount": 45.99,
"accountCurrency": "USD",
"merchantAmount": 45.99,
"merchantCurrency": "USD",
"date": "2025-08-01",
"instant": "2025-08-01T14:30:00.000Z",
"policy": "OFFICE_SUPPLIES",
"policyName": "Office Supplies",
"details": {
"description": "Printer paper and pens for Q3",
"project": "Marketing-2025",
"participants": ["user-123"],
"customFieldValues": [
{
"fieldId": "field-1",
"fieldName": "Cost Center",
"value": "MKT-100"
}
],
"glCode": {
"uuid": "gl-789",
"number": "6100",
"name": "Office Supplies"
}
},
"receiptRequired": false,
"receiptKey": null,
"flagged": false,
"flag": {
"status": null,
"reasons": {},
"reasonList": []
},
"reimbursementMethod": "PAYROLL",
"reportingData": {
"department": "Marketing",
"billTo": "Corporate",
"region": "North America"
}
}
ExpenseListResponse - Paginated Expense List
{
"expenses": [
{
"uuid": "expense-1",
"merchant": "Starbucks",
"amount": 12.50,
"date": "2025-08-01",
"status": "APPROVED"
},
{
"uuid": "expense-2",
"merchant": "Uber",
"amount": 28.75,
"date": "2025-07-31",
"status": "PENDING"
}
],
"total": 156,
"page": 1,
"pageSize": 20,
"hasMore": true
}
SearchTransaction - Search Result Item
{
"uuid": "txn-123",
"type": "expense",
"merchantName": "Amazon",
"amount": 89.99,
"currency": "USD",
"date": "2025-08-01",
"status": "DRAFT",
"policyName": "Technology",
"description": "USB-C adapters",
"highlightedFields": {
"merchantName": "<em>Amazon</em> Web Services"
}
}
Template Data Structures
ExpenseTemplate - Complete Template Object
{
"id": "template-123",
"name": "Monthly Phone Bill",
"description": "Verizon monthly service charge",
"createdAt": "2025-07-01T10:00:00.000Z",
"lastModified": "2025-08-01T14:30:00.000Z",
"metadata": {
"usageCount": 7,
"lastUsed": "2025-08-01T09:00:00.000Z",
"isFavorite": true,
"tags": ["recurring", "utilities"],
"version": 1
},
"expenseData": {
"merchant": "Verizon",
"amount": 85.00,
"currency": "USD",
"policy": "PHONE",
"description": "Phone service - {month} {year}",
"project": "Operations",
"categoryGroup": "PHONE"
},
"scheduling": {
"enabled": true,
"frequency": "monthly",
"interval": 1,
"dayOfMonth": 15,
"startTime": "09:00",
"timezone": "America/New_York",
"nextExecution": "2025-09-15T13:00:00.000Z",
"endDate": null
},
"executionHistory": [
{
"id": "exec-456",
"executedAt": "2025-08-15T13:00:05.000Z",
"success": true,
"expenseId": "expense-789",
"error": null,
"duration": 1250
}
]
}
CreateTemplateRequest
{
"name": "Client Lunch Template",
"description": "Standard client lunch expense",
"expenseData": {
"merchant": "Restaurant (Variable)",
"amount": 75.00,
"currency": "USD",
"policy": "MEALS_CLIENT",
"description": "Client lunch - {client_name}"
},
"isFavorite": false
}
TemplateExecution - Execution History Entry
{
"id": "exec-123",
"templateId": "template-456",
"executedAt": "2025-08-01T12:00:00.000Z",
"success": true,
"expenseId": "expense-789",
"expenseData": {
"merchant": "Verizon",
"amount": 85.00,
"description": "Phone service - August 2025"
},
"error": null,
"duration": 1523,
"retryCount": 0
}
Authentication Structures
TokenData - Stored Authentication Token
{
"token": "Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"expiresAt": 1753396268728,
"refreshToken": "refresh_token_value",
"tokenType": "Bearer",
"scope": "expenses:read expenses:write",
"metadata": {
"userId": "user-123",
"companyId": "company-456",
"capturedAt": "2025-08-01T10:00:00.000Z",
"source": "login",
"lastValidated": "2025-08-01T14:00:00.000Z"
}
}
Message Types
BackgroundMessage Examples
Token Captured Message
{
"action": "TOKEN_CAPTURED",
"data": {
"token": "Bearer eyJhbGciOiJIUzI1NiIs...",
"source": "fetch",
"timestamp": 1753309868728
}
}
Create Expense Message
{
"action": "CREATE_EXPENSE",
"data": {
"merchant": "Uber",
"amount": 28.50,
"currency": "USD",
"date": "2025-08-01",
"policy": "TRANSPORTATION"
}
}
Execute Template Message
{
"action": "EXECUTE_TEMPLATE",
"data": {
"templateId": "template-123",
"variables": {
"month": "August",
"year": "2025"
}
}
}
MessageResponse
{
"success": true,
"data": {
"expenseId": "expense-123",
"status": "CREATED"
},
"error": null,
"timestamp": 1753309868728
}
Storage Structures
Storage Keys and Data Types
Key | Type | Example Data |
---|---|---|
auth_token | TokenData | See TokenData structure above |
templates | Map<string, ExpenseTemplate> | Template objects indexed by ID |
recent_expenses | Expense[] | Array of recent expense objects |
user_preferences | Object | {"theme": "light", "notifications": true} |
execution_log | TemplateExecution[] | Array of execution history |
pending_schedules | Object | {"template-123": "2025-09-15T13:00:00.000Z"} |
Transaction Storage Example
{
"transactionId": "txn-789",
"operations": [
{
"type": "set",
"key": "template-123",
"value": { "...template data..." },
"timestamp": 1753309868728
},
{
"type": "remove",
"key": "template-old",
"timestamp": 1753309868729
}
],
"status": "pending",
"createdAt": "2025-08-01T14:30:00.000Z"
}
Error Structures
ApiError Response
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Invalid expense data",
"details": {
"field": "amount",
"reason": "Amount must be greater than 0"
},
"timestamp": "2025-08-01T14:30:00.000Z",
"requestId": "req-123"
}
}
TemplateError
{
"code": "TEMPLATE_NOT_FOUND",
"message": "Template with ID 'template-999' not found",
"templateId": "template-999",
"timestamp": "2025-08-01T14:30:00.000Z"
}
Chrome Alarm Metadata
{
"alarm_template_123": {
"templateId": "template-123",
"created": "2025-08-01T10:00:00.000Z",
"nextExecution": "2025-09-15T13:00:00.000Z",
"frequency": "monthly",
"retryCount": 0,
"lastError": null
}
}
Policy and Validation Structures
PolicyDescription
{
"type": "MEALS_CLIENT",
"name": "Client Meals",
"description": "Meals with clients and prospects",
"picture": "https://example.com/icons/meals.png",
"warningAmounts": {
"DAILY": {
"USD": 150,
"EUR": 130,
"GBP": 120
}
},
"requiresReceipt": true,
"requiresParticipants": true,
"glCodeRequired": true
}
Custom Field Structures
{
"customFields": [
{
"id": "field-1",
"name": "Cost Center",
"type": "select",
"required": true,
"options": ["MKT-100", "ENG-200", "OPS-300"],
"value": "MKT-100"
},
{
"id": "field-2",
"name": "Project Code",
"type": "text",
"required": false,
"value": "PROJ-2025-08"
}
]
}