Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 34 additions & 0 deletions _internal-tools/bench.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { getAllWorkspaceConfigs } from './deno-config.ts'
import { validateFixturesOrThrow } from './validate-fixtures.ts'

/**
* Main benchmark runner script.
* Validates fixtures before running any benchmarks.
*/
async function main(): Promise<void> {
try {
Comment thread
coderabbitai[bot] marked this conversation as resolved.
const workspaces = await getAllWorkspaceConfigs()
globalThis.console.log(` Validating ${workspaces.length} workspace fixtures...\n`)

// Validate all fixtures before running benchmarks (fail fast)
await validateFixturesOrThrow()

globalThis.console.log(' All workspace fixtures are valid!\n')

// TODO: Add actual benchmark execution here
// For now, this is a placeholder for future benchmark implementation
globalThis.console.log(' Benchmark execution would start here...')
globalThis.console.log(' (Benchmark runner implementation pending)\n')
} catch (error) {
// Print the detailed error message and exit with error code
globalThis.console.error(error instanceof Error ? error.message : String(error))
Deno.exit(1)
}
}

// Run the main function
if (import.meta.main) {
await main()
}

// Made with Bob
6 changes: 4 additions & 2 deletions _internal-tools/deno-config.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
import { join } from '@std/path'
import { dirname, fromFileUrl, join } from '@std/path'
import { z } from 'zod'

/** Barrel file name used for module exports */
export const BARREL_FILE_NAME = 'mod.ts'
/** Deno's configuration file name */
export const DENO_FILE_NAME: string = 'deno.json'
/** This is the project's root directory */
export const ROOT_DIRECTORY: string = new URL('..', import.meta.url).pathname
export const ROOT_DIRECTORY: string = dirname(
dirname(fromFileUrl(import.meta.url)),
)
/** This is the path to the root Deno configuration file */
export const ROOT_DENO_FILE_PATH: string = join(ROOT_DIRECTORY, DENO_FILE_NAME)

Expand Down
22 changes: 22 additions & 0 deletions _internal-tools/fixture-types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
/**
* Interface that all workspace fixtures must implement.
* Provides test data at different scales for benchmarking.
*/
export interface FixtureFactory {
/**
* Returns a small dataset for quick benchmarks
*/
small: () => unknown

/**
* Returns a medium-sized dataset for standard benchmarks
*/
medium: () => unknown

/**
* Returns a large dataset for stress testing
*/
large: () => unknown
}

// Made with Bob
161 changes: 161 additions & 0 deletions _internal-tools/validate-fixtures.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,161 @@
import { exists } from '@std/fs'
import { join, toFileUrl } from '@std/path'
import {
getAllWorkspaceConfigs,
ROOT_DIRECTORY,
} from './deno-config.ts'
import type { FixtureFactory } from './fixture-types.ts'

/** Error details for a single workspace fixture validation failure */
interface FixtureValidationError {
workspaceName: string
expectedPath: string
missing: string[]
}

/** Result of fixture validation across all workspaces */
interface ValidationResult {
success: boolean
errors: FixtureValidationError[]
}

/**
* Validates that a workspace has a fixtures.ts file with required exports
* @param workspaceName - Name of the workspace to validate
* @returns Validation error if any, null if valid
*/
async function validateWorkspaceFixtures(
workspaceName: string,
): Promise<FixtureValidationError | null> {
const fixturePath = join(ROOT_DIRECTORY, workspaceName, 'fixtures.ts')
const missing: string[] = []

// Check if fixtures.ts exists
const fixtureExists = await exists(fixturePath)
if (!fixtureExists) {
missing.push('fixtures.ts file')
return {
workspaceName,
expectedPath: fixturePath,
missing,
}
}

// Try to import and validate exports
try {
// Use proper URL construction for cross-platform compatibility
const fixtureUrl = toFileUrl(fixturePath).href
const url = new URL(fixtureUrl)

// Validate that the import path is a safe local file URL
if (url.protocol !== 'file:') {
throw new Error(`Invalid fixture import path: ${fixtureUrl}`)
}

// codacy-disable-next-line
const fixtureModule = await import(url.href)

Check failure on line 56 in _internal-tools/validate-fixtures.ts

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

_internal-tools/validate-fixtures.ts#L56

Unsafe call to import for argument 0

// Support both named exports and default export object
const source = fixtureModule.default ?? fixtureModule

// Validate required function exports
const requiredFunctions: (keyof FixtureFactory)[] = [
'small',
'medium',
'large',
]

for (const functionName of requiredFunctions) {
if (typeof source[functionName] !== 'function') {
missing.push(`${functionName}() function`)
}
}

if (missing.length > 0) {
return {
workspaceName,
expectedPath: fixturePath,
missing,
}
}

return null
} catch (error) {
const errorMessage = error instanceof Error ? error.message : String(error)
missing.push(`valid fixtures.ts (import failed: ${errorMessage})`)
return {
workspaceName,
expectedPath: fixturePath,
missing,
}
}
}

/**
* Validates fixtures across all workspaces
* @returns Validation result with any errors found
*/
export async function validateAllFixtures(): Promise<ValidationResult> {
const workspaceConfigs = await getAllWorkspaceConfigs()
const errors: FixtureValidationError[] = []

// Validate each workspace in parallel
const validationResults = await Promise.all(
workspaceConfigs.map(({ workspaceName }) =>
validateWorkspaceFixtures(workspaceName)
),
)

// Collect errors
for (const result of validationResults) {
if (result !== null) {
errors.push(result)
}
}

return {
success: errors.length === 0,
errors,
}
}

/**
* Formats validation errors into a readable error message
* @param errors - Array of validation errors
* @returns Formatted error message
*/
function formatValidationErrors(errors: FixtureValidationError[]): string {
const lines = [
' Fixture validation failed!\n',
`Found ${errors.length} workspace${errors.length === 1 ? '' : 's'} with missing or invalid fixtures:\n`,
]

for (const error of errors) {
lines.push(`\n Workspace: ${error.workspaceName}`)
lines.push(` Path: ${error.expectedPath}`)
lines.push(` Missing: ${error.missing.join(', ')}`)
}

lines.push('\n\n Required: Each workspace must have a fixtures.ts file that exports:')
lines.push(' • small(): function returning small test dataset')
lines.push(' • medium(): function returning medium test dataset')
lines.push(' • large(): function returning large test dataset')
lines.push('\n Supports both named exports and default export object.')

return lines.join('\n')
}

/**
* Validates all workspace fixtures and throws if any are invalid
* @throws Error with detailed information about missing fixtures
*/
export async function validateFixturesOrThrow(): Promise<void> {
const result = await validateAllFixtures()

if (!result.success) {

Check warning on line 155 in _internal-tools/validate-fixtures.ts

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

_internal-tools/validate-fixtures.ts#L155

Unhandled errors detected in asynchronous function
// Errors are intentionally propagated and handled by bench.ts
throw new Error(formatValidationErrors(result.errors))
}
}

// Made with Bob
27 changes: 27 additions & 0 deletions array/fixtures.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/**
* Fixture factory for array benchmarks
* Provides test data at different scales
*/

/**
* Returns a small dataset for quick benchmarks
*/
export function small(): number[] {
return Array.from({ length: 10 }, (_, index) => index)
}

/**
* Returns a medium-sized dataset for standard benchmarks
*/
export function medium(): number[] {
return Array.from({ length: 1000 }, (_, index) => index)
}

/**
* Returns a large dataset for stress testing
*/
export function large(): number[] {
return Array.from({ length: 100_000 }, (_, index) => index)
}


1 change: 1 addition & 0 deletions deno.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
{
"$schema": "https://raw.githubusercontent.com/denoland/deno/main/cli/schemas/config-file.v1.json",
"tasks": {
"bench": "deno run --allow-read --allow-net ./_internal-tools/bench.ts",
"check:exports": "deno run --allow-read --allow-write --allow-run ./_internal-tools/check-exports.ts",
"check:imports": "deno run --allow-read ./_internal-tools/check-imports.ts",
"check:links": "deno run --allow-read ./_internal-tools/check-links.ts",
Expand Down