@useavalon/avalon 0.1.4 → 0.1.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (32) hide show
  1. package/package.json +31 -58
  2. package/src/vite-plugin/plugin.ts +22 -4
  3. package/src/build/README.md +0 -310
  4. package/src/client/tests/css-hmr-handler.test.ts +0 -360
  5. package/src/client/tests/framework-adapter.test.ts +0 -519
  6. package/src/client/tests/hmr-coordinator.test.ts +0 -176
  7. package/src/client/tests/hydration-option-parsing.test.ts +0 -107
  8. package/src/client/tests/lit-adapter.test.ts +0 -427
  9. package/src/client/tests/preact-adapter.test.ts +0 -353
  10. package/src/client/tests/qwik-adapter.test.ts +0 -343
  11. package/src/client/tests/react-adapter.test.ts +0 -317
  12. package/src/client/tests/solid-adapter.test.ts +0 -396
  13. package/src/client/tests/svelte-adapter.test.ts +0 -387
  14. package/src/client/tests/vue-adapter.test.ts +0 -407
  15. package/src/components/tests/component-analyzer.test.ts +0 -96
  16. package/src/components/tests/component-detection.test.ts +0 -347
  17. package/src/components/tests/persistent-islands.test.ts +0 -398
  18. package/src/core/components/tests/enhanced-framework-detector.test.ts +0 -577
  19. package/src/core/components/tests/framework-registry.test.ts +0 -465
  20. package/src/core/integrations/README.md +0 -282
  21. package/src/core/layout/tests/enhanced-layout-resolver.test.ts +0 -477
  22. package/src/core/layout/tests/layout-cache-optimization.test.ts +0 -149
  23. package/src/core/layout/tests/layout-composer.test.ts +0 -486
  24. package/src/core/layout/tests/layout-data-loader.test.ts +0 -443
  25. package/src/core/layout/tests/layout-discovery.test.ts +0 -253
  26. package/src/core/layout/tests/layout-matcher.test.ts +0 -480
  27. package/src/core/modules/tests/framework-module-resolver.test.ts +0 -263
  28. package/src/core/modules/tests/module-resolution-integration.test.ts +0 -117
  29. package/src/islands/discovery/tests/island-discovery.test.ts +0 -881
  30. package/src/middleware/__tests__/discovery.test.ts +0 -107
  31. package/src/types/tests/layout-types.test.ts +0 -197
  32. package/src/vite-plugin/tests/image-optimization.test.ts +0 -54
@@ -1,107 +0,0 @@
1
- import { describe, it, expect, beforeEach, afterEach } from 'vitest';
2
- import { join } from 'node:path';
3
- import { mkdtemp, mkdir, writeFile, rm } from 'node:fs/promises';
4
- import { tmpdir } from 'node:os';
5
- import { discoverScopedMiddleware, getMatchingMiddleware } from '../discovery.ts';
6
-
7
- describe('discoverScopedMiddleware', () => {
8
- let tempDir: string;
9
-
10
- beforeEach(async () => {
11
- tempDir = await mkdtemp(join(tmpdir(), 'middleware-test-'));
12
- });
13
-
14
- afterEach(async () => {
15
- await rm(tempDir, { recursive: true, force: true });
16
- });
17
-
18
- it('discovers _middleware.ts files in pages subdirectories', async () => {
19
- // Create pages directory structure with middleware files
20
- await mkdir(join(tempDir, 'pages', 'admin'), { recursive: true });
21
- await mkdir(join(tempDir, 'pages', 'blog'), { recursive: true });
22
- await writeFile(join(tempDir, 'pages', 'admin', '_middleware.ts'), 'export default () => {};');
23
- await writeFile(join(tempDir, 'pages', 'blog', '_middleware.ts'), 'export default () => {};');
24
-
25
- const routes = await discoverScopedMiddleware({ baseDir: tempDir });
26
-
27
- expect(routes).toHaveLength(2);
28
- expect(routes.every(r => r.type === 'pages')).toBe(true);
29
- expect(routes.map(r => r.filePath)).toEqual(
30
- expect.arrayContaining([
31
- join(tempDir, 'pages', 'admin', '_middleware.ts'),
32
- join(tempDir, 'pages', 'blog', '_middleware.ts'),
33
- ])
34
- );
35
- });
36
-
37
- it('discovers nested _middleware.ts files with correct priority ordering', async () => {
38
- await mkdir(join(tempDir, 'pages', 'admin', 'users'), { recursive: true });
39
- await writeFile(join(tempDir, 'pages', 'admin', '_middleware.ts'), 'export default () => {};');
40
- await writeFile(join(tempDir, 'pages', 'admin', 'users', '_middleware.ts'), 'export default () => {};');
41
-
42
- const routes = await discoverScopedMiddleware({ baseDir: tempDir });
43
-
44
- expect(routes).toHaveLength(2);
45
- // Parent middleware (depth 1) should come before child (depth 2)
46
- expect(routes[0].priority).toBeLessThan(routes[1].priority);
47
- expect(routes[0].filePath).toContain(join('admin', '_middleware.ts'));
48
- expect(routes[1].filePath).toContain(join('admin', 'users', '_middleware.ts'));
49
- });
50
-
51
- it('does NOT scan api directory for middleware', async () => {
52
- await mkdir(join(tempDir, 'pages', 'admin'), { recursive: true });
53
- await mkdir(join(tempDir, 'api', 'admin'), { recursive: true });
54
- await writeFile(join(tempDir, 'pages', 'admin', '_middleware.ts'), 'export default () => {};');
55
- await writeFile(join(tempDir, 'api', 'admin', '_middleware.ts'), 'export default () => {};');
56
-
57
- const routes = await discoverScopedMiddleware({ baseDir: tempDir });
58
-
59
- expect(routes).toHaveLength(1);
60
- expect(routes[0].type).toBe('pages');
61
- expect(routes[0].filePath).toContain(join('pages', 'admin', '_middleware.ts'));
62
- });
63
-
64
- it('returns empty array when no middleware files exist', async () => {
65
- await mkdir(join(tempDir, 'pages'), { recursive: true });
66
-
67
- const routes = await discoverScopedMiddleware({ baseDir: tempDir });
68
-
69
- expect(routes).toHaveLength(0);
70
- });
71
-
72
- it('returns empty array when pages directory does not exist', async () => {
73
- const routes = await discoverScopedMiddleware({ baseDir: tempDir });
74
-
75
- expect(routes).toHaveLength(0);
76
- });
77
- });
78
-
79
- describe('getMatchingMiddleware', () => {
80
- it('matches page middleware for page routes', () => {
81
- const routes = [
82
- {
83
- pattern: new URLPattern({ pathname: '/admin{/*}?' }),
84
- filePath: '/src/pages/admin/_middleware.ts',
85
- priority: 51,
86
- type: 'pages' as const,
87
- },
88
- ];
89
-
90
- const matches = getMatchingMiddleware(routes, new URL('http://localhost/admin/dashboard'));
91
- expect(matches).toHaveLength(1);
92
- });
93
-
94
- it('does not match page middleware for API routes', () => {
95
- const routes = [
96
- {
97
- pattern: new URLPattern({ pathname: '/*' }),
98
- filePath: '/src/pages/_middleware.ts',
99
- priority: 50,
100
- type: 'pages' as const,
101
- },
102
- ];
103
-
104
- const matches = getMatchingMiddleware(routes, new URL('http://localhost/api/users'));
105
- expect(matches).toHaveLength(0);
106
- });
107
- });
@@ -1,197 +0,0 @@
1
- import { describe, it, expect } from 'vitest';
2
- import {
3
- LayoutContextSchema,
4
- LayoutDataSchema,
5
- LayoutRouteSchema,
6
- LayoutHandlerSchema,
7
- LayoutPropsSchema,
8
- LayoutDiscoveryOptionsSchema,
9
- LayoutConfigSchema,
10
- ResolvedLayoutSchema,
11
- } from '../../schemas/layout.ts';
12
- import { validators, safeValidators } from '../../schemas/index.ts';
13
- import type {
14
- LayoutContext,
15
- LayoutData,
16
- LayoutRoute,
17
- LayoutHandler,
18
- LayoutProps,
19
- LayoutDiscoveryOptions,
20
- LayoutConfig,
21
- ResolvedLayout,
22
- } from '../layout.ts';
23
-
24
- describe('Layout System Types and Schemas', () => {
25
- it('LayoutContext - should validate valid layout context', () => {
26
- const mockRequest = new Request('https://example.com/test');
27
- const mockParams = { id: '123' };
28
- const mockQuery = new URLSearchParams('?page=1');
29
- const mockState = new Map();
30
-
31
- const validContext: LayoutContext = {
32
- request: mockRequest,
33
- params: mockParams,
34
- query: mockQuery,
35
- state: mockState,
36
- };
37
-
38
- const result = safeValidators.layoutContext(validContext);
39
- expect(result.success).toEqual(true);
40
- });
41
-
42
- it('LayoutContext - should reject invalid layout context', () => {
43
- const invalidContext = {
44
- request: 'not-a-request',
45
- params: 'not-an-object',
46
- query: 'not-urlsearchparams',
47
- state: 'not-a-map',
48
- };
49
-
50
- const result = safeValidators.layoutContext(invalidContext);
51
- expect(result.success).toEqual(false);
52
- });
53
-
54
- it('LayoutData - should validate layout data as record', () => {
55
- const validData: LayoutData = {
56
- user: { name: 'John', id: 123 },
57
- settings: { theme: 'dark' },
58
- items: [1, 2, 3],
59
- };
60
-
61
- const result = safeValidators.layoutData(validData);
62
- expect(result.success).toEqual(true);
63
- });
64
-
65
- it('LayoutData - should accept empty layout data', () => {
66
- const emptyData: LayoutData = {};
67
-
68
- const result = safeValidators.layoutData(emptyData);
69
- expect(result.success).toEqual(true);
70
- });
71
-
72
- it('LayoutHandler - should validate valid layout handler', () => {
73
- const validHandler = {
74
- component: () => null,
75
- path: '/src/pages/blog/_layout.tsx',
76
- priority: 10,
77
- };
78
-
79
- const result = safeValidators.layoutHandler(validHandler);
80
- expect(result.success).toEqual(true);
81
- });
82
-
83
- it('LayoutDiscoveryOptions - should validate with defaults', () => {
84
- const options = {
85
- baseDirectory: '/src/pages',
86
- };
87
-
88
- const result = safeValidators.layoutDiscoveryOptions(options);
89
- expect(result.success).toEqual(true);
90
- if (result.success) {
91
- expect(result.data.filePattern).toEqual('_layout.tsx');
92
- expect(result.data.excludeDirectories).toEqual([]);
93
- expect(result.data.enableWatching).toEqual(false);
94
- expect(result.data.developmentMode).toEqual(false);
95
- }
96
- });
97
-
98
- it('LayoutDiscoveryOptions - should validate with custom options', () => {
99
- const options: LayoutDiscoveryOptions = {
100
- baseDirectory: '/src/pages',
101
- filePattern: 'layout.tsx',
102
- excludeDirectories: ['node_modules', '.git'],
103
- enableWatching: true,
104
- developmentMode: true,
105
- };
106
-
107
- const result = safeValidators.layoutDiscoveryOptions(options);
108
- expect(result.success).toEqual(true);
109
- if (result.success) {
110
- expect(result.data.filePattern).toEqual('layout.tsx');
111
- expect(result.data.excludeDirectories).toEqual(['node_modules', '.git']);
112
- expect(result.data.enableWatching).toEqual(true);
113
- expect(result.data.developmentMode).toEqual(true);
114
- }
115
- });
116
-
117
- it('LayoutConfig - should validate layout config with all options', () => {
118
- const config: LayoutConfig = {
119
- skipLayouts: ['root', 'admin'],
120
- replaceLayout: true,
121
- onlyLayouts: ['custom'],
122
- customLayout: '/custom/layout.tsx',
123
- };
124
-
125
- const result = safeValidators.layoutConfig(config);
126
- expect(result.success).toEqual(true);
127
- });
128
-
129
- it('LayoutConfig - should validate empty layout config', () => {
130
- const config: LayoutConfig = {};
131
-
132
- const result = safeValidators.layoutConfig(config);
133
- expect(result.success).toEqual(true);
134
- });
135
-
136
- it('ResolvedLayout - should validate complete resolved layout', () => {
137
- const resolvedLayout: ResolvedLayout = {
138
- handlers: [],
139
- dataLoaders: [],
140
- errorBoundaries: [],
141
- streamingComponents: [],
142
- metadata: {
143
- totalLayouts: 2,
144
- resolutionTime: 15.5,
145
- cacheHit: false,
146
- },
147
- };
148
-
149
- const result = safeValidators.resolvedLayout(resolvedLayout);
150
- expect(result.success).toEqual(true);
151
- });
152
-
153
- it('ResolvedLayout - should require all metadata fields', () => {
154
- const incompleteLayout = {
155
- handlers: [],
156
- dataLoaders: [],
157
- errorBoundaries: [],
158
- streamingComponents: [],
159
- metadata: {
160
- totalLayouts: 2,
161
- },
162
- };
163
-
164
- const result = safeValidators.resolvedLayout(incompleteLayout);
165
- expect(result.success).toEqual(false);
166
- });
167
-
168
- it('Type compatibility - should ensure TypeScript types match Zod schemas', () => {
169
- const mockRequest = new Request('https://example.com');
170
- const layoutContext: LayoutContext = {
171
- request: mockRequest,
172
- params: { id: '123' },
173
- query: new URLSearchParams(),
174
- state: new Map(),
175
- };
176
-
177
- const validatedContext = validators.layoutContext(layoutContext);
178
- expect(validatedContext).toBeDefined();
179
- expect(validatedContext.request).toEqual(mockRequest);
180
- });
181
-
182
- it('Error handling - should provide meaningful error messages', () => {
183
- const invalidData = {
184
- request: null,
185
- params: null,
186
- query: null,
187
- state: null,
188
- };
189
-
190
- const result = safeValidators.layoutContext(invalidData);
191
- expect(result.success).toEqual(false);
192
- if (!result.success) {
193
- expect(result.error.message).toContain('Invalid layout context');
194
- expect(result.error.getFormattedErrors().length > 0).toEqual(true);
195
- }
196
- });
197
- });
@@ -1,54 +0,0 @@
1
- import { describe, it, expect, vi, beforeEach } from "vitest";
2
- import { createImagePlugin } from "../image-optimization.ts";
3
- import type { ResolvedImageConfig } from "../types.ts";
4
-
5
- describe("createImagePlugin", () => {
6
- const defaultConfig: ResolvedImageConfig = {
7
- enabled: true,
8
- defaultFormat: "webp",
9
- quality: 80,
10
- widths: [200, 400, 600, 800, 1200],
11
- removeMetadata: true,
12
- include: /^[^?]+\.(heif|avif|jpeg|jpg|png|tiff|webp|gif)(\?.*)?$/,
13
- exclude: "public/**/*",
14
- };
15
-
16
- beforeEach(() => {
17
- vi.clearAllMocks();
18
- });
19
-
20
- it("returns empty array when disabled", async () => {
21
- const plugins = await createImagePlugin({ ...defaultConfig, enabled: false }, false);
22
- expect(plugins).toEqual([]);
23
- });
24
-
25
- it("returns imagetools plugin when enabled", async () => {
26
- const plugins = await createImagePlugin(defaultConfig, false);
27
- expect(plugins.length).toBe(1);
28
- expect(plugins[0].name).toBe("imagetools");
29
- });
30
-
31
- it("logs info when verbose is true", async () => {
32
- const consoleSpy = vi.spyOn(console, "log").mockImplementation(() => {});
33
-
34
- await createImagePlugin(defaultConfig, true);
35
-
36
- expect(consoleSpy).toHaveBeenCalledWith(expect.stringContaining("Image optimization enabled"));
37
- consoleSpy.mockRestore();
38
- });
39
-
40
- it("respects custom format setting", async () => {
41
- const plugins = await createImagePlugin({ ...defaultConfig, defaultFormat: "avif" }, true);
42
- expect(plugins.length).toBe(1);
43
- });
44
-
45
- it("respects custom quality setting", async () => {
46
- const plugins = await createImagePlugin({ ...defaultConfig, quality: 90 }, false);
47
- expect(plugins.length).toBe(1);
48
- });
49
-
50
- it("respects custom widths setting", async () => {
51
- const plugins = await createImagePlugin({ ...defaultConfig, widths: [320, 640, 1280] }, false);
52
- expect(plugins.length).toBe(1);
53
- });
54
- });