update naming and publish info
This commit is contained in:
33
README.md
33
README.md
@@ -1,8 +1,8 @@
|
|||||||
# Mongo Assert
|
# Mongo Validate
|
||||||
|
|
||||||
Stronger, more intuitive type checking and assertions for MongoDB.
|
Stronger, more intuitive type checking and assertions for MongoDB.
|
||||||
|
|
||||||
Mongo Assert extends the functionality of Zod, integrated with the MongoDB Node.js driver, to provide a more intuitive and powerful way to validate and assert MongoDB documents.
|
Mongo Validate extends the functionality of Zod, integrated with the MongoDB Node.js driver, to provide a more intuitive and powerful way to validate MongoDB documents.
|
||||||
|
|
||||||
Some of its features include:
|
Some of its features include:
|
||||||
|
|
||||||
@@ -12,20 +12,20 @@ Some of its features include:
|
|||||||
|
|
||||||
## But why?
|
## But why?
|
||||||
|
|
||||||
Mongo Assert is something I put together out of frustration with existing, heavy handed solutions for MongoDB schema management. Mongo Assert is intended to have a minimal footprint, add on to existing validation infrastructure, and plug in seamlessly to build-time integrity checks.
|
Mongo Validate is something I put together out of frustration with existing, heavy handed solutions for MongoDB schema management. Mongo Validate is intended to have a minimal footprint, add on to existing validation infrastructure, and plug in seamlessly to build-time integrity checks.
|
||||||
|
|
||||||
## Usage
|
## Usage
|
||||||
|
|
||||||
Mongo Assert is available as an NPM package. To install it, run:
|
Mongo Validate is available as an NPM package. To install it, run:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm install mongo-assert
|
npm install mongo-validate
|
||||||
pnpm install mongo-assert
|
pnpm install mongo-validate
|
||||||
yarn add mongo-assert
|
yarn add mongo-validate
|
||||||
bun install mongo-assert
|
bun install mongo-validate
|
||||||
```
|
```
|
||||||
|
|
||||||
Mongo Assert supports Zod schemas out of the box, so any schemas you may already have defined can be used
|
Mongo Validate supports Zod schemas out of the box, so any schemas you may already have defined can be used
|
||||||
with any MongoDB instance.
|
with any MongoDB instance.
|
||||||
|
|
||||||
## Examples
|
## Examples
|
||||||
@@ -36,7 +36,7 @@ For all of the examples below, we'll be using the following schema:
|
|||||||
|
|
||||||
```ts
|
```ts
|
||||||
import { z } from 'zod';
|
import { z } from 'zod';
|
||||||
import { ObjectId } from "mongo-assert/lib/mongodb"
|
import { ObjectId } from "mongo-validate/lib/mongodb"
|
||||||
|
|
||||||
export const userSchema = z.object({
|
export const userSchema = z.object({
|
||||||
_id: ObjectId,
|
_id: ObjectId,
|
||||||
@@ -49,13 +49,14 @@ export type User = z.infer<typeof userSchema>;
|
|||||||
|
|
||||||
### Unique field validation
|
### Unique field validation
|
||||||
|
|
||||||
Mongo Assert extends Zod schemas to check that your documents match the desired schema. For example:
|
Mongo Validate extends Zod schemas to check that your documents match the desired schema. For example:
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import MongoAssert, { type AssertUniqueType } from 'mongo-assert';
|
import mongo-validate, { type AssertUniqueType } from 'mongo-validate';
|
||||||
import { userSchema, type User } from "./schemas";
|
import { userSchema, type User } from "./schemas";
|
||||||
|
|
||||||
export const UserEmailsUniqueValidator: AssertUniqueType<User> = MongoAssert.unique.fromSchema(userSchema, ["email"]);
|
export const UserEmailsUniqueValidator = MongoValidate.assertUnique.fromSchema(userSchema, ["email"]);
|
||||||
|
// ^? AssertUniqueType<User>
|
||||||
```
|
```
|
||||||
|
|
||||||
The returned object is a Zod schema that can be directly invoked to validate a result from MongoDB. This object
|
The returned object is a Zod schema that can be directly invoked to validate a result from MongoDB. This object
|
||||||
@@ -87,7 +88,7 @@ async function main() {
|
|||||||
|
|
||||||
### Reference validation
|
### Reference validation
|
||||||
|
|
||||||
Mongo Assert also supports validation of references to other collections.
|
Mongo Validate also supports validation of references to other collections.
|
||||||
|
|
||||||
For example, suppose we have a collection of `Store`s that must be associated to an existing `User`. Let's define our schema first:
|
For example, suppose we have a collection of `Store`s that must be associated to an existing `User`. Let's define our schema first:
|
||||||
|
|
||||||
@@ -107,9 +108,9 @@ export type Store = z.infer<typeof storeSchema>;
|
|||||||
Now, we can define a reference validator between these two collections:
|
Now, we can define a reference validator between these two collections:
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import MongoAssert from 'mongo-assert';
|
import mongo-validate from 'mongo-validate';
|
||||||
|
|
||||||
const StoresHaveOwnersValidator = new MongoAssert.relation({
|
const StoresHaveOwnersValidator = new MongoValidate.assertRelation({
|
||||||
db: "your-db",
|
db: "your-db",
|
||||||
mainCollection: "users",
|
mainCollection: "users",
|
||||||
relationCollection: "stores",
|
relationCollection: "stores",
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import { z } from 'zod';
|
import { z } from 'zod';
|
||||||
import MongoAssert from '..';
|
import MongoValidator from '..';
|
||||||
import dotenv from 'dotenv';
|
import dotenv from 'dotenv';
|
||||||
import path from 'path';
|
import path from 'path';
|
||||||
import { createMongoClient, ObjectId } from '../pkg/lib/mongodb';
|
import { createMongoClient, ObjectId } from '../pkg/lib/mongodb';
|
||||||
@@ -52,10 +52,10 @@ async function main() {
|
|||||||
type AssertUniqueType<T extends Record<string, unknown>> = z.ZodEffects<z.ZodArray<z.ZodType<T>>, T[], unknown>;
|
type AssertUniqueType<T extends Record<string, unknown>> = z.ZodEffects<z.ZodArray<z.ZodType<T>>, T[], unknown>;
|
||||||
|
|
||||||
// validate against internal schema
|
// validate against internal schema
|
||||||
const MusicEntryValidator = MongoAssert.unique.fromSchema(MusicEntry, ["slug"]) satisfies AssertUniqueType<MusicEntryType>;
|
const MusicEntryValidator = MongoValidator.unique.fromSchema(MusicEntry, ["slug"]) satisfies AssertUniqueType<MusicEntryType>;
|
||||||
const MusicCollections = MongoAssert.unique.fromSchema(MusicCollection, ["collectionslug"]);
|
const MusicCollections = MongoValidator.unique.fromSchema(MusicCollection, ["collectionslug"]);
|
||||||
|
|
||||||
const result: Promise<number | undefined> = MongoAssert.relation.check({
|
const result: Promise<number | undefined> = MongoValidator.relation.check({
|
||||||
db: "mikayladotdev",
|
db: "mikayladotdev",
|
||||||
mainCollection: "music",
|
mainCollection: "music",
|
||||||
relationCollection: "music-collection",
|
relationCollection: "music-collection",
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
{
|
{
|
||||||
"name": "mongo-assert",
|
"name": "mongo-validate",
|
||||||
"version": "0.0.1",
|
"version": "0.0.1",
|
||||||
"description": "Lightweight schema validation for MongoDB with Zod",
|
"description": "Lightweight schema validation for MongoDB with Zod",
|
||||||
"author": "Mikayla Dobson",
|
"author": "Mikayla Dobson",
|
||||||
|
|||||||
88
pkg/examples/main.ts
Normal file
88
pkg/examples/main.ts
Normal file
@@ -0,0 +1,88 @@
|
|||||||
|
import { z } from 'zod';
|
||||||
|
import MongoAssert from '..';
|
||||||
|
import dotenv from 'dotenv';
|
||||||
|
import path from 'path';
|
||||||
|
import { createMongoClient, ObjectId } from '../lib/mongodb';
|
||||||
|
|
||||||
|
dotenv.config();
|
||||||
|
|
||||||
|
const MusicEntry = z.object({
|
||||||
|
_id: ObjectId,
|
||||||
|
name: z.string(),
|
||||||
|
shortdescription: z.string(),
|
||||||
|
longdescription: z.string().optional(),
|
||||||
|
artist: z.string().optional(),
|
||||||
|
compositiondate: z.string().optional(),
|
||||||
|
pathtoentry: z.string(),
|
||||||
|
collection: z.string(),
|
||||||
|
slug: z.string(),
|
||||||
|
})
|
||||||
|
|
||||||
|
const MusicCollection = z.object({
|
||||||
|
_id: ObjectId,
|
||||||
|
name: z.string(),
|
||||||
|
description: z.string().optional(),
|
||||||
|
collectionslug: z.string(),
|
||||||
|
})
|
||||||
|
|
||||||
|
type MusicEntryType = z.infer<typeof MusicEntry>;
|
||||||
|
type MusicCollectionType = z.infer<typeof MusicCollection>;
|
||||||
|
|
||||||
|
async function main() {
|
||||||
|
try {
|
||||||
|
const url = process.env.MONGO_URL;
|
||||||
|
const cert = process.env.MONGO_CERT;
|
||||||
|
|
||||||
|
if (!url || !cert) {
|
||||||
|
throw new Error('Missing environment variables');
|
||||||
|
}
|
||||||
|
|
||||||
|
const client = await createMongoClient(url, {
|
||||||
|
tlsCertificateKeyFile: path.resolve(__dirname, '..', cert)
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!client) return null;
|
||||||
|
|
||||||
|
const mdotdev = client.db('mikayladotdev');
|
||||||
|
const music = mdotdev.collection('music');
|
||||||
|
|
||||||
|
const musicData = await music.find().toArray();
|
||||||
|
const collectionData = await mdotdev.collection('music-collection').find().toArray();
|
||||||
|
|
||||||
|
type AssertUniqueType<T extends Record<string, unknown>> = z.ZodEffects<z.ZodArray<z.ZodType<T>>, T[], unknown>;
|
||||||
|
|
||||||
|
// validate against internal schema
|
||||||
|
const MusicEntryValidator = MongoAssert.assertUnique.fromSchema(MusicEntry, ["slug"]) satisfies AssertUniqueType<MusicEntryType>;
|
||||||
|
const MusicCollections = MongoAssert.assertUnique.fromSchema(MusicCollection, ["collectionslug"]);
|
||||||
|
|
||||||
|
const result: Promise<number | undefined> = MongoAssert.assertRelation.check({
|
||||||
|
db: "mikayladotdev",
|
||||||
|
mainCollection: "music",
|
||||||
|
relationCollection: "music-collection",
|
||||||
|
mainSchema: MusicEntry,
|
||||||
|
relationSchema: MusicCollection,
|
||||||
|
relations: {
|
||||||
|
"collection": "collectionslug"
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
await Promise.allSettled([
|
||||||
|
MusicEntryValidator.parseAsync(musicData) satisfies Promise<MusicEntryType[]>,
|
||||||
|
MusicCollections.parseAsync(collectionData) satisfies Promise<MusicCollectionType[]>,
|
||||||
|
result
|
||||||
|
]).then((results) => {
|
||||||
|
results.forEach((result) => {
|
||||||
|
if (result.status === 'rejected') {
|
||||||
|
console.log(result.reason);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
.catch(console.error)
|
||||||
|
.finally(() => client.close());
|
||||||
|
|
||||||
|
} catch(e) {
|
||||||
|
console.log(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
main().catch(console.error);
|
||||||
@@ -5,8 +5,8 @@ import { AssertConstrained } from './actions/constrained';
|
|||||||
export type { AssertUniqueType } from "./actions/unique";
|
export type { AssertUniqueType } from "./actions/unique";
|
||||||
export type { AssertRelationType } from "./actions/relation";
|
export type { AssertRelationType } from "./actions/relation";
|
||||||
|
|
||||||
export default class MongoAssert {
|
export default class MongoValidator {
|
||||||
static unique = AssertUnique;
|
static assertUnique = AssertUnique;
|
||||||
static relation = AssertRelation;
|
static assertRelation = AssertRelation;
|
||||||
static constrained = AssertConstrained;
|
static assertConstrained = AssertConstrained;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user