Skip to content

Security Best Practices

Keep your ExtensionLogin integration secure.

API Key Security

Understanding API Keys

Your API key identifies your extension and authorizes requests to ExtensionLogin. It's designed to be used client-side.

javascript
// API keys are expected to be in client code
ExtensionLogin.init({
  apiKey: 'el_live_xxxxxx'
});

What API Keys Can Do

  • Identify users for your specific extension
  • Retrieve user session data
  • Send data to your configured CRMs

What API Keys Cannot Do

  • Access other extensions' data
  • Modify your account settings
  • Delete users or data
  • Access CRM credentials

Key Best Practices

  1. Use test keys in development

    javascript
    const apiKey = isDev ? 'el_test_xxx' : 'el_live_xxx';
  2. Don't share keys between extensions

    • Each extension should have its own API key
    • Create separate applications in the dashboard
  3. Rotate keys if compromised

    • Generate new keys in the dashboard
    • Update your extension and publish a new version

Environment Separation

Test vs Production Keys

PrefixEnvironmentUsage
el_test_TestingDevelopment, staging
el_live_ProductionPublished extensions
javascript
// Development
ExtensionLogin.init({ apiKey: 'el_test_xxx' });

// Production
ExtensionLogin.init({ apiKey: 'el_live_xxx' });

Build-Time Configuration

javascript
// Using environment variables (Webpack, Vite, etc.)
ExtensionLogin.init({
  apiKey: process.env.EXTENSIONLOGIN_API_KEY
});
javascript
// webpack.config.js
const webpack = require('webpack');

module.exports = {
  plugins: [
    new webpack.DefinePlugin({
      'process.env.EXTENSIONLOGIN_API_KEY': JSON.stringify(
        process.env.NODE_ENV === 'production'
          ? 'el_live_xxx'
          : 'el_test_xxx'
      )
    })
  ]
};

Data Security

What Data is Stored

ExtensionLogin stores:

  • User email and name
  • Custom metadata you send
  • Session tokens (encrypted)
  • Timestamps

Data Encryption

  • In Transit: All API calls use HTTPS/TLS
  • At Rest: Sensitive data encrypted with AES-256
  • CRM Credentials: Encrypted with per-account keys

Data You Should NOT Send

javascript
// Never send sensitive data
await ExtensionLogin.identify({
  email: '[email protected]',
  metadata: {
    // DON'T DO THIS
    password: 'user_password',
    creditCard: '4111111111111111',
    ssn: '123-45-6789',
    bankAccount: '12345678'
  }
});

Data You CAN Send

javascript
// Safe to send
await ExtensionLogin.identify({
  email: '[email protected]',
  metadata: {
    plan: 'premium',
    company: 'Acme Inc',
    source: 'google_ads',
    extensionVersion: '1.2.3'
  }
});

Webhook Security

Verify Webhook Signatures

Always verify webhook signatures:

javascript
const crypto = require('crypto');

function verifyWebhook(req, secret) {
  const signature = req.headers['x-extensionlogin-signature'];
  const timestamp = req.headers['x-extensionlogin-timestamp'];

  // Reject old webhooks (prevent replay attacks)
  if (Date.now() - parseInt(timestamp) > 300000) {
    return false;
  }

  const payload = JSON.stringify(req.body);
  const expected = 'sha256=' + crypto
    .createHmac('sha256', secret)
    .update(`${timestamp}.${payload}`)
    .digest('hex');

  return crypto.timingSafeEqual(
    Buffer.from(signature),
    Buffer.from(expected)
  );
}

Webhook Secret Management

  1. Store secrets in environment variables
  2. Never commit secrets to version control
  3. Rotate secrets periodically
bash
# .env (never commit this file)
WEBHOOK_SECRET=your_webhook_secret_here

Chrome Extension Security

Manifest Permissions

Request only necessary permissions:

json
{
  "permissions": [
    "storage"
  ],
  "host_permissions": [
    "https://api.extensionlogin.com/*"
  ]
}

Content Security Policy

If using CSP, allow ExtensionLogin:

json
{
  "content_security_policy": {
    "extension_pages": "script-src 'self'; connect-src https://api.extensionlogin.com"
  }
}

Secure Storage

ExtensionLogin uses Chrome's secure storage:

javascript
// Data is stored securely
ExtensionLogin.init({
  apiKey: 'el_live_xxx',
  storage: 'local' // Uses chrome.storage.local
});

User Privacy

Disclosure

Inform users about data collection:

  1. Add privacy disclosure to your extension listing
  2. Include data practices in your privacy policy
  3. Explain what ExtensionLogin collects

Example Privacy Disclosure

"This extension uses ExtensionLogin to provide authentication. We collect your email address and name to create your account. This data may be shared with [Your Company] and third-party CRM services as configured."

Data Minimization

Only collect what you need:

javascript
// Good - minimal data
await ExtensionLogin.identify({
  email: '[email protected]'
});

// Avoid - excessive data
await ExtensionLogin.identify({
  email: '[email protected]',
  metadata: {
    browserHistory: [...],
    allCookies: [...],
    // Don't collect unnecessary data
  }
});

CORS and Origin Security

How It Works

ExtensionLogin validates request origins:

  • Requests must come from registered extension IDs
  • Web requests are blocked unless explicitly allowed
  • API responses include proper CORS headers

Registering Extension ID

For added security, register your extension ID:

  1. Go to Extension Settings in dashboard
  2. Add your extension ID (from Chrome Web Store)
  3. Only requests from that extension will be accepted
json
// Your manifest.json
{
  "key": "your_extension_key"
}

Rate Limiting

Limits by Plan

PlanRequests/minuteRequests/day
Free601,000
Pro30010,000
EnterpriseUnlimitedUnlimited

Handling Rate Limits

javascript
const result = await ExtensionLogin.identify({ email: '[email protected]' });

if (!result.success && result.error?.code === 'RATE_LIMITED') {
  const retryAfter = result.error.retryAfter;
  console.log(`Rate limited. Retry after ${retryAfter}ms`);

  // Implement backoff
  setTimeout(() => {
    retryIdentify();
  }, retryAfter);
}

Audit Logging

Dashboard Logs

Monitor security events in the dashboard:

  1. Go to Logs section
  2. Filter by event type
  3. Review suspicious activity

What's Logged

  • API key usage
  • Failed authentication attempts
  • CRM delivery failures
  • Rate limit violations

Security Checklist

  • [ ] Using test keys in development
  • [ ] Using production keys only in published extensions
  • [ ] Not storing sensitive user data in metadata
  • [ ] Verifying webhook signatures
  • [ ] Using HTTPS for all endpoints
  • [ ] Registered extension ID in dashboard
  • [ ] Minimal permissions in manifest
  • [ ] Privacy disclosure in place
  • [ ] Monitoring dashboard logs

Reporting Security Issues

Found a security vulnerability? Please report it responsibly:

  1. Email: [email protected]
  2. Include detailed reproduction steps
  3. Allow time for us to fix before disclosure

Next Steps

Built for Chrome Extension Developers