# SKU Generator (TypeORM + PostgreSQL)
A lightweight utility for generating and retrieving SKUs (Stock Keeping Units) stored in a PostgreSQL database using TypeORM. This library:
- Connects to PostgreSQL once and reuses the same connection until explicitly closed.
- Checks if a SKU already exists for a given manufacturer and part number.
- Creates a new SKU if none exists.
- Stores and retrieves SKUs in a database table (named `skus` by default if using `@Entity('skus')`).
## Table of Contents
- [Installation](#installation)
- [Usage](#usage)
- [Constructor Parameters](#constructor-parameters)
- [Basic Example](#basic-example)
- [Multiple Calls Example](#multiple-calls-example)
- [Methods](#methods)
- [`init()`](#init)
- [`getOrCreateSKU(params)`](#getorcreateskuparams)
- [`close()`](#close)
- [Environment Variables](#environment-variables)
- [License](#license)
---
## Installation
```bash
npm install @nishanprime/sku-generator
/**
* The options you can pass to the constructor:
* {
* url: string; // PostgreSQL connection string
* synchronize: boolean; // Whether to auto-sync the database schema
* logging: boolean; // Enable TypeORM query logging
* extra: {
* max: number; // Max DB connections in the pool
* idleTimeoutMillis: number; // Idle timeout in ms
* connectionTimeoutMillis: number; // Connection timeout in ms
* };
* }
*/
-
url: The connection string for your Postgres DB. E.g.
"postgres://user:pass@localhost:5432/dbname"
. -
synchronize: In development,
true
can auto-create or update tables. In production, you typically use migrations and set this tofalse
. -
logging: Prints SQL queries to the console if
true
. - extra: Pool settings (default values shown in the code).
If you omit these options, it will look for a POSTGRES_CONNECTION_STRING
in your environment variables.
import { SKUGenerator } from "@nishanprime/sku-generator";
(async () => {
// Create a new SKUGenerator instance with optional connection settings
const skuGen = new SKUGenerator({
url: "postgres://user:password@localhost:5432/mydb",
synchronize: true, // For dev only
logging: false,
extra: {
max: 10,
idleTimeoutMillis: 30000,
connectionTimeoutMillis: 5000,
},
});
// Make sure the data source is initialized
await skuGen.init();
// Generate or get an existing SKU
const sku = await skuGen.getOrCreateSKU({
manufacturerName: "Apple",
manufacturerPartNumber: "M1Chip",
category: "Laptop",
subcategory: "MacBook",
});
console.log("Generated or retrieved SKU:", sku);
// Close the connection when done
await skuGen.close();
})();
If you have to process many items, you can do something like:
import { SKUGenerator } from "@nishanprime/sku-generator";
(async () => {
const skuGen = new SKUGenerator({
url: "postgres://user:password@localhost:5432/mydb",
synchronize: false,
logging: false,
});
await skuGen.init(); // connect once
const products = [
{ manufacturerName: "Apple", manufacturerPartNumber: "M1Chip", category: "Laptop", subcategory: "MacBook" },
{ manufacturerName: "Intel", manufacturerPartNumber: "i7-12700", category: "CPU" },
// ... potentially thousands more
];
for (const product of products) {
const sku = await skuGen.getOrCreateSKU(product);
console.log("SKU for", product.manufacturerPartNumber, ":", sku);
}
await skuGen.close(); // close after all operations
})();
In this example, the connection is opened once (init()
) and stays open until you explicitly close()
it, which is important for performance when dealing with bulk operations.
public async init(): Promise<void>;
Ensures the data source is initialized exactly once.
- If the data source is already initialized, this does nothing.
- Otherwise, it connects to PostgreSQL using the provided URL or the
POSTGRES_CONNECTION_STRING
environment variable.
public async getOrCreateSKU(params: SKUParams): Promise<string>;
-
Params:
interface SKUParams { manufacturerName: string; manufacturerPartNumber: string; category: string; subcategory?: string; }
-
Behavior:
- Checks if a row with the same
manufacturerName
andmanufacturerPartNumber
already exists. - If it does, returns the existing
sku
. - If not, generates a new SKU (e.g.,
A5<6-digit-random><first-letter-of-category><first-letter-of-subcategory-or-second-letter-of-category>
) and inserts a new row into the DB. - Returns the newly created SKU string.
- Checks if a row with the same
public async close(): Promise<void>;
- Closes the database connection (destroying the TypeORM data source).
- Once closed, you can re-init if needed, but typically you close just before your application ends or if you no longer need SKU operations.
-
POSTGRES_CONNECTION_STRING
: If you do not pass aurl
in the constructor, this library will attempt to useprocess.env.POSTGRES_CONNECTION_STRING
.- For example:
export POSTGRES_CONNECTION_STRING="postgres://user:pass@localhost:5432/dbname"
- For example:
- You can also configure the pool and logging behavior via constructor options or by editing your environment variables. However, the library as shown expects direct constructor options for advanced settings.
MIT
Feel free to modify, distribute, and use this library in your own projects under the terms of the MIT license.