Thank you for your interest in contributing to tinyframejs, the high-performance JavaScript engine for tabular data. We welcome contributions of all kinds — code, docs, benchmarks, ideas.
This repository is a standalone part of the AlphaQuantJS ecosystem and contains:
- ✅ The core tabular engine built on TypedArray structures (TinyFrame)
- ✅ Functional APIs for stats, filtering, reshaping
- ✅ Chainable
DataFramewrapper (inspired by Pandas) - ✅ Vitest-based unit tests
- ✅ Benchmarks vs competitors in
/benchmarks
Project structure is in README.md
Enables you to add new aggregators in a plug-and-play fashion — simply create a file in
primitives/and export it inindex.js.
-
Create the “primitive” file
(Here,aggregationis just an example — you may have other module directories, each with their ownprimitives/folder for plug-and-play modules.) Inmethods/aggregation/primitives/, createyourNew.js:// methods/aggregation/primitives/yourNew.js /** * yourNew — example of a new aggregator * * @param {{ validateColumn(frame, column): void }} deps * @returns {(frame: TinyFrame, column: string) => any} */ export const yourNew = ({ validateColumn }) => (frame, column) => { validateColumn(frame, column); // …your logic here return; /* result */ };
-
Register it in the barrel
Openmethods/aggregation/primitives/index.jsand add:// at the top, alongside other exports export { yourNew as _yourNew } from './yourNew.js';
-
Inject dependencies
Ensure yourindex.jswires it up automatically:import * as rawFns from './index.js'; // _yourNew is now part of rawFns import { validateColumn } from '../../../primitives/validators.js'; const deps = { validateColumn /*, other shared deps */ }; export const aggregationFunctions = Object.fromEntries( Object.entries(rawFns).map(([key, fn]) => [ key.replace(/^_/, ''), // strip the leading “_” fn(deps), // yields a (frame, column) => … function ]), );
-
Facade remains unchanged
Inmethods/aggregation/groupByAgg.jsyou don’t need to touch a thing —yourNewis picked up automatically:import { aggregationFunctions } from './primitives/index.js'; export function groupByAgg(frame, column, aggName) { const fn = aggregationFunctions[aggName]; if (!fn) throw new Error(`Unknown aggregator: ${aggName}`); return fn(frame, column); }
-
Use your new aggregator
import { groupByAgg } from 'methods/aggregation'; const result = groupByAgg(myFrame, 'someColumn', 'yourNew');
That’s it —
yourNewworks out of the box, with no further edits to the facade or other modules.
- Fork this repo on GitHub
- Clone your fork locally:
git clone [email protected]:AlphaQuantJS/tinyframejs.git cd tinyframejs npm install
- Create a feature branch:
git checkout -b feat/your-feature-name
- Implement your feature or fix inside
src/ - Run tests and linting before pushing (see workflow below)
- Push and open a Pull Request to the
mainbranch
Please review our Coding Guidelines for:
- Performance tips for V8
- Data integrity and numerical precision
- Modular and reusable function design
- Memory-efficient handling of large datasets
- Code builds with
pnpm build - Added or updated relevant tests in
test/ - Follows ESLint/Prettier rules
- Descriptive commit message (see below)
- Linked to a GitHub Issue (if applicable)
- Clear description in PR body of what was changed and why
- If change is test-only or doc-only, ensure CI does not fail due to lack of coverage
- If no tests are added, check that Vitest is configured with
passWithNoTests: trueand Codecov usesfail_ci_if_error: falseorhandle_no_reports_found: false - If new code is added, ensure at least minimal test coverage is present (to trigger coverage report upload)
pnpm format📌 Automatically applies the .prettierrc style to all .js, .json, .md, .yml, etc.
pnpm lint --fix📌 Fixes linting errors and style, including JSDoc, spaces, indents, no-unused-vars, etc.
pnpm test📌 Runs all tests (via Vitest) and checks that code is not broken.
pnpm coverage📌 Generates coverage/lcov.info and prints the report to the console.
git add .
git commit -m "feat: describe your change"📌 This will automatically trigger:
npx lint-stagednpx prettier --writeon staged fileseslint --fixon staged.js/.ts
pnpm format && pnpm lint --fix && pnpm testWe use Conventional Commits for changelogs and releases.
<type>(scope): short summary
feat(core): add corrMatrix support
fix(frame): handle NaN edge case in rollingMean
docs(readme): add usage examples
Common types:
| Type | Description |
|---|---|
| feat | New feature |
| fix | Bug fix |
| docs | Documentation-only changes |
| refactor | Code refactor without behavioral change |
| test | Adding or updating tests |
| chore | Infrastructure, config, CI, etc. |
- Keep pull requests small and focused
- Add tests for each new piece of logic
- Document public functions with JSDoc
- Benchmark performance-critical paths
- Update
examples/when introducing new APIs
- Run tests via
pnpm test - Coverage is uploaded to Codecov
- Benchmarks are located in
benchmarks/ - Guard tests protect against performance/memory regressions
Use GitHub Issues for:
- Bugs and regressions
- Feature suggestions
- Discussion prompts
We tag beginner-friendly tasks as good first issue.
- See
examples/for real-world usage - Contribute examples, notebooks, articles, or benchmark comparisons!
- Ask in GitHub Discussions
- Submit new ideas via PR or Issues
- Mention us on Twitter: @AlphaQuantJS
Thanks again for being part of the TinyFrameJS open-source journey 🙌 Let's build next-gen tools for financial analysis and large-scale data processing in JavaScript together ⚡