mongodb-schema
Version:
Infer the probabilistic schema for a MongoDB collection.
104 lines • 3.44 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.toTypescriptTypeDefinition = void 0;
function getBSONType(property) {
return property.bsonType || property.type;
}
function assertIsDefined(value, message) {
if (value === undefined || value === null) {
throw new Error(message);
}
}
function toTypeName(type) {
switch (type) {
case 'string':
return 'string';
case 'number':
case 'integer':
return 'number';
case 'boolean':
return 'boolean';
case 'null':
return 'null';
case 'double':
return ['bson.Double', 'number'];
case 'binData':
return 'bson.Binary';
case 'objectId':
return 'bson.ObjectId';
case 'bool':
return 'boolean';
case 'date':
return 'bson.Date';
case 'regex':
return 'bson.BSONRegExp';
case 'symbol':
return 'bson.BSONSymbol';
case 'javascript':
case 'javascriptWithScope':
return 'bson.Code';
case 'int':
return ['bson.Int32', 'number'];
case 'timestamp':
return 'bson.Timestamp';
case 'long':
return ['bson.Long', 'number'];
case 'decimal':
return 'bson.Decimal128';
case 'minKey':
return 'bson.MinKey';
case 'maxKey':
return 'bson.MaxKey';
case 'dbPointer':
return 'bson.DBPointer';
case 'undefined':
return 'undefined';
default:
return 'any';
}
}
function uniqueTypes(property) {
const type = getBSONType(property);
const types = (Array.isArray(type) ? type : [type !== null && type !== void 0 ? type : 'any'])
.map((t) => toTypeName(t))
.flat();
return new Set(types.flat());
}
function indentSpaces(indent) {
const spaces = [];
for (let i = 0; i < indent; i++) {
spaces.push(' ');
}
return spaces.join('');
}
function arrayType(types) {
if (types.length === 1) {
return `${types[0]}[]`;
}
return `${types.join(' | ')})[]`;
}
function toTypescriptType(properties, indent) {
const eachFieldDefinition = Object.entries(properties).map(([propertyName, schema]) => {
switch (getBSONType(schema)) {
case 'array':
assertIsDefined(schema.items, 'schema.items must be defined');
return `${indentSpaces(indent)}${propertyName}?: ${arrayType([
...uniqueTypes(schema.items)
])}`;
case 'object':
assertIsDefined(schema.properties, 'schema.properties must be defined');
return `${indentSpaces(indent)}${propertyName}?: ${toTypescriptType(schema.properties, indent + 1)}`;
default:
return `${indentSpaces(indent)}${propertyName}?: ${[
...uniqueTypes(schema)
].join(' | ')}`;
}
});
return `{\n${eachFieldDefinition.join(';\n')};\n${indentSpaces(indent - 1)}}`;
}
function toTypescriptTypeDefinition(schema) {
assertIsDefined(schema.properties, 'schema.properties must be defined');
return toTypescriptType(schema.properties, 1);
}
exports.toTypescriptTypeDefinition = toTypescriptTypeDefinition;
//# sourceMappingURL=to-typescript.js.map