lamix 4.2.22 → 4.2.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -0
- package/lib/@types/index.d.ts +12 -2
- package/lib/index.js +232 -205
- package/package.json +3 -4
package/README.md
CHANGED
package/lib/@types/index.d.ts
CHANGED
|
@@ -499,14 +499,24 @@ export class DBError extends Error {
|
|
|
499
499
|
}
|
|
500
500
|
export class LamixSessionStore {
|
|
501
501
|
constructor(options?: {});
|
|
502
|
+
table: any;
|
|
502
503
|
ttl: any;
|
|
503
504
|
cleanupInterval: any;
|
|
505
|
+
compress: boolean;
|
|
506
|
+
lazyInit: any;
|
|
507
|
+
cache: LRUCache<{}, {}, unknown>;
|
|
508
|
+
_ensureTable(): Promise<void>;
|
|
509
|
+
_compress(data: any): Promise<Buffer<any>>;
|
|
510
|
+
_decompress(buffer: any): Promise<any>;
|
|
511
|
+
_getExpiry(sessionData: any): number;
|
|
512
|
+
_cacheTTL(expires: any): number;
|
|
504
513
|
get(sid: any, cb: any): Promise<any>;
|
|
505
514
|
set(sid: any, sessionData: any, cb: any): Promise<void>;
|
|
506
515
|
destroy(sid: any, cb: any): Promise<void>;
|
|
507
516
|
touch(sid: any, sessionData: any, cb: any): Promise<any>;
|
|
508
517
|
_startCleanup(): void;
|
|
509
518
|
_cleanupTimer: NodeJS.Timeout;
|
|
519
|
+
close(): void;
|
|
510
520
|
}
|
|
511
521
|
export class BaseModel extends Model {
|
|
512
522
|
static passwordField: string;
|
|
@@ -575,7 +585,7 @@ declare class SimpleCache {
|
|
|
575
585
|
maxSize: number;
|
|
576
586
|
};
|
|
577
587
|
}
|
|
578
|
-
import { AsyncLocalStorage } from "
|
|
588
|
+
import { AsyncLocalStorage } from "async_hooks";
|
|
579
589
|
declare class HasManyThrough extends Relation {
|
|
580
590
|
constructor(parent: any, relatedClass: any, throughClass: any, firstKey: any, secondKey: any, localKey: any, secondLocalKey: any);
|
|
581
591
|
throughClass: any;
|
|
@@ -607,7 +617,7 @@ declare class MorphToMany extends Relation {
|
|
|
607
617
|
}
|
|
608
618
|
declare class MorphedByMany extends MorphToMany {
|
|
609
619
|
}
|
|
610
|
-
import util = require("util");
|
|
620
|
+
import util = require("node:util");
|
|
611
621
|
declare class Paginator {
|
|
612
622
|
constructor(data: any, total: any, page: any, perPage: any);
|
|
613
623
|
data: any;
|
package/lib/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
const util = require('util');
|
|
3
|
+
const util = require('node:util');
|
|
4
4
|
const { performance } = require('perf_hooks');
|
|
5
5
|
const { AsyncLocalStorage } = require('async_hooks');
|
|
6
6
|
require('dotenv').config();
|
|
@@ -382,13 +382,13 @@ class DB {
|
|
|
382
382
|
|
|
383
383
|
static select(sql, bindings = []) { return this.raw(sql, bindings); }
|
|
384
384
|
static statement(sql, bindings = []) { return this.affectingStatement(sql, bindings); }
|
|
385
|
-
static insert(sql, bindings = []) {
|
|
386
|
-
|
|
387
|
-
|
|
385
|
+
static async insert(sql, bindings = []) {
|
|
386
|
+
const r = await this.affectingStatement(sql, bindings);
|
|
387
|
+
return r.insertId ?? true;
|
|
388
388
|
}
|
|
389
|
-
static update(sql, bindings = []) {
|
|
390
|
-
|
|
391
|
-
|
|
389
|
+
static async update(sql, bindings = []) {
|
|
390
|
+
const r = await this.affectingStatement(sql, bindings);
|
|
391
|
+
return r.affectedRows ?? 0;
|
|
392
392
|
}
|
|
393
393
|
static delete(sql, bindings = []) { return this.update(sql, bindings); }
|
|
394
394
|
|
|
@@ -459,6 +459,222 @@ class DB {
|
|
|
459
459
|
|
|
460
460
|
const escapeId = s => DB.escapeId(s);
|
|
461
461
|
|
|
462
|
+
class LamixSessionStore extends session.Store {
|
|
463
|
+
constructor(options = {}) {
|
|
464
|
+
super();
|
|
465
|
+
|
|
466
|
+
this.table = options.table || 'sessions';
|
|
467
|
+
this.ttl = options.ttl || 86400; // seconds
|
|
468
|
+
this.cleanupInterval = options.cleanupInterval || 60000; // ms
|
|
469
|
+
this.compress = options.compress !== false; // default true
|
|
470
|
+
this.lazyInit = options.lazyInit || false;
|
|
471
|
+
|
|
472
|
+
const {
|
|
473
|
+
cacheSizeMB = 50,
|
|
474
|
+
cacheTTL = 1000 * 60 * 5
|
|
475
|
+
} = options;
|
|
476
|
+
|
|
477
|
+
this.cache = new LRUCache({
|
|
478
|
+
maxSize: cacheSizeMB * 1024 * 1024,
|
|
479
|
+
ttl: cacheTTL,
|
|
480
|
+
ttlAutopurge: true,
|
|
481
|
+
sizeCalculation: (value) => {
|
|
482
|
+
try { return Buffer.byteLength(JSON.stringify(value)); }
|
|
483
|
+
catch { return 1024; }
|
|
484
|
+
}
|
|
485
|
+
});
|
|
486
|
+
|
|
487
|
+
if (!this.lazyInit) {
|
|
488
|
+
this._ensureTable().catch(err => {
|
|
489
|
+
console.error('Session table init failed:', err);
|
|
490
|
+
});
|
|
491
|
+
}
|
|
492
|
+
|
|
493
|
+
this._startCleanup();
|
|
494
|
+
}
|
|
495
|
+
|
|
496
|
+
/* ---------- Ensure Table ---------- */
|
|
497
|
+
|
|
498
|
+
async _ensureTable() {
|
|
499
|
+
const table = DB.escapeId(this.table);
|
|
500
|
+
|
|
501
|
+
if (DB.driver === 'pg') {
|
|
502
|
+
await DB.statement(`
|
|
503
|
+
CREATE TABLE IF NOT EXISTS ${table} (
|
|
504
|
+
sid TEXT PRIMARY KEY,
|
|
505
|
+
data TEXT NOT NULL,
|
|
506
|
+
expires BIGINT NOT NULL
|
|
507
|
+
)
|
|
508
|
+
`);
|
|
509
|
+
} else if (DB.driver === 'sqlite') {
|
|
510
|
+
await DB.statement(`
|
|
511
|
+
CREATE TABLE IF NOT EXISTS ${table} (
|
|
512
|
+
sid TEXT PRIMARY KEY,
|
|
513
|
+
data TEXT NOT NULL,
|
|
514
|
+
expires INTEGER NOT NULL
|
|
515
|
+
)
|
|
516
|
+
`);
|
|
517
|
+
} else {
|
|
518
|
+
await DB.statement(`
|
|
519
|
+
CREATE TABLE IF NOT EXISTS ${table} (
|
|
520
|
+
sid VARCHAR(255) PRIMARY KEY,
|
|
521
|
+
data TEXT NOT NULL,
|
|
522
|
+
expires BIGINT NOT NULL
|
|
523
|
+
)
|
|
524
|
+
`);
|
|
525
|
+
}
|
|
526
|
+
}
|
|
527
|
+
|
|
528
|
+
/* ---------- Utilities ---------- */
|
|
529
|
+
|
|
530
|
+
async _compress(data) {
|
|
531
|
+
if (!this.compress) return Buffer.from(data);
|
|
532
|
+
return util.promisify(zlib.deflate)(data);
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
async _decompress(buffer) {
|
|
536
|
+
try {
|
|
537
|
+
if (!this.compress) return buffer;
|
|
538
|
+
return await util.promisify(zlib.inflate)(buffer);
|
|
539
|
+
} catch {
|
|
540
|
+
// fallback for old non-compressed sessions
|
|
541
|
+
return buffer;
|
|
542
|
+
}
|
|
543
|
+
}
|
|
544
|
+
|
|
545
|
+
_getExpiry(sessionData) {
|
|
546
|
+
return sessionData.cookie?.expires
|
|
547
|
+
? new Date(sessionData.cookie.expires).getTime()
|
|
548
|
+
: Date.now() + this.ttl * 1000;
|
|
549
|
+
}
|
|
550
|
+
|
|
551
|
+
_cacheTTL(expires) {
|
|
552
|
+
const ms = expires - Date.now();
|
|
553
|
+
return ms > 0 ? ms : 1;
|
|
554
|
+
}
|
|
555
|
+
|
|
556
|
+
/* ---------- Core ---------- */
|
|
557
|
+
|
|
558
|
+
async get(sid, cb) {
|
|
559
|
+
try {
|
|
560
|
+
const cached = this.cache.get(sid);
|
|
561
|
+
if (cached) return cb(null, cached);
|
|
562
|
+
|
|
563
|
+
const rows = await DB.select(
|
|
564
|
+
`SELECT data, expires FROM ${DB.escapeId(this.table)} WHERE sid = ? AND expires > ?`,
|
|
565
|
+
[sid, Date.now()]
|
|
566
|
+
);
|
|
567
|
+
|
|
568
|
+
if (!rows.length) return cb(null, null);
|
|
569
|
+
|
|
570
|
+
const buffer = Buffer.from(rows[0].data, 'base64');
|
|
571
|
+
const decompressed = await this._decompress(buffer);
|
|
572
|
+
|
|
573
|
+
const sessionData = JSON.parse(decompressed.toString());
|
|
574
|
+
|
|
575
|
+
this.cache.set(sid, sessionData, { ttl: this._cacheTTL(rows[0].expires) });
|
|
576
|
+
|
|
577
|
+
cb(null, sessionData);
|
|
578
|
+
} catch (err) {
|
|
579
|
+
cb(err);
|
|
580
|
+
}
|
|
581
|
+
}
|
|
582
|
+
|
|
583
|
+
async set(sid, sessionData, cb) {
|
|
584
|
+
try {
|
|
585
|
+
const expires = this._getExpiry(sessionData);
|
|
586
|
+
const raw = JSON.stringify(sessionData);
|
|
587
|
+
const compressed = await this._compress(raw);
|
|
588
|
+
const data = compressed.toString('base64');
|
|
589
|
+
|
|
590
|
+
const table = DB.escapeId(this.table);
|
|
591
|
+
|
|
592
|
+
if (DB.driver === 'pg') {
|
|
593
|
+
await DB.statement(`
|
|
594
|
+
INSERT INTO ${table} (sid, data, expires)
|
|
595
|
+
VALUES (?, ?, ?)
|
|
596
|
+
ON CONFLICT (sid)
|
|
597
|
+
DO UPDATE SET data = EXCLUDED.data, expires = EXCLUDED.expires
|
|
598
|
+
`, [sid, data, expires]);
|
|
599
|
+
|
|
600
|
+
} else if (DB.driver === 'sqlite') {
|
|
601
|
+
await DB.statement(`
|
|
602
|
+
INSERT INTO ${table} (sid, data, expires)
|
|
603
|
+
VALUES (?, ?, ?)
|
|
604
|
+
ON CONFLICT(sid)
|
|
605
|
+
DO UPDATE SET data=excluded.data, expires=excluded.expires
|
|
606
|
+
`, [sid, data, expires]);
|
|
607
|
+
|
|
608
|
+
} else {
|
|
609
|
+
await DB.statement(`
|
|
610
|
+
INSERT INTO ${table} (sid, data, expires)
|
|
611
|
+
VALUES (?, ?, ?)
|
|
612
|
+
ON DUPLICATE KEY UPDATE data=VALUES(data), expires=VALUES(expires)
|
|
613
|
+
`, [sid, data, expires]);
|
|
614
|
+
}
|
|
615
|
+
|
|
616
|
+
this.cache.set(sid, sessionData, { ttl: this._cacheTTL(expires) });
|
|
617
|
+
|
|
618
|
+
cb(null);
|
|
619
|
+
} catch (err) {
|
|
620
|
+
cb(err);
|
|
621
|
+
}
|
|
622
|
+
}
|
|
623
|
+
|
|
624
|
+
async destroy(sid, cb) {
|
|
625
|
+
try {
|
|
626
|
+
await DB.delete(
|
|
627
|
+
`DELETE FROM ${DB.escapeId(this.table)} WHERE sid = ?`,
|
|
628
|
+
[sid]
|
|
629
|
+
);
|
|
630
|
+
this.cache.delete(sid);
|
|
631
|
+
cb(null);
|
|
632
|
+
} catch (err) {
|
|
633
|
+
cb(err);
|
|
634
|
+
}
|
|
635
|
+
}
|
|
636
|
+
|
|
637
|
+
async touch(sid, sessionData, cb) {
|
|
638
|
+
if (!sessionData) return cb();
|
|
639
|
+
|
|
640
|
+
try {
|
|
641
|
+
const expires = this._getExpiry(sessionData);
|
|
642
|
+
|
|
643
|
+
await DB.update(
|
|
644
|
+
`UPDATE ${DB.escapeId(this.table)} SET expires = ? WHERE sid = ?`,
|
|
645
|
+
[expires, sid]
|
|
646
|
+
);
|
|
647
|
+
|
|
648
|
+
this.cache.set(sid, sessionData, { ttl: this._cacheTTL(expires) });
|
|
649
|
+
|
|
650
|
+
cb();
|
|
651
|
+
} catch (err) {
|
|
652
|
+
cb(err);
|
|
653
|
+
}
|
|
654
|
+
}
|
|
655
|
+
|
|
656
|
+
/* ---------- Cleanup ---------- */
|
|
657
|
+
|
|
658
|
+
_startCleanup() {
|
|
659
|
+
this._cleanupTimer = setInterval(async () => {
|
|
660
|
+
try {
|
|
661
|
+
await DB.delete(
|
|
662
|
+
`DELETE FROM ${DB.escapeId(this.table)} WHERE expires < ?`,
|
|
663
|
+
[Date.now()]
|
|
664
|
+
);
|
|
665
|
+
} catch {}
|
|
666
|
+
}, this.cleanupInterval);
|
|
667
|
+
|
|
668
|
+
this._cleanupTimer.unref();
|
|
669
|
+
}
|
|
670
|
+
|
|
671
|
+
close() {
|
|
672
|
+
if (this._cleanupTimer) {
|
|
673
|
+
clearInterval(this._cleanupTimer);
|
|
674
|
+
}
|
|
675
|
+
}
|
|
676
|
+
}
|
|
677
|
+
|
|
462
678
|
|
|
463
679
|
// -----------------------------
|
|
464
680
|
// MAIN Validator
|
|
@@ -4028,204 +4244,6 @@ class Model {
|
|
|
4028
4244
|
}
|
|
4029
4245
|
}
|
|
4030
4246
|
|
|
4031
|
-
/* -------------------- DB Model -------------------- */
|
|
4032
|
-
class Session extends Model {
|
|
4033
|
-
static table = 'sessions';
|
|
4034
|
-
static primaryKey = 'sid';
|
|
4035
|
-
static slugKey = null;
|
|
4036
|
-
static timestamps = false;
|
|
4037
|
-
|
|
4038
|
-
static fillable = ['sid', 'data', 'expires'];
|
|
4039
|
-
}
|
|
4040
|
-
|
|
4041
|
-
/* -------------------- Optional Session Model -------------------- */
|
|
4042
|
-
let SessionModel = null;
|
|
4043
|
-
|
|
4044
|
-
try {
|
|
4045
|
-
SessionModel = Session;
|
|
4046
|
-
} catch (err) {
|
|
4047
|
-
SessionModel = null;
|
|
4048
|
-
}
|
|
4049
|
-
|
|
4050
|
-
/* -------------------- Store -------------------- */
|
|
4051
|
-
const { promisify } = require('util');
|
|
4052
|
-
|
|
4053
|
-
const gzip = promisify(zlib.gzip);
|
|
4054
|
-
const gunzip = promisify(zlib.gunzip);
|
|
4055
|
-
|
|
4056
|
-
class LamixSessionStore extends session.Store {
|
|
4057
|
-
constructor(options = {}) {
|
|
4058
|
-
super();
|
|
4059
|
-
|
|
4060
|
-
this.ttl = options.ttl || 86400; // seconds
|
|
4061
|
-
this.cleanupInterval = options.cleanupInterval || 60000;
|
|
4062
|
-
|
|
4063
|
-
this._startCleanup();
|
|
4064
|
-
}
|
|
4065
|
-
|
|
4066
|
-
/* ---------- Get ---------- */
|
|
4067
|
-
|
|
4068
|
-
async get(sid, cb) {
|
|
4069
|
-
try {
|
|
4070
|
-
const now = Date.now();
|
|
4071
|
-
|
|
4072
|
-
const row = await Session
|
|
4073
|
-
.query()
|
|
4074
|
-
.where('sid', sid)
|
|
4075
|
-
.where('expires', '>', now)
|
|
4076
|
-
.first();
|
|
4077
|
-
|
|
4078
|
-
if (!row) return cb(null, null);
|
|
4079
|
-
|
|
4080
|
-
let sessionJSON;
|
|
4081
|
-
|
|
4082
|
-
// ---------- Step 1: Decompress ----------
|
|
4083
|
-
try {
|
|
4084
|
-
const buffer = Buffer.from(row.data, 'base64');
|
|
4085
|
-
const decompressed = await gunzip(buffer);
|
|
4086
|
-
sessionJSON = decompressed.toString('utf8');
|
|
4087
|
-
} catch {
|
|
4088
|
-
// fallback to legacy plain JSON
|
|
4089
|
-
sessionJSON = row.data;
|
|
4090
|
-
}
|
|
4091
|
-
|
|
4092
|
-
// ---------- Step 2: Parse JSON safely ----------
|
|
4093
|
-
try {
|
|
4094
|
-
const parsed = JSON.parse(sessionJSON);
|
|
4095
|
-
return cb(null, parsed);
|
|
4096
|
-
} catch (parseErr) {
|
|
4097
|
-
console.warn('Corrupted session detected. Destroying:', sid);
|
|
4098
|
-
|
|
4099
|
-
// destroy corrupted session
|
|
4100
|
-
await Session
|
|
4101
|
-
.query()
|
|
4102
|
-
.where('sid', sid)
|
|
4103
|
-
.delete();
|
|
4104
|
-
|
|
4105
|
-
return cb(null, null); // treat as no session
|
|
4106
|
-
}
|
|
4107
|
-
|
|
4108
|
-
} catch (err) {
|
|
4109
|
-
console.error('Session GET failed:', err);
|
|
4110
|
-
|
|
4111
|
-
// IMPORTANT: never pass fatal error to express-session
|
|
4112
|
-
return cb(null, null);
|
|
4113
|
-
}
|
|
4114
|
-
}
|
|
4115
|
-
|
|
4116
|
-
/* ---------- Set ---------- */
|
|
4117
|
-
|
|
4118
|
-
async set(sid, sessionData, cb) {
|
|
4119
|
-
try {
|
|
4120
|
-
const expires =
|
|
4121
|
-
sessionData.cookie?.expires
|
|
4122
|
-
? new Date(sessionData.cookie.expires).getTime()
|
|
4123
|
-
: Date.now() + this.ttl * 1000;
|
|
4124
|
-
|
|
4125
|
-
const json = JSON.stringify(sessionData);
|
|
4126
|
-
|
|
4127
|
-
// Async compression (non-blocking)
|
|
4128
|
-
const compressed = await gzip(json);
|
|
4129
|
-
const base64Data = compressed.toString('base64');
|
|
4130
|
-
|
|
4131
|
-
const payload = {
|
|
4132
|
-
sid,
|
|
4133
|
-
data: base64Data,
|
|
4134
|
-
expires
|
|
4135
|
-
};
|
|
4136
|
-
|
|
4137
|
-
const existing = await Session
|
|
4138
|
-
.query()
|
|
4139
|
-
.where('sid', sid)
|
|
4140
|
-
.first();
|
|
4141
|
-
|
|
4142
|
-
if (existing) {
|
|
4143
|
-
await existing.update(payload);
|
|
4144
|
-
} else {
|
|
4145
|
-
const session = new Session(payload, false);
|
|
4146
|
-
await session.saveNew(payload);
|
|
4147
|
-
}
|
|
4148
|
-
|
|
4149
|
-
cb(null);
|
|
4150
|
-
} catch (err) {
|
|
4151
|
-
cb(new DBError('Failed to persist session', {
|
|
4152
|
-
sid,
|
|
4153
|
-
operation: 'set',
|
|
4154
|
-
err
|
|
4155
|
-
}));
|
|
4156
|
-
}
|
|
4157
|
-
}
|
|
4158
|
-
|
|
4159
|
-
/* ---------- Destroy ---------- */
|
|
4160
|
-
|
|
4161
|
-
async destroy(sid, cb) {
|
|
4162
|
-
try {
|
|
4163
|
-
await Session
|
|
4164
|
-
.query()
|
|
4165
|
-
.where('sid', sid)
|
|
4166
|
-
.delete();
|
|
4167
|
-
|
|
4168
|
-
cb(null);
|
|
4169
|
-
} catch (err) {
|
|
4170
|
-
cb(new DBError('Failed to destroy session', {
|
|
4171
|
-
sid,
|
|
4172
|
-
operation: 'destroy',
|
|
4173
|
-
err
|
|
4174
|
-
}));
|
|
4175
|
-
}
|
|
4176
|
-
}
|
|
4177
|
-
|
|
4178
|
-
/* ---------- Touch ---------- */
|
|
4179
|
-
|
|
4180
|
-
async touch(sid, sessionData, cb) {
|
|
4181
|
-
if (!sessionData) return cb(null);
|
|
4182
|
-
|
|
4183
|
-
try {
|
|
4184
|
-
const expires =
|
|
4185
|
-
sessionData.cookie?.expires
|
|
4186
|
-
? new Date(sessionData.cookie.expires).getTime()
|
|
4187
|
-
: Date.now() + this.ttl * 1000;
|
|
4188
|
-
|
|
4189
|
-
await Session
|
|
4190
|
-
.query()
|
|
4191
|
-
.where('sid', sid)
|
|
4192
|
-
.update({ expires });
|
|
4193
|
-
|
|
4194
|
-
cb();
|
|
4195
|
-
} catch (err) {
|
|
4196
|
-
cb(new DBError('Failed to touch session', {
|
|
4197
|
-
sid,
|
|
4198
|
-
operation: 'touch',
|
|
4199
|
-
err
|
|
4200
|
-
}));
|
|
4201
|
-
}
|
|
4202
|
-
}
|
|
4203
|
-
|
|
4204
|
-
/* ---------- Cleanup ---------- */
|
|
4205
|
-
|
|
4206
|
-
_startCleanup() {
|
|
4207
|
-
this._cleanupTimer = setInterval(async () => {
|
|
4208
|
-
try {
|
|
4209
|
-
await Session
|
|
4210
|
-
.query()
|
|
4211
|
-
.where('expires', '<', Date.now())
|
|
4212
|
-
.delete();
|
|
4213
|
-
} catch (err) {
|
|
4214
|
-
console.error(
|
|
4215
|
-
new DBError('Session cleanup failed', {
|
|
4216
|
-
operation: 'cleanup',
|
|
4217
|
-
err
|
|
4218
|
-
})
|
|
4219
|
-
);
|
|
4220
|
-
}
|
|
4221
|
-
}, this.cleanupInterval);
|
|
4222
|
-
|
|
4223
|
-
this._cleanupTimer.unref();
|
|
4224
|
-
}
|
|
4225
|
-
}
|
|
4226
|
-
|
|
4227
|
-
|
|
4228
|
-
|
|
4229
4247
|
// --- BaseModel with bcrypt hashing ---
|
|
4230
4248
|
const bcrypt = tryRequire('bcrypt');
|
|
4231
4249
|
class BaseModel extends Model {
|
|
@@ -4314,4 +4332,13 @@ class BaseModel extends Model {
|
|
|
4314
4332
|
}
|
|
4315
4333
|
}
|
|
4316
4334
|
|
|
4335
|
+
// ======================
|
|
4336
|
+
// Database Init
|
|
4337
|
+
// ======================
|
|
4338
|
+
DB.initFromEnv();
|
|
4339
|
+
|
|
4340
|
+
(async () => {
|
|
4341
|
+
await DB.connect();
|
|
4342
|
+
})();
|
|
4343
|
+
|
|
4317
4344
|
module.exports = { DB, Model, Validator, ValidationError, Collection, QueryBuilder, HasMany, HasOne, BelongsTo, BelongsToMany, DBError, LamixSessionStore, BaseModel};
|
package/package.json
CHANGED
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "lamix",
|
|
3
|
-
"version": "4.2.
|
|
3
|
+
"version": "4.2.24",
|
|
4
4
|
"description": "lamix - ORM for Node-express js",
|
|
5
5
|
"main": "./lib/index.js",
|
|
6
|
-
"types": "./lib/@types/index.d.ts",
|
|
7
6
|
"type": "commonjs",
|
|
8
7
|
"exports": {
|
|
9
8
|
".": {
|
|
@@ -26,8 +25,8 @@
|
|
|
26
25
|
"build": "tsc && echo 'Build complete'"
|
|
27
26
|
},
|
|
28
27
|
"devDependencies": {
|
|
29
|
-
"@types/node": "^
|
|
30
|
-
"typescript": "^5.
|
|
28
|
+
"@types/node": "^20.11.30",
|
|
29
|
+
"typescript": "^5.4.5"
|
|
31
30
|
},
|
|
32
31
|
"dependencies": {
|
|
33
32
|
"bcrypt": "^6.0.0",
|