Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

inbatches

Package Overview
Dependencies
Maintainers
1
Versions
10
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

inbatches - npm Package Compare versions

Comparing version 0.0.7 to 0.0.8

8

dist/batcher.js

@@ -6,7 +6,7 @@ "use strict";

active = true;
cache = new Map();
uniques = new Map();
callbacks = [];
append(key) {
if (this.cache.has(key)) {
return this.cache.get(key);
if (this.uniques.has(key)) {
return this.uniques.get(key);
}

@@ -16,3 +16,3 @@ const promise = new Promise((resolve, reject) => {

});
this.cache.set(key, promise);
this.uniques.set(key, promise);
return promise;

@@ -19,0 +19,0 @@ }

@@ -17,16 +17,21 @@ "use strict";

}
function getInstanceBatcher(self, property, fn, options) {
const bkey = `${property}_____batcher`;
// check if the instance already has a batcher for this method
if (self[bkey])
return self[bkey];
// otherwise, create a new batcher and store it in the instance so it is unique for that instance
self[bkey] = new MethodBatcher(self, fn, options);
return self[bkey];
// this Symbol is used to store the MethodBatcher instances in the instance of the class that is using the decorator
// this way we can have a unique batcher for each instance and method of the class decorated with @InBatches
const holder = Symbol('__inbatches__');
function getInstanceBatcher(instance, property, descriptor, options) {
// check if the instance already has a holder for all the batchers in the class
instance[holder] = instance[holder] ?? new Map();
// check if the instance already has a method matcher for this specific method
if (instance[holder].has(property))
return instance[holder].get(property);
// otherwise, create a new batcher and store it in the instance batchers holder
const batcher = new MethodBatcher(instance, descriptor, options);
instance[holder].set(property, batcher);
return batcher;
}
function InBatches(options) {
return function (_, property, descriptor) {
const fn = descriptor.value;
const method = descriptor.value;
descriptor.value = function (...args) {
const batcher = getInstanceBatcher(this, property, fn, options);
const batcher = getInstanceBatcher(this, property, method, options);
return batcher.enqueue(args);

@@ -33,0 +38,0 @@ };

{
"name": "inbatches",
"version": "0.0.7",
"version": "0.0.8",
"private": false,

@@ -5,0 +5,0 @@ "license": "MIT",

@@ -12,3 +12,5 @@ # @InBatches(📦,📦,📦,...)

Heavily inspired by [graphql/dataloader](https://github.com/graphql/dataloader) but using classes and decorators 😜
Heavily inspired by [graphql/dataloader](https://github.com/graphql/dataloader) but simpler using decorators (😜 really
decoupled). Because of that the
rest of your application doesn't event need to know about the batching/dataloader, it just works!

@@ -19,8 +21,6 @@ ## Table of Contents

- [Usage](#usage)
- [Basic Usage](#basic-usage)
- [Using the `@InBatches` Decorator](#using-the-inbatches-decorator)
- [Basic usage with `@InBatches` Decorator](#basic-usage-with-inbatches-decorator)
- [Advanced usage with custom `Batcher` class](#advanced-usage-with-custom-batcher-class)
- [API](#api)
- [`BatcherOptions`](#batcheroptions)
- [`Batcher<K, V>` Class](#batcherk-v-class)
- [`InBatches<K, V>` Decorator](#inbatches-decorator)
- [Contributing](#contributing)

@@ -35,25 +35,41 @@ - [License](#license)

or
```bash
yarn add inbatches
```
## Usage
### Using the `Batcher` Class
### Basic usage with `@InBatches` Decorator
The simplest way to get the grown running is to use the `@InBatches` decorator. This decorator will wrap your method
and will batch-enable it, like magic! 🧙‍♂️
```typescript
import { Batcher } from 'inbatches';
import { InBatches } from 'inbatches';
// Define a class that extends Batcher and implements the `run` method
// the `run` method will be called with an array of keys collected from the `enqueue` method
class MyBatcher extends Batcher<number, string> {
async run(ids: number[]): Promise<string[]> {
// Perform asynchronous operations using the keys
// you must return an array of results in the same order as the keys
return this.db.getMany(ids);
class MyService {
// (optional) overloaded method, where you define the keys as `number` and the return type as `User` for typings
async fetch(key: number): Promise<User>;
// This method is now batch-enabled
@InBatches()
async fetch(keys: number | number[]): Promise<User | User[]> {
if (Array.isArray(keys)) return await this.db.getMany(keys);
// in reality the Decorator will wrap this method and it will never be called with a single key :)
throw new Error('It will never be called with a single key 😉');
}
}
```
// Create an instance of your batcher
const batcher = new MyBatcher();
Profit! 🤑
// Enqueue keys for batched execution
```typescript
const service = new MyService();
const result = [1, 2, 3, 4, 5].map(async id => {
return await batcher.enqueue(id);
return await service.fetch(id);
});

@@ -67,30 +83,29 @@

### Using the `@InBatches` Decorator
### Advanced usage with custom `Batcher` class
The library also provides a decorator called `InBatches` that you can use to batch-enable methods of your class.
Another way to use the library is to create a class that extends the `Batcher` class and implement the `run` method.
This class will provide a `enqueue` method that you can use to enqueue keys for batched execution.
```typescript
import { InBatches } from 'inbatches';
import { Batcher } from 'inbatches';
class MyService {
// (optional) overloaded method, where you define the keys as `number` and the return type as `string` for typings
async fetch(keys: number): Promise<string>;
// in reality the Decorator will wrap this method and it will never be called with a single key :)
@InBatches() // This method is now batch-enabled
async fetch(keys: number | number[]): Promise<string | string[]> {
if (Array.isArray(keys)) {
return this.db.getMany(keys);
}
// the Decorator will wrap this method and because of that it will never be called with a single key
throw new Error('It will never be called with a single key 😉');
// The `run` method will be called with an array of keys collected from the `enqueue` method
class MyBatcher extends Batcher<number, string> {
async run(ids: number[]): Promise<string[]> {
// Perform asynchronous operations using the keys
// you must return an array of results in the same order as the keys
return this.db.getMany(ids);
}
}
```
const service = new MyService();
then
```typescript
// Create an instance of your batcher
const batcher = new MyBatcher();
// Enqueue keys for batched execution
const result = [1, 2, 3, 4, 5].map(async id => {
return await service.fetch(id);
return await batcher.enqueue(id);
});

@@ -115,29 +130,2 @@

### `Batcher<K, V>` Class
An abstract class that provides the core functionality for batching and executing asynchronous operations.
- `enqueue(key: K): Promise<V>`: Enqueues a key for batching and returns a promise that resolves to the result when
available.
### `InBatches` Decorator
A decorator function that can be applied to methods to enable batching.
- Usage: `@InBatches(options?: BatcherOptions)`
- Example:
```typescript
class MyService {
// (optional) overloaded method, where you define the keys as `number` and the return type as `string` for typings
async fetchResults(keys: number): Promise<string>
@InBatches({ maxBatchSize: 10 })
async fetchResults(keys: number | number[]): Promise<string | string[]> {
// Batch-enabled method logic
}
}
```
## Contributing

@@ -144,0 +132,0 @@

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc