Skip to content

Commit

Permalink
Remove reliance on Node libraries for browser compatibility (#44)
Browse files Browse the repository at this point in the history
  • Loading branch information
JstnMcBrd authored Dec 9, 2024
1 parent 27e34e3 commit 3d9b2fb
Show file tree
Hide file tree
Showing 7 changed files with 22 additions and 26 deletions.
14 changes: 7 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@

## About

**dectalk-tts** is a simple [Node](https://nodejs.org/) package to interact with the **aeiou** Dectalk web API. It is developed in [TypeScript](https://www.typescriptlang.org/) and transpiles to JavaScript (ESM).
**dectalk-tts** is a simple package to interact with the **aeiou** Dectalk web API. It is developed in [TypeScript](https://www.typescriptlang.org/) and transpiles to JavaScript (ESM).

[Dectalk](https://github.com/dectalk/dectalk) is a text-to-speech engine originally created in the 1980s. Today, it is best known for [viral videos](https://www.youtube.com/watch?v=Hv6RbEOlqRo) of the game [Moonbase Alpha](https://store.steampowered.com/app/39000/Moonbase_Alpha/).

Expand All @@ -27,9 +27,7 @@
## Prerequesites

This package has no production dependencies!

However, it does require Node 18 or higher. Use `node --version` to check your node version.
This package has no production dependencies, and works with Node (`>=18`) or the browser.

## Installation

Expand All @@ -44,26 +42,28 @@ None of the examples below include error handling, but don't forget it!

```js
import dectalk from 'dectalk-tts';
import { Buffer } from 'node:buffer';
import { writeFileSync } from 'node:fs';

const output = await dectalk('aeiou');
writeFileSync('output.wav', output);
writeFileSync('output.wav', Buffer.from(output));
```

### CommonJS

```js
const dectalk = require('dectalk-tts');
const { Buffer } = require('node:buffer');
const { writeFileSync } = require('node:fs');

(async () => {
const output = await dectalk('John Madden');
writeFileSync('output.wav', output);
writeFileSync('output.wav', Buffer.from(output));
})();

// or

dectalk('uuuuuuuuuu').then((output) => writeFileSync('output.wav', output));
dectalk('uuuuuuuuuu').then((output) => writeFileSync('output.wav', Buffer.from(output)));
```

### Options
Expand Down
4 changes: 2 additions & 2 deletions package-lock.json

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

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "dectalk-tts",
"version": "1.0.2-alpha",
"version": "2.0.0-alpha",
"description": "API wrapper for the Dectalk TTS system",
"keywords": [
"api",
Expand Down
10 changes: 4 additions & 6 deletions src/index.cts
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
import type { Buffer } from 'node:buffer';

/**
* @param text The text to send to the aeiou Dectalk API
* @returns A buffer containing wav-encoded binary output
* @returns An array buffer containing wav-encoded binary output
* @throws If `text` is empty or only whitespace
* @throws If the API returns a non-200 response
*/
export = async function dectalk(input: string): Promise<Buffer> {
const dectalkESM = (await import('./index.js')).default;
return await dectalkESM(input);
export = async function dectalk(input: string): Promise<ArrayBuffer> {
const dectalk = (await import('./index.js')).default;
return await dectalk(input);
};
3 changes: 1 addition & 2 deletions src/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import { Buffer } from 'node:buffer';
import { basename } from 'node:path';

import { afterAll, describe, expect, it, vi } from 'vitest';
Expand Down Expand Up @@ -35,7 +34,7 @@ describe(basename(import.meta.url), () => {
it('should return the buffer if it receives a good response', async () => {
fetchMock.mockResolvedValue(goodResponse);
const output = await dectalk('test');
expect(output).toEqual(Buffer.from(goodResponseBuffer));
expect(output).toEqual(goodResponseBuffer);
});

it('should throw an error if it receives a bad response', async () => {
Expand Down
10 changes: 3 additions & 7 deletions src/index.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,10 @@
import { Buffer } from 'node:buffer';
import { URL } from 'node:url';

/**
* @param text The text to send to the aeiou Dectalk API
* @returns A buffer containing wav-encoded binary output
* @returns An array buffer containing wav-encoded binary output
* @throws If `text` is empty or only whitespace
* @throws If the API returns a non-200 response
*/
export default async function dectalk(text: string): Promise<Buffer> {
export default async function dectalk(text: string): Promise<ArrayBuffer> {
// The API does not like empty prompts
text = text.trim();
if (text.length === 0) {
Expand All @@ -28,6 +25,5 @@ export default async function dectalk(text: string): Promise<Buffer> {
}

// Parse and return response
const binaryData = await response.arrayBuffer();
return Buffer.from(binaryData);
return await response.arrayBuffer();
}
5 changes: 4 additions & 1 deletion test/api.test.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { Buffer } from 'node:buffer';
import { readFileSync } from 'node:fs';
import { basename } from 'node:path';

Expand All @@ -7,7 +8,9 @@ import dectalk from '../src/index.js';

describe(basename(import.meta.url), () => {
it('should succeed', async () => {
const actual = await dectalk('test');
const actual = Buffer.from(
await dectalk('test'),
);
const expected = readFileSync('./test/test.wav');
expect(actual).toEqual(expected);
});
Expand Down

0 comments on commit 3d9b2fb

Please sign in to comment.