refactor(core): modularize request pipeline

This commit is contained in:
xixu-me committed 2026-03-20 15:36:10 +08:00
1 parent b86be36d67
commit 1b67fd2ff1
36 files changed
+2047 -1271

No files matched your search

+2 -1
View File
@@ -1,5 +1,6 @@
import { describe, expect, it } from 'vitest';
import { PLATFORMS, transformPath } from '../../src/config/platforms.js';
import { PLATFORM_CATALOG as PLATFORMS } from '../../src/config/platform-catalog.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('CRAN Platform Configuration', () => {
it('should have CRAN platform configured', () => {
+1 -1
View File
@@ -1,5 +1,5 @@
import { describe, expect, it } from 'vitest';
import { transformPath } from '../../src/config/platforms.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('crates.io path transformation', () => {
it('should transform crate download URLs correctly', () => {
+2 -1
View File
@@ -1,5 +1,6 @@
import { describe, expect, it } from 'vitest';
import { PLATFORMS, transformPath } from '../../src/config/platforms.js';
import { PLATFORM_CATALOG as PLATFORMS } from '../../src/config/platform-catalog.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('Flathub Platform Configuration', () => {
it('should have Flathub platform configured', () => {
+1 -1
View File
@@ -1,5 +1,5 @@
import { describe, expect, it } from 'vitest';
import { transformPath } from '../../src/config/platforms.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('Homebrew path transformation', () => {
describe('homebrew-api platform', () => {
+1 -1
View File
@@ -1,5 +1,5 @@
import { describe, expect, it } from 'vitest';
import { transformPath } from '../../src/config/platforms.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('Jenkins Plugin Support', () => {
describe('Update Center Transformations', () => {
+2 -1
View File
@@ -1,5 +1,6 @@
import { describe, expect, it } from 'vitest';
import { PLATFORMS, transformPath } from '../../src/config/platforms.js';
import { PLATFORM_CATALOG as PLATFORMS } from '../../src/config/platform-catalog.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('openSUSE Platform Configuration', () => {
it('should have openSUSE platform configured', () => {
+52
View File
@@ -0,0 +1,52 @@
import { describe, expect, it } from 'vitest';
import apiHandler, { config as vercelConfig } from '../../adapters/functions/api/index.js';
import { handler as denoHandler } from '../../adapters/functions/deno.js';
import { onRequest } from '../../adapters/pages/functions/[[path]].js';
import { createRequestContext } from '../../src/app/request-context.js';
import { PLATFORM_CATALOG } from '../../src/config/platform-catalog.js';
import { normalizeEffectivePath, resolveTarget } from '../../src/routing/resolve-target.js';
describe('Application structure', () => {
it('builds a shared request context for protocol-aware routing', () => {
const request = new Request('https://example.com/ip/openai/v1/chat/completions', {
method: 'OPTIONS',
headers: {
Origin: 'https://app.example.com',
'Access-Control-Request-Method': 'POST'
}
});
const context = createRequestContext(request, {
ALLOWED_METHODS: 'GET,HEAD,POST'
});
expect(context.isAI).toBe(true);
expect(context.isCorsPreflight).toBe(true);
expect(context.config.SECURITY.ALLOWED_METHODS).toContain('POST');
});
it('normalizes Docker host-style paths before resolving upstream targets', () => {
const url = new URL('https://example.com/v2/cr/ghcr/xixu-me/xget/manifests/latest');
const normalized = normalizeEffectivePath(url, true);
expect('effectivePath' in normalized).toBe(true);
if ('effectivePath' in normalized) {
expect(normalized.effectivePath).toBe('/cr/ghcr/v2/xixu-me/xget/manifests/latest');
const target = resolveTarget(url, normalized.effectivePath, PLATFORM_CATALOG);
expect('response' in target).toBe(false);
if (!('response' in target)) {
expect(target.platform).toBe('cr-ghcr');
expect(target.targetUrl).toBe('https://ghcr.io/v2/xixu-me/xget/manifests/latest');
}
}
});
it('exposes thin runtime adapter entrypoints', () => {
expect(typeof apiHandler).toBe('function');
expect(typeof denoHandler).toBe('function');
expect(typeof onRequest).toBe('function');
expect(vercelConfig).toEqual({ runtime: 'edge' });
});
});
+116
View File
@@ -0,0 +1,116 @@
import { afterEach, describe, expect, it, vi } from 'vitest';
import { createRequestContext } from '../../src/app/request-context.js';
import { CONFIG } from '../../src/config/index.js';
import { finalizeResponse } from '../../src/response/finalize-response.js';
import { tryReadCachedResponse } from '../../src/upstream/cache.js';
import { fetchUpstreamResponse } from '../../src/upstream/fetch-upstream.js';
import { PerformanceMonitor } from '../../src/utils/performance.js';
afterEach(() => {
vi.restoreAllMocks();
});
describe('Pipeline modules', () => {
it('reuses cached full content for range requests through the cache helper', async () => {
const cache = {
match: vi
.fn()
.mockResolvedValueOnce(null)
.mockResolvedValueOnce(
new Response('full-body', {
status: 200,
headers: { 'Content-Type': 'text/plain' }
})
)
};
const monitor = new PerformanceMonitor();
const markSpy = vi.spyOn(monitor, 'mark');
const request = new Request('https://example.com/gh/user/repo/file.txt', {
headers: { Range: 'bytes=0-3' }
});
const response = await tryReadCachedResponse({
cache: /** @type {Cache} */ (/** @type {unknown} */ (cache)),
cacheTargetUrl: 'https://github.com/user/repo/file.txt',
canUseCache: true,
hasSensitiveHeaders: false,
monitor,
request,
requestContext: createRequestContext(request, {})
});
expect(await response?.text()).toBe('full-body');
expect(markSpy).toHaveBeenCalledWith('cache_hit_full_content');
});
it('retries upstream fetches through the transport helper before succeeding', async () => {
const request = new Request('https://example.com/gh/user/repo/file.txt');
const requestContext = createRequestContext(request, {});
const fetchSpy = vi
.spyOn(globalThis, 'fetch')
.mockRejectedValueOnce(new Error('temporary-network-error'))
.mockResolvedValueOnce(
new Response('ok', {
status: 200,
headers: { 'Content-Type': 'text/plain' }
})
);
const result = await fetchUpstreamResponse({
authorization: null,
canUseCache: true,
config: { ...CONFIG, MAX_RETRIES: 2, RETRY_DELAY_MS: 0 },
effectivePath: '/gh/user/repo/file.txt',
monitor: new PerformanceMonitor(),
platform: 'gh',
request,
requestContext,
shouldPassthroughRequest: false,
targetUrl: 'https://github.com/user/repo/file.txt'
});
expect(result.responseGeneratedLocally).toBe(false);
expect(result.response.status).toBe(200);
expect(fetchSpy).toHaveBeenCalledTimes(2);
});
it('rewrites npm metadata and refreshes content length during response finalization', async () => {
const request = new Request('https://example.com/npm/pkg');
const requestContext = createRequestContext(request, {});
const upstreamBody = JSON.stringify({
dist: {
tarball: 'https://registry.npmjs.org/pkg/-/pkg-1.0.0.tgz'
}
});
const response = await finalizeResponse({
cache: null,
cacheTargetUrl: 'https://registry.npmjs.org/pkg',
canUseCache: true,
config: CONFIG,
ctx: /** @type {ExecutionContext} */ ({ waitUntil() {}, passThroughOnException() {} }),
effectivePath: '/npm/pkg',
hasSensitiveHeaders: false,
monitor: new PerformanceMonitor(),
platform: 'npm',
request,
requestContext,
response: new Response(upstreamBody, {
status: 200,
headers: {
'Content-Type': 'application/json',
'Content-Length': String(upstreamBody.length)
}
}),
responseGeneratedLocally: false,
url: new URL(request.url)
});
const body = await response.text();
expect(body).toContain('https://example.com/npm/pkg/-/pkg-1.0.0.tgz');
expect(response.headers.get('Content-Length')).toBe(
String(new TextEncoder().encode(body).byteLength)
);
});
});
+31
View File
@@ -0,0 +1,31 @@
import { describe, expect, it } from 'vitest';
import { PLATFORM_CATALOG } from '../../src/config/platform-catalog.js';
import { PLATFORMS, SORTED_PLATFORMS, transformPath } from '../../src/config/platforms.js';
import { getPlatformPathPrefix } from '../../src/routing/platform-index.js';
import { transformPath as transformPlatformPath } from '../../src/routing/platform-transformers.js';
describe('Platform module boundaries', () => {
it('keeps the compatibility export wired to the platform catalog', () => {
expect(PLATFORMS).toBe(PLATFORM_CATALOG);
});
it('sorts platform keys by the longest routable prefix first', () => {
const prefixLengths = SORTED_PLATFORMS.map(
platformKey => getPlatformPathPrefix(platformKey).length
);
prefixLengths.forEach((length, index) => {
if (index < prefixLengths.length - 1) {
expect(length).toBeGreaterThanOrEqual(prefixLengths[index + 1]);
}
});
});
it('routes legacy transform imports through the dedicated transformer module', () => {
expect(transformPath('/crates/?q=tokio', 'crates')).toBe(
transformPlatformPath('/crates/?q=tokio', 'crates')
);
expect(transformPath('/jenkins/test-path', 'jenkins')).toBe('/current/test-path');
});
});
+2 -1
View File
@@ -1,5 +1,6 @@
import { describe, expect, it } from 'vitest';
import { PLATFORMS, transformPath } from '../../src/config/platforms.js';
import { PLATFORM_CATALOG as PLATFORMS } from '../../src/config/platform-catalog.js';
import { transformPath } from '../../src/routing/platform-transformers.js';
describe('Platform Configuration', () => {
describe('Platform Definitions', () => {
+52
View File
@@ -0,0 +1,52 @@
import { describe, expect, it } from 'vitest';
import {
createPlatformEntries,
extractPlatformsModule,
loadPlatformsFromSource
} from '../../skills/xget/scripts/xget.mjs';
describe('xget skill script', () => {
it('extracts platform data from the new platform catalog source', () => {
const source = `export const PLATFORM_CATALOG = {
gh: 'https://github.com',
'cr-ghcr': 'https://ghcr.io'
};
export const PLATFORMS = PLATFORM_CATALOG;
`;
expect(extractPlatformsModule(source)).toEqual({
gh: 'https://github.com',
'cr-ghcr': 'https://ghcr.io'
});
});
it('still accepts the legacy PLATFORMS object source', () => {
const source = `export const PLATFORMS = {
npm: 'https://registry.npmjs.org'
};
`;
expect(extractPlatformsModule(source)).toEqual({
npm: 'https://registry.npmjs.org'
});
});
it('loads categorized platform entries from the extracted source', () => {
const entries = loadPlatformsFromSource(`export const PLATFORM_CATALOG = {
gh: 'https://github.com',
'ip-openai': 'https://api.openai.com',
'cr-ghcr': 'https://ghcr.io'
};
`);
expect(entries).toEqual(
createPlatformEntries({
gh: 'https://github.com',
'ip-openai': 'https://api.openai.com',
'cr-ghcr': 'https://ghcr.io'
})
);
});
});