Skip to content

Commit

Permalink
Much better and broader tests
Browse files Browse the repository at this point in the history
  • Loading branch information
catuhana committed Jul 19, 2024
1 parent ce29078 commit 739ab8e
Show file tree
Hide file tree
Showing 3 changed files with 185 additions and 179 deletions.
10 changes: 5 additions & 5 deletions deno.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

274 changes: 106 additions & 168 deletions src/extend.test.ts
Original file line number Diff line number Diff line change
@@ -1,180 +1,130 @@
import { describe, it } from '@std/testing/bdd';
import { assert, assertEquals, assertInstanceOf } from '@std/assert';

import { _extendTheme } from './extend.ts';
import {
type CatppuccinColors as CatppuccinColours,
type CatppuccinFlavors as CatppuccinFlavours,
flavorEntries as flavourEntries,
flavors as flavours,
} from '@catppuccin/palette';
import { flavorEntries as flavourEntries } from '@catppuccin/palette';

const CUSTOM_PREFIX = 'meow';
import { _extendTheme } from './extend.ts';
import type { ExtendOptions, ThemeObject } from './types.ts';

describe('extending theme with defaults results an object in required format', () => {
describe('`_extendTheme` with', () => {
const expectedFlavours = flavourEntries.map(([flavourName]) => flavourName);
const expectedColours = flavours[expectedFlavours[0]].colorEntries.map(
([colourName]) => colourName,
);

it('with default prefix', () => {
const theme = {} as Record<
'colors',
{
ctp: {
[flavour in keyof CatppuccinFlavours]: {
[colour in keyof CatppuccinColours]: string;
};
};
const expectedColours = flavourEntries[0][1].colorEntries.map((
[colourName],
) => colourName);

createExtendTestCases({ prefix: 'meow' }, [{
description: 'results a correct object schema',
validate: (theme, options) => {
assert(theme);
assertInstanceOf(theme, Object);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), [options.prefix]);
assertEquals(Object.keys(theme.colors[options.prefix]), expectedFlavours);

for (const flavour of expectedFlavours) {
assertEquals(
Object.keys(theme.colors[options.prefix][flavour]),
expectedColours,
);
}
>;
_extendTheme()(theme);
},
}]);

assertInstanceOf(theme, Object);
createExtendTestCases({ prefix: false }, [{
description: 'results a correct object schema',
validate: (theme) => {
assert(theme);
assertInstanceOf(theme, Object);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), ['ctp']);
assertEquals(Object.keys(theme.colors.ctp), expectedFlavours);
for (const flavour of expectedFlavours) {
assertEquals(Object.keys(theme.colors.ctp[flavour]), expectedColours);
}
});

it('without a prefix', () => {
const theme = {} as Record<
'colors',
{
[flavour in keyof CatppuccinFlavours]: {
[colour in keyof CatppuccinColours]: string;
};
assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), expectedFlavours);

for (const flavour of expectedFlavours) {
assertEquals(Object.keys(theme.colors[flavour]), expectedColours);
}
>;
},
}]);

_extendTheme({ prefix: false })(theme);
createExtendTestCases({}, [{
description: 'results a correct object schema',
validate: (theme) => {
assert(theme);
assertInstanceOf(theme, Object);

assertInstanceOf(theme, Object);
assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), ['ctp']);
assertEquals(Object.keys(theme.colors.ctp), expectedFlavours);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), expectedFlavours);
for (const flavour of expectedFlavours) {
assertEquals(Object.keys(theme.colors[flavour]), expectedColours);
}
});

it('with custom prefix', () => {
const theme = {} as Record<
'colors',
{
[CUSTOM_PREFIX]: {
[flavour in keyof CatppuccinFlavours]: {
[colour in keyof CatppuccinColours]: string;
};
};
for (const flavour of expectedFlavours) {
assertEquals(Object.keys(theme.colors.ctp[flavour]), expectedColours);
}
>;

_extendTheme({ prefix: CUSTOM_PREFIX })(theme);

assertInstanceOf(theme, Object);
},
}]);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), [CUSTOM_PREFIX]);
assertEquals(Object.keys(theme.colors[CUSTOM_PREFIX]), expectedFlavours);
for (const flavour of expectedFlavours) {
assertEquals(
Object.keys(theme.colors[CUSTOM_PREFIX][flavour]),
expectedColours,
);
}
});
});
createExtendTestCases({ prefix: 'meow', defaultFlavour: 'frappe' }, [{
description: 'results a correct object schema',
validate: (theme, options) => {
assert(theme);
assertInstanceOf(theme, Object);

describe("extending theme with 'defaultFlavour'", () => {
const expectedFlavours = flavourEntries.map(([flavourName]) => flavourName);

describe('results an object in required format', () => {
for (const flavour of expectedFlavours) {
const expectedColours = flavours[flavour].colorEntries.map(
([colourName]) => colourName,
);

describe(`with ${flavour} flavour`, () => {
it('using default prefix', () => {
const theme = {} as Record<
'colors',
{
ctp: {
[colour in keyof CatppuccinColours]: string;
};
}
>;

_extendTheme({ defaultFlavour: flavour })(theme);

assertInstanceOf(theme, Object);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), ['ctp']);
assertEquals(Object.keys(theme.colors.ctp), expectedColours);
});
assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), [options.prefix]);
assertEquals(Object.keys(theme.colors[options.prefix]), expectedColours);
},
}]);

it(`without a prefix`, () => {
const theme = {} as Record<
'colors',
{
[colour in keyof CatppuccinColours]: string;
}
>;
createExtendTestCases({ prefix: false, defaultFlavour: 'latte' }, [{
description: 'results a correct object schema',
validate: (theme) => {
assert(theme);
assertInstanceOf(theme, Object);

_extendTheme({ prefix: false, defaultFlavour: flavour })(theme);
assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), expectedColours);
},
}]);

assertInstanceOf(theme, Object);
createExtendTestCases({ defaultFlavour: 'macchiato' }, [{
description: 'results a correct object schema',
validate: (theme) => {
assert(theme);
assertInstanceOf(theme, Object);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), expectedColours);
assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), ['ctp']);
assertEquals(Object.keys(theme.colors.ctp), expectedColours);
},
}]);

function createExtendTestCases<P extends string, O extends ExtendOptions<P>>(
extendOptions: O,
tests: {
description: string;
validate: (theme: ThemeObject<O>, extendOptions: O) => void;
}[],
) {
const theme = {} as ThemeObject<O>;

describe(`with \`${Deno.inspect(extendOptions)}\` options`, () => {
for (const test of tests) {
it(test.description, () => {
_extendTheme(extendOptions)(theme);

test.validate(theme, extendOptions);
});
}
});

it(`with custom prefix`, () => {
const theme = {} as Record<
'colors',
{
[CUSTOM_PREFIX]: {
[colour in keyof CatppuccinColours]: string;
};
}
>;

_extendTheme({ prefix: CUSTOM_PREFIX, defaultFlavour: flavour })(
theme,
);

assertInstanceOf(theme, Object);

assertEquals(Object.keys(theme), ['colors']);
assertEquals(Object.keys(theme.colors), [CUSTOM_PREFIX]);
assertEquals(
Object.keys(theme.colors[CUSTOM_PREFIX]),
expectedColours,
);
});
});
}
});
return theme;
}
});

Deno.test('generated colours are accurate to Catppuccin', () => {
const theme = {} as Record<
'colors',
{
ctp: {
[flavour in keyof CatppuccinFlavours]: {
[colour in keyof CatppuccinColours]: string;
};
};
}
>;
Deno.test("generated colours are accurate to Catppuccin's", () => {
const options = {};
const theme = {} as ThemeObject<typeof options>;

_extendTheme()(theme);
_extendTheme(options)(theme);

for (const [flavourName, flavour] of flavourEntries) {
assertInstanceOf(theme.colors.ctp[flavourName], Object);
Expand All @@ -186,23 +136,11 @@ Deno.test('generated colours are accurate to Catppuccin', () => {
});

Deno.test("conflicting keys don't override existing keys", () => {
const theme = {
colors: {
red: 'meow',
},
} as Record<
'colors',
{
[colour in keyof CatppuccinColours]: string;
} & {
ctp: {
[colour in keyof CatppuccinColours]: string;
};
}
>;
const options = { prefix: false, defaultFlavour: 'mocha' } as const;
const theme = { colors: { red: 'meow' } } as ThemeObject<typeof options>;

_extendTheme({ defaultFlavour: 'frappe', prefix: false })(theme);
_extendTheme(options)(theme);

assertEquals(theme.colors.red, 'meow');
assert(theme.colors.ctp.red);
assert(theme.colors.ctp?.red);
});
Loading

0 comments on commit 739ab8e

Please sign in to comment.