@ozdao/martyrs 0.2.473 → 0.2.474
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/dist/{Media-DW8RLbfM.js → Media-_vz04tII.js} +1 -1
- package/dist/{Media-y_TX6us_.mjs → Media-sGk7Bp9b.mjs} +1 -1
- package/dist/auth.server.js +6 -2
- package/dist/auth.server.mjs +6 -2
- package/dist/authJwt-CELQKF2s.js +82 -0
- package/dist/authJwt-DnXu3BFq.mjs +83 -0
- package/dist/builder.js +7 -4
- package/dist/builder.mjs +7 -4
- package/dist/chats.server.js +1 -1
- package/dist/chats.server.mjs +1 -1
- package/dist/community.server.js +4 -4
- package/dist/community.server.mjs +4 -4
- package/dist/events.server.js +4 -4
- package/dist/events.server.mjs +4 -4
- package/dist/files.server.js +1 -1
- package/dist/files.server.mjs +1 -1
- package/dist/gallery.server.js +3 -3
- package/dist/gallery.server.mjs +3 -3
- package/dist/{globals.abac-DT0VjfaZ.js → globals.abac-Bn-4tbX8.js} +110 -16
- package/dist/{globals.abac-CvmZM8XG.mjs → globals.abac-DZpTRxKR.mjs} +110 -16
- package/dist/globals.server.js +70 -10
- package/dist/globals.server.mjs +70 -10
- package/dist/{globals.verifier-C_VZYebB.mjs → globals.verifier-BdJxc8-8.mjs} +34 -0
- package/dist/{globals.verifier-ChDpCdy_.js → globals.verifier-CKYpYfQl.js} +34 -0
- package/dist/{index-CVXl1rB5.js → index-BOmxJQ5W.js} +7 -86
- package/dist/{index-Df8vtZx7.mjs → index-C_Fw0Umg.mjs} +7 -86
- package/dist/{main-CgmHzhq5.mjs → main-CqMtW7Hq.mjs} +274 -276
- package/dist/{main-CCfQH-Dd.js → main-CsGkbSyK.js} +2 -2
- package/dist/martyrs/src/components/Select/Select.vue.cjs +4 -4
- package/dist/martyrs/src/components/Select/Select.vue.cjs.map +1 -1
- package/dist/martyrs/src/components/Select/Select.vue.js +4 -4
- package/dist/martyrs/src/components/Select/Select.vue.js.map +1 -1
- package/dist/martyrs/src/modules/community/community.client.js +27 -27
- package/dist/martyrs/src/modules/community/community.client.js.map +1 -1
- package/dist/martyrs/src/modules/community/components/sections/HotPosts.vue.cjs +2 -3
- package/dist/martyrs/src/modules/community/components/sections/HotPosts.vue.cjs.map +1 -1
- package/dist/martyrs/src/modules/community/components/sections/HotPosts.vue.js +2 -3
- package/dist/martyrs/src/modules/community/components/sections/HotPosts.vue.js.map +1 -1
- package/dist/martyrs/src/modules/orders/components/pages/OrderCreate.vue.cjs +88 -27
- package/dist/martyrs/src/modules/orders/components/pages/OrderCreate.vue.cjs.map +1 -1
- package/dist/martyrs/src/modules/orders/components/pages/OrderCreate.vue.js +89 -28
- package/dist/martyrs/src/modules/orders/components/pages/OrderCreate.vue.js.map +1 -1
- package/dist/martyrs/src/modules/orders/store/shopcart.cjs +1 -0
- package/dist/martyrs/src/modules/orders/store/shopcart.cjs.map +1 -1
- package/dist/martyrs/src/modules/orders/store/shopcart.js +1 -0
- package/dist/martyrs/src/modules/orders/store/shopcart.js.map +1 -1
- package/dist/martyrs/src/modules/products/components/pages/CategoryEdit.vue.cjs +19 -0
- package/dist/martyrs/src/modules/products/components/pages/CategoryEdit.vue.cjs.map +1 -1
- package/dist/martyrs/src/modules/products/components/pages/CategoryEdit.vue.js +19 -0
- package/dist/martyrs/src/modules/products/components/pages/CategoryEdit.vue.js.map +1 -1
- package/dist/martyrs/src/modules/products/components/pages/Product.vue.cjs +1 -0
- package/dist/martyrs/src/modules/products/components/pages/Product.vue.cjs.map +1 -1
- package/dist/martyrs/src/modules/products/components/pages/Product.vue.js +1 -0
- package/dist/martyrs/src/modules/products/components/pages/Product.vue.js.map +1 -1
- package/dist/martyrs/src/modules/products/components/pages/ProductEdit.vue.cjs +2 -2
- package/dist/martyrs/src/modules/products/components/pages/ProductEdit.vue.cjs.map +1 -1
- package/dist/martyrs/src/modules/products/components/pages/ProductEdit.vue.js +2 -2
- package/dist/martyrs/src/modules/products/components/pages/ProductEdit.vue.js.map +1 -1
- package/dist/martyrs/src/modules/products/store/categories.cjs +2 -0
- package/dist/martyrs/src/modules/products/store/categories.cjs.map +1 -1
- package/dist/martyrs/src/modules/products/store/categories.js +2 -0
- package/dist/martyrs/src/modules/products/store/categories.js.map +1 -1
- package/dist/martyrs/src/modules/spots/components/pages/SpotEdit.vue.cjs +30 -24
- package/dist/martyrs/src/modules/spots/components/pages/SpotEdit.vue.cjs.map +1 -1
- package/dist/martyrs/src/modules/spots/components/pages/SpotEdit.vue.js +30 -24
- package/dist/martyrs/src/modules/spots/components/pages/SpotEdit.vue.js.map +1 -1
- package/dist/martyrs/src/modules/spots/components/sections/WorktimeEdit.vue.cjs +807 -0
- package/dist/martyrs/src/modules/spots/components/sections/WorktimeEdit.vue.cjs.map +1 -0
- package/dist/martyrs/src/modules/spots/components/sections/WorktimeEdit.vue.js +807 -0
- package/dist/martyrs/src/modules/spots/components/sections/WorktimeEdit.vue.js.map +1 -0
- package/dist/martyrs/src/modules/spots/store/spots.cjs +4 -1
- package/dist/martyrs/src/modules/spots/store/spots.cjs.map +1 -1
- package/dist/martyrs/src/modules/spots/store/spots.js +4 -1
- package/dist/martyrs/src/modules/spots/store/spots.js.map +1 -1
- package/dist/martyrs.cjs.js +1 -1
- package/dist/martyrs.css +1 -1
- package/dist/martyrs.es.js +1 -1
- package/dist/notifications.server.js +1 -1
- package/dist/notifications.server.mjs +1 -1
- package/dist/orders.server.js +5 -4
- package/dist/orders.server.mjs +5 -4
- package/dist/organizations.server.js +120 -47
- package/dist/organizations.server.mjs +120 -47
- package/dist/{ownership.schema-C0w02Vw1.mjs → ownership.schema-CNCotD3D.mjs} +10 -4
- package/dist/{ownership.schema-Ck2H9clB.js → ownership.schema-MxfJlPtq.js} +10 -4
- package/dist/products.server.js +415 -149
- package/dist/products.server.mjs +415 -149
- package/dist/{profile.schema-h61hhB2w.js → profile.schema-BLSuV_VC.js} +0 -4
- package/dist/{profile.schema-kP_zKXNt.mjs → profile.schema-BRuvQ7QV.mjs} +0 -4
- package/dist/{queryProcessor-CWnMIe2U.mjs → queryProcessor-CVKI651_.mjs} +62 -8
- package/dist/{queryProcessor-D6GuKfTV.js → queryProcessor-DSUqSk3I.js} +62 -8
- package/dist/rents.server.js +4 -4
- package/dist/rents.server.mjs +4 -4
- package/dist/spots.server.js +162 -8
- package/dist/spots.server.mjs +162 -8
- package/dist/style.css +27 -4
- package/dist/wallet.server.js +2 -2
- package/dist/wallet.server.mjs +2 -2
- package/package.json +1 -1
- package/src/builder/rspack/rspack.config.base.js +1 -1
- package/src/builder/rspack/rspack.config.client.js +13 -5
- package/src/components/Select/Select.vue +4 -2
- package/src/modules/auth/models/user.model.js +4 -1
- package/src/modules/community/components/sections/HotPosts.vue +1 -1
- package/src/modules/globals/controllers/classes/globals.abac.js +148 -23
- package/src/modules/globals/controllers/classes/globals.validator.js +37 -0
- package/src/modules/globals/controllers/classes/globals.verifier.js +2 -0
- package/src/modules/globals/controllers/policies/globals.policies.js +91 -74
- package/src/modules/globals/controllers/utils/queryProcessor.js +59 -11
- package/src/modules/globals/models/schemas/ownership.schema.js +11 -6
- package/src/modules/globals/models/schemas/profile.schema.js +0 -4
- package/src/modules/music/components/layouts/MusicLayout.vue +10 -58
- package/src/modules/music/components/pages/MusicHome.vue +5 -5
- package/src/modules/orders/components/pages/OrderCreate.vue +85 -12
- package/src/modules/orders/controllers/orders.controller.js +3 -0
- package/src/modules/orders/store/shopcart.js +1 -0
- package/src/modules/organizations/models/schemas/accesses.schema.js +18 -0
- package/src/modules/organizations/policies/organizations.policies.js +117 -61
- package/src/modules/products/components/pages/CategoryEdit.vue +27 -2
- package/src/modules/products/components/pages/Product.vue +1 -0
- package/src/modules/products/components/pages/ProductEdit.vue +2 -2
- package/src/modules/products/controllers/categories.controller.js +297 -133
- package/src/modules/products/middlewares/categories.verifier.js +177 -0
- package/src/modules/products/models/category.model.js +12 -14
- package/src/modules/products/routes/categories.routes.js +50 -11
- package/src/modules/products/store/categories.js +2 -0
- package/src/modules/spots/components/pages/SpotEdit.vue +21 -17
- package/src/modules/spots/components/sections/WorktimeEdit.vue +840 -0
- package/src/modules/spots/controllers/queries/getIsOpenNowStage.js +109 -0
- package/src/modules/spots/controllers/spots.controller.js +2 -1
- package/src/modules/spots/models/spot.model.js +59 -13
- package/src/modules/spots/store/spots.js +4 -1
- package/src/modules/products/middlewares/index.js +0 -11
- package/src/modules/products/middlewares/verifyCategory.js +0 -25
|
@@ -56,8 +56,34 @@ function requireGlobals_abac() {
|
|
|
56
56
|
}
|
|
57
57
|
return model;
|
|
58
58
|
}
|
|
59
|
+
/**
|
|
60
|
+
* Нормализация результата политики для единообразной обработки
|
|
61
|
+
* @param {any} result - Результат выполнения политики
|
|
62
|
+
* @param {string} policyName - Имя политики для формирования причины
|
|
63
|
+
* @returns {Object} Нормализованный результат
|
|
64
|
+
*/
|
|
65
|
+
_normalizeResult(result, policyName) {
|
|
66
|
+
if (result && typeof result === "object" && ("allow" in result || "force" in result)) {
|
|
67
|
+
return {
|
|
68
|
+
allow: !!result.allow,
|
|
69
|
+
force: !!result.force,
|
|
70
|
+
reason: result.reason || `POLICY_${policyName.toUpperCase()}`
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
if (result === true) {
|
|
74
|
+
return { allow: true, force: false, reason: `ALLOWED_BY_${policyName.toUpperCase()}` };
|
|
75
|
+
}
|
|
76
|
+
if (result === false) {
|
|
77
|
+
return { allow: false, force: false, reason: `DENIED_BY_${policyName.toUpperCase()}` };
|
|
78
|
+
}
|
|
79
|
+
if (result === void 0 && policyName === "AdminModeratorAccessPolicy" && (this._context && this._context.adminAccessGranted)) {
|
|
80
|
+
return { allow: true, force: true, reason: "ADMIN_MODERATOR_ACCESS_GRANTED" };
|
|
81
|
+
}
|
|
82
|
+
return { allow: true, force: false, reason: `NEUTRAL_${policyName.toUpperCase()}` };
|
|
83
|
+
}
|
|
59
84
|
// Базовый метод проверки доступа
|
|
60
85
|
async checkAccess(context) {
|
|
86
|
+
this._context = context;
|
|
61
87
|
const {
|
|
62
88
|
user,
|
|
63
89
|
// Пользователь
|
|
@@ -109,27 +135,95 @@ function requireGlobals_abac() {
|
|
|
109
135
|
};
|
|
110
136
|
}
|
|
111
137
|
}
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
};
|
|
138
|
+
const policyEntries = Object.entries(this.policies.global);
|
|
139
|
+
const policyPromises = policyEntries.map(async ([policyName, policyFn]) => {
|
|
140
|
+
try {
|
|
141
|
+
const result = await policyFn(context);
|
|
142
|
+
return { policyName, result };
|
|
143
|
+
} catch (error) {
|
|
144
|
+
console.error(`Error in policy ${policyName}:`, error);
|
|
145
|
+
return { policyName, result: void 0, error };
|
|
146
|
+
}
|
|
147
|
+
});
|
|
148
|
+
const policyResults = await Promise.all(policyPromises);
|
|
149
|
+
let hasForceAllow = false;
|
|
150
|
+
let hasForceDisallow = false;
|
|
151
|
+
let hasDeny = false;
|
|
152
|
+
let denyReason = "";
|
|
153
|
+
let allowReason = "";
|
|
154
|
+
for (const { policyName, result, error } of policyResults) {
|
|
155
|
+
if (error) continue;
|
|
156
|
+
const normalizedResult = this._normalizeResult(result, policyName);
|
|
157
|
+
if (normalizedResult.force) {
|
|
158
|
+
if (normalizedResult.allow) {
|
|
159
|
+
hasForceAllow = true;
|
|
160
|
+
allowReason = normalizedResult.reason;
|
|
161
|
+
} else {
|
|
162
|
+
hasForceDisallow = true;
|
|
163
|
+
denyReason = normalizedResult.reason;
|
|
164
|
+
}
|
|
165
|
+
} else if (!normalizedResult.allow) {
|
|
166
|
+
hasDeny = true;
|
|
167
|
+
if (!denyReason) denyReason = normalizedResult.reason;
|
|
119
168
|
}
|
|
120
169
|
}
|
|
170
|
+
if (hasForceDisallow) {
|
|
171
|
+
return {
|
|
172
|
+
allowed: false,
|
|
173
|
+
reason: denyReason || "FORCE_DENIED_BY_POLICY"
|
|
174
|
+
};
|
|
175
|
+
}
|
|
176
|
+
if (hasForceAllow) {
|
|
177
|
+
return {
|
|
178
|
+
allowed: true,
|
|
179
|
+
reason: allowReason || "FORCE_ALLOWED_BY_POLICY"
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
if (hasDeny) {
|
|
183
|
+
return {
|
|
184
|
+
allowed: false,
|
|
185
|
+
reason: denyReason || "DENIED_BY_POLICY"
|
|
186
|
+
};
|
|
187
|
+
}
|
|
121
188
|
if (this.policies.resources[resource]) {
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
189
|
+
try {
|
|
190
|
+
const resourceResult = await this.policies.resources[resource](context);
|
|
191
|
+
const normalizedResult = this._normalizeResult(resourceResult, `RESOURCE_${resource}`);
|
|
192
|
+
if (normalizedResult.force) {
|
|
193
|
+
return {
|
|
194
|
+
allowed: normalizedResult.allow,
|
|
195
|
+
reason: normalizedResult.reason
|
|
196
|
+
};
|
|
197
|
+
}
|
|
198
|
+
if (!normalizedResult.allow) {
|
|
199
|
+
return {
|
|
200
|
+
allowed: false,
|
|
201
|
+
reason: normalizedResult.reason
|
|
202
|
+
};
|
|
203
|
+
}
|
|
204
|
+
if (normalizedResult.allow) {
|
|
205
|
+
return {
|
|
206
|
+
allowed: true,
|
|
207
|
+
reason: normalizedResult.reason
|
|
208
|
+
};
|
|
209
|
+
}
|
|
210
|
+
} catch (error) {
|
|
211
|
+
console.error(`Error in resource policy for ${resource}:`, error);
|
|
128
212
|
}
|
|
129
213
|
}
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
214
|
+
const extensionPromises = Object.entries(this.policies.extensions).map(async ([moduleName, extensionFn]) => {
|
|
215
|
+
try {
|
|
216
|
+
const extensionResult = await extensionFn(context);
|
|
217
|
+
return { moduleName, result: extensionResult };
|
|
218
|
+
} catch (error) {
|
|
219
|
+
console.error(`Error in extension ${moduleName}:`, error);
|
|
220
|
+
return { moduleName, result: null, error };
|
|
221
|
+
}
|
|
222
|
+
});
|
|
223
|
+
const extensionResults = await Promise.all(extensionPromises);
|
|
224
|
+
for (const { moduleName, result, error } of extensionResults) {
|
|
225
|
+
if (error) continue;
|
|
226
|
+
if (result && result.allowed) {
|
|
133
227
|
return {
|
|
134
228
|
allowed: true,
|
|
135
229
|
reason: `ALLOWED_BY_${moduleName.toUpperCase()}_EXTENSION`
|
package/dist/globals.server.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
const _commonjsHelpers = require("./_commonjsHelpers-DHfMLFPC.js");
|
|
3
|
-
const globals_abac = require("./globals.abac-
|
|
3
|
+
const globals_abac = require("./globals.abac-Bn-4tbX8.js");
|
|
4
4
|
const require$$0 = require("ws");
|
|
5
5
|
const require$$0$1 = require("jsonwebtoken");
|
|
6
6
|
var globals_policies;
|
|
@@ -9,11 +9,48 @@ function requireGlobals_policies() {
|
|
|
9
9
|
if (hasRequiredGlobals_policies) return globals_policies;
|
|
10
10
|
hasRequiredGlobals_policies = 1;
|
|
11
11
|
globals_policies = function initializeDefaultPolicies(abacAccessControl) {
|
|
12
|
+
abacAccessControl.registerGlobalPolicy("AdminModeratorAccessPolicy", async (context) => {
|
|
13
|
+
const { user, req } = context;
|
|
14
|
+
if (!user) {
|
|
15
|
+
return { allow: true, force: false };
|
|
16
|
+
}
|
|
17
|
+
try {
|
|
18
|
+
const userModel = abacAccessControl.db.user;
|
|
19
|
+
const userDoc = await userModel.findById(user).populate("roles");
|
|
20
|
+
if (userDoc && userDoc.roles) {
|
|
21
|
+
context.userDoc = userDoc;
|
|
22
|
+
userRoles = userDoc.roles.map(
|
|
23
|
+
(role) => typeof role === "string" ? role : role.name || role
|
|
24
|
+
);
|
|
25
|
+
}
|
|
26
|
+
const isAdmin = userRoles.includes("admin");
|
|
27
|
+
const isModerator = userRoles.includes("moderator");
|
|
28
|
+
if (isAdmin || isModerator) {
|
|
29
|
+
return {
|
|
30
|
+
allow: true,
|
|
31
|
+
force: true,
|
|
32
|
+
reason: isAdmin ? "ADMIN_ACCESS_GRANTED" : "MODERATOR_ACCESS_GRANTED"
|
|
33
|
+
};
|
|
34
|
+
}
|
|
35
|
+
return { allow: true, force: false };
|
|
36
|
+
} catch (error) {
|
|
37
|
+
console.error("Error in AdminModeratorPolicy:", error);
|
|
38
|
+
return { allow: true, force: false };
|
|
39
|
+
}
|
|
40
|
+
});
|
|
12
41
|
abacAccessControl.registerGlobalPolicy("PersonalResourceOwnerPolicy", async (context) => {
|
|
13
42
|
let { user, action, data, currentResource, options } = context;
|
|
14
43
|
const ObjectId = abacAccessControl.db.mongoose.Types.ObjectId;
|
|
15
|
-
if (action === "create" && data.owner
|
|
16
|
-
|
|
44
|
+
if (action === "create" && data.owner?.type === "user") {
|
|
45
|
+
if (data.owner.target === user && data.creator.target === user) {
|
|
46
|
+
return { allow: true, force: false };
|
|
47
|
+
} else {
|
|
48
|
+
return {
|
|
49
|
+
allow: false,
|
|
50
|
+
force: false,
|
|
51
|
+
reason: "UNAUTHORIZED_RESOURCE_CREATION"
|
|
52
|
+
};
|
|
53
|
+
}
|
|
17
54
|
}
|
|
18
55
|
if (action === "read") {
|
|
19
56
|
const allowedPublicStatuses = ["published", "active", "featured"];
|
|
@@ -23,26 +60,49 @@ function requireGlobals_policies() {
|
|
|
23
60
|
if (Array.isArray(context.req.query.status)) {
|
|
24
61
|
for (const queryStatus of context.req.query.status) {
|
|
25
62
|
if (!allowedPublicStatuses.includes(queryStatus)) {
|
|
26
|
-
return
|
|
63
|
+
return {
|
|
64
|
+
allow: false,
|
|
65
|
+
force: true,
|
|
66
|
+
// Стопроцентный запрет для неразрешенных статусов
|
|
67
|
+
reason: "UNAUTHORIZED_STATUS_ACCESS"
|
|
68
|
+
};
|
|
27
69
|
}
|
|
28
70
|
}
|
|
29
71
|
} else {
|
|
30
72
|
if (!allowedPublicStatuses.includes(context.req.query.status)) {
|
|
31
|
-
return
|
|
73
|
+
return {
|
|
74
|
+
allow: false,
|
|
75
|
+
force: true,
|
|
76
|
+
// Стопроцентный запрет для неразрешенных статусов
|
|
77
|
+
reason: "UNAUTHORIZED_STATUS_ACCESS"
|
|
78
|
+
};
|
|
32
79
|
}
|
|
33
80
|
}
|
|
34
81
|
}
|
|
35
82
|
}
|
|
36
83
|
if (currentResource && !allowedPublicStatuses.includes(currentResource.status)) {
|
|
37
|
-
return
|
|
84
|
+
return {
|
|
85
|
+
allow: false,
|
|
86
|
+
force: true,
|
|
87
|
+
// Стопроцентный запрет для неразрешенных статусов
|
|
88
|
+
reason: "UNAUTHORIZED_RESOURCE_ACCESS"
|
|
89
|
+
};
|
|
38
90
|
}
|
|
39
91
|
}
|
|
40
|
-
return true;
|
|
92
|
+
return { allow: true, force: false };
|
|
41
93
|
}
|
|
42
|
-
if ((action === "edit" || action === "delete") && currentResource && currentResource.owner
|
|
43
|
-
|
|
94
|
+
if ((action === "edit" || action === "delete") && currentResource && currentResource.owner?.type === "user") {
|
|
95
|
+
if (currentResource.creator.target.equals(new ObjectId(user))) {
|
|
96
|
+
return { allow: true, force: false };
|
|
97
|
+
} else {
|
|
98
|
+
return {
|
|
99
|
+
allow: false,
|
|
100
|
+
force: false,
|
|
101
|
+
reason: "NOT_RESOURCE_OWNER"
|
|
102
|
+
};
|
|
103
|
+
}
|
|
44
104
|
}
|
|
45
|
-
return true;
|
|
105
|
+
return { allow: true, force: false };
|
|
46
106
|
});
|
|
47
107
|
return abacAccessControl;
|
|
48
108
|
};
|
package/dist/globals.server.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { g as getDefaultExportFromCjs } from "./_commonjsHelpers-CUmg6egw.mjs";
|
|
2
|
-
import { r as requireGlobals_abac } from "./globals.abac-
|
|
2
|
+
import { r as requireGlobals_abac } from "./globals.abac-DZpTRxKR.mjs";
|
|
3
3
|
import require$$0 from "ws";
|
|
4
4
|
import require$$0$1 from "jsonwebtoken";
|
|
5
5
|
var globals_policies;
|
|
@@ -8,11 +8,48 @@ function requireGlobals_policies() {
|
|
|
8
8
|
if (hasRequiredGlobals_policies) return globals_policies;
|
|
9
9
|
hasRequiredGlobals_policies = 1;
|
|
10
10
|
globals_policies = function initializeDefaultPolicies(abacAccessControl) {
|
|
11
|
+
abacAccessControl.registerGlobalPolicy("AdminModeratorAccessPolicy", async (context) => {
|
|
12
|
+
const { user, req } = context;
|
|
13
|
+
if (!user) {
|
|
14
|
+
return { allow: true, force: false };
|
|
15
|
+
}
|
|
16
|
+
try {
|
|
17
|
+
const userModel = abacAccessControl.db.user;
|
|
18
|
+
const userDoc = await userModel.findById(user).populate("roles");
|
|
19
|
+
if (userDoc && userDoc.roles) {
|
|
20
|
+
context.userDoc = userDoc;
|
|
21
|
+
userRoles = userDoc.roles.map(
|
|
22
|
+
(role) => typeof role === "string" ? role : role.name || role
|
|
23
|
+
);
|
|
24
|
+
}
|
|
25
|
+
const isAdmin = userRoles.includes("admin");
|
|
26
|
+
const isModerator = userRoles.includes("moderator");
|
|
27
|
+
if (isAdmin || isModerator) {
|
|
28
|
+
return {
|
|
29
|
+
allow: true,
|
|
30
|
+
force: true,
|
|
31
|
+
reason: isAdmin ? "ADMIN_ACCESS_GRANTED" : "MODERATOR_ACCESS_GRANTED"
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
return { allow: true, force: false };
|
|
35
|
+
} catch (error) {
|
|
36
|
+
console.error("Error in AdminModeratorPolicy:", error);
|
|
37
|
+
return { allow: true, force: false };
|
|
38
|
+
}
|
|
39
|
+
});
|
|
11
40
|
abacAccessControl.registerGlobalPolicy("PersonalResourceOwnerPolicy", async (context) => {
|
|
12
41
|
let { user, action, data, currentResource, options } = context;
|
|
13
42
|
const ObjectId = abacAccessControl.db.mongoose.Types.ObjectId;
|
|
14
|
-
if (action === "create" && data.owner
|
|
15
|
-
|
|
43
|
+
if (action === "create" && data.owner?.type === "user") {
|
|
44
|
+
if (data.owner.target === user && data.creator.target === user) {
|
|
45
|
+
return { allow: true, force: false };
|
|
46
|
+
} else {
|
|
47
|
+
return {
|
|
48
|
+
allow: false,
|
|
49
|
+
force: false,
|
|
50
|
+
reason: "UNAUTHORIZED_RESOURCE_CREATION"
|
|
51
|
+
};
|
|
52
|
+
}
|
|
16
53
|
}
|
|
17
54
|
if (action === "read") {
|
|
18
55
|
const allowedPublicStatuses = ["published", "active", "featured"];
|
|
@@ -22,26 +59,49 @@ function requireGlobals_policies() {
|
|
|
22
59
|
if (Array.isArray(context.req.query.status)) {
|
|
23
60
|
for (const queryStatus of context.req.query.status) {
|
|
24
61
|
if (!allowedPublicStatuses.includes(queryStatus)) {
|
|
25
|
-
return
|
|
62
|
+
return {
|
|
63
|
+
allow: false,
|
|
64
|
+
force: true,
|
|
65
|
+
// Стопроцентный запрет для неразрешенных статусов
|
|
66
|
+
reason: "UNAUTHORIZED_STATUS_ACCESS"
|
|
67
|
+
};
|
|
26
68
|
}
|
|
27
69
|
}
|
|
28
70
|
} else {
|
|
29
71
|
if (!allowedPublicStatuses.includes(context.req.query.status)) {
|
|
30
|
-
return
|
|
72
|
+
return {
|
|
73
|
+
allow: false,
|
|
74
|
+
force: true,
|
|
75
|
+
// Стопроцентный запрет для неразрешенных статусов
|
|
76
|
+
reason: "UNAUTHORIZED_STATUS_ACCESS"
|
|
77
|
+
};
|
|
31
78
|
}
|
|
32
79
|
}
|
|
33
80
|
}
|
|
34
81
|
}
|
|
35
82
|
if (currentResource && !allowedPublicStatuses.includes(currentResource.status)) {
|
|
36
|
-
return
|
|
83
|
+
return {
|
|
84
|
+
allow: false,
|
|
85
|
+
force: true,
|
|
86
|
+
// Стопроцентный запрет для неразрешенных статусов
|
|
87
|
+
reason: "UNAUTHORIZED_RESOURCE_ACCESS"
|
|
88
|
+
};
|
|
37
89
|
}
|
|
38
90
|
}
|
|
39
|
-
return true;
|
|
91
|
+
return { allow: true, force: false };
|
|
40
92
|
}
|
|
41
|
-
if ((action === "edit" || action === "delete") && currentResource && currentResource.owner
|
|
42
|
-
|
|
93
|
+
if ((action === "edit" || action === "delete") && currentResource && currentResource.owner?.type === "user") {
|
|
94
|
+
if (currentResource.creator.target.equals(new ObjectId(user))) {
|
|
95
|
+
return { allow: true, force: false };
|
|
96
|
+
} else {
|
|
97
|
+
return {
|
|
98
|
+
allow: false,
|
|
99
|
+
force: false,
|
|
100
|
+
reason: "NOT_RESOURCE_OWNER"
|
|
101
|
+
};
|
|
102
|
+
}
|
|
43
103
|
}
|
|
44
|
-
return true;
|
|
104
|
+
return { allow: true, force: false };
|
|
45
105
|
});
|
|
46
106
|
return abacAccessControl;
|
|
47
107
|
};
|
|
@@ -232,6 +232,37 @@ function requireGlobals_validator() {
|
|
|
232
232
|
});
|
|
233
233
|
return this;
|
|
234
234
|
}
|
|
235
|
+
/**
|
|
236
|
+
* Проверяет, что значение соответствует одному из указанных типов через уже существующие правила валидатора
|
|
237
|
+
* @param {string[]} types - Массив допустимых типов (например: ['string', 'number', 'null', 'array'])
|
|
238
|
+
* @param {string} [message] - Сообщение об ошибке
|
|
239
|
+
* @returns {Validator}
|
|
240
|
+
*/
|
|
241
|
+
oneOfTypes(types, message) {
|
|
242
|
+
const validators = types.map((type) => {
|
|
243
|
+
const schema = Validator.schema();
|
|
244
|
+
if (type === "string") return schema.string();
|
|
245
|
+
if (type === "number") return schema.number();
|
|
246
|
+
if (type === "integer") return schema.integer();
|
|
247
|
+
if (type === "boolean") return schema.boolean();
|
|
248
|
+
if (type === "array") return schema.array();
|
|
249
|
+
if (type === "object") return schema.object({});
|
|
250
|
+
if (type === "date") return schema.date();
|
|
251
|
+
if (type === "null") {
|
|
252
|
+
return Validator.schema().custom((val) => val === null, "Значение должно быть null");
|
|
253
|
+
}
|
|
254
|
+
throw new Error(`Unsupported type in oneOfTypes: ${type}`);
|
|
255
|
+
});
|
|
256
|
+
this.rules.push({
|
|
257
|
+
type: "oneOfTypes",
|
|
258
|
+
check: (value) => {
|
|
259
|
+
return validators.some((validator) => validator.validate(value).isValid);
|
|
260
|
+
},
|
|
261
|
+
param: types,
|
|
262
|
+
message
|
|
263
|
+
});
|
|
264
|
+
return this;
|
|
265
|
+
}
|
|
235
266
|
/**
|
|
236
267
|
* Добавляет пользовательскую проверку
|
|
237
268
|
* @param {function} fn - Функция проверки
|
|
@@ -369,6 +400,8 @@ function requireGlobals_validator() {
|
|
|
369
400
|
return `${context}должно быть корректным email-адресом`;
|
|
370
401
|
case "oneOf":
|
|
371
402
|
return `${context}должно быть одним из: ${rule.param.join(", ")}`;
|
|
403
|
+
case "oneOfTypes":
|
|
404
|
+
return `${context}должно быть одного из типов: ${rule.param.join(", ")}`;
|
|
372
405
|
case "custom":
|
|
373
406
|
return rule.param;
|
|
374
407
|
case "items":
|
|
@@ -550,6 +583,7 @@ function requireGlobals_verifier() {
|
|
|
550
583
|
if (Object.keys(result.verificationErrors).length === 0) {
|
|
551
584
|
result.verificationErrors = null;
|
|
552
585
|
}
|
|
586
|
+
console.log("Verification result:", result);
|
|
553
587
|
return result;
|
|
554
588
|
}
|
|
555
589
|
/**
|
|
@@ -233,6 +233,37 @@ function requireGlobals_validator() {
|
|
|
233
233
|
});
|
|
234
234
|
return this;
|
|
235
235
|
}
|
|
236
|
+
/**
|
|
237
|
+
* Проверяет, что значение соответствует одному из указанных типов через уже существующие правила валидатора
|
|
238
|
+
* @param {string[]} types - Массив допустимых типов (например: ['string', 'number', 'null', 'array'])
|
|
239
|
+
* @param {string} [message] - Сообщение об ошибке
|
|
240
|
+
* @returns {Validator}
|
|
241
|
+
*/
|
|
242
|
+
oneOfTypes(types, message) {
|
|
243
|
+
const validators = types.map((type) => {
|
|
244
|
+
const schema = Validator.schema();
|
|
245
|
+
if (type === "string") return schema.string();
|
|
246
|
+
if (type === "number") return schema.number();
|
|
247
|
+
if (type === "integer") return schema.integer();
|
|
248
|
+
if (type === "boolean") return schema.boolean();
|
|
249
|
+
if (type === "array") return schema.array();
|
|
250
|
+
if (type === "object") return schema.object({});
|
|
251
|
+
if (type === "date") return schema.date();
|
|
252
|
+
if (type === "null") {
|
|
253
|
+
return Validator.schema().custom((val) => val === null, "Значение должно быть null");
|
|
254
|
+
}
|
|
255
|
+
throw new Error(`Unsupported type in oneOfTypes: ${type}`);
|
|
256
|
+
});
|
|
257
|
+
this.rules.push({
|
|
258
|
+
type: "oneOfTypes",
|
|
259
|
+
check: (value) => {
|
|
260
|
+
return validators.some((validator) => validator.validate(value).isValid);
|
|
261
|
+
},
|
|
262
|
+
param: types,
|
|
263
|
+
message
|
|
264
|
+
});
|
|
265
|
+
return this;
|
|
266
|
+
}
|
|
236
267
|
/**
|
|
237
268
|
* Добавляет пользовательскую проверку
|
|
238
269
|
* @param {function} fn - Функция проверки
|
|
@@ -370,6 +401,8 @@ function requireGlobals_validator() {
|
|
|
370
401
|
return `${context}должно быть корректным email-адресом`;
|
|
371
402
|
case "oneOf":
|
|
372
403
|
return `${context}должно быть одним из: ${rule.param.join(", ")}`;
|
|
404
|
+
case "oneOfTypes":
|
|
405
|
+
return `${context}должно быть одного из типов: ${rule.param.join(", ")}`;
|
|
373
406
|
case "custom":
|
|
374
407
|
return rule.param;
|
|
375
408
|
case "items":
|
|
@@ -551,6 +584,7 @@ function requireGlobals_verifier() {
|
|
|
551
584
|
if (Object.keys(result.verificationErrors).length === 0) {
|
|
552
585
|
result.verificationErrors = null;
|
|
553
586
|
}
|
|
587
|
+
console.log("Verification result:", result);
|
|
554
588
|
return result;
|
|
555
589
|
}
|
|
556
590
|
/**
|
|
@@ -1,92 +1,13 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
const
|
|
3
|
-
const require$$0
|
|
4
|
-
const require$$0$
|
|
5
|
-
var authJwt;
|
|
6
|
-
var hasRequiredAuthJwt;
|
|
7
|
-
function requireAuthJwt() {
|
|
8
|
-
if (hasRequiredAuthJwt) return authJwt;
|
|
9
|
-
hasRequiredAuthJwt = 1;
|
|
10
|
-
const jwt = require$$0;
|
|
11
|
-
const middlewareFactory = (db) => {
|
|
12
|
-
const User = db.user;
|
|
13
|
-
const Role = db.role;
|
|
14
|
-
const verifyToken = (continueOnFail = false) => {
|
|
15
|
-
return async (req, res, next) => {
|
|
16
|
-
try {
|
|
17
|
-
let token = req.headers["x-access-token"];
|
|
18
|
-
if (!token && req.cookies.user) {
|
|
19
|
-
let user = JSON.parse(req.cookies.user);
|
|
20
|
-
token = user.accessToken;
|
|
21
|
-
}
|
|
22
|
-
if (req.headers["x-service-key"]) {
|
|
23
|
-
const serviceKey = req.headers["x-service-key"];
|
|
24
|
-
const validServiceKey = process.env.SERVICE_KEY;
|
|
25
|
-
if (serviceKey !== validServiceKey) {
|
|
26
|
-
return res.status(403).send({ message: "Unauthorized: Invalid service key" });
|
|
27
|
-
}
|
|
28
|
-
req.isServiceRequest = true;
|
|
29
|
-
return next();
|
|
30
|
-
}
|
|
31
|
-
if (!token) {
|
|
32
|
-
req.userId = null;
|
|
33
|
-
if (continueOnFail) {
|
|
34
|
-
return next();
|
|
35
|
-
} else {
|
|
36
|
-
return res.status(401).send({ message: "Unauthorized: No token provided" });
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
const decoded = jwt.verify(token, process.env.SECRET_KEY);
|
|
40
|
-
req.userId = decoded._id;
|
|
41
|
-
req.user = {
|
|
42
|
-
_id: decoded._id
|
|
43
|
-
};
|
|
44
|
-
next();
|
|
45
|
-
} catch (err) {
|
|
46
|
-
req.userId = null;
|
|
47
|
-
if (continueOnFail) {
|
|
48
|
-
next();
|
|
49
|
-
} else {
|
|
50
|
-
res.status(401).send({ message: "Unauthorized: Invalid token" });
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
};
|
|
54
|
-
};
|
|
55
|
-
const checkRole = (roleToCheck) => async (req, res, next) => {
|
|
56
|
-
try {
|
|
57
|
-
const user = await User.findById(req.userId).exec();
|
|
58
|
-
if (!user) {
|
|
59
|
-
return res.status(404).send({ message: "User Not found." });
|
|
60
|
-
}
|
|
61
|
-
const roles = await Role.find({ _id: { $in: user.roles } }).exec();
|
|
62
|
-
for (let role of roles) {
|
|
63
|
-
if (role.name === roleToCheck) {
|
|
64
|
-
next();
|
|
65
|
-
return;
|
|
66
|
-
}
|
|
67
|
-
}
|
|
68
|
-
res.status(403).send({ message: `Require ${roleToCheck} Role!` });
|
|
69
|
-
} catch (err) {
|
|
70
|
-
res.status(500).send({ message: err.message });
|
|
71
|
-
}
|
|
72
|
-
};
|
|
73
|
-
const isAdmin = checkRole("admin");
|
|
74
|
-
const isModerator = checkRole("moderator");
|
|
75
|
-
return {
|
|
76
|
-
verifyToken,
|
|
77
|
-
isAdmin,
|
|
78
|
-
isModerator
|
|
79
|
-
};
|
|
80
|
-
};
|
|
81
|
-
authJwt = middlewareFactory;
|
|
82
|
-
return authJwt;
|
|
83
|
-
}
|
|
2
|
+
const authJwt = require("./authJwt-CELQKF2s.js");
|
|
3
|
+
const require$$0 = require("crypto");
|
|
4
|
+
const require$$0$1 = require("mongodb");
|
|
84
5
|
var authSecret;
|
|
85
6
|
var hasRequiredAuthSecret;
|
|
86
7
|
function requireAuthSecret() {
|
|
87
8
|
if (hasRequiredAuthSecret) return authSecret;
|
|
88
9
|
hasRequiredAuthSecret = 1;
|
|
89
|
-
const crypto = require$$0
|
|
10
|
+
const crypto = require$$0;
|
|
90
11
|
const middlewareFactory = () => {
|
|
91
12
|
const verifySecret = (method, endpoint, secret) => async (req, res, next) => {
|
|
92
13
|
const requestSignature = req.headers.signature;
|
|
@@ -207,7 +128,7 @@ var hasRequiredVerifyInvites;
|
|
|
207
128
|
function requireVerifyInvites() {
|
|
208
129
|
if (hasRequiredVerifyInvites) return verifyInvites;
|
|
209
130
|
hasRequiredVerifyInvites = 1;
|
|
210
|
-
const { ObjectId } = require$$0$
|
|
131
|
+
const { ObjectId } = require$$0$1;
|
|
211
132
|
const middlewareFactory = (db) => {
|
|
212
133
|
const User = db.user;
|
|
213
134
|
const Invite = db.invite;
|
|
@@ -265,13 +186,13 @@ function requireMiddlewares() {
|
|
|
265
186
|
if (hasRequiredMiddlewares) return middlewares;
|
|
266
187
|
hasRequiredMiddlewares = 1;
|
|
267
188
|
const middlewareIndexFactory = (db) => {
|
|
268
|
-
const
|
|
189
|
+
const authJwt$1 = authJwt.requireAuthJwt()(db);
|
|
269
190
|
const authSecret2 = requireAuthSecret()();
|
|
270
191
|
const verifySignUp2 = requireVerifySignUp()(db);
|
|
271
192
|
const verifyUser2 = requireVerifyUser()(db);
|
|
272
193
|
const verifyInvites2 = requireVerifyInvites()(db);
|
|
273
194
|
return {
|
|
274
|
-
authJwt:
|
|
195
|
+
authJwt: authJwt$1,
|
|
275
196
|
authSecret: authSecret2,
|
|
276
197
|
verifySignUp: verifySignUp2,
|
|
277
198
|
verifyUser: verifyUser2,
|