> ## Documentation Index
> Fetch the complete documentation index at: https://www.adspirer.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Adspirer Security: OAuth, Encryption & Data Privacy

> How Adspirer protects your ad accounts: OAuth 2.1 with PKCE, API key auth, no password storage, encrypted tokens, and revocable access.

<Info>
  Adspirer never sees your ad platform passwords. All authentication uses OAuth 2.1 with <Tooltip tip="Proof Key for Code Exchange — prevents authorization code interception attacks">PKCE</Tooltip> — the same standard used by banking apps.
</Info>

## Authentication: OAuth 2.1 with PKCE

When you connect an ad platform (Google Ads, Meta, LinkedIn, TikTok), Adspirer uses **OAuth 2.1 with PKCE** — the same standard used by banking apps and enterprise software.

### What This Means

* **Your passwords stay with Google/Meta/Amazon/LinkedIn/TikTok.** Adspirer never receives, stores, or transmits your login credentials. (ChatGPT Ads has no login — you paste an OpenAI Advertiser API key, which Adspirer stores encrypted and never exposes to the AI client.)
* **PKCE prevents interception.** Every authentication generates a cryptographic proof that only your specific session can complete. Even if someone intercepts the authorization code, they can't use it.
* **Scoped permissions.** You authorize exactly what Adspirer can do — read campaign data, create ads, manage budgets. Nothing more.
* **Meta approved access.** Adspirer has Meta approved Ads Management Standard Access, meaning Meta has verified the app's use of their Marketing API. Meta's account enforcement systems (security reviews, restrictions, account disabling) operate independently from Adspirer and are governed by Meta's own Community Standards and policies.
* **Google agency-level approval.** Google reviewed and classified Adspirer as an agency, full-service ad platform for the Google Ads API and granted Standard Access — verifying how Adspirer uses the API and lifting the daily operations cap. (This is the Google Ads API "external full-service" classification — not the separate Google Partners program.)

### Token Lifecycle

| Token         | Lifetime | Purpose                                      |
| ------------- | -------- | -------------------------------------------- |
| Access token  | 1 hour   | Authorizes tool calls                        |
| Refresh token | 30 days  | Generates new access tokens without re-login |

Tokens are encrypted at rest and automatically refreshed. If a token expires, your AI client prompts you to re-authenticate.

## API Key Authentication

For remote servers, Docker containers, and CI/CD pipelines where browser-based OAuth isn't possible, Adspirer supports **Personal Access Tokens** (API keys).

### How API Keys Work

1. You generate a key from the Adspirer dashboard at [adspirer.ai/keys](https://adspirer.ai/keys)
2. The key starts with `sk_live_` and is shown **once** — copy it immediately
3. Adspirer stores a **SHA-256 hash** of the key — the raw token is never stored
4. On each request, the server hashes the provided token and looks up the hash in the database

### API Key Security Properties

| Property        | Detail                                                             |
| --------------- | ------------------------------------------------------------------ |
| **Format**      | `sk_live_` prefix + 32 URL-safe random characters                  |
| **Storage**     | SHA-256 hash only — raw token never stored server-side             |
| **Lookup**      | O(1) indexed hash lookup (no bcrypt iteration)                     |
| **Expiration**  | Optional — set at creation (30 days, 90 days, 1 year, or never)    |
| **Revocation**  | Instant — revoked keys are rejected immediately                    |
| **Scope**       | Full account access (same as OAuth) — cannot manage other API keys |
| **Tier limits** | Free: 2 keys, Plus: 5, Pro: 10, Max: 20                            |

### Revoking API Keys

Revoke a key instantly from [adspirer.ai/keys](https://adspirer.ai/keys). Revoked keys return a `401` error on the next request. The key record is preserved for audit trail (revocation timestamp visible in admin).

### API Keys vs OAuth

|                    | OAuth 2.1 (PKCE)                    | API Key                       |
| ------------------ | ----------------------------------- | ----------------------------- |
| **Best for**       | Browser-based AI clients            | Remote servers, Docker, CI/CD |
| **Auth flow**      | Browser redirect                    | `--token` flag or env var     |
| **Token rotation** | Automatic (1hr access, 30d refresh) | Manual (generate new key)     |
| **Security**       | PKCE-protected code exchange        | SHA-256 hashed token          |

## What Data Adspirer Accesses

**Reads:**

* Campaign names, statuses, budgets
* Performance metrics (spend, conversions, CPA, ROAS, CTR)
* Keywords, ad copy, targeting settings
* Asset metadata (image/video dimensions, file sizes)

**Writes (with your confirmation):**

* Create campaigns (always created PAUSED)
* Update budgets and bids
* Pause or resume campaigns
* Add keywords, ad copy, or extensions

**Never accesses:**

* Your ad platform login credentials
* Billing/payment information (credit cards, bank accounts)
* Personal data beyond what's shown in ad account settings
* Data from other ad accounts you haven't explicitly connected

## Campaign Safety

Every write operation has built-in safety:

* **Campaigns created PAUSED** — You review before any money is spent
* **User confirmation required** — Your AI assistant asks before budget-affecting actions
* **No automatic retries** — If a campaign creation fails, it reports the error instead of retrying
* **Read-before-write** — Research and validation always happen before creation

## Revoking Access

You can disconnect Adspirer at any time:

1. **From Adspirer:** Visit [adspirer.ai](https://adspirer.ai?utm_source=docs\&utm_medium=page\&utm_content=account) and disconnect the platform
2. **From the ad platform:** Revoke access in your platform's security settings:
   * Google: [Security Settings](https://myaccount.google.com/permissions)
   * Meta: [Business Integrations](https://www.facebook.com/settings?tab=business_tools)
   * LinkedIn: [Permitted Services](https://www.linkedin.com/psettings/permitted-services)
   * TikTok: Business Center > Settings > Authorized Partners

Revoking from either side immediately stops all tool access.

3. **API Keys:** Visit [adspirer.ai/keys](https://adspirer.ai/keys) and click **Revoke** on any active key. The key is invalidated immediately.

## Infrastructure Security

| Layer         | Protection                                                   |
| ------------- | ------------------------------------------------------------ |
| **Transport** | HTTPS/TLS encryption for all API calls                       |
| **Hosting**   | Google Cloud Run with auto-scaling and DDoS protection       |
| **Sessions**  | Redis with auto-expiring keys (1hr TTL)                      |
| **Tokens**    | Encrypted at rest, hashed in database                        |
| **Logging**   | Structured logs exclude sensitive data (tokens, credentials) |

## FAQ

<AccordionGroup>
  <Accordion title="Is my ad data shared with other users?">
    No. Your data is isolated to your Adspirer account. No data is shared between users, used for training, or sold to third parties.
  </Accordion>

  <Accordion title="Can Adspirer spend money without my approval?">
    No. All campaigns are created PAUSED, and budget changes require explicit user confirmation. Even autonomous agents (like Codex) follow this rule.
  </Accordion>

  <Accordion title="What happens if Adspirer goes down?">
    Your ad campaigns continue running normally — they're managed by Google/Meta/LinkedIn/TikTok, not by Adspirer. You just can't make changes via AI until the service recovers. Downtime does not affect live campaigns.
  </Accordion>
</AccordionGroup>
