forked from niahmiah/mongoose-uuid
-
Notifications
You must be signed in to change notification settings - Fork 0
/
index.js
136 lines (105 loc) · 3.83 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
'use strict';
var mongoose = require('mongoose');
var bson = require('bson');
var util = require('util');
var uuid = require('node-uuid');
var Document = mongoose.Document;
function SchemaUUID(path, options) {
mongoose.SchemaTypes.Buffer.call(this, path, options);
}
util.inherits(SchemaUUID, mongoose.SchemaTypes.Buffer);
SchemaUUID.schemaName = 'UUID';
SchemaUUID.decodeUUID = (binary) => {
const len = binary.length();
const b = binary.read(0, len);
let buf = new Buffer(len);
for (let i = 0; i < len; i++) {
buf[i] = b[i];
}
let hex = '';
for (let i = 0; i < len; i++) {
const n = buf.readUInt8(i);
if (n < 16)
hex += '0' + n.toString(16);
else
hex += n.toString(16);
}
return hex.substr(0, 8) + '-' + hex.substr(8, 4) + '-' + hex.substr(12, 4) + '-' + hex.substr(16, 4) + '-' + hex.substr(20, 12);
};
SchemaUUID.prototype.checkRequired = function (value) {
return value instanceof mongoose.Types.Buffer.Binary;
};
SchemaUUID.prototype.cast = function (value, doc, init) {
if (mongoose.SchemaType._isRef(this, value, doc, init)) {
// wait! we may need to cast this to a document
if (value === null || value === undefined) {
return value;
}
if (value instanceof Document) {
value.$__.wasPopulated = true;
return value;
}
// setting a populated path
if (value instanceof mongoose.Types.Buffer.Binary) {
return value;
} else if (typeof value === 'string') {
var uuidBuffer = new mongoose.Types.Buffer(uuid.parse(value));
uuidBuffer.subtype(bson.Binary.SUBTYPE_UUID);
return uuidBuffer.toObject();
} else if (Buffer.isBuffer(value) || !util.isObject(value)) {
throw new CastError('UUID', value, this.path);
}
// Handle the case where user directly sets a populated
// path to a plain object; cast to the Model used in
// the population query.
const path = doc.$__fullPath(this.path);
const owner = doc.ownerDocument ? doc.ownerDocument() : doc;
const pop = owner.populated(path, true);
let ret = value;
if (!doc.$__.populated ||
!doc.$__.populated[path] ||
!doc.$__.populated[path].options ||
!doc.$__.populated[path].options.options ||
!doc.$__.populated[path].options.options.lean) {
ret = new pop.options.model(value);
ret.$__.wasPopulated = true;
}
return ret;
}
if (value === null || value === undefined) {
return value;
}
if (value instanceof mongoose.Types.Buffer.Binary)
return value;
if (value._id) {
if (value._id instanceof mongoose.Types.Buffer.Binary) {
return value._id;
}
if (typeof value._id === 'string') {
let uuidBuffer = new mongoose.Types.Buffer(uuid.parse(value._id));
uuidBuffer.subtype(bson.Binary.SUBTYPE_UUID);
return uuidBuffer.toObject();
}
}
if (typeof value === 'string') {
let uuidBuffer = new mongoose.Types.Buffer(uuid.parse(value));
uuidBuffer.subtype(bson.Binary.SUBTYPE_UUID);
return uuidBuffer.toObject();
}
throw new Error('Could not cast ' + value + ' to uuid.');
};
SchemaUUID.prototype.castForQuery = function ($conditional, val) {
var handler;
if (arguments.length === 2) {
handler = this.$conditionalHandlers[$conditional];
if (!handler)
throw new Error("Can't use " + $conditional + " with Buffer.");
return handler.call(this, val);
} else {
val = $conditional;
return this.cast(val);
}
};
module.exports = (mongoose) => {
mongoose.Types.UUID = mongoose.SchemaTypes.UUID = SchemaUUID;
};