@xeno-js/core 0.1.2 → 0.1.4
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 -2
- package/dist/index.cjs +690 -315
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +153 -4
- package/dist/index.d.ts +153 -4
- package/dist/index.js +545 -168
- package/dist/index.js.map +1 -1
- package/package.json +160 -160
package/dist/index.cjs
CHANGED
|
@@ -1366,8 +1366,7 @@ var init_sentry_logger_factory = __esm({
|
|
|
1366
1366
|
dsn: sentryConfig.dsn,
|
|
1367
1367
|
environment: env,
|
|
1368
1368
|
tracesSampleRate: env === "production" ? 0.1 : 1,
|
|
1369
|
-
|
|
1370
|
-
integrations: [new Sentry.Integrations.Http({ tracing: true })],
|
|
1369
|
+
integrations: [Sentry.httpIntegration()],
|
|
1371
1370
|
beforeSend(event, hint) {
|
|
1372
1371
|
const error = hint.originalException;
|
|
1373
1372
|
if (error instanceof Error && error.name === "ZodError") {
|
|
@@ -1510,15 +1509,15 @@ var init_logger_utils = __esm({
|
|
|
1510
1509
|
*/
|
|
1511
1510
|
async addLogger(container, opts) {
|
|
1512
1511
|
const loggerDependencies = [];
|
|
1513
|
-
const { Guards:
|
|
1514
|
-
if (!
|
|
1512
|
+
const { Guards: Guards46, LOG_LEVEL: LOG_LEVEL7, TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
1513
|
+
if (!Guards46.isDefined(opts) || opts.console) {
|
|
1515
1514
|
const { ConsoleLogger: ConsoleLogger2 } = await Promise.resolve().then(() => (init_console_logger(), console_logger_exports));
|
|
1516
1515
|
container.addSingleton(TOKENS4.CONSOLE_LOGGER, () => new ConsoleLogger2(opts?.level));
|
|
1517
1516
|
loggerDependencies.push(TOKENS4.CONSOLE_LOGGER);
|
|
1518
1517
|
}
|
|
1519
1518
|
const customLoggerFactories = [];
|
|
1520
|
-
if (
|
|
1521
|
-
if (
|
|
1519
|
+
if (Guards46.isDefined(opts)) {
|
|
1520
|
+
if (Guards46.isDefined(opts.sentry.config)) {
|
|
1522
1521
|
const { SentryLoggerFactory: SentryLoggerFactory2 } = await Promise.resolve().then(() => (init_sentry_logger_factory(), sentry_logger_factory_exports));
|
|
1523
1522
|
container.addSingleton(TOKENS4.SENTRY_LOGGER, () => {
|
|
1524
1523
|
const factory = new SentryLoggerFactory2();
|
|
@@ -1526,7 +1525,7 @@ var init_logger_utils = __esm({
|
|
|
1526
1525
|
});
|
|
1527
1526
|
loggerDependencies.push(TOKENS4.SENTRY_LOGGER);
|
|
1528
1527
|
}
|
|
1529
|
-
if (
|
|
1528
|
+
if (Guards46.isDefined(opts.pino.config)) {
|
|
1530
1529
|
const { PinoLoggerFactory: PinoLoggerFactory2 } = await Promise.resolve().then(() => (init_pino_logger_factory(), pino_logger_factory_exports));
|
|
1531
1530
|
container.addSingleton(TOKENS4.PINO_LOGGER, () => {
|
|
1532
1531
|
const factory = new PinoLoggerFactory2();
|
|
@@ -1534,10 +1533,10 @@ var init_logger_utils = __esm({
|
|
|
1534
1533
|
});
|
|
1535
1534
|
loggerDependencies.push(TOKENS4.PINO_LOGGER);
|
|
1536
1535
|
}
|
|
1537
|
-
if (!
|
|
1536
|
+
if (!Guards46.isNullOrEmpty(opts.customLoggers)) {
|
|
1538
1537
|
const customLoggers = opts.customLoggers;
|
|
1539
1538
|
customLoggers.forEach((f) => {
|
|
1540
|
-
if (
|
|
1539
|
+
if (Guards46.isDefined(f)) {
|
|
1541
1540
|
customLoggerFactories.push(f);
|
|
1542
1541
|
}
|
|
1543
1542
|
});
|
|
@@ -1557,12 +1556,34 @@ var init_logger_utils = __esm({
|
|
|
1557
1556
|
}
|
|
1558
1557
|
});
|
|
1559
1558
|
|
|
1559
|
+
// src/infrastructure/cache/inmemory.cache.ts
|
|
1560
|
+
var inmemory_cache_exports = {};
|
|
1561
|
+
__export(inmemory_cache_exports, {
|
|
1562
|
+
InMemoryCacheExtended: () => InMemoryCacheExtended
|
|
1563
|
+
});
|
|
1564
|
+
var import_shared39, InMemoryCacheExtended;
|
|
1565
|
+
var init_inmemory_cache = __esm({
|
|
1566
|
+
"src/infrastructure/cache/inmemory.cache.ts"() {
|
|
1567
|
+
"use strict";
|
|
1568
|
+
import_shared39 = require("@xeno-js/shared");
|
|
1569
|
+
InMemoryCacheExtended = class extends import_shared39.InMemoryCache {
|
|
1570
|
+
async increment(key, ttlSeconds) {
|
|
1571
|
+
const current = await this.get(key) ?? 0;
|
|
1572
|
+
const next = Number(current) + 1;
|
|
1573
|
+
const ttl = import_shared39.Guards.isDefined(ttlSeconds) ? Number(ttlSeconds) : 60;
|
|
1574
|
+
await this.set(key, next, ttl);
|
|
1575
|
+
return next;
|
|
1576
|
+
}
|
|
1577
|
+
};
|
|
1578
|
+
}
|
|
1579
|
+
});
|
|
1580
|
+
|
|
1560
1581
|
// src/infrastructure/cache/redis.cache.ts
|
|
1561
|
-
var
|
|
1582
|
+
var import_shared40, RedisCache;
|
|
1562
1583
|
var init_redis_cache = __esm({
|
|
1563
1584
|
"src/infrastructure/cache/redis.cache.ts"() {
|
|
1564
1585
|
"use strict";
|
|
1565
|
-
|
|
1586
|
+
import_shared40 = require("@xeno-js/shared");
|
|
1566
1587
|
RedisCache = class {
|
|
1567
1588
|
/**
|
|
1568
1589
|
* @description Constructs a new instance of the RedisCache class, which takes an instance of the Redis client as a parameter. This client is used to perform caching operations such as setting, getting, and removing values from the Redis database. The constructor initializes the RedisCache with the provided Redis client, allowing it to interact with the Redis server for all caching operations defined in the ICache interface.
|
|
@@ -1578,21 +1599,28 @@ var init_redis_cache = __esm({
|
|
|
1578
1599
|
this._redisClient = _redisClient;
|
|
1579
1600
|
}
|
|
1580
1601
|
_redisClient;
|
|
1602
|
+
async increment(key, ttlSeconds) {
|
|
1603
|
+
const multi = this._redisClient.multi();
|
|
1604
|
+
multi.incr(key);
|
|
1605
|
+
multi.expire(key, ttlSeconds ?? 60);
|
|
1606
|
+
const results = await multi.exec();
|
|
1607
|
+
return results?.[0]?.[1] ?? 1;
|
|
1608
|
+
}
|
|
1581
1609
|
async get(key) {
|
|
1582
1610
|
const value = await this._redisClient.get(key);
|
|
1583
|
-
if (!
|
|
1611
|
+
if (!import_shared40.Guards.isDefined(value)) {
|
|
1584
1612
|
return void 0;
|
|
1585
1613
|
}
|
|
1586
1614
|
return JSON.parse(value);
|
|
1587
1615
|
}
|
|
1588
1616
|
async set(key, value, ttl) {
|
|
1589
|
-
const stringValue =
|
|
1590
|
-
const ttlOption =
|
|
1617
|
+
const stringValue = import_shared40.StringHelper.safeStringify(value);
|
|
1618
|
+
const ttlOption = import_shared40.Guards.isDefined(ttl) ? ttl : 86400;
|
|
1591
1619
|
await this._redisClient.set(key, stringValue, "EX", ttlOption);
|
|
1592
1620
|
}
|
|
1593
1621
|
async setIfAbsent(key, value, ttl) {
|
|
1594
|
-
const stringValue =
|
|
1595
|
-
const ttlOption =
|
|
1622
|
+
const stringValue = import_shared40.StringHelper.safeStringify(value);
|
|
1623
|
+
const ttlOption = import_shared40.Guards.isDefined(ttl) ? ttl : 300;
|
|
1596
1624
|
const result = await this._redisClient.set(key, stringValue, "EX", ttlOption, "NX");
|
|
1597
1625
|
return result === "OK";
|
|
1598
1626
|
}
|
|
@@ -1615,11 +1643,11 @@ var redis_cache_factory_exports = {};
|
|
|
1615
1643
|
__export(redis_cache_factory_exports, {
|
|
1616
1644
|
RedisCacheFactory: () => RedisCacheFactory
|
|
1617
1645
|
});
|
|
1618
|
-
var
|
|
1646
|
+
var import_shared41, import_ioredis, RedisCacheFactory;
|
|
1619
1647
|
var init_redis_cache_factory = __esm({
|
|
1620
1648
|
"src/infrastructure/factories/redis-cache.factory.ts"() {
|
|
1621
1649
|
"use strict";
|
|
1622
|
-
|
|
1650
|
+
import_shared41 = require("@xeno-js/shared");
|
|
1623
1651
|
import_ioredis = require("ioredis");
|
|
1624
1652
|
init_redis_cache();
|
|
1625
1653
|
RedisCacheFactory = class {
|
|
@@ -1640,10 +1668,10 @@ var init_redis_cache_factory = __esm({
|
|
|
1640
1668
|
return delay;
|
|
1641
1669
|
}
|
|
1642
1670
|
};
|
|
1643
|
-
if (
|
|
1671
|
+
if (import_shared41.Guards.isDefined(password)) {
|
|
1644
1672
|
redisOptions.password = password;
|
|
1645
1673
|
}
|
|
1646
|
-
if (
|
|
1674
|
+
if (import_shared41.Guards.isDefined(username)) {
|
|
1647
1675
|
redisOptions.username = username;
|
|
1648
1676
|
}
|
|
1649
1677
|
if (useTls) {
|
|
@@ -1681,8 +1709,8 @@ var init_cache_utils = __esm({
|
|
|
1681
1709
|
* @link https://github.com/xeno-js/xeno-js
|
|
1682
1710
|
*/
|
|
1683
1711
|
async addCache(container, opts) {
|
|
1684
|
-
const { Guards:
|
|
1685
|
-
if (!opts.inMemory && !
|
|
1712
|
+
const { Guards: Guards46, TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
1713
|
+
if (!opts.inMemory && !Guards46.isDefined(opts.redis)) {
|
|
1686
1714
|
throw new Error(
|
|
1687
1715
|
"No cache strategies are configured. Please provide at least one cache strategy."
|
|
1688
1716
|
);
|
|
@@ -1692,12 +1720,12 @@ var init_cache_utils = __esm({
|
|
|
1692
1720
|
TOKENS4.CACHE_KEY_BUILDER,
|
|
1693
1721
|
(c) => new CacheKeyBuilder(c.resolve(TOKENS4.IDENTITY_ACCESSOR))
|
|
1694
1722
|
);
|
|
1695
|
-
if (opts.inMemory || !
|
|
1696
|
-
const {
|
|
1697
|
-
container.addSingleton(TOKENS4.CACHE, () => new
|
|
1723
|
+
if (opts.inMemory || !Guards46.isDefined(opts.redis)) {
|
|
1724
|
+
const { InMemoryCacheExtended: InMemoryCacheExtended2 } = await Promise.resolve().then(() => (init_inmemory_cache(), inmemory_cache_exports));
|
|
1725
|
+
container.addSingleton(TOKENS4.CACHE, () => new InMemoryCacheExtended2());
|
|
1698
1726
|
return;
|
|
1699
1727
|
}
|
|
1700
|
-
if (
|
|
1728
|
+
if (Guards46.isDefined(opts.redis)) {
|
|
1701
1729
|
const { RedisCacheFactory: RedisCacheFactory2 } = await Promise.resolve().then(() => (init_redis_cache_factory(), redis_cache_factory_exports));
|
|
1702
1730
|
container.addSingleton(TOKENS4.CACHE, () => {
|
|
1703
1731
|
const config = opts.redis;
|
|
@@ -1710,11 +1738,11 @@ var init_cache_utils = __esm({
|
|
|
1710
1738
|
});
|
|
1711
1739
|
|
|
1712
1740
|
// src/infrastructure/services/allow_methods/allow-method.service.ts
|
|
1713
|
-
var
|
|
1741
|
+
var import_shared42, AllowMethodRegistry;
|
|
1714
1742
|
var init_allow_method_service = __esm({
|
|
1715
1743
|
"src/infrastructure/services/allow_methods/allow-method.service.ts"() {
|
|
1716
1744
|
"use strict";
|
|
1717
|
-
|
|
1745
|
+
import_shared42 = require("@xeno-js/shared");
|
|
1718
1746
|
AllowMethodRegistry = class {
|
|
1719
1747
|
_staticRoutes = /* @__PURE__ */ new Map();
|
|
1720
1748
|
_dynamicRoutes = [];
|
|
@@ -1730,7 +1758,7 @@ var init_allow_method_service = __esm({
|
|
|
1730
1758
|
check(path, method) {
|
|
1731
1759
|
const cleanPath = this.normalizePath(path.split("?")[0].split("#")[0]);
|
|
1732
1760
|
const staticMethods = this._staticRoutes.get(cleanPath);
|
|
1733
|
-
if (
|
|
1761
|
+
if (import_shared42.Guards.isDefined(staticMethods)) return staticMethods.includes(method);
|
|
1734
1762
|
for (const route of this._dynamicRoutes) {
|
|
1735
1763
|
if (route.pattern.test(cleanPath)) return route.methods.includes(method);
|
|
1736
1764
|
}
|
|
@@ -1767,18 +1795,18 @@ var init_allow_methods = __esm({
|
|
|
1767
1795
|
});
|
|
1768
1796
|
|
|
1769
1797
|
// src/infrastructure/services/allow_origins/allow-origin.http.ts
|
|
1770
|
-
var
|
|
1798
|
+
var import_shared43, AllowOrigin;
|
|
1771
1799
|
var init_allow_origin_http = __esm({
|
|
1772
1800
|
"src/infrastructure/services/allow_origins/allow-origin.http.ts"() {
|
|
1773
1801
|
"use strict";
|
|
1774
|
-
|
|
1802
|
+
import_shared43 = require("@xeno-js/shared");
|
|
1775
1803
|
AllowOrigin = class {
|
|
1776
1804
|
constructor(_list) {
|
|
1777
1805
|
this._list = _list;
|
|
1778
1806
|
}
|
|
1779
1807
|
_list;
|
|
1780
1808
|
isAllowed(origin) {
|
|
1781
|
-
if (
|
|
1809
|
+
if (import_shared43.Guards.isNullOrEmpty(origin)) return true;
|
|
1782
1810
|
const cleanOrigin = origin.trim().toLowerCase();
|
|
1783
1811
|
for (const pattern of this._list) {
|
|
1784
1812
|
const cleanPattern = pattern.trim().toLowerCase();
|
|
@@ -1788,7 +1816,7 @@ var init_allow_origin_http = __esm({
|
|
|
1788
1816
|
const domainSuffix = cleanPattern.substring(1);
|
|
1789
1817
|
if (cleanOrigin.endsWith(domainSuffix)) {
|
|
1790
1818
|
const prefix = cleanOrigin.slice(0, cleanOrigin.length - domainSuffix.length);
|
|
1791
|
-
if (!
|
|
1819
|
+
if (!import_shared43.Guards.isNullOrEmpty(prefix) && !prefix.includes(".")) return true;
|
|
1792
1820
|
}
|
|
1793
1821
|
}
|
|
1794
1822
|
}
|
|
@@ -1834,25 +1862,116 @@ var init_concurrency = __esm({
|
|
|
1834
1862
|
}
|
|
1835
1863
|
});
|
|
1836
1864
|
|
|
1865
|
+
// src/infrastructure/services/crypto/crypto.service.ts
|
|
1866
|
+
var EdgeCryptoService;
|
|
1867
|
+
var init_crypto_service = __esm({
|
|
1868
|
+
"src/infrastructure/services/crypto/crypto.service.ts"() {
|
|
1869
|
+
"use strict";
|
|
1870
|
+
EdgeCryptoService = class {
|
|
1871
|
+
randomBytes(size) {
|
|
1872
|
+
const buffer = new Uint8Array(size);
|
|
1873
|
+
crypto.getRandomValues(buffer);
|
|
1874
|
+
return buffer;
|
|
1875
|
+
}
|
|
1876
|
+
async hmacSha256(secret, data) {
|
|
1877
|
+
const encoder = new TextEncoder();
|
|
1878
|
+
const keyData = encoder.encode(secret);
|
|
1879
|
+
const messageData = encoder.encode(data);
|
|
1880
|
+
const cryptoKey = await crypto.subtle.importKey(
|
|
1881
|
+
"raw",
|
|
1882
|
+
keyData,
|
|
1883
|
+
{ name: "HMAC", hash: "SHA-256" },
|
|
1884
|
+
false,
|
|
1885
|
+
["sign"]
|
|
1886
|
+
);
|
|
1887
|
+
const signature = await crypto.subtle.sign("HMAC", cryptoKey, messageData);
|
|
1888
|
+
return btoa(String.fromCharCode(...new Uint8Array(signature))).replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
|
|
1889
|
+
}
|
|
1890
|
+
timingSafeEqual(a, b) {
|
|
1891
|
+
if (a.length !== b.length) {
|
|
1892
|
+
return false;
|
|
1893
|
+
}
|
|
1894
|
+
let mismatch = 0;
|
|
1895
|
+
for (let i = 0; i < a.length; i++) {
|
|
1896
|
+
mismatch |= a[i] ^ b[i];
|
|
1897
|
+
}
|
|
1898
|
+
return mismatch === 0;
|
|
1899
|
+
}
|
|
1900
|
+
};
|
|
1901
|
+
}
|
|
1902
|
+
});
|
|
1903
|
+
|
|
1904
|
+
// src/infrastructure/services/crypto/index.ts
|
|
1905
|
+
var init_crypto = __esm({
|
|
1906
|
+
"src/infrastructure/services/crypto/index.ts"() {
|
|
1907
|
+
"use strict";
|
|
1908
|
+
init_crypto_service();
|
|
1909
|
+
}
|
|
1910
|
+
});
|
|
1911
|
+
|
|
1912
|
+
// src/infrastructure/services/csrf/csrf-token.service.ts
|
|
1913
|
+
var import_shared44, CsrfTokenService;
|
|
1914
|
+
var init_csrf_token_service = __esm({
|
|
1915
|
+
"src/infrastructure/services/csrf/csrf-token.service.ts"() {
|
|
1916
|
+
"use strict";
|
|
1917
|
+
import_shared44 = require("@xeno-js/shared");
|
|
1918
|
+
CsrfTokenService = class {
|
|
1919
|
+
constructor(_secret, _cryptoService) {
|
|
1920
|
+
this._secret = _secret;
|
|
1921
|
+
this._cryptoService = _cryptoService;
|
|
1922
|
+
}
|
|
1923
|
+
_secret;
|
|
1924
|
+
_cryptoService;
|
|
1925
|
+
async generate(subject) {
|
|
1926
|
+
const randomBuffer = this._cryptoService.randomBytes(32);
|
|
1927
|
+
const nonce = btoa(String.fromCharCode(...randomBuffer)).replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
|
|
1928
|
+
const signature = await this._cryptoService.hmacSha256(this._secret, `${subject}.${nonce}`);
|
|
1929
|
+
return `${nonce}.${signature}`;
|
|
1930
|
+
}
|
|
1931
|
+
async validate(token, subject) {
|
|
1932
|
+
const separatorIndex = token.indexOf(".");
|
|
1933
|
+
if (separatorIndex <= 0) return false;
|
|
1934
|
+
const nonce = token.slice(0, separatorIndex);
|
|
1935
|
+
const signature = token.slice(separatorIndex + 1);
|
|
1936
|
+
if (import_shared44.Guards.isNullOrEmpty(nonce) || import_shared44.Guards.isNullOrEmpty(signature)) return false;
|
|
1937
|
+
const expected = await this._cryptoService.hmacSha256(this._secret, `${subject}.${nonce}`);
|
|
1938
|
+
const encoder = new TextEncoder();
|
|
1939
|
+
const actualBuffer = encoder.encode(signature);
|
|
1940
|
+
const expectedBuffer = encoder.encode(expected);
|
|
1941
|
+
if (actualBuffer.length !== expectedBuffer.length) return false;
|
|
1942
|
+
return this._cryptoService.timingSafeEqual(actualBuffer, expectedBuffer);
|
|
1943
|
+
}
|
|
1944
|
+
};
|
|
1945
|
+
}
|
|
1946
|
+
});
|
|
1947
|
+
|
|
1948
|
+
// src/infrastructure/services/csrf/index.ts
|
|
1949
|
+
var init_csrf = __esm({
|
|
1950
|
+
"src/infrastructure/services/csrf/index.ts"() {
|
|
1951
|
+
"use strict";
|
|
1952
|
+
init_csrf_token_service();
|
|
1953
|
+
}
|
|
1954
|
+
});
|
|
1955
|
+
|
|
1837
1956
|
// src/infrastructure/services/extractors/extract-bearer.extractor.ts
|
|
1838
|
-
var
|
|
1957
|
+
var import_shared45, BearerTokenExtractor;
|
|
1839
1958
|
var init_extract_bearer_extractor = __esm({
|
|
1840
1959
|
"src/infrastructure/services/extractors/extract-bearer.extractor.ts"() {
|
|
1841
1960
|
"use strict";
|
|
1842
|
-
|
|
1961
|
+
import_shared45 = require("@xeno-js/shared");
|
|
1843
1962
|
BearerTokenExtractor = class {
|
|
1844
1963
|
extract(headers) {
|
|
1845
|
-
const authHeader =
|
|
1846
|
-
if (!
|
|
1964
|
+
const authHeader = import_shared45.StringHelper.getSingleValue(headers["authorization"]);
|
|
1965
|
+
if (!import_shared45.Guards.isDefined(authHeader)) {
|
|
1847
1966
|
return void 0;
|
|
1848
1967
|
}
|
|
1849
1968
|
if (authHeader.toLowerCase().startsWith("bearer ")) {
|
|
1850
1969
|
return authHeader.substring(7);
|
|
1851
1970
|
}
|
|
1852
|
-
const cookieHeader =
|
|
1853
|
-
if (
|
|
1971
|
+
const cookieHeader = import_shared45.StringHelper.getSingleValue(headers["cookie"]);
|
|
1972
|
+
if (import_shared45.Guards.isDefined(cookieHeader)) {
|
|
1854
1973
|
const match = /sb-access-token=([^;]+)/.exec(cookieHeader);
|
|
1855
|
-
if (!
|
|
1974
|
+
if (!import_shared45.Guards.isNullOrEmpty(match) && import_shared45.Guards.isDefined(match[1])) {
|
|
1856
1975
|
return match[1].trim();
|
|
1857
1976
|
}
|
|
1858
1977
|
}
|
|
@@ -1863,44 +1982,44 @@ var init_extract_bearer_extractor = __esm({
|
|
|
1863
1982
|
});
|
|
1864
1983
|
|
|
1865
1984
|
// src/infrastructure/services/extractors/extract-ssr-bearer.extractor.ts
|
|
1866
|
-
var
|
|
1985
|
+
var import_shared46, SupabaseSsrTokenExtractor;
|
|
1867
1986
|
var init_extract_ssr_bearer_extractor = __esm({
|
|
1868
1987
|
"src/infrastructure/services/extractors/extract-ssr-bearer.extractor.ts"() {
|
|
1869
1988
|
"use strict";
|
|
1870
|
-
|
|
1989
|
+
import_shared46 = require("@xeno-js/shared");
|
|
1871
1990
|
SupabaseSsrTokenExtractor = class {
|
|
1872
1991
|
extract(headers) {
|
|
1873
|
-
const authHeader =
|
|
1874
|
-
if (
|
|
1992
|
+
const authHeader = import_shared46.StringHelper.getSingleValue(headers["authorization"]);
|
|
1993
|
+
if (import_shared46.Guards.isDefined(authHeader) && authHeader.toLowerCase().startsWith("bearer ")) {
|
|
1875
1994
|
return authHeader.substring(7);
|
|
1876
1995
|
}
|
|
1877
|
-
const cookieHeader =
|
|
1878
|
-
if (
|
|
1996
|
+
const cookieHeader = import_shared46.StringHelper.getSingleValue(headers["cookie"]);
|
|
1997
|
+
if (import_shared46.Guards.isNullOrEmpty(cookieHeader)) return void 0;
|
|
1879
1998
|
const cookies = cookieHeader.split(";").map((c) => c.trim());
|
|
1880
1999
|
const tokenChunks = {};
|
|
1881
2000
|
let unchunkedToken;
|
|
1882
2001
|
for (const cookie of cookies) {
|
|
1883
2002
|
const [name, ...rest] = cookie.split("=");
|
|
1884
|
-
if (!
|
|
2003
|
+
if (!import_shared46.Guards.isDefined(name) || import_shared46.Guards.isNullOrEmpty(rest)) continue;
|
|
1885
2004
|
const value = decodeURIComponent(rest.join("="));
|
|
1886
|
-
if (
|
|
2005
|
+
if (import_shared46.Guards.isDefined(/^sb-[a-z0-9]+-auth-token$/.exec(name))) {
|
|
1887
2006
|
unchunkedToken = value;
|
|
1888
2007
|
} else {
|
|
1889
2008
|
const match = /^sb-[a-z0-9]+-auth-token\.(\d+)$/.exec(name);
|
|
1890
|
-
if (
|
|
2009
|
+
if (import_shared46.Guards.isDefined(match)) tokenChunks[parseInt(match[1], 10)] = value;
|
|
1891
2010
|
}
|
|
1892
2011
|
}
|
|
1893
2012
|
let fullTokenString = unchunkedToken;
|
|
1894
|
-
if (!
|
|
2013
|
+
if (!import_shared46.Guards.isDefined(fullTokenString) && Object.keys(tokenChunks).length > 0) {
|
|
1895
2014
|
const indices = Object.keys(tokenChunks).map(Number).sort((a, b) => a - b);
|
|
1896
2015
|
fullTokenString = indices.map((i) => tokenChunks[i]).join("");
|
|
1897
2016
|
}
|
|
1898
|
-
if (
|
|
2017
|
+
if (import_shared46.Guards.isNullOrEmpty(fullTokenString)) return void 0;
|
|
1899
2018
|
try {
|
|
1900
|
-
const parsed =
|
|
1901
|
-
if (
|
|
2019
|
+
const parsed = import_shared46.StringHelper.safeParse(fullTokenString);
|
|
2020
|
+
if (import_shared46.Guards.isDefined(parsed) && import_shared46.Guards.isObject(parsed) && "access_token" in parsed) {
|
|
1902
2021
|
const accessToken = parsed["access_token"];
|
|
1903
|
-
if (
|
|
2022
|
+
if (import_shared46.Guards.isString(accessToken)) return accessToken;
|
|
1904
2023
|
}
|
|
1905
2024
|
} catch {
|
|
1906
2025
|
return void 0;
|
|
@@ -1910,12 +2029,39 @@ var init_extract_ssr_bearer_extractor = __esm({
|
|
|
1910
2029
|
}
|
|
1911
2030
|
});
|
|
1912
2031
|
|
|
2032
|
+
// src/infrastructure/services/extractors/http-cookie.extractor.ts
|
|
2033
|
+
var import_shared47, HttpCookieExtractor;
|
|
2034
|
+
var init_http_cookie_extractor = __esm({
|
|
2035
|
+
"src/infrastructure/services/extractors/http-cookie.extractor.ts"() {
|
|
2036
|
+
"use strict";
|
|
2037
|
+
import_shared47 = require("@xeno-js/shared");
|
|
2038
|
+
HttpCookieExtractor = class {
|
|
2039
|
+
extract(cookie) {
|
|
2040
|
+
if (!import_shared47.Guards.isDefined(cookie.header)) return void 0;
|
|
2041
|
+
for (const rawCookie of cookie.header.split(";")) {
|
|
2042
|
+
const separatorIndex = rawCookie.indexOf("=");
|
|
2043
|
+
if (separatorIndex <= 0) continue;
|
|
2044
|
+
const name = rawCookie.slice(0, separatorIndex).trim();
|
|
2045
|
+
if (name !== cookie.name) continue;
|
|
2046
|
+
const value = rawCookie.slice(separatorIndex + 1).trim();
|
|
2047
|
+
try {
|
|
2048
|
+
return decodeURIComponent(value);
|
|
2049
|
+
} catch {
|
|
2050
|
+
return void 0;
|
|
2051
|
+
}
|
|
2052
|
+
}
|
|
2053
|
+
return void 0;
|
|
2054
|
+
}
|
|
2055
|
+
};
|
|
2056
|
+
}
|
|
2057
|
+
});
|
|
2058
|
+
|
|
1913
2059
|
// src/infrastructure/services/extractors/http-header.extractor.ts
|
|
1914
|
-
var
|
|
2060
|
+
var import_shared48, HttpHeaderExtractor;
|
|
1915
2061
|
var init_http_header_extractor = __esm({
|
|
1916
2062
|
"src/infrastructure/services/extractors/http-header.extractor.ts"() {
|
|
1917
2063
|
"use strict";
|
|
1918
|
-
|
|
2064
|
+
import_shared48 = require("@xeno-js/shared");
|
|
1919
2065
|
HttpHeaderExtractor = class {
|
|
1920
2066
|
/**
|
|
1921
2067
|
* @description Constructor for HttpHeaderExtractor. It takes an instance of IServiceExtractor for extracting Bearer tokens, allowing for separation of concerns and adherence to the Single Responsibility Principle (SRP). This design enables the HttpHeaderExtractor to focus on general header extraction while delegating the specific logic of Bearer token extraction to a dedicated extractor, promoting code reusability and maintainability.
|
|
@@ -1926,32 +2072,41 @@ var init_http_header_extractor = __esm({
|
|
|
1926
2072
|
* @since 2025-09-30
|
|
1927
2073
|
* @link https://github.com/xeno-js/xeno-js
|
|
1928
2074
|
*/
|
|
1929
|
-
constructor(_bearerExtractor, _trustedIp) {
|
|
2075
|
+
constructor(_bearerExtractor, _cookieExtractor, _trustedIp, _cookieName) {
|
|
1930
2076
|
this._bearerExtractor = _bearerExtractor;
|
|
2077
|
+
this._cookieExtractor = _cookieExtractor;
|
|
1931
2078
|
this._trustedIp = _trustedIp;
|
|
2079
|
+
this._cookieName = _cookieName;
|
|
1932
2080
|
}
|
|
1933
2081
|
_bearerExtractor;
|
|
2082
|
+
_cookieExtractor;
|
|
1934
2083
|
_trustedIp;
|
|
2084
|
+
_cookieName;
|
|
1935
2085
|
extract(headers) {
|
|
1936
|
-
const correlationId =
|
|
1937
|
-
const requestId =
|
|
2086
|
+
const correlationId = import_shared48.GuidHelper.parse(import_shared48.StringHelper.getSingleValue(headers["x-correlation-id"]));
|
|
2087
|
+
const requestId = import_shared48.GuidHelper.parse(import_shared48.StringHelper.getSingleValue(headers["x-request-id"]));
|
|
1938
2088
|
const token = this._bearerExtractor.extract(headers);
|
|
1939
|
-
const clientIp =
|
|
1940
|
-
const spanId =
|
|
1941
|
-
const parentSpanId =
|
|
1942
|
-
const acceptHeader =
|
|
1943
|
-
const contentTypeHeader =
|
|
1944
|
-
const userAgent =
|
|
1945
|
-
const returnAddress =
|
|
1946
|
-
const sequenceId =
|
|
1947
|
-
const position =
|
|
1948
|
-
const size =
|
|
1949
|
-
const expiration =
|
|
1950
|
-
const csrf =
|
|
1951
|
-
const
|
|
1952
|
-
const
|
|
1953
|
-
|
|
1954
|
-
|
|
2089
|
+
const clientIp = import_shared48.StringHelper.getSingleValue(headers[this._trustedIp?.toLowerCase() ?? "x-forwarded-for"]) ?? import_shared48.StringHelper.getSingleValue(headers["x-real-ip"]);
|
|
2090
|
+
const spanId = import_shared48.GuidHelper.parse(import_shared48.StringHelper.getSingleValue(headers["x-span-id"]));
|
|
2091
|
+
const parentSpanId = import_shared48.StringHelper.getSingleValue(headers["x-parent-span-id"]);
|
|
2092
|
+
const acceptHeader = import_shared48.StringHelper.getSingleValue(headers["accept"]);
|
|
2093
|
+
const contentTypeHeader = import_shared48.StringHelper.getSingleValue(headers["content-type"]);
|
|
2094
|
+
const userAgent = import_shared48.StringHelper.getSingleValue(headers["user-agent"]);
|
|
2095
|
+
const returnAddress = import_shared48.StringHelper.getSingleValue(headers["x-return-address"]);
|
|
2096
|
+
const sequenceId = import_shared48.StringHelper.getSingleValue(headers["x-sequence-id"]);
|
|
2097
|
+
const position = import_shared48.StringHelper.getSingleValue(headers["x-sequence-position"]);
|
|
2098
|
+
const size = import_shared48.StringHelper.getSingleValue(headers["x-sequence-size"]);
|
|
2099
|
+
const expiration = import_shared48.StringHelper.getSingleValue(headers["x-expiration"]);
|
|
2100
|
+
const csrf = import_shared48.StringHelper.getSingleValue(headers["x-csrf-token"]);
|
|
2101
|
+
const cookieHeader = import_shared48.StringHelper.getSingleValue(headers["cookie"]);
|
|
2102
|
+
const csrfCookie = this._cookieExtractor.extract({
|
|
2103
|
+
header: cookieHeader,
|
|
2104
|
+
name: this._cookieName
|
|
2105
|
+
});
|
|
2106
|
+
const origin = import_shared48.StringHelper.getSingleValue(headers["origin"]);
|
|
2107
|
+
const cleanOrigin = import_shared48.HttpHelper.sanitizeOriginUrl(origin);
|
|
2108
|
+
const referer = import_shared48.StringHelper.getSingleValue(headers["referer"]);
|
|
2109
|
+
const cleanReferer = import_shared48.HttpHelper.sanitizeOriginUrl(referer);
|
|
1955
2110
|
const accept = acceptHeader === "*/*" ? void 0 : acceptHeader;
|
|
1956
2111
|
const formatIndicator = accept ?? contentTypeHeader ?? "application/json";
|
|
1957
2112
|
const metadata = {
|
|
@@ -1965,14 +2120,15 @@ var init_http_header_extractor = __esm({
|
|
|
1965
2120
|
userAgent,
|
|
1966
2121
|
returnAddress,
|
|
1967
2122
|
csrf,
|
|
2123
|
+
csrfCookie,
|
|
1968
2124
|
origin: cleanOrigin,
|
|
1969
2125
|
referer: cleanReferer,
|
|
1970
2126
|
sequence: {
|
|
1971
2127
|
sequenceId,
|
|
1972
|
-
position:
|
|
1973
|
-
size:
|
|
2128
|
+
position: import_shared48.Guards.isDefined(position) ? import_shared48.MathHelper.toNumber(position) : void 0,
|
|
2129
|
+
size: import_shared48.Guards.isDefined(size) ? import_shared48.MathHelper.toNumber(size) : void 0
|
|
1974
2130
|
},
|
|
1975
|
-
expiration:
|
|
2131
|
+
expiration: import_shared48.Guards.isDefined(expiration) ? import_shared48.MathHelper.toNumber(expiration) : void 0
|
|
1976
2132
|
};
|
|
1977
2133
|
return metadata;
|
|
1978
2134
|
}
|
|
@@ -1986,23 +2142,24 @@ var init_extractors = __esm({
|
|
|
1986
2142
|
"use strict";
|
|
1987
2143
|
init_extract_bearer_extractor();
|
|
1988
2144
|
init_extract_ssr_bearer_extractor();
|
|
2145
|
+
init_http_cookie_extractor();
|
|
1989
2146
|
init_http_header_extractor();
|
|
1990
2147
|
}
|
|
1991
2148
|
});
|
|
1992
2149
|
|
|
1993
2150
|
// src/infrastructure/services/resiliences/resilience.service.ts
|
|
1994
|
-
var
|
|
2151
|
+
var import_shared49, ServiceResilience;
|
|
1995
2152
|
var init_resilience_service = __esm({
|
|
1996
2153
|
"src/infrastructure/services/resiliences/resilience.service.ts"() {
|
|
1997
2154
|
"use strict";
|
|
1998
|
-
|
|
2155
|
+
import_shared49 = require("@xeno-js/shared");
|
|
1999
2156
|
ServiceResilience = class {
|
|
2000
2157
|
constructor(policy) {
|
|
2001
2158
|
this.policy = policy;
|
|
2002
2159
|
}
|
|
2003
2160
|
policy;
|
|
2004
2161
|
async execute(operation, signal) {
|
|
2005
|
-
|
|
2162
|
+
import_shared49.AppError.throwIfAborted(signal, "ServiceResilience.execute");
|
|
2006
2163
|
return this.policy.execute(() => operation(), signal);
|
|
2007
2164
|
}
|
|
2008
2165
|
};
|
|
@@ -2017,12 +2174,80 @@ var init_resiliences = __esm({
|
|
|
2017
2174
|
}
|
|
2018
2175
|
});
|
|
2019
2176
|
|
|
2177
|
+
// src/infrastructure/services/resolver/utils/socket.utils.ts
|
|
2178
|
+
var import_shared50, SocketIpExtractor;
|
|
2179
|
+
var init_socket_utils = __esm({
|
|
2180
|
+
"src/infrastructure/services/resolver/utils/socket.utils.ts"() {
|
|
2181
|
+
"use strict";
|
|
2182
|
+
import_shared50 = require("@xeno-js/shared");
|
|
2183
|
+
SocketIpExtractor = Object.freeze({
|
|
2184
|
+
/**
|
|
2185
|
+
* @description Extracts the IP address of the remote socket from an incoming request.
|
|
2186
|
+
* @param req The incoming request object.
|
|
2187
|
+
* @returns The IP address of the remote socket, or undefined if not available.
|
|
2188
|
+
*/
|
|
2189
|
+
extract(req) {
|
|
2190
|
+
if (import_shared50.Guards.isDefined(req) && import_shared50.Guards.isObject(req)) {
|
|
2191
|
+
const candidate = req;
|
|
2192
|
+
return candidate.socket?.remoteAddress ?? candidate.connection?.remoteAddress;
|
|
2193
|
+
}
|
|
2194
|
+
return void 0;
|
|
2195
|
+
}
|
|
2196
|
+
});
|
|
2197
|
+
}
|
|
2198
|
+
});
|
|
2199
|
+
|
|
2200
|
+
// src/infrastructure/services/resolver/utils/index.ts
|
|
2201
|
+
var init_utils = __esm({
|
|
2202
|
+
"src/infrastructure/services/resolver/utils/index.ts"() {
|
|
2203
|
+
"use strict";
|
|
2204
|
+
init_socket_utils();
|
|
2205
|
+
}
|
|
2206
|
+
});
|
|
2207
|
+
|
|
2208
|
+
// src/infrastructure/services/resolver/client-ip.resolver.ts
|
|
2209
|
+
var import_shared51, ClientIpResolver;
|
|
2210
|
+
var init_client_ip_resolver = __esm({
|
|
2211
|
+
"src/infrastructure/services/resolver/client-ip.resolver.ts"() {
|
|
2212
|
+
"use strict";
|
|
2213
|
+
import_shared51 = require("@xeno-js/shared");
|
|
2214
|
+
init_utils();
|
|
2215
|
+
ClientIpResolver = class {
|
|
2216
|
+
constructor(_trustedProxies = []) {
|
|
2217
|
+
this._trustedProxies = _trustedProxies;
|
|
2218
|
+
}
|
|
2219
|
+
_trustedProxies;
|
|
2220
|
+
resolve(req, clientIp) {
|
|
2221
|
+
const socketIp = SocketIpExtractor.extract(req);
|
|
2222
|
+
if (!import_shared51.Guards.isDefined(socketIp))
|
|
2223
|
+
return !import_shared51.Guards.isNullOrEmpty(clientIp) ? clientIp.split(",")[0].trim() : void 0;
|
|
2224
|
+
const isTrustedProxy = this._trustedProxies.includes(socketIp);
|
|
2225
|
+
if (!isTrustedProxy) return socketIp;
|
|
2226
|
+
if (import_shared51.Guards.isDefined(clientIp)) return clientIp.split(",")[0].trim();
|
|
2227
|
+
return socketIp;
|
|
2228
|
+
}
|
|
2229
|
+
};
|
|
2230
|
+
}
|
|
2231
|
+
});
|
|
2232
|
+
|
|
2233
|
+
// src/infrastructure/services/resolver/index.ts
|
|
2234
|
+
var init_resolver = __esm({
|
|
2235
|
+
"src/infrastructure/services/resolver/index.ts"() {
|
|
2236
|
+
"use strict";
|
|
2237
|
+
init_client_ip_resolver();
|
|
2238
|
+
}
|
|
2239
|
+
});
|
|
2240
|
+
|
|
2020
2241
|
// src/infrastructure/services/index.ts
|
|
2021
2242
|
var services_exports = {};
|
|
2022
2243
|
__export(services_exports, {
|
|
2023
2244
|
AllowMethodRegistry: () => AllowMethodRegistry,
|
|
2024
2245
|
AllowOrigin: () => AllowOrigin,
|
|
2025
2246
|
BearerTokenExtractor: () => BearerTokenExtractor,
|
|
2247
|
+
ClientIpResolver: () => ClientIpResolver,
|
|
2248
|
+
CsrfTokenService: () => CsrfTokenService,
|
|
2249
|
+
EdgeCryptoService: () => EdgeCryptoService,
|
|
2250
|
+
HttpCookieExtractor: () => HttpCookieExtractor,
|
|
2026
2251
|
HttpHeaderExtractor: () => HttpHeaderExtractor,
|
|
2027
2252
|
PLimitConcurrencyService: () => PLimitConcurrencyService,
|
|
2028
2253
|
ServiceResilience: () => ServiceResilience,
|
|
@@ -2034,8 +2259,11 @@ var init_services = __esm({
|
|
|
2034
2259
|
init_allow_methods();
|
|
2035
2260
|
init_allow_origins();
|
|
2036
2261
|
init_concurrency();
|
|
2262
|
+
init_crypto();
|
|
2263
|
+
init_csrf();
|
|
2037
2264
|
init_extractors();
|
|
2038
2265
|
init_resiliences();
|
|
2266
|
+
init_resolver();
|
|
2039
2267
|
}
|
|
2040
2268
|
});
|
|
2041
2269
|
|
|
@@ -2058,15 +2286,15 @@ var init_allow_method_factory = __esm({
|
|
|
2058
2286
|
});
|
|
2059
2287
|
|
|
2060
2288
|
// src/infrastructure/factories/axios.factory.ts
|
|
2061
|
-
var import_node_http, import_node_https,
|
|
2289
|
+
var import_node_http, import_node_https, import_shared52, import_axios, NodeAxiosFactory;
|
|
2062
2290
|
var init_axios_factory = __esm({
|
|
2063
2291
|
"src/infrastructure/factories/axios.factory.ts"() {
|
|
2064
2292
|
"use strict";
|
|
2065
2293
|
import_node_http = __toESM(require("http"), 1);
|
|
2066
2294
|
import_node_https = __toESM(require("https"), 1);
|
|
2067
|
-
|
|
2295
|
+
import_shared52 = require("@xeno-js/shared");
|
|
2068
2296
|
import_axios = __toESM(require("axios"), 1);
|
|
2069
|
-
NodeAxiosFactory = class extends
|
|
2297
|
+
NodeAxiosFactory = class extends import_shared52.AxiosFactory {
|
|
2070
2298
|
create(config) {
|
|
2071
2299
|
const isKeepAlive = config.keepAlive ?? true;
|
|
2072
2300
|
const maxSockets = config.maxSockets ?? 100;
|
|
@@ -2091,18 +2319,18 @@ var init_axios_factory = __esm({
|
|
|
2091
2319
|
proxy: config.proxy,
|
|
2092
2320
|
withCredentials: config.withCredentials
|
|
2093
2321
|
});
|
|
2094
|
-
return new
|
|
2322
|
+
return new import_shared52.AxiosHttpClient(axiosInstance);
|
|
2095
2323
|
}
|
|
2096
2324
|
};
|
|
2097
2325
|
}
|
|
2098
2326
|
});
|
|
2099
2327
|
|
|
2100
2328
|
// src/infrastructure/factories/cockatiel-resilience.factory.ts
|
|
2101
|
-
var
|
|
2329
|
+
var import_shared53, import_cockatiel, CockatielResilienceFactory;
|
|
2102
2330
|
var init_cockatiel_resilience_factory = __esm({
|
|
2103
2331
|
"src/infrastructure/factories/cockatiel-resilience.factory.ts"() {
|
|
2104
2332
|
"use strict";
|
|
2105
|
-
|
|
2333
|
+
import_shared53 = require("@xeno-js/shared");
|
|
2106
2334
|
import_cockatiel = require("cockatiel");
|
|
2107
2335
|
init_resilience_service();
|
|
2108
2336
|
CockatielResilienceFactory = class {
|
|
@@ -2112,36 +2340,36 @@ var init_cockatiel_resilience_factory = __esm({
|
|
|
2112
2340
|
retry: {
|
|
2113
2341
|
attempts: this.checkConfigValue(
|
|
2114
2342
|
config.retry.attempts,
|
|
2115
|
-
|
|
2343
|
+
import_shared53.RESILIENCE_DEFAULTS.RETRY.ATTEMPTS,
|
|
2116
2344
|
message
|
|
2117
2345
|
),
|
|
2118
2346
|
baseDelayMs: this.checkConfigValue(
|
|
2119
2347
|
config.retry.baseDelayMs,
|
|
2120
|
-
|
|
2348
|
+
import_shared53.RESILIENCE_DEFAULTS.RETRY.BASE_DELAY_MS,
|
|
2121
2349
|
message
|
|
2122
2350
|
),
|
|
2123
2351
|
maxDelayMs: this.checkConfigValue(
|
|
2124
2352
|
config.retry.maxDelayMs,
|
|
2125
|
-
|
|
2353
|
+
import_shared53.RESILIENCE_DEFAULTS.RETRY.MAX_DELAY_MS,
|
|
2126
2354
|
message
|
|
2127
2355
|
)
|
|
2128
2356
|
},
|
|
2129
2357
|
circuitBreaker: {
|
|
2130
2358
|
consecutiveFailures: this.checkConfigValue(
|
|
2131
2359
|
config.circuitBreaker.consecutiveFailures,
|
|
2132
|
-
|
|
2360
|
+
import_shared53.RESILIENCE_DEFAULTS.CIRCUIT_BREAKER.CONSECUTIVE_FAILURES,
|
|
2133
2361
|
message
|
|
2134
2362
|
),
|
|
2135
2363
|
halfOpenTimeoutMs: this.checkConfigValue(
|
|
2136
2364
|
config.circuitBreaker.halfOpenTimeoutMs,
|
|
2137
|
-
|
|
2365
|
+
import_shared53.RESILIENCE_DEFAULTS.CIRCUIT_BREAKER.HALF_OPEN_TIMEOUT_MS,
|
|
2138
2366
|
message
|
|
2139
2367
|
)
|
|
2140
2368
|
},
|
|
2141
2369
|
bulkhead: {
|
|
2142
2370
|
maxConcurrent: this.checkConfigValue(
|
|
2143
2371
|
config.bulkhead.maxConcurrent,
|
|
2144
|
-
|
|
2372
|
+
import_shared53.RESILIENCE_DEFAULTS.BULKHEAD.MAX_CONCURRENT,
|
|
2145
2373
|
message
|
|
2146
2374
|
)
|
|
2147
2375
|
}
|
|
@@ -2167,13 +2395,13 @@ var init_cockatiel_resilience_factory = __esm({
|
|
|
2167
2395
|
return new ServiceResilience((0, import_cockatiel.wrap)(bulkheadPolicy, circuitBreakerPolicy, retryPolicy));
|
|
2168
2396
|
}
|
|
2169
2397
|
isTransientError(error) {
|
|
2170
|
-
if (!
|
|
2398
|
+
if (!import_shared53.Guards.isDefined(error) || !import_shared53.Guards.isObject(error)) return false;
|
|
2171
2399
|
let status;
|
|
2172
2400
|
let isNetworkError = false;
|
|
2173
|
-
if (error instanceof
|
|
2401
|
+
if (error instanceof import_shared53.AppError) {
|
|
2174
2402
|
status = error.status;
|
|
2175
2403
|
const cause = error.cause;
|
|
2176
|
-
if (
|
|
2404
|
+
if (import_shared53.Guards.isDefined(cause) && import_shared53.Guards.isString(cause.code)) {
|
|
2177
2405
|
isNetworkError = [
|
|
2178
2406
|
"ECONNABORTED",
|
|
2179
2407
|
"ECONNRESET",
|
|
@@ -2185,7 +2413,7 @@ var init_cockatiel_resilience_factory = __esm({
|
|
|
2185
2413
|
} else {
|
|
2186
2414
|
const err = error;
|
|
2187
2415
|
status = err.status;
|
|
2188
|
-
if (
|
|
2416
|
+
if (import_shared53.Guards.isString(err.code)) {
|
|
2189
2417
|
isNetworkError = [
|
|
2190
2418
|
"ECONNABORTED",
|
|
2191
2419
|
"ECONNRESET",
|
|
@@ -2196,7 +2424,7 @@ var init_cockatiel_resilience_factory = __esm({
|
|
|
2196
2424
|
}
|
|
2197
2425
|
}
|
|
2198
2426
|
if (isNetworkError) return true;
|
|
2199
|
-
if (
|
|
2427
|
+
if (import_shared53.Guards.isDefined(status)) {
|
|
2200
2428
|
return status === 408 || status === 429 || status >= 500 && status < 600;
|
|
2201
2429
|
}
|
|
2202
2430
|
return false;
|
|
@@ -2204,24 +2432,24 @@ var init_cockatiel_resilience_factory = __esm({
|
|
|
2204
2432
|
isTransientAndIdempotent(error) {
|
|
2205
2433
|
if (!this.isTransientError(error)) return false;
|
|
2206
2434
|
let method;
|
|
2207
|
-
if (error instanceof
|
|
2435
|
+
if (error instanceof import_shared53.AppError) {
|
|
2208
2436
|
const cause = error.cause;
|
|
2209
|
-
if (
|
|
2437
|
+
if (import_shared53.Guards.isDefined(cause) && import_shared53.Guards.isDefined(cause.config) && import_shared53.Guards.isString(cause.config.method)) {
|
|
2210
2438
|
method = cause.config.method.toUpperCase();
|
|
2211
2439
|
}
|
|
2212
2440
|
} else {
|
|
2213
2441
|
const err = error;
|
|
2214
|
-
if (
|
|
2442
|
+
if (import_shared53.Guards.isDefined(err.config) && import_shared53.Guards.isString(err.config.method)) {
|
|
2215
2443
|
method = err.config.method.toUpperCase();
|
|
2216
2444
|
}
|
|
2217
2445
|
}
|
|
2218
|
-
if (
|
|
2446
|
+
if (import_shared53.Guards.isNullOrEmpty(method)) return false;
|
|
2219
2447
|
const idempotentMethods = ["GET", "PUT", "DELETE", "HEAD", "OPTIONS"];
|
|
2220
2448
|
return idempotentMethods.includes(method);
|
|
2221
2449
|
}
|
|
2222
2450
|
checkConfigValue(value, defaultValue, message) {
|
|
2223
|
-
if (
|
|
2224
|
-
|
|
2451
|
+
if (import_shared53.Guards.isDefined(value)) {
|
|
2452
|
+
import_shared53.Guards.throwIfNegative(value, message);
|
|
2225
2453
|
return value;
|
|
2226
2454
|
}
|
|
2227
2455
|
return defaultValue;
|
|
@@ -2253,11 +2481,11 @@ var init_db_client_factory = __esm({
|
|
|
2253
2481
|
});
|
|
2254
2482
|
|
|
2255
2483
|
// src/infrastructure/context/request-context.ts
|
|
2256
|
-
var
|
|
2484
|
+
var import_shared54, NodeRequestContext;
|
|
2257
2485
|
var init_request_context = __esm({
|
|
2258
2486
|
"src/infrastructure/context/request-context.ts"() {
|
|
2259
2487
|
"use strict";
|
|
2260
|
-
|
|
2488
|
+
import_shared54 = require("@xeno-js/shared");
|
|
2261
2489
|
NodeRequestContext = class {
|
|
2262
2490
|
/**
|
|
2263
2491
|
* @description Constructs a new instance of the NodeRequestContext class, which requires an instance of AsyncLocalStorage to manage the request context. The AsyncLocalStorage instance is used to create and access the context for each request, allowing for the storage of identity information and other relevant data that needs to be accessible across asynchronous operations. This constructor initializes the NodeRequestContext with the provided AsyncLocalStorage, enabling it to implement the methods defined in the IRequestContext interface for managing request-specific context data.
|
|
@@ -2285,7 +2513,7 @@ var init_request_context = __esm({
|
|
|
2285
2513
|
}
|
|
2286
2514
|
updateIdentity(identity) {
|
|
2287
2515
|
const store = this._storage.getStore();
|
|
2288
|
-
if (
|
|
2516
|
+
if (import_shared54.Guards.isDefined(store) && import_shared54.Guards.isDefined(store.context)) {
|
|
2289
2517
|
store.context = Object.freeze({
|
|
2290
2518
|
...store.context,
|
|
2291
2519
|
identity: Object.freeze(identity)
|
|
@@ -2294,23 +2522,23 @@ var init_request_context = __esm({
|
|
|
2294
2522
|
}
|
|
2295
2523
|
getContext() {
|
|
2296
2524
|
const store = this._storage.getStore();
|
|
2297
|
-
if (!
|
|
2525
|
+
if (!import_shared54.Guards.isDefined(store)) return void 0;
|
|
2298
2526
|
const context = store.context;
|
|
2299
2527
|
return Object.freeze(context);
|
|
2300
2528
|
}
|
|
2301
2529
|
getIdentity() {
|
|
2302
2530
|
const store = this._storage.getStore();
|
|
2303
|
-
if (!
|
|
2531
|
+
if (!import_shared54.Guards.isDefined(store)) return void 0;
|
|
2304
2532
|
return Object.freeze(store.context?.identity);
|
|
2305
2533
|
}
|
|
2306
2534
|
getScope() {
|
|
2307
2535
|
const store = this._storage.getStore();
|
|
2308
|
-
if (!
|
|
2536
|
+
if (!import_shared54.Guards.isDefined(store)) return void 0;
|
|
2309
2537
|
return store.scope;
|
|
2310
2538
|
}
|
|
2311
2539
|
getNetworkContext() {
|
|
2312
2540
|
const store = this._storage.getStore();
|
|
2313
|
-
if (!
|
|
2541
|
+
if (!import_shared54.Guards.isDefined(store)) return void 0;
|
|
2314
2542
|
return Object.freeze(store.context?.network);
|
|
2315
2543
|
}
|
|
2316
2544
|
};
|
|
@@ -2383,18 +2611,18 @@ var init_sql_light_db_client_factory = __esm({
|
|
|
2383
2611
|
});
|
|
2384
2612
|
|
|
2385
2613
|
// src/infrastructure/factories/supabase.factory.ts
|
|
2386
|
-
var import_ssr,
|
|
2614
|
+
var import_ssr, import_shared55, SupabaseServerAuthFactory;
|
|
2387
2615
|
var init_supabase_factory = __esm({
|
|
2388
2616
|
"src/infrastructure/factories/supabase.factory.ts"() {
|
|
2389
2617
|
"use strict";
|
|
2390
2618
|
import_ssr = require("@supabase/ssr");
|
|
2391
|
-
|
|
2619
|
+
import_shared55 = require("@xeno-js/shared");
|
|
2392
2620
|
SupabaseServerAuthFactory = class {
|
|
2393
2621
|
create({
|
|
2394
2622
|
config,
|
|
2395
2623
|
container
|
|
2396
2624
|
}) {
|
|
2397
|
-
if (!
|
|
2625
|
+
if (!import_shared55.Guards.isDefined(config.ssrOpts)) {
|
|
2398
2626
|
throw new Error("ISsrCookieHandler is required for @supabase/ssr initialization.");
|
|
2399
2627
|
}
|
|
2400
2628
|
const cookieService = config.ssrOpts(container);
|
|
@@ -2409,9 +2637,9 @@ var init_supabase_factory = __esm({
|
|
|
2409
2637
|
}
|
|
2410
2638
|
}
|
|
2411
2639
|
});
|
|
2412
|
-
const mapper = new
|
|
2413
|
-
const sessionMapper = new
|
|
2414
|
-
return new
|
|
2640
|
+
const mapper = new import_shared55.SupabaseClaimsMapper();
|
|
2641
|
+
const sessionMapper = new import_shared55.SupabaseSessionMapper(mapper);
|
|
2642
|
+
return new import_shared55.SupabaseAuthService(client, mapper, sessionMapper, config);
|
|
2415
2643
|
}
|
|
2416
2644
|
};
|
|
2417
2645
|
}
|
|
@@ -2422,11 +2650,11 @@ var user_context_factory_exports = {};
|
|
|
2422
2650
|
__export(user_context_factory_exports, {
|
|
2423
2651
|
UserContextFactory: () => UserContextFactory
|
|
2424
2652
|
});
|
|
2425
|
-
var
|
|
2653
|
+
var import_shared56, UserContextFactory;
|
|
2426
2654
|
var init_user_context_factory = __esm({
|
|
2427
2655
|
"src/infrastructure/factories/user-context.factory.ts"() {
|
|
2428
2656
|
"use strict";
|
|
2429
|
-
|
|
2657
|
+
import_shared56 = require("@xeno-js/shared");
|
|
2430
2658
|
UserContextFactory = class {
|
|
2431
2659
|
/**
|
|
2432
2660
|
* @description Constructs an instance of UserContextFactory.
|
|
@@ -2447,7 +2675,7 @@ var init_user_context_factory = __esm({
|
|
|
2447
2675
|
tenantId: void 0
|
|
2448
2676
|
};
|
|
2449
2677
|
const identity = this._identityFactory.getIdentity();
|
|
2450
|
-
if (
|
|
2678
|
+
if (import_shared56.Guards.isDefined(identity)) {
|
|
2451
2679
|
output.userId = identity.userId;
|
|
2452
2680
|
output.tenantId = identity.tenantId;
|
|
2453
2681
|
}
|
|
@@ -2462,14 +2690,14 @@ var zod_validator_factory_exports = {};
|
|
|
2462
2690
|
__export(zod_validator_factory_exports, {
|
|
2463
2691
|
ZodValidatorFactory: () => ZodValidatorFactory
|
|
2464
2692
|
});
|
|
2465
|
-
var
|
|
2693
|
+
var import_shared57, ZodValidatorFactory;
|
|
2466
2694
|
var init_zod_validator_factory = __esm({
|
|
2467
2695
|
"src/infrastructure/factories/zod-validator.factory.ts"() {
|
|
2468
2696
|
"use strict";
|
|
2469
|
-
|
|
2697
|
+
import_shared57 = require("@xeno-js/shared");
|
|
2470
2698
|
ZodValidatorFactory = class {
|
|
2471
2699
|
create(opts) {
|
|
2472
|
-
const validatorService = new
|
|
2700
|
+
const validatorService = new import_shared57.ZodValidatorService(/* @__PURE__ */ new Map(), opts.logger);
|
|
2473
2701
|
for (const [intentKey, schema] of Object.entries(opts.schemas)) {
|
|
2474
2702
|
validatorService.addSchema(intentKey, schema);
|
|
2475
2703
|
}
|
|
@@ -2540,8 +2768,8 @@ var init_auth_utils = __esm({
|
|
|
2540
2768
|
const { TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
2541
2769
|
const pipelines = [];
|
|
2542
2770
|
const strategies = [];
|
|
2543
|
-
const { Guards:
|
|
2544
|
-
if (
|
|
2771
|
+
const { Guards: Guards46 } = await import("@xeno-js/shared");
|
|
2772
|
+
if (Guards46.isDefined(opts.policies)) {
|
|
2545
2773
|
const { PolicyRegistry: PolicyRegistry2 } = await Promise.resolve().then(() => (init_application(), application_exports));
|
|
2546
2774
|
container.addSingleton(TOKENS4.POLICY_REGISTRY, () => new PolicyRegistry2());
|
|
2547
2775
|
const policyRegistry = opts.policies;
|
|
@@ -2550,16 +2778,16 @@ var init_auth_utils = __esm({
|
|
|
2550
2778
|
for (const [intent, policy] of Object.entries(policyRegistry)) {
|
|
2551
2779
|
const intentLower = intent.toLowerCase();
|
|
2552
2780
|
registryInstance.addPolicy(intentLower, policy);
|
|
2553
|
-
if (!
|
|
2781
|
+
if (!Guards46.isNullOrEmpty(policy.roles)) {
|
|
2554
2782
|
Policies.add("roles");
|
|
2555
2783
|
}
|
|
2556
|
-
if (!
|
|
2784
|
+
if (!Guards46.isNullOrEmpty(policy.permissions)) {
|
|
2557
2785
|
Policies.add("permissions");
|
|
2558
2786
|
}
|
|
2559
|
-
if (!
|
|
2787
|
+
if (!Guards46.isNullOrEmpty(policy.userId)) {
|
|
2560
2788
|
Policies.add("userId");
|
|
2561
2789
|
}
|
|
2562
|
-
if (!
|
|
2790
|
+
if (!Guards46.isNullOrEmpty(policy.tenantId)) {
|
|
2563
2791
|
Policies.add("tenantId");
|
|
2564
2792
|
}
|
|
2565
2793
|
}
|
|
@@ -2608,10 +2836,10 @@ var init_auth_utils = __esm({
|
|
|
2608
2836
|
strategies.push(TOKENS4.TENANT_AUTHORIZATION_PIPELINE);
|
|
2609
2837
|
}
|
|
2610
2838
|
}
|
|
2611
|
-
if (!
|
|
2839
|
+
if (!Guards46.isNullOrEmpty(opts.customAuthorizationStrategy)) {
|
|
2612
2840
|
const customStrategies = opts.customAuthorizationStrategy;
|
|
2613
2841
|
customStrategies.forEach((strategyToken, index) => {
|
|
2614
|
-
if (
|
|
2842
|
+
if (Guards46.isDefined(strategyToken)) {
|
|
2615
2843
|
const token = `CUSTOM_AUTHORIZATION_STRATEGY_${index}`;
|
|
2616
2844
|
container.addSingleton(token, (c) => {
|
|
2617
2845
|
return strategyToken(c);
|
|
@@ -2753,12 +2981,12 @@ var unit_of_work_exports = {};
|
|
|
2753
2981
|
__export(unit_of_work_exports, {
|
|
2754
2982
|
UnitOfWork: () => UnitOfWork
|
|
2755
2983
|
});
|
|
2756
|
-
var
|
|
2984
|
+
var import_shared58, import_shared59, UnitOfWork;
|
|
2757
2985
|
var init_unit_of_work = __esm({
|
|
2758
2986
|
"src/infrastructure/transaction/unit-of-work.ts"() {
|
|
2759
2987
|
"use strict";
|
|
2760
|
-
|
|
2761
|
-
|
|
2988
|
+
import_shared58 = require("@xeno-js/shared");
|
|
2989
|
+
import_shared59 = require("@xeno-js/shared");
|
|
2762
2990
|
UnitOfWork = class {
|
|
2763
2991
|
/**
|
|
2764
2992
|
* Creates an instance of UnitOfWork.
|
|
@@ -2777,7 +3005,7 @@ var init_unit_of_work = __esm({
|
|
|
2777
3005
|
_dbContext;
|
|
2778
3006
|
_ttx;
|
|
2779
3007
|
async runInTransaction(callback, signal) {
|
|
2780
|
-
|
|
3008
|
+
import_shared58.AppError.throwIfAborted(signal, "UnitOfWork.runInTransaction");
|
|
2781
3009
|
return this._dbContext.transaction(async (tx) => {
|
|
2782
3010
|
this._ttx.state = tx;
|
|
2783
3011
|
try {
|
|
@@ -2789,9 +3017,9 @@ var init_unit_of_work = __esm({
|
|
|
2789
3017
|
});
|
|
2790
3018
|
}
|
|
2791
3019
|
async dispose() {
|
|
2792
|
-
if (
|
|
3020
|
+
if (import_shared59.Guards.isDefined(this._ttx.state)) {
|
|
2793
3021
|
try {
|
|
2794
|
-
if (
|
|
3022
|
+
if (import_shared59.Guards.hasMethod(this._ttx.state, "rollback")) {
|
|
2795
3023
|
await this._ttx.state.rollback();
|
|
2796
3024
|
}
|
|
2797
3025
|
} finally {
|
|
@@ -2814,7 +3042,7 @@ var init_db_module = __esm({
|
|
|
2814
3042
|
"use strict";
|
|
2815
3043
|
DbModule = class {
|
|
2816
3044
|
async configure(container, opts) {
|
|
2817
|
-
const { Guards:
|
|
3045
|
+
const { Guards: Guards46, TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
2818
3046
|
const { DbUtils: DbUtils2 } = await Promise.resolve().then(() => (init_db_utils(), db_utils_exports));
|
|
2819
3047
|
const db = opts.enableSqlLite ? await DbUtils2.addSqlLite(opts) : await DbUtils2.addDbClient(opts);
|
|
2820
3048
|
const { TransactionState: TransactionState2 } = await Promise.resolve().then(() => (init_transaction_state(), transaction_state_exports));
|
|
@@ -2831,7 +3059,7 @@ var init_db_module = __esm({
|
|
|
2831
3059
|
return new Proxy(db, {
|
|
2832
3060
|
get(_target, prop, receiver) {
|
|
2833
3061
|
const activeState = ttx.state;
|
|
2834
|
-
if (
|
|
3062
|
+
if (Guards46.isDefined(activeState)) {
|
|
2835
3063
|
if (prop === "transaction") {
|
|
2836
3064
|
return activeState.transaction.bind(activeState);
|
|
2837
3065
|
}
|
|
@@ -2868,14 +3096,14 @@ var init_http_utils = __esm({
|
|
|
2868
3096
|
*/
|
|
2869
3097
|
async addAxios(container, opts) {
|
|
2870
3098
|
const { NodeAxiosFactory: NodeAxiosFactory2 } = await Promise.resolve().then(() => (init_factories(), factories_exports));
|
|
2871
|
-
const { Guards:
|
|
2872
|
-
if (!
|
|
3099
|
+
const { Guards: Guards46 } = await import("@xeno-js/shared");
|
|
3100
|
+
if (!Guards46.isDefined(opts.token)) {
|
|
2873
3101
|
throw new Error("HttpConfig.token is required and must be defined.");
|
|
2874
3102
|
}
|
|
2875
3103
|
container.addSingleton(opts.token, () => {
|
|
2876
3104
|
const factory = new NodeAxiosFactory2();
|
|
2877
3105
|
const instance = factory.create(opts.client);
|
|
2878
|
-
if (!
|
|
3106
|
+
if (!Guards46.hasMethod(instance, "get") || !Guards46.hasMethod(instance, "post") || !Guards46.hasMethod(instance, "put") || !Guards46.hasMethod(instance, "patch") || !Guards46.hasMethod(instance, "delete")) {
|
|
2879
3107
|
throw new Error(
|
|
2880
3108
|
"The created HTTP client instance does not implement the required methods of IHttpClient."
|
|
2881
3109
|
);
|
|
@@ -2902,8 +3130,8 @@ var init_http_utils = __esm({
|
|
|
2902
3130
|
});
|
|
2903
3131
|
},
|
|
2904
3132
|
async addAllowOrigin(container, opts) {
|
|
2905
|
-
const { Guards:
|
|
2906
|
-
if (
|
|
3133
|
+
const { Guards: Guards46 } = await import("@xeno-js/shared");
|
|
3134
|
+
if (Guards46.isNullOrEmpty(opts)) throw new Error("At least an allow origin must be passed");
|
|
2907
3135
|
const { TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
2908
3136
|
const { AllowOrigin: AllowOrigin2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
2909
3137
|
const allowOrigin = [];
|
|
@@ -2963,13 +3191,13 @@ var init_validation_utils = __esm({
|
|
|
2963
3191
|
* @link https://github.com/xeno-js/xeno-js
|
|
2964
3192
|
*/
|
|
2965
3193
|
async addValidation(container, opts, logger) {
|
|
2966
|
-
const { Guards:
|
|
2967
|
-
if (!
|
|
3194
|
+
const { Guards: Guards46, TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
3195
|
+
if (!Guards46.isDefined(opts.zod) && Guards46.isNullOrEmpty(opts.customValidationStrategy)) {
|
|
2968
3196
|
return [];
|
|
2969
3197
|
}
|
|
2970
3198
|
const pipelines = [];
|
|
2971
3199
|
const validationStrategies = [];
|
|
2972
|
-
if (
|
|
3200
|
+
if (Guards46.isDefined(opts.zod)) {
|
|
2973
3201
|
const config = opts.zod;
|
|
2974
3202
|
const { ZodValidatorFactory: ZodValidatorFactory2 } = await Promise.resolve().then(() => (init_zod_validator_factory(), zod_validator_factory_exports));
|
|
2975
3203
|
container.addSingleton(TOKENS4.ZOD_VALIDATOR, () => {
|
|
@@ -2983,9 +3211,9 @@ var init_validation_utils = __esm({
|
|
|
2983
3211
|
validationStrategies.push(TOKENS4.SCHEMA_VALIDATION_STRATEGY);
|
|
2984
3212
|
}
|
|
2985
3213
|
const customValidationFactory = [];
|
|
2986
|
-
if (!
|
|
3214
|
+
if (!Guards46.isNullOrEmpty(opts.customValidationStrategy)) {
|
|
2987
3215
|
for (const strategyToken of opts.customValidationStrategy) {
|
|
2988
|
-
if (
|
|
3216
|
+
if (Guards46.isDefined(strategyToken)) {
|
|
2989
3217
|
customValidationFactory.push(strategyToken);
|
|
2990
3218
|
}
|
|
2991
3219
|
}
|
|
@@ -3010,11 +3238,11 @@ var idempotency_store_exports = {};
|
|
|
3010
3238
|
__export(idempotency_store_exports, {
|
|
3011
3239
|
IdempotencyStore: () => IdempotencyStore
|
|
3012
3240
|
});
|
|
3013
|
-
var
|
|
3241
|
+
var import_shared60, IdempotencyStore;
|
|
3014
3242
|
var init_idempotency_store = __esm({
|
|
3015
3243
|
"src/infrastructure/idempotency/idempotency-store.ts"() {
|
|
3016
3244
|
"use strict";
|
|
3017
|
-
|
|
3245
|
+
import_shared60 = require("@xeno-js/shared");
|
|
3018
3246
|
IdempotencyStore = class {
|
|
3019
3247
|
/**
|
|
3020
3248
|
* @description Constructs a new instance of IdempotencyStore, accepting an instance of ICache for accessing the caching system and an instance of IIdentityAccessor for obtaining the user's identity context. The IdempotencyStore uses the caching system to manage locks and results of idempotent commands, ensuring that commands with the same ID are processed only once. The identity context is used to build contextual keys, allowing for more granular management of idempotent commands in multi-tenant scenarios.
|
|
@@ -3036,31 +3264,31 @@ var init_idempotency_store = __esm({
|
|
|
3036
3264
|
async acquireLock(requestId, ttlSeconds) {
|
|
3037
3265
|
const key = this._cacheKeyBuilder.buildContextualKey(`command:${requestId}`);
|
|
3038
3266
|
return await this._cache.setIfAbsent(
|
|
3039
|
-
`${
|
|
3040
|
-
|
|
3267
|
+
`${import_shared60.IDEMPOTENCY_CONSTANTS.LOCK_KEY_PREFIX}${key}`,
|
|
3268
|
+
import_shared60.IDEMPOTENCY_CONSTANTS.LOCKED_VALUE,
|
|
3041
3269
|
ttlSeconds
|
|
3042
3270
|
);
|
|
3043
3271
|
}
|
|
3044
3272
|
async hasBeenProcessed(commandId) {
|
|
3045
3273
|
const key = this._cacheKeyBuilder.buildContextualKey(`command:${commandId}`);
|
|
3046
|
-
return await this._cache.has(`${
|
|
3274
|
+
return await this._cache.has(`${import_shared60.IDEMPOTENCY_CONSTANTS.PROCESSED_KEY_PREFIX}${key}`);
|
|
3047
3275
|
}
|
|
3048
3276
|
async markAsProcessed(commandId, payload, ttlSeconds) {
|
|
3049
3277
|
const key = this._cacheKeyBuilder.buildContextualKey(`command:${commandId}`);
|
|
3050
3278
|
await this._cache.set(
|
|
3051
|
-
`${
|
|
3279
|
+
`${import_shared60.IDEMPOTENCY_CONSTANTS.PROCESSED_KEY_PREFIX}${key}`,
|
|
3052
3280
|
payload,
|
|
3053
3281
|
ttlSeconds
|
|
3054
3282
|
);
|
|
3055
3283
|
}
|
|
3056
3284
|
async getPayload(commandId) {
|
|
3057
3285
|
const key = this._cacheKeyBuilder.buildContextualKey(`command:${commandId}`);
|
|
3058
|
-
const payload = await this._cache.get(`${
|
|
3286
|
+
const payload = await this._cache.get(`${import_shared60.IDEMPOTENCY_CONSTANTS.PROCESSED_KEY_PREFIX}${key}`);
|
|
3059
3287
|
return payload;
|
|
3060
3288
|
}
|
|
3061
3289
|
async releaseLock(commandId) {
|
|
3062
3290
|
const key = this._cacheKeyBuilder.buildContextualKey(`command:${commandId}`);
|
|
3063
|
-
await this._cache.remove(`${
|
|
3291
|
+
await this._cache.remove(`${import_shared60.IDEMPOTENCY_CONSTANTS.LOCK_KEY_PREFIX}${key}`);
|
|
3064
3292
|
}
|
|
3065
3293
|
};
|
|
3066
3294
|
}
|
|
@@ -3088,8 +3316,8 @@ var init_pipeline_utils = __esm({
|
|
|
3088
3316
|
*/
|
|
3089
3317
|
async addCommand(container, opts) {
|
|
3090
3318
|
const pipelines = [];
|
|
3091
|
-
const { Guards:
|
|
3092
|
-
if (
|
|
3319
|
+
const { Guards: Guards46, TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
3320
|
+
if (Guards46.isDefined(opts.idempotency)) {
|
|
3093
3321
|
const { IdempotencyStore: IdempotencyStore2 } = await Promise.resolve().then(() => (init_idempotency_store(), idempotency_store_exports));
|
|
3094
3322
|
container.addSingleton(
|
|
3095
3323
|
TOKENS4.IDEMPOTENCY_STORE,
|
|
@@ -3109,7 +3337,7 @@ var init_pipeline_utils = __esm({
|
|
|
3109
3337
|
});
|
|
3110
3338
|
pipelines.push(TOKENS4.IDEMPOTENCY_PIPELINE);
|
|
3111
3339
|
}
|
|
3112
|
-
if (
|
|
3340
|
+
if (Guards46.isDefined(opts.concurrency)) {
|
|
3113
3341
|
const { ConcurrencyRetryPipeline: ConcurrencyRetryPipeline2 } = await Promise.resolve().then(() => (init_application(), application_exports));
|
|
3114
3342
|
container.addSingleton(TOKENS4.CONCURRENCY_RETRY_PIPELINE, () => {
|
|
3115
3343
|
const config = opts.concurrency;
|
|
@@ -3189,13 +3417,13 @@ var init_cqrs_module = __esm({
|
|
|
3189
3417
|
return new PerformancePipeline2(logger, thresholdMs);
|
|
3190
3418
|
});
|
|
3191
3419
|
pipelines.push(TOKENS4.PERFORMANCE_PIPELINE);
|
|
3192
|
-
const { Guards:
|
|
3193
|
-
if (
|
|
3420
|
+
const { Guards: Guards46 } = await import("@xeno-js/shared");
|
|
3421
|
+
if (Guards46.isDefined(opts.authorization.policies) || Guards46.isDefined(opts.authorization.customAuthorizationStrategy)) {
|
|
3194
3422
|
const { AuthUtils: AuthUtils2 } = await Promise.resolve().then(() => (init_auth_utils(), auth_utils_exports));
|
|
3195
3423
|
const authPipelines = await AuthUtils2.addAuthZ(container, opts.authorization);
|
|
3196
3424
|
pipelines.push(...authPipelines);
|
|
3197
3425
|
}
|
|
3198
|
-
if (
|
|
3426
|
+
if (Guards46.isDefined(opts.validation.zod) || Guards46.isDefined(opts.validation.customValidationStrategy)) {
|
|
3199
3427
|
const { ValidationUtils: ValidationUtils2 } = await Promise.resolve().then(() => (init_validation_utils(), validation_utils_exports));
|
|
3200
3428
|
const logger = container.resolve(TOKENS4.LOGGER);
|
|
3201
3429
|
const validationPipelines = await ValidationUtils2.addValidation(
|
|
@@ -3207,11 +3435,11 @@ var init_cqrs_module = __esm({
|
|
|
3207
3435
|
}
|
|
3208
3436
|
const commandPipelines = pipelines;
|
|
3209
3437
|
const queryPipelines = pipelines;
|
|
3210
|
-
if ((
|
|
3438
|
+
if ((Guards46.isDefined(opts.commandBus.idempotency) || opts.queryBus.isEnabled) && opts.isCache) {
|
|
3211
3439
|
const { CacheUtils: CacheUtils2 } = await Promise.resolve().then(() => (init_cache_utils(), cache_utils_exports));
|
|
3212
3440
|
await CacheUtils2.addCache(container, { inMemory: true, redis: void 0 });
|
|
3213
3441
|
}
|
|
3214
|
-
if (
|
|
3442
|
+
if (Guards46.isDefined(opts.commandBus.idempotency) || Guards46.isDefined(opts.commandBus.concurrency)) {
|
|
3215
3443
|
const { PipelineUtils: PipelineUtils2 } = await Promise.resolve().then(() => (init_pipeline_utils(), pipeline_utils_exports));
|
|
3216
3444
|
const newCommandPipelines = await PipelineUtils2.addCommand(container, {
|
|
3217
3445
|
...opts.commandBus,
|
|
@@ -3244,11 +3472,11 @@ var init_cqrs_module = __esm({
|
|
|
3244
3472
|
});
|
|
3245
3473
|
|
|
3246
3474
|
// src/presentation/controllers/base.controller.ts
|
|
3247
|
-
var
|
|
3475
|
+
var import_shared61, BaseController;
|
|
3248
3476
|
var init_base_controller = __esm({
|
|
3249
3477
|
"src/presentation/controllers/base.controller.ts"() {
|
|
3250
3478
|
"use strict";
|
|
3251
|
-
|
|
3479
|
+
import_shared61 = require("@xeno-js/shared");
|
|
3252
3480
|
BaseController = class {
|
|
3253
3481
|
/**
|
|
3254
3482
|
* Constructs a new instance of the BaseController class.
|
|
@@ -3280,7 +3508,7 @@ var init_base_controller = __esm({
|
|
|
3280
3508
|
* @link https://github.com/xeno-js/xeno-js
|
|
3281
3509
|
*/
|
|
3282
3510
|
ok(data, status = 200, meta = {}, headers = {}) {
|
|
3283
|
-
return
|
|
3511
|
+
return import_shared61.HttpHelper.success(data, status, meta, headers);
|
|
3284
3512
|
}
|
|
3285
3513
|
/**
|
|
3286
3514
|
* Helper to automatically map a failed Result (from the CQRS pipeline)
|
|
@@ -3298,7 +3526,7 @@ var init_base_controller = __esm({
|
|
|
3298
3526
|
fail(error, details = void 0, headers = {}) {
|
|
3299
3527
|
const context = this._requestContext.getContext();
|
|
3300
3528
|
const customHeaders = error["header"];
|
|
3301
|
-
return
|
|
3529
|
+
return import_shared61.HttpHelper.error(
|
|
3302
3530
|
{
|
|
3303
3531
|
success: false,
|
|
3304
3532
|
error: {
|
|
@@ -3307,9 +3535,9 @@ var init_base_controller = __esm({
|
|
|
3307
3535
|
path: context?.network.path,
|
|
3308
3536
|
details: details ?? error.message
|
|
3309
3537
|
},
|
|
3310
|
-
correlationId: context?.tracing.correlationId ??
|
|
3311
|
-
requestId: context?.network.requestId ??
|
|
3312
|
-
spanId: context?.tracing.spanId ??
|
|
3538
|
+
correlationId: context?.tracing.correlationId ?? import_shared61.GuidHelper.generate(),
|
|
3539
|
+
requestId: context?.network.requestId ?? import_shared61.GuidHelper.generate(),
|
|
3540
|
+
spanId: context?.tracing.spanId ?? import_shared61.GuidHelper.generate(),
|
|
3313
3541
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3314
3542
|
},
|
|
3315
3543
|
error.status,
|
|
@@ -3364,11 +3592,11 @@ var init_controllers = __esm({
|
|
|
3364
3592
|
});
|
|
3365
3593
|
|
|
3366
3594
|
// src/presentation/middlewares/allow-method.middleware.ts
|
|
3367
|
-
var
|
|
3595
|
+
var import_shared62, MethodCheckMiddleware;
|
|
3368
3596
|
var init_allow_method_middleware = __esm({
|
|
3369
3597
|
"src/presentation/middlewares/allow-method.middleware.ts"() {
|
|
3370
3598
|
"use strict";
|
|
3371
|
-
|
|
3599
|
+
import_shared62 = require("@xeno-js/shared");
|
|
3372
3600
|
MethodCheckMiddleware = class {
|
|
3373
3601
|
constructor(_requestContext, _allowMethod) {
|
|
3374
3602
|
this._requestContext = _requestContext;
|
|
@@ -3380,21 +3608,21 @@ var init_allow_method_middleware = __esm({
|
|
|
3380
3608
|
const isAllowed = this._allowMethod.check(req.path, req.method);
|
|
3381
3609
|
if (!isAllowed) {
|
|
3382
3610
|
const { network, tracing } = this._requestContext.getContext() ?? {};
|
|
3383
|
-
return
|
|
3611
|
+
return import_shared62.HttpHelper.error(
|
|
3384
3612
|
{
|
|
3385
3613
|
success: false,
|
|
3386
3614
|
error: {
|
|
3387
|
-
code:
|
|
3388
|
-
message:
|
|
3615
|
+
code: import_shared62.ERROR_CODES.NOT_ALLOWED,
|
|
3616
|
+
message: import_shared62.ERROR_CODE_MESSAGES[import_shared62.ERROR_CODES.NOT_ALLOWED],
|
|
3389
3617
|
details: `Operation blocked by allow method middleware`,
|
|
3390
3618
|
path: req.path
|
|
3391
3619
|
},
|
|
3392
|
-
correlationId: tracing?.correlationId ??
|
|
3393
|
-
requestId: network?.requestId ??
|
|
3394
|
-
spanId: tracing?.spanId ??
|
|
3620
|
+
correlationId: tracing?.correlationId ?? import_shared62.GuidHelper.generate(),
|
|
3621
|
+
requestId: network?.requestId ?? import_shared62.GuidHelper.generate(),
|
|
3622
|
+
spanId: tracing?.spanId ?? import_shared62.GuidHelper.generate(),
|
|
3395
3623
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3396
3624
|
},
|
|
3397
|
-
|
|
3625
|
+
import_shared62.STATUS_CODES.NOT_ALLOWED
|
|
3398
3626
|
);
|
|
3399
3627
|
}
|
|
3400
3628
|
return await next();
|
|
@@ -3404,11 +3632,11 @@ var init_allow_method_middleware = __esm({
|
|
|
3404
3632
|
});
|
|
3405
3633
|
|
|
3406
3634
|
// src/presentation/middlewares/allow-origin.middleware.ts
|
|
3407
|
-
var
|
|
3635
|
+
var import_shared63, AllowOriginMiddleware;
|
|
3408
3636
|
var init_allow_origin_middleware = __esm({
|
|
3409
3637
|
"src/presentation/middlewares/allow-origin.middleware.ts"() {
|
|
3410
3638
|
"use strict";
|
|
3411
|
-
|
|
3639
|
+
import_shared63 = require("@xeno-js/shared");
|
|
3412
3640
|
AllowOriginMiddleware = class {
|
|
3413
3641
|
constructor(_allowOrigin, _requestContext, _logger) {
|
|
3414
3642
|
this._allowOrigin = _allowOrigin;
|
|
@@ -3423,21 +3651,21 @@ var init_allow_origin_middleware = __esm({
|
|
|
3423
3651
|
const origin = network?.origin;
|
|
3424
3652
|
if (!this._allowOrigin.isAllowed(origin)) {
|
|
3425
3653
|
this._logger.warn(`Access denied by AllowOrigin policy for origin: ${origin ?? "unknown"}`);
|
|
3426
|
-
return
|
|
3654
|
+
return import_shared63.HttpHelper.error(
|
|
3427
3655
|
{
|
|
3428
3656
|
success: false,
|
|
3429
3657
|
error: {
|
|
3430
|
-
code:
|
|
3431
|
-
message:
|
|
3658
|
+
code: import_shared63.ERROR_CODES.FORBIDDEN,
|
|
3659
|
+
message: import_shared63.ERROR_CODE_MESSAGES[import_shared63.ERROR_CODES.FORBIDDEN],
|
|
3432
3660
|
details: `The origin '${origin ?? "unknown"}' is not allowed to access this resource.`,
|
|
3433
3661
|
path: req.path
|
|
3434
3662
|
},
|
|
3435
|
-
correlationId: tracing?.correlationId ??
|
|
3436
|
-
requestId: network?.requestId ??
|
|
3437
|
-
spanId: tracing?.spanId ??
|
|
3663
|
+
correlationId: tracing?.correlationId ?? import_shared63.GuidHelper.generate(),
|
|
3664
|
+
requestId: network?.requestId ?? import_shared63.GuidHelper.generate(),
|
|
3665
|
+
spanId: tracing?.spanId ?? import_shared63.GuidHelper.generate(),
|
|
3438
3666
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3439
3667
|
},
|
|
3440
|
-
|
|
3668
|
+
import_shared63.STATUS_CODES.FORBIDDEN
|
|
3441
3669
|
);
|
|
3442
3670
|
}
|
|
3443
3671
|
return next();
|
|
@@ -3447,11 +3675,11 @@ var init_allow_origin_middleware = __esm({
|
|
|
3447
3675
|
});
|
|
3448
3676
|
|
|
3449
3677
|
// src/presentation/middlewares/auth.middleware.ts
|
|
3450
|
-
var
|
|
3678
|
+
var import_shared64, AuthenticationMiddleware;
|
|
3451
3679
|
var init_auth_middleware = __esm({
|
|
3452
3680
|
"src/presentation/middlewares/auth.middleware.ts"() {
|
|
3453
3681
|
"use strict";
|
|
3454
|
-
|
|
3682
|
+
import_shared64 = require("@xeno-js/shared");
|
|
3455
3683
|
AuthenticationMiddleware = class {
|
|
3456
3684
|
constructor(_requestContext, _tokenExtractor, _gateKeeper, _logger) {
|
|
3457
3685
|
this._requestContext = _requestContext;
|
|
@@ -3472,7 +3700,7 @@ var init_auth_middleware = __esm({
|
|
|
3472
3700
|
`Authentication failed for request on path: ${req.path}. Code: ${error.code}. Error: ${error}`
|
|
3473
3701
|
);
|
|
3474
3702
|
const { network, tracing } = this._requestContext.getContext() ?? {};
|
|
3475
|
-
return
|
|
3703
|
+
return import_shared64.HttpHelper.error(
|
|
3476
3704
|
{
|
|
3477
3705
|
success: false,
|
|
3478
3706
|
error: {
|
|
@@ -3481,12 +3709,12 @@ var init_auth_middleware = __esm({
|
|
|
3481
3709
|
details: `[Authentication Error] Failed to authenticate request on path: ${req.path}`,
|
|
3482
3710
|
path: req.path
|
|
3483
3711
|
},
|
|
3484
|
-
correlationId: tracing?.correlationId ??
|
|
3485
|
-
requestId: network?.requestId ??
|
|
3486
|
-
spanId: tracing?.spanId ??
|
|
3712
|
+
correlationId: tracing?.correlationId ?? import_shared64.GuidHelper.generate(),
|
|
3713
|
+
requestId: network?.requestId ?? import_shared64.GuidHelper.generate(),
|
|
3714
|
+
spanId: tracing?.spanId ?? import_shared64.GuidHelper.generate(),
|
|
3487
3715
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3488
3716
|
},
|
|
3489
|
-
error.status ??
|
|
3717
|
+
error.status ?? import_shared64.STATUS_CODES.UNAUTHORIZED,
|
|
3490
3718
|
{ "Content-Type": [network?.formatIndicator ?? "application/json"] }
|
|
3491
3719
|
);
|
|
3492
3720
|
}
|
|
@@ -3521,11 +3749,11 @@ var init_composite_middleware = __esm({
|
|
|
3521
3749
|
});
|
|
3522
3750
|
|
|
3523
3751
|
// src/presentation/middlewares/cors.middleware.ts
|
|
3524
|
-
var
|
|
3752
|
+
var import_shared65, CORSMiddleware;
|
|
3525
3753
|
var init_cors_middleware = __esm({
|
|
3526
3754
|
"src/presentation/middlewares/cors.middleware.ts"() {
|
|
3527
3755
|
"use strict";
|
|
3528
|
-
|
|
3756
|
+
import_shared65 = require("@xeno-js/shared");
|
|
3529
3757
|
CORSMiddleware = class {
|
|
3530
3758
|
constructor(_requestContext) {
|
|
3531
3759
|
this._requestContext = _requestContext;
|
|
@@ -3535,7 +3763,7 @@ var init_cors_middleware = __esm({
|
|
|
3535
3763
|
const { network } = this._requestContext.getContext() ?? {};
|
|
3536
3764
|
const origin = network?.origin;
|
|
3537
3765
|
const response = await next();
|
|
3538
|
-
if (
|
|
3766
|
+
if (import_shared65.Guards.isDefined(origin))
|
|
3539
3767
|
response.headers = {
|
|
3540
3768
|
...response.headers ?? {},
|
|
3541
3769
|
"Access-Control-Allow-Origin": origin,
|
|
@@ -3549,44 +3777,83 @@ var init_cors_middleware = __esm({
|
|
|
3549
3777
|
});
|
|
3550
3778
|
|
|
3551
3779
|
// src/presentation/middlewares/csrf.middleware.ts
|
|
3552
|
-
var
|
|
3780
|
+
var import_shared66, CsrfMiddleware;
|
|
3553
3781
|
var init_csrf_middleware = __esm({
|
|
3554
3782
|
"src/presentation/middlewares/csrf.middleware.ts"() {
|
|
3555
3783
|
"use strict";
|
|
3556
|
-
|
|
3784
|
+
import_shared66 = require("@xeno-js/shared");
|
|
3557
3785
|
CsrfMiddleware = class {
|
|
3558
|
-
constructor(_requestContext,
|
|
3786
|
+
constructor(_requestContext, _csrfTokenService) {
|
|
3559
3787
|
this._requestContext = _requestContext;
|
|
3560
|
-
this.
|
|
3788
|
+
this._csrfTokenService = _csrfTokenService;
|
|
3561
3789
|
}
|
|
3562
3790
|
_requestContext;
|
|
3563
|
-
|
|
3564
|
-
/**
|
|
3565
|
-
* @param requestContext Dati base della richiesta (metodo, path)
|
|
3566
|
-
* @param headers Header HTTP della richiesta
|
|
3567
|
-
* @param next Funzione delegata per passare al middleware successivo
|
|
3568
|
-
*/
|
|
3791
|
+
_csrfTokenService;
|
|
3569
3792
|
async execute(req, _headers, next) {
|
|
3570
3793
|
const method = req.method.toUpperCase();
|
|
3571
3794
|
const isStateChanging = ["POST", "PUT", "DELETE", "PATCH"].includes(method);
|
|
3572
3795
|
if (isStateChanging) {
|
|
3573
|
-
const { network, tracing } = this._requestContext.getContext() ?? {};
|
|
3574
|
-
|
|
3575
|
-
|
|
3796
|
+
const { network, tracing, identity } = this._requestContext.getContext() ?? {};
|
|
3797
|
+
const headerToken = network?.csrf;
|
|
3798
|
+
const cookieToken = network?.csrfCookie;
|
|
3799
|
+
if (!import_shared66.Guards.isDefined(headerToken) || !import_shared66.Guards.isDefined(cookieToken)) {
|
|
3800
|
+
return import_shared66.HttpHelper.error(
|
|
3801
|
+
{
|
|
3802
|
+
success: false,
|
|
3803
|
+
error: {
|
|
3804
|
+
code: import_shared66.ERROR_CODES.FORBIDDEN,
|
|
3805
|
+
message: import_shared66.ERROR_CODE_MESSAGES[import_shared66.ERROR_CODES.FORBIDDEN],
|
|
3806
|
+
details: "CSRF token missing",
|
|
3807
|
+
path: req.path
|
|
3808
|
+
},
|
|
3809
|
+
correlationId: tracing?.correlationId ?? import_shared66.GuidHelper.generate(),
|
|
3810
|
+
requestId: network?.requestId ?? import_shared66.GuidHelper.generate(),
|
|
3811
|
+
spanId: tracing?.spanId ?? import_shared66.GuidHelper.generate(),
|
|
3812
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3813
|
+
},
|
|
3814
|
+
import_shared66.STATUS_CODES.FORBIDDEN,
|
|
3815
|
+
{
|
|
3816
|
+
"Content-Type": [network?.formatIndicator ?? "application/json"]
|
|
3817
|
+
}
|
|
3818
|
+
);
|
|
3819
|
+
}
|
|
3820
|
+
if (headerToken !== cookieToken) {
|
|
3821
|
+
return import_shared66.HttpHelper.error(
|
|
3576
3822
|
{
|
|
3577
3823
|
success: false,
|
|
3578
3824
|
error: {
|
|
3579
|
-
code:
|
|
3580
|
-
message:
|
|
3581
|
-
details: "CSRF
|
|
3825
|
+
code: import_shared66.ERROR_CODES.FORBIDDEN,
|
|
3826
|
+
message: import_shared66.ERROR_CODE_MESSAGES[import_shared66.ERROR_CODES.FORBIDDEN],
|
|
3827
|
+
details: "CSRF token mismatch",
|
|
3582
3828
|
path: req.path
|
|
3583
3829
|
},
|
|
3584
|
-
correlationId: tracing?.correlationId ??
|
|
3585
|
-
requestId: network?.requestId ??
|
|
3586
|
-
spanId: tracing?.spanId ??
|
|
3830
|
+
correlationId: tracing?.correlationId ?? import_shared66.GuidHelper.generate(),
|
|
3831
|
+
requestId: network?.requestId ?? import_shared66.GuidHelper.generate(),
|
|
3832
|
+
spanId: tracing?.spanId ?? import_shared66.GuidHelper.generate(),
|
|
3587
3833
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3588
3834
|
},
|
|
3589
|
-
|
|
3835
|
+
import_shared66.STATUS_CODES.FORBIDDEN,
|
|
3836
|
+
{
|
|
3837
|
+
"Content-Type": [network?.formatIndicator ?? "application/json"]
|
|
3838
|
+
}
|
|
3839
|
+
);
|
|
3840
|
+
}
|
|
3841
|
+
if (!import_shared66.Guards.isDefined(identity?.userId) || !await this._csrfTokenService.validate(headerToken, identity?.userId)) {
|
|
3842
|
+
return import_shared66.HttpHelper.error(
|
|
3843
|
+
{
|
|
3844
|
+
success: false,
|
|
3845
|
+
error: {
|
|
3846
|
+
code: import_shared66.ERROR_CODES.FORBIDDEN,
|
|
3847
|
+
message: import_shared66.ERROR_CODE_MESSAGES[import_shared66.ERROR_CODES.FORBIDDEN],
|
|
3848
|
+
details: "CSRF token invalid",
|
|
3849
|
+
path: req.path
|
|
3850
|
+
},
|
|
3851
|
+
correlationId: tracing?.correlationId ?? import_shared66.GuidHelper.generate(),
|
|
3852
|
+
requestId: network?.requestId ?? import_shared66.GuidHelper.generate(),
|
|
3853
|
+
spanId: tracing?.spanId ?? import_shared66.GuidHelper.generate(),
|
|
3854
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3855
|
+
},
|
|
3856
|
+
import_shared66.STATUS_CODES.FORBIDDEN,
|
|
3590
3857
|
{
|
|
3591
3858
|
"Content-Type": [network?.formatIndicator ?? "application/json"]
|
|
3592
3859
|
}
|
|
@@ -3599,12 +3866,50 @@ var init_csrf_middleware = __esm({
|
|
|
3599
3866
|
}
|
|
3600
3867
|
});
|
|
3601
3868
|
|
|
3869
|
+
// src/presentation/middlewares/csrf-cookie.middleware.ts
|
|
3870
|
+
var import_shared67, CsrfCookieMiddleware;
|
|
3871
|
+
var init_csrf_cookie_middleware = __esm({
|
|
3872
|
+
"src/presentation/middlewares/csrf-cookie.middleware.ts"() {
|
|
3873
|
+
"use strict";
|
|
3874
|
+
import_shared67 = require("@xeno-js/shared");
|
|
3875
|
+
CsrfCookieMiddleware = class {
|
|
3876
|
+
constructor(_requestContext, _csrfTokenService, _csrf) {
|
|
3877
|
+
this._requestContext = _requestContext;
|
|
3878
|
+
this._csrfTokenService = _csrfTokenService;
|
|
3879
|
+
this._csrf = _csrf;
|
|
3880
|
+
}
|
|
3881
|
+
_requestContext;
|
|
3882
|
+
_csrfTokenService;
|
|
3883
|
+
_csrf;
|
|
3884
|
+
async execute(_req, _headers, next) {
|
|
3885
|
+
const response = await next();
|
|
3886
|
+
const context = this._requestContext.getContext();
|
|
3887
|
+
const identity = context?.identity;
|
|
3888
|
+
const network = context?.network;
|
|
3889
|
+
if (!import_shared67.Guards.isDefined(identity?.userId)) return response;
|
|
3890
|
+
if (import_shared67.Guards.isDefined(network?.csrfCookie)) return response;
|
|
3891
|
+
const token = await this._csrfTokenService.generate(identity.userId);
|
|
3892
|
+
const cookieName = this._csrf.cookieName ?? "__Host-xeno-csrf";
|
|
3893
|
+
const maxAge = this._csrf.cookieMaxAgeSeconds ?? 3600;
|
|
3894
|
+
const sameSite = this._csrf.sameSite ?? "lax";
|
|
3895
|
+
const cookie = `${cookieName}=${encodeURIComponent(token)}; Path=/; Secure; SameSite=${sameSite}; Max-Age=${maxAge}`;
|
|
3896
|
+
const existingCookies = response.headers["Set-Cookie"];
|
|
3897
|
+
response.headers = {
|
|
3898
|
+
...response.headers ?? {},
|
|
3899
|
+
"Set-Cookie": [...existingCookies ?? [], cookie]
|
|
3900
|
+
};
|
|
3901
|
+
return response;
|
|
3902
|
+
}
|
|
3903
|
+
};
|
|
3904
|
+
}
|
|
3905
|
+
});
|
|
3906
|
+
|
|
3602
3907
|
// src/presentation/middlewares/options.middleware.ts
|
|
3603
|
-
var
|
|
3908
|
+
var import_shared68, OptionsMiddleware;
|
|
3604
3909
|
var init_options_middleware = __esm({
|
|
3605
3910
|
"src/presentation/middlewares/options.middleware.ts"() {
|
|
3606
3911
|
"use strict";
|
|
3607
|
-
|
|
3912
|
+
import_shared68 = require("@xeno-js/shared");
|
|
3608
3913
|
OptionsMiddleware = class {
|
|
3609
3914
|
constructor(_requestContext) {
|
|
3610
3915
|
this._requestContext = _requestContext;
|
|
@@ -3615,14 +3920,14 @@ var init_options_middleware = __esm({
|
|
|
3615
3920
|
const network = this._requestContext.getNetworkContext();
|
|
3616
3921
|
const origin = network?.origin;
|
|
3617
3922
|
const headers = {};
|
|
3618
|
-
if (
|
|
3923
|
+
if (import_shared68.Guards.isDefined(origin)) {
|
|
3619
3924
|
headers["Access-Control-Allow-Origin"] = origin;
|
|
3620
3925
|
headers["Access-Control-Allow-Credentials"] = "true";
|
|
3621
3926
|
headers["Vary"] = "Origin";
|
|
3622
3927
|
}
|
|
3623
|
-
headers["Access-Control-Allow-Methods"] = "POST,GET,PUT,DELETE,OPTIONS";
|
|
3624
|
-
headers["Access-Control-Allow-Headers"] = "X-CSRF-Token,
|
|
3625
|
-
return
|
|
3928
|
+
headers["Access-Control-Allow-Methods"] = "POST,GET,PUT,PATCH,DELETE,OPTIONS";
|
|
3929
|
+
headers["Access-Control-Allow-Headers"] = "X-CSRF-Token, Accept, Accept-Version, Content-Type, Authorization, X-Correlation-Id";
|
|
3930
|
+
return import_shared68.HttpHelper.success(null, import_shared68.STATUS_CODES.NO_CONTENT, {}, headers);
|
|
3626
3931
|
}
|
|
3627
3932
|
return await next();
|
|
3628
3933
|
}
|
|
@@ -3631,11 +3936,11 @@ var init_options_middleware = __esm({
|
|
|
3631
3936
|
});
|
|
3632
3937
|
|
|
3633
3938
|
// src/presentation/middlewares/rate-limiter.middleware.ts
|
|
3634
|
-
var
|
|
3939
|
+
var import_shared69, RateLimitMiddleware;
|
|
3635
3940
|
var init_rate_limiter_middleware = __esm({
|
|
3636
3941
|
"src/presentation/middlewares/rate-limiter.middleware.ts"() {
|
|
3637
3942
|
"use strict";
|
|
3638
|
-
|
|
3943
|
+
import_shared69 = require("@xeno-js/shared");
|
|
3639
3944
|
RateLimitMiddleware = class {
|
|
3640
3945
|
constructor(_ctxAccessor, _cache, _logger, _opts) {
|
|
3641
3946
|
this._ctxAccessor = _ctxAccessor;
|
|
@@ -3647,35 +3952,55 @@ var init_rate_limiter_middleware = __esm({
|
|
|
3647
3952
|
_cache;
|
|
3648
3953
|
_logger;
|
|
3649
3954
|
_opts;
|
|
3650
|
-
async execute(req,
|
|
3955
|
+
async execute(req, _headers, next) {
|
|
3651
3956
|
const { network, tracing } = this._ctxAccessor.getContext() ?? {};
|
|
3957
|
+
if (!import_shared69.Guards.isDefined(network?.clientIp))
|
|
3958
|
+
return import_shared69.HttpHelper.error(
|
|
3959
|
+
{
|
|
3960
|
+
success: false,
|
|
3961
|
+
error: {
|
|
3962
|
+
code: import_shared69.ERROR_CODES.SYSTEM_ERROR,
|
|
3963
|
+
message: "IP undefined. Please contact the administrator.",
|
|
3964
|
+
details: `IP undefined. Please contact the administrator.`,
|
|
3965
|
+
path: req.path
|
|
3966
|
+
},
|
|
3967
|
+
correlationId: tracing?.correlationId ?? import_shared69.GuidHelper.generate(),
|
|
3968
|
+
requestId: network?.requestId ?? import_shared69.GuidHelper.generate(),
|
|
3969
|
+
spanId: tracing?.spanId ?? import_shared69.GuidHelper.generate(),
|
|
3970
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3971
|
+
},
|
|
3972
|
+
import_shared69.STATUS_CODES.SERVICE_UNAVAILABLE,
|
|
3973
|
+
{
|
|
3974
|
+
"Content-Type": [network?.formatIndicator ?? "application/json"],
|
|
3975
|
+
"Retry-After": [String(this._opts.windowSeconds)]
|
|
3976
|
+
}
|
|
3977
|
+
);
|
|
3652
3978
|
const clientIp = network?.clientIp;
|
|
3653
3979
|
const cacheKey = `rate_limit:${clientIp}`;
|
|
3654
|
-
const currentHits = await this._cache.
|
|
3655
|
-
if (currentHits
|
|
3980
|
+
const currentHits = await this._cache.increment(cacheKey, this._opts.windowSeconds);
|
|
3981
|
+
if (currentHits > this._opts.maxRequests) {
|
|
3656
3982
|
this._logger.warn(`[RateLimit] IP ${clientIp} blocked on ${req.path}`);
|
|
3657
|
-
return
|
|
3983
|
+
return import_shared69.HttpHelper.error(
|
|
3658
3984
|
{
|
|
3659
3985
|
success: false,
|
|
3660
3986
|
error: {
|
|
3661
|
-
code:
|
|
3987
|
+
code: import_shared69.ERROR_CODES.TOO_MANY_REQUESTS,
|
|
3662
3988
|
message: "Rate limit exceeded.",
|
|
3663
3989
|
details: `IP ${clientIp} throttled.`,
|
|
3664
3990
|
path: req.path
|
|
3665
3991
|
},
|
|
3666
|
-
correlationId: tracing?.correlationId ??
|
|
3667
|
-
requestId: network?.requestId ??
|
|
3668
|
-
spanId: tracing?.spanId ??
|
|
3992
|
+
correlationId: tracing?.correlationId ?? import_shared69.GuidHelper.generate(),
|
|
3993
|
+
requestId: network?.requestId ?? import_shared69.GuidHelper.generate(),
|
|
3994
|
+
spanId: tracing?.spanId ?? import_shared69.GuidHelper.generate(),
|
|
3669
3995
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3670
3996
|
},
|
|
3671
|
-
|
|
3997
|
+
import_shared69.STATUS_CODES.TOO_MANY_REQUESTS,
|
|
3672
3998
|
{
|
|
3673
3999
|
"Content-Type": [network?.formatIndicator ?? "application/json"],
|
|
3674
4000
|
"Retry-After": [String(this._opts.windowSeconds)]
|
|
3675
4001
|
}
|
|
3676
4002
|
);
|
|
3677
4003
|
}
|
|
3678
|
-
await this._cache.set(cacheKey, currentHits + 1, this._opts.windowSeconds);
|
|
3679
4004
|
return next();
|
|
3680
4005
|
}
|
|
3681
4006
|
};
|
|
@@ -3684,8 +4009,8 @@ var init_rate_limiter_middleware = __esm({
|
|
|
3684
4009
|
|
|
3685
4010
|
// src/presentation/mappers/context.mapper.ts
|
|
3686
4011
|
function _buildMessagingContext(meta) {
|
|
3687
|
-
const hasSequenceData =
|
|
3688
|
-
const hasMessagingData = hasSequenceData ||
|
|
4012
|
+
const hasSequenceData = import_shared70.Guards.isDefined(meta.sequence?.sequenceId) || import_shared70.Guards.isDefined(meta.sequence?.position) || import_shared70.Guards.isDefined(meta.sequence?.size);
|
|
4013
|
+
const hasMessagingData = hasSequenceData || import_shared70.Guards.isDefined(meta.expiration) || import_shared70.Guards.isDefined(meta.returnAddress);
|
|
3689
4014
|
const messaging = hasMessagingData ? {
|
|
3690
4015
|
returnAddress: meta.returnAddress,
|
|
3691
4016
|
expiration: meta.expiration,
|
|
@@ -3693,11 +4018,11 @@ function _buildMessagingContext(meta) {
|
|
|
3693
4018
|
} : void 0;
|
|
3694
4019
|
return messaging;
|
|
3695
4020
|
}
|
|
3696
|
-
var
|
|
4021
|
+
var import_shared70, ContextMapper;
|
|
3697
4022
|
var init_context_mapper = __esm({
|
|
3698
4023
|
"src/presentation/mappers/context.mapper.ts"() {
|
|
3699
4024
|
"use strict";
|
|
3700
|
-
|
|
4025
|
+
import_shared70 = require("@xeno-js/shared");
|
|
3701
4026
|
ContextMapper = Object.freeze({
|
|
3702
4027
|
/**
|
|
3703
4028
|
* @description Maps to RequestContext. It extracts relevant information from the object, such as correlation ID, request ID, authentication token, client IP, user agent, format indicator, and messaging context (if available). The method constructs a RequestContext object that encapsulates all this information, providing a structured representation of the request context for further processing in the application.
|
|
@@ -3717,6 +4042,7 @@ var init_context_mapper = __esm({
|
|
|
3717
4042
|
path,
|
|
3718
4043
|
transport,
|
|
3719
4044
|
csrf: metadata.csrf,
|
|
4045
|
+
csrfCookie: metadata.csrfCookie,
|
|
3720
4046
|
origin: metadata.origin
|
|
3721
4047
|
};
|
|
3722
4048
|
const tracing = {
|
|
@@ -3740,11 +4066,11 @@ var init_context_mapper = __esm({
|
|
|
3740
4066
|
});
|
|
3741
4067
|
|
|
3742
4068
|
// src/presentation/middlewares/request.middleware.ts
|
|
3743
|
-
var
|
|
4069
|
+
var import_shared71, RequestContextMiddleware;
|
|
3744
4070
|
var init_request_middleware = __esm({
|
|
3745
4071
|
"src/presentation/middlewares/request.middleware.ts"() {
|
|
3746
4072
|
"use strict";
|
|
3747
|
-
|
|
4073
|
+
import_shared71 = require("@xeno-js/shared");
|
|
3748
4074
|
init_context_mapper();
|
|
3749
4075
|
RequestContextMiddleware = class {
|
|
3750
4076
|
/**
|
|
@@ -3758,23 +4084,27 @@ var init_request_middleware = __esm({
|
|
|
3758
4084
|
* @since 2025-09-30
|
|
3759
4085
|
* @link https://github.com/xeno-js/xeno-js
|
|
3760
4086
|
*/
|
|
3761
|
-
constructor(_requestContext, _extractor, _logger) {
|
|
4087
|
+
constructor(_requestContext, _extractor, _resolver, _logger) {
|
|
3762
4088
|
this._requestContext = _requestContext;
|
|
3763
4089
|
this._extractor = _extractor;
|
|
4090
|
+
this._resolver = _resolver;
|
|
3764
4091
|
this._logger = _logger;
|
|
3765
4092
|
}
|
|
3766
4093
|
_requestContext;
|
|
3767
4094
|
_extractor;
|
|
4095
|
+
_resolver;
|
|
3768
4096
|
_logger;
|
|
3769
4097
|
async execute(req, headers, next) {
|
|
3770
|
-
const correlationId =
|
|
3771
|
-
const requestId =
|
|
4098
|
+
const correlationId = import_shared71.GuidHelper.generate();
|
|
4099
|
+
const requestId = import_shared71.GuidHelper.generate();
|
|
3772
4100
|
const spanId = correlationId;
|
|
3773
4101
|
const formatIndicator = "application/json";
|
|
3774
4102
|
try {
|
|
3775
4103
|
const meta = this._extractor.extract(headers);
|
|
4104
|
+
const clientIp = this._resolver.resolve(req.transport.req, meta.clientIp);
|
|
3776
4105
|
const metadata = {
|
|
3777
4106
|
...meta,
|
|
4107
|
+
clientIp,
|
|
3778
4108
|
correlationId: meta.correlationId ?? correlationId,
|
|
3779
4109
|
requestId: meta.requestId ?? requestId,
|
|
3780
4110
|
spanId: meta.spanId ?? spanId,
|
|
@@ -3782,7 +4112,7 @@ var init_request_middleware = __esm({
|
|
|
3782
4112
|
};
|
|
3783
4113
|
const tmpContext = ContextMapper.map({
|
|
3784
4114
|
metadata,
|
|
3785
|
-
identity:
|
|
4115
|
+
identity: import_shared71.GUEST,
|
|
3786
4116
|
path: req.path,
|
|
3787
4117
|
transport: req.transport
|
|
3788
4118
|
});
|
|
@@ -3794,12 +4124,12 @@ var init_request_middleware = __esm({
|
|
|
3794
4124
|
return result;
|
|
3795
4125
|
} catch (error) {
|
|
3796
4126
|
this._logger.error("RequestContextMiddleware encountered an error", error);
|
|
3797
|
-
return
|
|
4127
|
+
return import_shared71.HttpHelper.error(
|
|
3798
4128
|
{
|
|
3799
4129
|
success: false,
|
|
3800
4130
|
error: {
|
|
3801
|
-
code:
|
|
3802
|
-
message:
|
|
4131
|
+
code: import_shared71.ERROR_CODES.SYSTEM_ERROR,
|
|
4132
|
+
message: import_shared71.ERROR_CODE_MESSAGES[import_shared71.ERROR_CODES.SYSTEM_ERROR],
|
|
3803
4133
|
details: `[Fatal System Error] Exception caught during request handling on path: ${req.path}`,
|
|
3804
4134
|
path: req.path
|
|
3805
4135
|
},
|
|
@@ -3808,7 +4138,7 @@ var init_request_middleware = __esm({
|
|
|
3808
4138
|
spanId,
|
|
3809
4139
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
3810
4140
|
},
|
|
3811
|
-
|
|
4141
|
+
import_shared71.STATUS_CODES.INTERNAL_SERVER_ERROR,
|
|
3812
4142
|
{ "Content-Type": [formatIndicator] }
|
|
3813
4143
|
);
|
|
3814
4144
|
}
|
|
@@ -3827,6 +4157,7 @@ var init_middlewares = __esm({
|
|
|
3827
4157
|
init_composite_middleware();
|
|
3828
4158
|
init_cors_middleware();
|
|
3829
4159
|
init_csrf_middleware();
|
|
4160
|
+
init_csrf_cookie_middleware();
|
|
3830
4161
|
init_options_middleware();
|
|
3831
4162
|
init_rate_limiter_middleware();
|
|
3832
4163
|
init_request_middleware();
|
|
@@ -3841,6 +4172,7 @@ __export(presentation_exports, {
|
|
|
3841
4172
|
BaseController: () => BaseController,
|
|
3842
4173
|
CORSMiddleware: () => CORSMiddleware,
|
|
3843
4174
|
CompositeMiddleware: () => CompositeMiddleware,
|
|
4175
|
+
CsrfCookieMiddleware: () => CsrfCookieMiddleware,
|
|
3844
4176
|
CsrfMiddleware: () => CsrfMiddleware,
|
|
3845
4177
|
MethodCheckMiddleware: () => MethodCheckMiddleware,
|
|
3846
4178
|
OptionsMiddleware: () => OptionsMiddleware,
|
|
@@ -3860,11 +4192,11 @@ var middleware_module_exports = {};
|
|
|
3860
4192
|
__export(middleware_module_exports, {
|
|
3861
4193
|
MiddlewareModule: () => MiddlewareModule
|
|
3862
4194
|
});
|
|
3863
|
-
var
|
|
4195
|
+
var import_shared72, MiddlewareModule;
|
|
3864
4196
|
var init_middleware_module = __esm({
|
|
3865
4197
|
"src/infrastructure/modules/middleware.module.ts"() {
|
|
3866
4198
|
"use strict";
|
|
3867
|
-
|
|
4199
|
+
import_shared72 = require("@xeno-js/shared");
|
|
3868
4200
|
MiddlewareModule = class {
|
|
3869
4201
|
async configure(container, opts) {
|
|
3870
4202
|
const { TOKENS: TOKENS4 } = await import("@xeno-js/shared");
|
|
@@ -3879,15 +4211,24 @@ var init_middleware_module = __esm({
|
|
|
3879
4211
|
const { BearerTokenExtractor: BearerTokenExtractor2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
3880
4212
|
container.addSingleton(TOKENS4.BEARER_TOKEN_EXTRACTOR, () => new BearerTokenExtractor2());
|
|
3881
4213
|
}
|
|
4214
|
+
const { HttpCookieExtractor: HttpCookieExtractor2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
4215
|
+
container.addSingleton("COOKIE_EXTRACTOR", () => new HttpCookieExtractor2());
|
|
3882
4216
|
const { HttpHeaderExtractor: HttpHeaderExtractor2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
3883
4217
|
container.addSingleton(
|
|
3884
4218
|
TOKENS4.SERVICE_EXTRACTOR,
|
|
3885
|
-
(c) => new HttpHeaderExtractor2(
|
|
4219
|
+
(c) => new HttpHeaderExtractor2(
|
|
4220
|
+
c.resolve(TOKENS4.BEARER_TOKEN_EXTRACTOR),
|
|
4221
|
+
c.resolve("COOKIE_EXTRACTOR"),
|
|
4222
|
+
opts.trustedIpHeader,
|
|
4223
|
+
opts.csrf?.cookieName ?? "__Host-xeno-csrf"
|
|
4224
|
+
)
|
|
3886
4225
|
);
|
|
3887
4226
|
if (!opts.isLogger) {
|
|
3888
4227
|
const { LoggerUtils: LoggerUtils2 } = await Promise.resolve().then(() => (init_logger_utils(), logger_utils_exports));
|
|
3889
4228
|
await LoggerUtils2.addLogger(container, void 0);
|
|
3890
4229
|
}
|
|
4230
|
+
const { ClientIpResolver: ClientIpResolver2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
4231
|
+
container.addSingleton("IP_RESOLVER", () => new ClientIpResolver2(opts.trustedProxies));
|
|
3891
4232
|
const middlewares = [TOKENS4.REQUEST_CONTEXT_MIDDLEWARE];
|
|
3892
4233
|
const { RequestContextMiddleware: RequestContextMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
3893
4234
|
container.addSingleton(
|
|
@@ -3895,18 +4236,14 @@ var init_middleware_module = __esm({
|
|
|
3895
4236
|
(c) => new RequestContextMiddleware2(
|
|
3896
4237
|
c.resolve(TOKENS4.REQUEST_CONTEXT),
|
|
3897
4238
|
c.resolve(TOKENS4.SERVICE_EXTRACTOR),
|
|
4239
|
+
c.resolve("IP_RESOLVER"),
|
|
3898
4240
|
c.resolve(TOKENS4.LOGGER)
|
|
3899
4241
|
)
|
|
3900
4242
|
);
|
|
3901
|
-
if (opts.
|
|
3902
|
-
const
|
|
3903
|
-
|
|
3904
|
-
|
|
3905
|
-
(c) => new OptionsMiddleware2(c.resolve(TOKENS4.NETWORK_CONTEXT_ACCESSOR))
|
|
3906
|
-
);
|
|
3907
|
-
middlewares.push(TOKENS4.OPTIONS_MIDDLEWARE);
|
|
3908
|
-
}
|
|
3909
|
-
if (!import_shared66.Guards.isNullOrEmpty(opts.allowOrigins)) {
|
|
4243
|
+
if (!import_shared72.Guards.isNullOrEmpty(opts.allowOrigins)) {
|
|
4244
|
+
const withCredentials = import_shared72.Guards.isDefined(opts.httpConfig.withCredentials) ? opts.httpConfig.withCredentials : false;
|
|
4245
|
+
if (withCredentials && opts.allowOrigins.includes("*"))
|
|
4246
|
+
throw new Error("Wildcard CORS origin is not allowed when withCredentials is set to true");
|
|
3910
4247
|
const { AllowOrigin: AllowOrigin2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
3911
4248
|
container.addSingleton("ALLOW_ORIGIN", () => {
|
|
3912
4249
|
return new AllowOrigin2(opts.allowOrigins);
|
|
@@ -3921,6 +4258,14 @@ var init_middleware_module = __esm({
|
|
|
3921
4258
|
});
|
|
3922
4259
|
middlewares.push(TOKENS4.ALLOW_ORIGIN_MIDDLEWARE);
|
|
3923
4260
|
}
|
|
4261
|
+
if (opts.optionsMiddleware) {
|
|
4262
|
+
const { OptionsMiddleware: OptionsMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
4263
|
+
container.addSingleton(
|
|
4264
|
+
TOKENS4.OPTIONS_MIDDLEWARE,
|
|
4265
|
+
(c) => new OptionsMiddleware2(c.resolve(TOKENS4.NETWORK_CONTEXT_ACCESSOR))
|
|
4266
|
+
);
|
|
4267
|
+
middlewares.push(TOKENS4.OPTIONS_MIDDLEWARE);
|
|
4268
|
+
}
|
|
3924
4269
|
if (opts.cors) {
|
|
3925
4270
|
const { CORSMiddleware: CORSMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
3926
4271
|
container.addSingleton(TOKENS4.CORS_MIDDLEWARE, (c) => {
|
|
@@ -3928,7 +4273,7 @@ var init_middleware_module = __esm({
|
|
|
3928
4273
|
});
|
|
3929
4274
|
middlewares.push(TOKENS4.CORS_MIDDLEWARE);
|
|
3930
4275
|
}
|
|
3931
|
-
if (
|
|
4276
|
+
if (import_shared72.Guards.isDefined(opts.routeRegistry)) {
|
|
3932
4277
|
const registry = opts.routeRegistry;
|
|
3933
4278
|
const { AllowMethodFactory: AllowMethodFactory2 } = await Promise.resolve().then(() => (init_factories(), factories_exports));
|
|
3934
4279
|
container.addSingleton(TOKENS4.ALLOW_METHOD, () => new AllowMethodFactory2().create(registry));
|
|
@@ -3942,21 +4287,47 @@ var init_middleware_module = __esm({
|
|
|
3942
4287
|
);
|
|
3943
4288
|
middlewares.push(TOKENS4.METHOD_CHECK_MIDDLEWARE);
|
|
3944
4289
|
}
|
|
3945
|
-
|
|
4290
|
+
const { AuthenticationMiddleware: AuthenticationMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
4291
|
+
container.addSingleton(TOKENS4.AUTH_MIDDLEWARE, (c) => {
|
|
4292
|
+
return new AuthenticationMiddleware2(
|
|
4293
|
+
c.resolve(TOKENS4.REQUEST_CONTEXT),
|
|
4294
|
+
c.resolve(TOKENS4.BEARER_TOKEN_EXTRACTOR),
|
|
4295
|
+
c.resolve(TOKENS4.GATE_KEEPER),
|
|
4296
|
+
c.resolve(TOKENS4.LOGGER)
|
|
4297
|
+
);
|
|
4298
|
+
});
|
|
4299
|
+
middlewares.push(TOKENS4.AUTH_MIDDLEWARE);
|
|
4300
|
+
if (import_shared72.Guards.isDefined(opts.csrf)) {
|
|
3946
4301
|
const csrf = opts.csrf;
|
|
4302
|
+
const { CsrfTokenService: CsrfTokenService2 } = await Promise.resolve().then(() => (init_services(), services_exports));
|
|
4303
|
+
container.addSingleton("CSRF_TOKEN_SERVICE", (c) => {
|
|
4304
|
+
return new CsrfTokenService2(csrf.secret, c.resolve("CRYPTO_SERVICE"));
|
|
4305
|
+
});
|
|
4306
|
+
const { CsrfCookieMiddleware: CsrfCookieMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
4307
|
+
container.addSingleton("CSRF_COOKIE_MIDDLEWARE", (c) => {
|
|
4308
|
+
return new CsrfCookieMiddleware2(
|
|
4309
|
+
c.resolve(TOKENS4.REQUEST_CONTEXT),
|
|
4310
|
+
c.resolve("CSRF_TOKEN_SERVICE"),
|
|
4311
|
+
csrf
|
|
4312
|
+
);
|
|
4313
|
+
});
|
|
4314
|
+
middlewares.push("CSRF_COOKIE_MIDDLEWARE");
|
|
3947
4315
|
const { CsrfMiddleware: CsrfMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
3948
4316
|
container.addSingleton(TOKENS4.CSRF_MIDDLEWARE, (c) => {
|
|
3949
|
-
return new CsrfMiddleware2(
|
|
4317
|
+
return new CsrfMiddleware2(
|
|
4318
|
+
c.resolve(TOKENS4.REQUEST_CONTEXT),
|
|
4319
|
+
c.resolve("CSRF_TOKEN_SERVICE")
|
|
4320
|
+
);
|
|
3950
4321
|
});
|
|
3951
4322
|
middlewares.push(TOKENS4.CSRF_MIDDLEWARE);
|
|
3952
4323
|
}
|
|
3953
|
-
if (
|
|
4324
|
+
if (import_shared72.Guards.isDefined(opts.rateLimite.maxRequests) || import_shared72.Guards.isDefined(opts.rateLimite.windowSeconds)) {
|
|
3954
4325
|
const maxRequests = opts.rateLimite.maxRequests ?? 30;
|
|
3955
|
-
|
|
3956
|
-
|
|
4326
|
+
import_shared72.Guards.throwIfNegative(maxRequests, "MaxRequests must be positive");
|
|
4327
|
+
import_shared72.Guards.throwIfNotInteger(maxRequests, "MaxRequests must be an integer");
|
|
3957
4328
|
const windowSeconds = opts.rateLimite.windowSeconds ?? 30;
|
|
3958
|
-
|
|
3959
|
-
|
|
4329
|
+
import_shared72.Guards.throwIfNegative(windowSeconds, "WindowSeconds must be positive");
|
|
4330
|
+
import_shared72.Guards.throwIfNotInteger(windowSeconds, "WindowSeconds must be an integer");
|
|
3960
4331
|
if (!opts.isCache) {
|
|
3961
4332
|
const { CacheUtils: CacheUtils2 } = await Promise.resolve().then(() => (init_cache_utils(), cache_utils_exports));
|
|
3962
4333
|
await CacheUtils2.addCache(container, { inMemory: true, redis: void 0 });
|
|
@@ -3975,16 +4346,6 @@ var init_middleware_module = __esm({
|
|
|
3975
4346
|
});
|
|
3976
4347
|
middlewares.push(TOKENS4.RATE_LIMITER_MIDDLEWARE);
|
|
3977
4348
|
}
|
|
3978
|
-
const { AuthenticationMiddleware: AuthenticationMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
3979
|
-
container.addSingleton(TOKENS4.AUTH_MIDDLEWARE, (c) => {
|
|
3980
|
-
return new AuthenticationMiddleware2(
|
|
3981
|
-
c.resolve(TOKENS4.REQUEST_CONTEXT),
|
|
3982
|
-
c.resolve(TOKENS4.BEARER_TOKEN_EXTRACTOR),
|
|
3983
|
-
c.resolve(TOKENS4.GATE_KEEPER),
|
|
3984
|
-
c.resolve(TOKENS4.LOGGER)
|
|
3985
|
-
);
|
|
3986
|
-
});
|
|
3987
|
-
middlewares.push(TOKENS4.AUTH_MIDDLEWARE);
|
|
3988
4349
|
const { CompositeMiddleware: CompositeMiddleware2 } = await Promise.resolve().then(() => (init_presentation(), presentation_exports));
|
|
3989
4350
|
container.addSingleton(TOKENS4.MIDDLEWARE, (c) => {
|
|
3990
4351
|
const resolvedMiddleware = middlewares.map(
|
|
@@ -4044,7 +4405,7 @@ __export(index_exports, {
|
|
|
4044
4405
|
BaseAuthorizationStrategy: () => BaseAuthorizationStrategy,
|
|
4045
4406
|
BaseController: () => BaseController,
|
|
4046
4407
|
BaseHandler: () => BaseHandler,
|
|
4047
|
-
BaseQuery: () =>
|
|
4408
|
+
BaseQuery: () => import_shared79.Query,
|
|
4048
4409
|
ContainerUtils: () => ContainerUtils,
|
|
4049
4410
|
ReadDao: () => ReadDao,
|
|
4050
4411
|
Repository: () => Repository,
|
|
@@ -4055,7 +4416,7 @@ module.exports = __toCommonJS(index_exports);
|
|
|
4055
4416
|
init_application();
|
|
4056
4417
|
|
|
4057
4418
|
// src/infrastructure/builder/app.builder.ts
|
|
4058
|
-
var
|
|
4419
|
+
var import_shared73 = require("@xeno-js/shared");
|
|
4059
4420
|
|
|
4060
4421
|
// src/infrastructure/configuration/configuration.ts
|
|
4061
4422
|
var import_shared32 = require("@xeno-js/shared");
|
|
@@ -4327,10 +4688,13 @@ var AppBuilder = class {
|
|
|
4327
4688
|
constructor(container) {
|
|
4328
4689
|
this._container = container ?? new ServiceContainer();
|
|
4329
4690
|
this._container.addSingleton(
|
|
4330
|
-
|
|
4691
|
+
import_shared73.TOKENS.CONFIGURATION_SERVICE,
|
|
4331
4692
|
() => new EnvironmentConfigurationService()
|
|
4332
4693
|
);
|
|
4333
|
-
this._configuration = this._container.resolve(
|
|
4694
|
+
this._configuration = this._container.resolve(import_shared73.TOKENS.CONFIGURATION_SERVICE);
|
|
4695
|
+
this._middlewareConfig.allowOrigins?.push(
|
|
4696
|
+
this._configuration.get("APP_URL") ?? `http://localhost:${this._configuration.getNumber("PORT", 3e3)}`
|
|
4697
|
+
);
|
|
4334
4698
|
}
|
|
4335
4699
|
// --- Module Configurations ---
|
|
4336
4700
|
_modules = [];
|
|
@@ -4362,7 +4726,8 @@ var AppBuilder = class {
|
|
|
4362
4726
|
optionsMiddleware: false,
|
|
4363
4727
|
routeRegistry: void 0,
|
|
4364
4728
|
trustedIpHeader: void 0,
|
|
4365
|
-
|
|
4729
|
+
trustedProxies: [],
|
|
4730
|
+
allowOrigins: [],
|
|
4366
4731
|
cors: true
|
|
4367
4732
|
};
|
|
4368
4733
|
_httpConfig = {
|
|
@@ -4439,13 +4804,13 @@ var AppBuilder = class {
|
|
|
4439
4804
|
if (this._isLoggerModuleQueued) return this;
|
|
4440
4805
|
this._isLoggerModuleQueued = true;
|
|
4441
4806
|
const config = {
|
|
4442
|
-
level:
|
|
4807
|
+
level: import_shared73.LOG_LEVEL.DEBUG,
|
|
4443
4808
|
console: true,
|
|
4444
4809
|
sentry: { config: void 0 },
|
|
4445
4810
|
pino: { config: void 0 },
|
|
4446
4811
|
customLoggers: void 0
|
|
4447
4812
|
};
|
|
4448
|
-
if (
|
|
4813
|
+
if (import_shared73.Guards.isDefined(setupAction) && import_shared73.Guards.isDefined(config))
|
|
4449
4814
|
setupAction(config, this._configuration);
|
|
4450
4815
|
this._modules.push({
|
|
4451
4816
|
priority: 3,
|
|
@@ -4471,7 +4836,7 @@ var AppBuilder = class {
|
|
|
4471
4836
|
addCache(setupAction) {
|
|
4472
4837
|
if (this._isCacheModuleQueued) return this;
|
|
4473
4838
|
this._isCacheModuleQueued = true;
|
|
4474
|
-
if (
|
|
4839
|
+
if (import_shared73.Guards.isDefined(setupAction)) setupAction(this._config, this._configuration);
|
|
4475
4840
|
this._modules.push({
|
|
4476
4841
|
priority: 3,
|
|
4477
4842
|
name: "CacheModule",
|
|
@@ -4580,7 +4945,7 @@ var AppBuilder = class {
|
|
|
4580
4945
|
* @link https://github.com/xeno-js/xeno-js
|
|
4581
4946
|
*/
|
|
4582
4947
|
addPipeline(setupAction) {
|
|
4583
|
-
if (
|
|
4948
|
+
if (import_shared73.Guards.isDefined(setupAction)) {
|
|
4584
4949
|
setupAction(this._pipelineConfig, this._configuration);
|
|
4585
4950
|
}
|
|
4586
4951
|
this._queuePipelineModule();
|
|
@@ -4714,7 +5079,7 @@ var AppBuilder = class {
|
|
|
4714
5079
|
console.error(`\u{1F449} Module: **${queued.name}**`);
|
|
4715
5080
|
console.error(`\u{1F4DD} Reason: ${errorMessage}
|
|
4716
5081
|
`);
|
|
4717
|
-
if (error instanceof Error &&
|
|
5082
|
+
if (error instanceof Error && import_shared73.Guards.isDefined(error.stack)) {
|
|
4718
5083
|
console.error(error.stack);
|
|
4719
5084
|
}
|
|
4720
5085
|
throw new Error(`Bootstrap failed at [${queued.name}]: ${errorMessage}`, { cause: error });
|
|
@@ -4776,7 +5141,8 @@ var AppBuilder = class {
|
|
|
4776
5141
|
...this._middlewareConfig,
|
|
4777
5142
|
isAuth: this._isAuthModuleQueued,
|
|
4778
5143
|
isLogger: this._isLoggerModuleQueued,
|
|
4779
|
-
isCache: this._isCacheModuleQueued || this._isPipelineModuleQueued
|
|
5144
|
+
isCache: this._isCacheModuleQueued || this._isPipelineModuleQueued,
|
|
5145
|
+
httpConfig: this._httpConfig.http.client
|
|
4780
5146
|
});
|
|
4781
5147
|
}
|
|
4782
5148
|
});
|
|
@@ -4812,7 +5178,7 @@ init_redis_cache();
|
|
|
4812
5178
|
init_request_context();
|
|
4813
5179
|
|
|
4814
5180
|
// src/infrastructure/datasources/remote.datasource.ts
|
|
4815
|
-
var
|
|
5181
|
+
var import_shared74 = require("@xeno-js/shared");
|
|
4816
5182
|
|
|
4817
5183
|
// src/infrastructure/index.ts
|
|
4818
5184
|
init_factories();
|
|
@@ -4842,8 +5208,8 @@ init_pipeline_utils();
|
|
|
4842
5208
|
init_validation_utils();
|
|
4843
5209
|
|
|
4844
5210
|
// src/infrastructure/repositories/read-dao.ts
|
|
4845
|
-
var
|
|
4846
|
-
var
|
|
5211
|
+
var import_shared75 = require("@xeno-js/shared");
|
|
5212
|
+
var import_shared76 = require("@xeno-js/shared");
|
|
4847
5213
|
var ReadDao = class {
|
|
4848
5214
|
/**
|
|
4849
5215
|
* Constructs a new ReadDao instance.
|
|
@@ -4863,23 +5229,23 @@ var ReadDao = class {
|
|
|
4863
5229
|
_dataSource;
|
|
4864
5230
|
_mapper;
|
|
4865
5231
|
async findById(id, ctx, signal) {
|
|
4866
|
-
|
|
5232
|
+
import_shared75.AppError.throwIfAborted(signal, "ReadDao.findById");
|
|
4867
5233
|
const result = await this._dataSource.findById(id, ctx, signal);
|
|
4868
|
-
if (
|
|
5234
|
+
if (import_shared76.Guards.isNullOrEmpty(result)) return import_shared75.Result.ok();
|
|
4869
5235
|
const entity = this._mapper.toEntity(result);
|
|
4870
|
-
return
|
|
5236
|
+
return import_shared75.Result.ok(entity);
|
|
4871
5237
|
}
|
|
4872
5238
|
async findAll(ctx, signal) {
|
|
4873
|
-
|
|
5239
|
+
import_shared75.AppError.throwIfAborted(signal, "ReadDao.findAll");
|
|
4874
5240
|
const results = await this._dataSource.findAll(ctx, signal);
|
|
4875
5241
|
const entities = results.map((result) => this._mapper.toEntity(result));
|
|
4876
|
-
return
|
|
5242
|
+
return import_shared75.Result.ok(entities);
|
|
4877
5243
|
}
|
|
4878
5244
|
};
|
|
4879
5245
|
|
|
4880
5246
|
// src/infrastructure/repositories/repository.ts
|
|
4881
|
-
var
|
|
4882
|
-
var
|
|
5247
|
+
var import_shared77 = require("@xeno-js/shared");
|
|
5248
|
+
var import_shared78 = require("@xeno-js/shared");
|
|
4883
5249
|
var Repository = class {
|
|
4884
5250
|
/**
|
|
4885
5251
|
* Constructs a new Repository instance.
|
|
@@ -4899,35 +5265,35 @@ var Repository = class {
|
|
|
4899
5265
|
_dataSource;
|
|
4900
5266
|
_mapper;
|
|
4901
5267
|
async findById(id, ctx, signal) {
|
|
4902
|
-
|
|
5268
|
+
import_shared77.AppError.throwIfAborted(signal, "Repository.findById");
|
|
4903
5269
|
const result = await this._dataSource.findById(id, ctx, signal);
|
|
4904
|
-
if (
|
|
5270
|
+
if (import_shared78.Guards.isNullOrEmpty(result)) return import_shared77.Result.ok();
|
|
4905
5271
|
const entity = this._mapper.toEntity(result);
|
|
4906
|
-
return
|
|
5272
|
+
return import_shared77.Result.ok(entity);
|
|
4907
5273
|
}
|
|
4908
5274
|
async findAll(ctx, signal) {
|
|
4909
|
-
|
|
5275
|
+
import_shared77.AppError.throwIfAborted(signal, "Repository.findAll");
|
|
4910
5276
|
const results = await this._dataSource.findAll(ctx, signal);
|
|
4911
5277
|
const entities = results.map((result) => this._mapper.toEntity(result));
|
|
4912
|
-
return
|
|
5278
|
+
return import_shared77.Result.ok(entities);
|
|
4913
5279
|
}
|
|
4914
5280
|
async save(entity, signal) {
|
|
4915
5281
|
const dto = this._mapper.toDto(entity);
|
|
4916
|
-
|
|
5282
|
+
import_shared77.AppError.throwIfAborted(signal, "Repository.save");
|
|
4917
5283
|
await this._dataSource.insert(dto, signal);
|
|
4918
|
-
return
|
|
5284
|
+
return import_shared77.Result.ok();
|
|
4919
5285
|
}
|
|
4920
5286
|
async delete(entity, ctx, signal) {
|
|
4921
5287
|
const dto = this._mapper.toDto(entity);
|
|
4922
|
-
|
|
5288
|
+
import_shared77.AppError.throwIfAborted(signal, "Repository.delete");
|
|
4923
5289
|
await this._dataSource.delete(dto, ctx, signal);
|
|
4924
|
-
return
|
|
5290
|
+
return import_shared77.Result.ok();
|
|
4925
5291
|
}
|
|
4926
5292
|
async update(id, entity, ctx, signal) {
|
|
4927
5293
|
const dto = this._mapper.toPartialDto(entity);
|
|
4928
|
-
|
|
5294
|
+
import_shared77.AppError.throwIfAborted(signal, "Repository.update");
|
|
4929
5295
|
await this._dataSource.update(id, dto, ctx, signal);
|
|
4930
|
-
return
|
|
5296
|
+
return import_shared77.Result.ok();
|
|
4931
5297
|
}
|
|
4932
5298
|
};
|
|
4933
5299
|
|
|
@@ -4945,7 +5311,7 @@ __reExport(drizzle_types_exports, require("drizzle-orm"));
|
|
|
4945
5311
|
__reExport(index_exports, drizzle_types_exports, module.exports);
|
|
4946
5312
|
init_presentation();
|
|
4947
5313
|
__reExport(index_exports, require("@xeno-js/shared"), module.exports);
|
|
4948
|
-
var
|
|
5314
|
+
var import_shared79 = require("@xeno-js/shared");
|
|
4949
5315
|
// Annotate the CommonJS export names for ESM import in node:
|
|
4950
5316
|
0 && (module.exports = {
|
|
4951
5317
|
AppBuilder,
|
|
@@ -4960,4 +5326,13 @@ var import_shared73 = require("@xeno-js/shared");
|
|
|
4960
5326
|
SupabaseServerAuthFactory,
|
|
4961
5327
|
...require("@xeno-js/shared")
|
|
4962
5328
|
});
|
|
5329
|
+
/**
|
|
5330
|
+
* @description The CsrfCookieMiddleware class implements the IMiddleware interface, providing a concrete implementation for handling CSRF token validation and cookie management. It checks the incoming request for a valid CSRF token and sets a CSRF cookie if necessary.
|
|
5331
|
+
*
|
|
5332
|
+
* @author Xeno
|
|
5333
|
+
* @version 1.0.0
|
|
5334
|
+
* @since 2025-09-30
|
|
5335
|
+
* @link https://github.com/xeno-js/xeno-js
|
|
5336
|
+
* @license MIT
|
|
5337
|
+
*/
|
|
4963
5338
|
//# sourceMappingURL=index.cjs.map
|