Ctrl K
ComunidadGuías…

test/connect-entitlement.test.js

Rama master · réplica de lectura del repositorio original.

Archivo original ↗Preguntar a KiBot
import { describe, it } from 'node:test';
import assert from 'node:assert/strict';
import { isConnectSelectorAllowedForAccount } from '../src/auth.js';
import { FREE_REACHABLE_SELECTORS } from '../src/devin-connect-models.js';

// A paid connect selector (e.g. a fable) routed to a free-tier account gets an
// upstream permission_denied (surfaced to the client as an opaque 529). The
// connect path historically selected accounts with modelKey=null (no filter),
// because the Cascade catalog filter (isModelAllowedForAccount) is a different
// namespace and would wrongly exclude EVERY account (even pro) for a connect
// selector. isConnectSelectorAllowedForAccount is the connect-namespace filter
// that keeps a paid selector off a free account without breaking pro.

describe('isConnectSelectorAllowedForAccount — connect-namespace entitlement', () => {
  const free = { tier: 'free' };
  const pro = { tier: 'pro' };
  const unknown = { tier: '' };        // unprobed new account
  const expired = { tier: 'expired' };

  it('free-reachable selector (swe-1-6-slow) is allowed on any account', () => {
    for (const sel of FREE_REACHABLE_SELECTORS) {
      assert.equal(isConnectSelectorAllowedForAccount(free, sel), true, `free ${sel}`);
      assert.equal(isConnectSelectorAllowedForAccount(pro, sel), true, `pro ${sel}`);
    }
  });

  it('#258 drought-safe selectors stay blocked on a free account', () => {
    // Drought allowlist must not leak into entitlement. swe-1-7 is weekly-
    // quota-exempt on Pro; unpaid accounts still get /upgrade.
    assert.equal(isConnectSelectorAllowedForAccount(free, 'swe-1-7'), false);
    assert.equal(isConnectSelectorAllowedForAccount(free, 'swe-1-7-medium'), false);
    assert.equal(isConnectSelectorAllowedForAccount(free, 'glm-5-2'), false);
    assert.equal(isConnectSelectorAllowedForAccount(pro, 'swe-1-7'), true);
  });

  it('paid selector (fable) is BLOCKED on a free account', () => {
    assert.equal(isConnectSelectorAllowedForAccount(free, 'claude-5-fable-medium'), false);
    assert.equal(isConnectSelectorAllowedForAccount(free, 'claude-opus-4-8-medium'), false);
  });

  it('paid selector is ALLOWED on a pro account', () => {
    assert.equal(isConnectSelectorAllowedForAccount(pro, 'claude-5-fable-medium'), true);
    assert.equal(isConnectSelectorAllowedForAccount(pro, 'claude-opus-4-8-medium'), true);
  });

  it('unprobed (unknown tier) account is optimistically allowed a paid selector', () => {
    // Self-heals: after a probe it becomes 'free' and then gets blocked. This
    // preserves pre-GetUserStatus behaviour (no false-negative on new accounts).
    assert.equal(isConnectSelectorAllowedForAccount(unknown, 'claude-5-fable-medium'), true);
  });

  it('expired account is blocked from a paid selector', () => {
    assert.equal(isConnectSelectorAllowedForAccount(expired, 'claude-5-fable-medium'), false);
  });

  it('operator blocklist excludes the selector even on a pro account', () => {
    const proBlocked = { tier: 'pro', blockedModels: ['claude-5-fable-medium'] };
    assert.equal(isConnectSelectorAllowedForAccount(proBlocked, 'claude-5-fable-medium'), false);
    // a different selector is still allowed
    assert.equal(isConnectSelectorAllowedForAccount(proBlocked, 'claude-opus-4-8-medium'), true);
  });

  it('no selector → no filter (back-compat)', () => {
    assert.equal(isConnectSelectorAllowedForAccount(free, null), true);
    assert.equal(isConnectSelectorAllowedForAccount(free, ''), true);
  });
});