Skip to content
Merged
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
240 changes: 240 additions & 0 deletions src/index.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -189,4 +189,244 @@ describe('gulpTateru', () => {
expect(error).toBeInstanceOf(PluginError);
expect((error as PluginError).message).toContain('Streaming not supported');
});

it('should handle null files by passing them through', async () => {
const stream = gulpTateruCli();
const nullFile = new Vinyl({
path: 'test.json',
contents: null,
});

const result = await new Promise((resolve) => {
stream.once('data', resolve);
stream.write(nullFile);
stream.end();
});

expect(result).toBe(nullFile);
});

it('should handle errors from core function', async () => {
const stream = gulpTateruCli();

// Create a config that will cause core() to fail
// Using an invalid cwd path should cause an error in core
const invalidConfigFile = new Vinyl({
path: 'test-config.json',
cwd: '/absolutely/nonexistent/path/that/should/cause/error',
base: '/test',
contents: Buffer.from(
JSON.stringify({
// Valid JSON structure but invalid paths/config for tateru-cli core
environments: {
dev: { minify: false },
},
translations: {},
pages: {
test: {
template: 'nonexistent.html.twig',
output: 'test.html',
},
},
})
),
});

const errorPromise = new Promise((resolve) => {
stream.once('error', resolve);
});

stream.write(invalidConfigFile);
stream.end();

const error = await errorPromise;

expect(error).toBeInstanceOf(PluginError);
expect((error as PluginError).plugin).toBe('gulp-tateru-cli');
});

it('should work with env option independently', async () => {
const { count } = await new Promise<{
count: number;
}>((resolve) => {
let n = 0;

gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(gulpTateruCli({ env: 'dev' }))
.on('data', () => {
n++;
})
.on('end', () => {
resolve({ count: n });
});
});

expect(count).toBe(6);
});

it('should apply both formatter and minify functions together', async () => {
const formatter: Formatter = async (contents, fileType) =>
`FORMATTED (${fileType}): ${contents}`;
const minify: Minify = async (contents) => contents.replace(/\s+/g, ' ');

const { generatedFile } = await new Promise<{
generatedFile: string;
}>((resolve) => {
let generatedFile: string;

gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(
gulpTateruCli({
formatter,
minify,
page: 'about',
env: 'prod',
})
)
.on('data', (file) => {
generatedFile = file.contents.toString();
})
.on('end', () => {
resolve({ generatedFile });
});
});

expect(generatedFile).toContain('FORMATTED (html):');
expect(generatedFile).not.toMatch(/\s{2,}/); // No multiple spaces
});

it('should handle different file types correctly', async () => {
const formatterCalls: { contents: string; fileType: string }[] = [];
const formatter: Formatter = async (contents, fileType) => {
formatterCalls.push({ contents, fileType: fileType ?? 'unknown' });
return Promise.resolve(contents);
};

await new Promise<void>((resolve) => {
gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(gulpTateruCli({ formatter }))
.on('data', () => {
// Just collect files
})
.on('end', () => {
resolve();
});
});

const fileTypes = formatterCalls.map((call) => call.fileType);
expect(fileTypes).toContain('html');
expect(fileTypes).toContain('txt');
expect(fileTypes).toContain('xml');
expect(fileTypes).toContain('webmanifest');
});

it('should set correct vinyl file properties', async () => {
const files: Vinyl[] = [];

await new Promise<void>((resolve) => {
gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(gulpTateruCli({ page: 'about' }))
.on('data', (file) => {
files.push(file);
})
.on('end', () => {
resolve();
});
});

expect(files).toHaveLength(1);
const file = files[0];

expect(file).toBeInstanceOf(Vinyl);
expect(file.contents).toBeInstanceOf(Buffer);
expect(file.path).toBeTruthy();
expect(file.base).toBeTruthy();
expect(file.cwd).toBeTruthy();
});

it('should handle nonexistent page gracefully', async () => {
const { count } = await new Promise<{
count: number;
}>((resolve) => {
let n = 0;

gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(gulpTateruCli({ page: 'nonexistent-page' }))
.on('data', () => {
n++;
})
.on('end', () => {
resolve({ count: n });
});
});

// Should generate 0 files for nonexistent page
expect(count).toBe(0);
});

it('should handle nonexistent language gracefully', async () => {
const { count } = await new Promise<{
count: number;
}>((resolve) => {
let n = 0;

gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(gulpTateruCli({ lang: 'nonexistent-lang' }))
.on('data', () => {
n++;
})
.on('end', () => {
resolve({ count: n });
});
});

// Should generate 0 files for nonexistent language
expect(count).toBe(0);
});

it('should handle async formatter and minify functions', async () => {
const formatter: Formatter = async (contents) => {
// Simulate async operation
await new Promise((resolve) => setTimeout(resolve, 1));
return `ASYNC_FORMATTED: ${contents}`;
};

const minify: Minify = async (contents) => {
// Simulate async operation
await new Promise((resolve) => setTimeout(resolve, 1));
return contents.replace(/\s+/g, '');
};

const { generatedFile } = await new Promise<{
generatedFile: string;
}>((resolve) => {
let generatedFile: string;

gulp
.src('./tateru.config.json', { cwd: 'test/fixtures' })
.pipe(
gulpTateruCli({
formatter,
minify,
page: 'about',
env: 'prod',
})
)
.on('data', (file) => {
generatedFile = file.contents.toString();
})
.on('end', () => {
resolve({ generatedFile });
});
});

expect(generatedFile).toContain('ASYNC_FORMATTED:');
expect(generatedFile).not.toMatch(/\s+/);
});
});