This repository has been archived on 2026-04-03. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
core/packages/sdk-test-runner/js/fixtures.js
gobha 96a4f16bc5 Changeset 0.37.17 (#229)
Co-authored-by: gobha <jasafpro@gmail.com>
Co-committed-by: gobha <jasafpro@gmail.com>
2026-03-24 16:50:00 +00:00

240 lines
8.2 KiB
JavaScript

/**
* SDK Test Runner — Fixtures
*
* Provisions reusable test resources before domains run and tears
* them down afterward. Modeled on the ICD test runner's fixture
* pattern.
*
* Fixture resources (all optional — domains degrade gracefully):
*
* providerConfig Global API config created from the first admin
* config that has at least one embedding model.
* Enables: knowledge.search, model preference tests.
*
* embeddingModel {model_id, provider_config_id} picked from the
* enabled models list after the config is created.
*
* policies Policy toggles applied at setup, reverted at
* teardown (e.g. allow_user_personas).
*
* team Test team (with current user as admin).
*
* Access: window.SDKR.fixtures.*
*/
(function () {
'use strict';
var T = window.SDKR;
if (!T) return;
T.fixtures = {
ready: false,
providerConfig: null, // { id, name, provider }
embeddingModel: null, // { model_id, provider_config_id }
team: null, // { id, name }
policies: {}, // key → original value (for revert)
errors: []
};
// ─── Policy helpers ──────────────────────────────────────
async function setPolicy(key, value) {
var fix = T.fixtures;
try {
// Save original for revert
if (!(key in fix.policies)) {
try {
var settings = await T.raw.get('/admin/settings');
fix.policies[key] = settings.policies?.[key] ?? null;
} catch (_) {
fix.policies[key] = null;
}
}
await T.raw.put('/admin/settings/' + key, { value: String(value) });
} catch (e) {
fix.errors.push('policy ' + key + ': ' + e.message);
}
}
async function revertPolicies() {
var fix = T.fixtures;
var keys = Object.keys(fix.policies);
for (var i = 0; i < keys.length; i++) {
var val = fix.policies[keys[i]];
try {
await T.raw.put('/admin/settings/' + keys[i], {
value: val === null ? 'false' : String(val)
});
} catch (_) { /* best effort */ }
}
}
// ─── Provider / model discovery ──────────────────────────
async function provisionProvider() {
var fix = T.fixtures;
// ── Read UI inputs (provider + API key) ──
var ui = T._fixtureInput || {};
var selectedProvider = ui.provSelect ? ui.provSelect.value : '';
var apiKey = ui.keyInput ? ui.keyInput.value.trim() : '';
var statusEl = ui.statusEl;
function setStatus(msg) {
if (statusEl) statusEl.textContent = msg;
console.log('[SDKR:fixtures] ' + msg);
}
// Check if any configs already exist
try {
var configs = await T.raw.get('/admin/configs');
var list = configs.data || configs.configs || [];
if (list.length > 0) {
fix.providerConfig = { id: list[0].id, name: list[0].name, provider: list[0].provider };
setStatus('Using existing config: ' + list[0].name);
}
} catch (e) {
fix.errors.push('config list: ' + e.message);
return;
}
// If no config exists and user provided a provider + key, create one
if (!fix.providerConfig && selectedProvider && apiKey) {
try {
var configData = {
name: 'sdkr-fixture-' + selectedProvider,
provider: selectedProvider,
api_key: apiKey,
scope: 'global'
};
setStatus('Creating ' + selectedProvider + ' config...');
var created = await T.raw.post('/admin/configs', configData);
if (created && created.id) {
fix.providerConfig = { id: created.id, name: configData.name, provider: selectedProvider };
fix._createdConfig = true; // mark for cleanup
setStatus('Config created: ' + configData.name);
T.registerCleanup(function () {
if (fix._createdConfig && fix.providerConfig) {
return T.safeDelete('/admin/configs/' + fix.providerConfig.id);
}
});
}
} catch (e) {
setStatus('Config create failed: ' + e.message);
fix.errors.push('config create: ' + e.message);
}
} else if (!fix.providerConfig && selectedProvider && !apiKey) {
// Provider selected but no key — try creating without key (some providers
// use server-side keys configured via env vars)
try {
var configData2 = {
name: 'sdkr-fixture-' + selectedProvider,
provider: selectedProvider,
scope: 'global'
};
var created2 = await T.raw.post('/admin/configs', configData2);
if (created2 && created2.id) {
fix.providerConfig = { id: created2.id, name: configData2.name, provider: selectedProvider };
fix._createdConfig = true;
setStatus('Config created (server key): ' + configData2.name);
T.registerCleanup(function () {
if (fix._createdConfig && fix.providerConfig) {
return T.safeDelete('/admin/configs/' + fix.providerConfig.id);
}
});
}
} catch (_) {
setStatus('No config — skipping model tests');
}
} else if (!fix.providerConfig) {
setStatus('No provider selected — model tests will be skipped');
}
// Fetch models if we have a config
if (fix.providerConfig) {
try {
await T.raw.post('/admin/models/fetch', {});
// Wait briefly for async model fetch
await new Promise(function (r) { setTimeout(r, 1500); });
} catch (_) { /* fetch may fail if no key */ }
// Look for an embedding model
try {
var models = await T.raw.get('/models/enabled');
var list2 = models.data || [];
for (var m = 0; m < list2.length; m++) {
var caps = list2[m].capabilities || {};
if (caps.embedding || list2[m].model_type === 'embedding') {
fix.embeddingModel = {
model_id: list2[m].model_id,
provider_config_id: list2[m].provider_config_id
};
console.log('[SDKR:fixtures] Embedding model: ' + list2[m].model_id);
break;
}
}
} catch (_) { /* no models available */ }
}
}
// ─── Team ────────────────────────────────────────────────
async function provisionTeam() {
var fix = T.fixtures;
try {
var team = await T.raw.post('/admin/teams', {
name: 'sdkr-fixture-' + Date.now(),
description: 'SDK test runner fixture team'
});
if (team && team.id) {
fix.team = { id: team.id, name: team.name };
T.registerCleanup(function () {
if (fix.team) return T.safeDelete('/admin/teams/' + fix.team.id);
});
}
} catch (e) {
fix.errors.push('team: ' + e.message);
}
}
// ─── Provision / Teardown ────────────────────────────────
T.provisionFixtures = async function () {
var fix = T.fixtures;
if (fix.ready) return;
console.log('[SDKR:fixtures] Provisioning...');
// Policies
await setPolicy('allow_user_personas', 'true');
// Provider + models
await provisionProvider();
// Team
await provisionTeam();
fix.ready = true;
if (fix.errors.length > 0) {
console.warn('[SDKR:fixtures] ' + fix.errors.length + ' errors:', fix.errors);
}
console.log('[SDKR:fixtures] Ready —',
'config:', fix.providerConfig ? fix.providerConfig.name : 'none',
'| embedding:', fix.embeddingModel ? fix.embeddingModel.model_id : 'none',
'| team:', fix.team ? fix.team.name : 'none'
);
};
T.teardownFixtures = async function () {
await revertPolicies();
// Cleanup functions registered via T.registerCleanup handle
// the config + team deletion.
T.fixtures = {
ready: false, providerConfig: null, embeddingModel: null,
team: null, policies: {}, errors: []
};
console.log('[SDKR:fixtures] Torn down');
};
})();