How to Configure FluentRead to Use Your Own AI API Keys: A Complete Guide

FluentRead stores AI API credentials in a local Config object with a token map that persists to browser storage, allowing you to configure custom keys through the settings UI or programmatically via the config.token interface.

FluentRead is an open-source browser extension that provides intelligent translation services using various AI providers. If you want to configure FluentRead to use your own AI API keys instead of default credentials, you need to understand how the extension manages authentication tokens across its architecture.

How FluentRead Stores API Credentials

The extension centralizes all configuration in a Config class defined in entrypoints/utils/model.ts. This class declares a token property as an IMapping type to hold string tokens for every service requiring authentication.

// entrypoints/utils/model.ts (lines 21-27)
export class Config {
  service: string;
  token: IMapping;  // Stores API keys for each service
  // ... other properties
}

When the extension initializes, entrypoints/utils/config.ts loads persisted settings from the browser's local storage and hydrates the exported config instance.

// entrypoints/utils/config.ts (lines 16-28)
const stored = await storage.getItem('local:config');
if (stored) {
  const parsed = JSON.parse(stored as string);
  Object.assign(config, parsed);  // Merges stored tokens into config
}

This architecture ensures your API keys remain in local browser storage and never transit to external servers except when making direct API calls to your chosen AI provider.

Setting Up Your AI API Keys in FluentRead

Using the Settings UI

The primary interface for entering credentials resides in components/Main.vue. The UI binds an <el-input> element directly to config.token[config.service], creating a two-way data binding that updates the configuration object as you type.

<!-- components/Main.vue (lines 92-104) -->
<el-row v-show="compute.showToken" class="margin-bottom margin-left-2em">
  <el-col :span="12" class="lightblue rounded-corner">
    <span class="popup-text popup-vertical-left">访问令牌</span>
  </el-col>
  <el-col :span="12">
    <el-input 
      v-model="config.token[config.service]" 
      type="password" 
      show-password 
      placeholder="请输入API访问令牌" />
  </el-col>
</el-row>

To configure your key through the UI:

  1. Open the FluentRead extension panel in your browser.
  2. Select your desired AI service from the dropdown (e.g., OpenAI, Azure OpenAI, Gemini).
  3. Locate the "访问令牌" (Access Token) field.
  4. Paste your API key into the password input.
  5. The extension automatically persists the value to local:config storage.

Programmatic Configuration

For advanced users who want to inject credentials via userscripts or extension popups, you can manipulate the config object directly:

import { config } from '@/entrypoints/utils/config';
import { services } from '@/entrypoints/utils/option';

// Configure OpenAI API key programmatically
config.token[services.openai] = 'sk-your-openai-api-key';

// Persist immediately to local storage
await storage.setItem('local:config', JSON.stringify(config));

This approach is useful when distributing FluentRead in managed environments where you pre-configure keys for users.

Validating API Keys Before Translation

Before dispatching any translation request, FluentRead validates that required credentials exist. The checkConfig() function in entrypoints/utils/check.ts verifies token presence for services marked as requiring authentication.

// entrypoints/utils/check.ts (lines 10-18)
export function checkConfig(): boolean {
  if (servicesType.isUseToken(config.service) && !config.token[config.service]) {
    // Validation fails - token required but not provided
    return false;
  }
  // Additional checks...
  return true;
}

The servicesType.isUseToken() method checks membership in a Set defined in entrypoints/utils/option.ts that enumerates all token-requiring services.

// entrypoints/utils/option.ts (lines 69-78)
export const servicesType = {
  useToken: new Set([
    services.openai,
    services.azureOpenai,
    services.gemini,
    services.anthropic,
    services.deepseek,
    services.moonshot,
    services.siliconflow,
    services.glm,
    services.groq,
    services.custom
  ])
};

If validation fails, FluentRead prompts the user to enter their API key before proceeding with the translation.

Adding Custom AI Services

You can extend FluentRead to support additional AI providers that require API keys by modifying three components:

First, register the new service in entrypoints/utils/option.ts:

// 1. Add to services enum
export const services = {
  // ... existing services
  myCustomAi: 'myCustomAi',
};

// 2. Add to token-requiring set
export const servicesType = {
  useToken: new Set([
    ...servicesType.useToken,
    services.myCustomAi
  ])
};

Next, implement the API client that reads the token from config.token:

// Custom service implementation example
import { config } from '@/entrypoints/utils/config';
import { services } from '@/entrypoints/utils/option';

export async function translateWithCustomAI(text: string) {
  const apiKey = config.token[services.myCustomAi];
  
  const response = await fetch('https://api.myservice.com/v1/chat', {
    method: 'POST',
    headers: {
      'Authorization': `Bearer ${apiKey}`,
      'Content-Type': 'application/json'
    },
    body: JSON.stringify({
      model: 'gpt-4',
      messages: [{ role: 'user', content: text }]
    })
  });
  
  return response.json();
}

The existing UI in components/Main.vue automatically supports your new service because the token input binds to config.token[config.service] dynamically.

Key Files and Architecture Reference

File Role Location
entrypoints/utils/model.ts Declares the Config class and the token map property. model.ts
entrypoints/utils/config.ts Loads and persists the Config instance from local browser storage. config.ts
entrypoints/utils/option.ts Defines available services and identifies which require tokens via servicesType.useToken. option.ts
entrypoints/utils/check.ts Validates token presence before translation requests via checkConfig(). check.ts
components/Main.vue Provides the settings UI where users input API keys bound to config.token. Main.vue

Summary

  • FluentRead uses a centralized Config class with a token map to store API keys for each AI service in entrypoints/utils/model.ts.
  • Credentials persist in browser local storage via entrypoints/utils/config.ts, ensuring keys remain private to your machine.
  • The settings UI in components/Main.vue binds directly to config.token[config.service], providing real-time updates and automatic persistence.
  • Validation occurs before translation through checkConfig() in entrypoints/utils/check.ts, which verifies tokens exist for services listed in servicesType.useToken.
  • You can extend support for new AI providers by adding entries to entrypoints/utils/option.ts and implementing the corresponding API client.

Frequently Asked Questions

Where does FluentRead store my API keys?

FluentRead stores your API keys in the browser's local storage under the key local:config. The Config class in entrypoints/utils/model.ts defines a token property that maps service names to their corresponding API keys. When you enter a key in the settings UI, it writes directly to config.token[config.service] and persists via storage.setItem('local:config', JSON.stringify(config)), ensuring your credentials never leave your local machine except when making direct API calls to your chosen AI provider.

Can I use multiple AI providers simultaneously with different API keys?

Yes, FluentRead supports multiple AI providers simultaneously through the token map structure. Each service defined in entrypoints/utils/option.ts—such as services.openai, services.gemini, or services.anthropic—maintains its own entry in config.token. You can configure a unique API key for each provider through the settings panel, and FluentRead will use the corresponding token based on whichever config.service is currently selected for translation.

How do I add a custom AI service that requires an API key?

To add a custom AI service, modify three files in the FluentRead source. First, add your service identifier to the services object in entrypoints/utils/option.ts. Second, add the service to the servicesType.useToken Set to indicate it requires authentication. Third, implement the API client in a new service file, reading the key via config.token[services.yourService]. The existing UI in components/Main.vue will automatically display the token input field for your new service because it dynamically binds to config.token[config.service].

What happens if my API key is invalid or missing?

Before sending any translation request, FluentRead executes checkConfig() in entrypoints/utils/check.ts to validate the configuration. If the selected service is listed in servicesType.useToken (defined in entrypoints/utils/option.ts) and config.token[config.service] is empty or undefined, the validation fails and FluentRead prompts you to enter your API key. The translation request will not proceed until a valid token is provided, preventing unnecessary API errors and ensuring you know exactly which service requires authentication.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →