@fiado/type-kit 3.88.0 → 3.89.0
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/_test_/unit/platformRbac/enums/__snapshots__/permissionBits.test.ts.snap +2 -1
- package/bin/platformRbac/dtos/AuthContext.d.ts +6 -0
- package/bin/platformRbac/dtos/CreateUserFieldRequest.d.ts +10 -0
- package/bin/platformRbac/dtos/CreateUserFieldRequest.js +54 -0
- package/bin/platformRbac/dtos/InjectableUserAttributesResponse.d.ts +5 -0
- package/bin/platformRbac/dtos/InjectableUserAttributesResponse.js +2 -0
- package/bin/platformRbac/dtos/UpdateUserFieldRequest.d.ts +8 -0
- package/bin/platformRbac/dtos/UpdateUserFieldRequest.js +51 -0
- package/bin/platformRbac/dtos/UserFieldDef.d.ts +19 -0
- package/bin/platformRbac/dtos/UserFieldDef.js +2 -0
- package/bin/platformRbac/enums/Permission.d.ts +1 -0
- package/bin/platformRbac/enums/Permission.js +5 -0
- package/bin/platformRbac/enums/UserFieldType.d.ts +5 -0
- package/bin/platformRbac/enums/UserFieldType.js +9 -0
- package/bin/platformRbac/index.d.ts +5 -0
- package/bin/platformRbac/index.js +9 -1
- package/package.json +1 -1
- package/src/platformRbac/dtos/AuthContext.ts +6 -0
- package/src/platformRbac/dtos/CreateUserFieldRequest.ts +13 -0
- package/src/platformRbac/dtos/InjectableUserAttributesResponse.ts +5 -0
- package/src/platformRbac/dtos/UpdateUserFieldRequest.ts +11 -0
- package/src/platformRbac/dtos/UserFieldDef.ts +20 -0
- package/src/platformRbac/enums/Permission.ts +5 -0
- package/src/platformRbac/enums/UserFieldType.ts +5 -0
- package/src/platformRbac/index.ts +11 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
// Jest Snapshot v1, https://jestjs.io/docs/snapshot-testing
|
|
2
2
|
|
|
3
|
-
exports[`PERMISSION_BIT_ORDER PERMS_VERSION es número estable 1`] = `
|
|
3
|
+
exports[`PERMISSION_BIT_ORDER PERMS_VERSION es número estable 1`] = `2577227741`;
|
|
4
4
|
|
|
5
5
|
exports[`PERMISSION_BIT_ORDER append-only: snapshot del ORDEN COMPLETO (rompe ante cualquier reorden/inserción) 1`] = `
|
|
6
6
|
[
|
|
@@ -120,5 +120,6 @@ exports[`PERMISSION_BIT_ORDER append-only: snapshot del ORDEN COMPLETO (rompe an
|
|
|
120
120
|
"agents.group.manage",
|
|
121
121
|
"agents.group.user.manage",
|
|
122
122
|
"agents.person.create",
|
|
123
|
+
"platform.tenant.userfields.manage",
|
|
123
124
|
]
|
|
124
125
|
`;
|
|
@@ -24,4 +24,10 @@ export interface AuthContext {
|
|
|
24
24
|
permVer?: number;
|
|
25
25
|
/** @deprecated DEC-RBAC-008: epoch de permisos. El authorizer ya no lo chequea. */
|
|
26
26
|
permsEpoch?: number;
|
|
27
|
+
/**
|
|
28
|
+
* Metadata de negocio por-usuario inyectada por jwt-inyector (campos personalizados del tenant
|
|
29
|
+
* marcados injectToToken). NO es autorización: NUNCA usar en un guard/decisión de acceso (DEC-RBAC-020).
|
|
30
|
+
* El gateway-adapter (buildAuthContextFromToken) parsea el claim JSON a este objeto.
|
|
31
|
+
*/
|
|
32
|
+
customAttributes?: Record<string, string>;
|
|
27
33
|
}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { UserFieldType } from '../enums/UserFieldType';
|
|
2
|
+
/** Body del POST /backoffice/tenants/{tenantId}/user-fields. La validación de `options` por `type` (no vacío si select) la hace el manager. */
|
|
3
|
+
export declare class CreateUserFieldRequest {
|
|
4
|
+
key: string;
|
|
5
|
+
label: string;
|
|
6
|
+
type: UserFieldType;
|
|
7
|
+
options?: string[];
|
|
8
|
+
required: boolean;
|
|
9
|
+
injectToToken: boolean;
|
|
10
|
+
}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.CreateUserFieldRequest = void 0;
|
|
13
|
+
const class_transformer_1 = require("class-transformer");
|
|
14
|
+
const class_validator_1 = require("class-validator");
|
|
15
|
+
const UserFieldType_1 = require("../enums/UserFieldType");
|
|
16
|
+
/** Body del POST /backoffice/tenants/{tenantId}/user-fields. La validación de `options` por `type` (no vacío si select) la hace el manager. */
|
|
17
|
+
class CreateUserFieldRequest {
|
|
18
|
+
}
|
|
19
|
+
exports.CreateUserFieldRequest = CreateUserFieldRequest;
|
|
20
|
+
__decorate([
|
|
21
|
+
(0, class_transformer_1.Expose)(),
|
|
22
|
+
(0, class_validator_1.IsString)(),
|
|
23
|
+
(0, class_validator_1.Matches)(/^[a-z][a-zA-Z0-9_]*$/, { message: 'key debe ser slug ^[a-z][a-zA-Z0-9_]*$' }),
|
|
24
|
+
__metadata("design:type", String)
|
|
25
|
+
], CreateUserFieldRequest.prototype, "key", void 0);
|
|
26
|
+
__decorate([
|
|
27
|
+
(0, class_transformer_1.Expose)(),
|
|
28
|
+
(0, class_validator_1.IsString)(),
|
|
29
|
+
(0, class_validator_1.MaxLength)(80),
|
|
30
|
+
__metadata("design:type", String)
|
|
31
|
+
], CreateUserFieldRequest.prototype, "label", void 0);
|
|
32
|
+
__decorate([
|
|
33
|
+
(0, class_transformer_1.Expose)(),
|
|
34
|
+
(0, class_validator_1.IsEnum)(UserFieldType_1.UserFieldType),
|
|
35
|
+
__metadata("design:type", String)
|
|
36
|
+
], CreateUserFieldRequest.prototype, "type", void 0);
|
|
37
|
+
__decorate([
|
|
38
|
+
(0, class_transformer_1.Expose)(),
|
|
39
|
+
(0, class_validator_1.IsOptional)(),
|
|
40
|
+
(0, class_validator_1.IsArray)(),
|
|
41
|
+
(0, class_validator_1.ArrayNotEmpty)(),
|
|
42
|
+
(0, class_validator_1.IsString)({ each: true }),
|
|
43
|
+
__metadata("design:type", Array)
|
|
44
|
+
], CreateUserFieldRequest.prototype, "options", void 0);
|
|
45
|
+
__decorate([
|
|
46
|
+
(0, class_transformer_1.Expose)(),
|
|
47
|
+
(0, class_validator_1.IsBoolean)(),
|
|
48
|
+
__metadata("design:type", Boolean)
|
|
49
|
+
], CreateUserFieldRequest.prototype, "required", void 0);
|
|
50
|
+
__decorate([
|
|
51
|
+
(0, class_transformer_1.Expose)(),
|
|
52
|
+
(0, class_validator_1.IsBoolean)(),
|
|
53
|
+
__metadata("design:type", Boolean)
|
|
54
|
+
], CreateUserFieldRequest.prototype, "injectToToken", void 0);
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
/** Respuesta del GET /internal/users/{cognitoSub}/injectable-attributes (consumida por jwt-inyector). */
|
|
2
|
+
export interface InjectableUserAttributesResponse {
|
|
3
|
+
/** Solo los campos injectToToken && enabled del tenant que tengan valor en el usuario. */
|
|
4
|
+
customAttributes: Record<string, string>;
|
|
5
|
+
}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/** Body del PATCH /backoffice/tenants/{tenantId}/user-fields/{key}. `key` y `type` NO son editables (inmutables, DEC-RBAC-016). */
|
|
2
|
+
export declare class UpdateUserFieldRequest {
|
|
3
|
+
label?: string;
|
|
4
|
+
options?: string[];
|
|
5
|
+
required?: boolean;
|
|
6
|
+
injectToToken?: boolean;
|
|
7
|
+
enabled?: boolean;
|
|
8
|
+
}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.UpdateUserFieldRequest = void 0;
|
|
13
|
+
const class_transformer_1 = require("class-transformer");
|
|
14
|
+
const class_validator_1 = require("class-validator");
|
|
15
|
+
/** Body del PATCH /backoffice/tenants/{tenantId}/user-fields/{key}. `key` y `type` NO son editables (inmutables, DEC-RBAC-016). */
|
|
16
|
+
class UpdateUserFieldRequest {
|
|
17
|
+
}
|
|
18
|
+
exports.UpdateUserFieldRequest = UpdateUserFieldRequest;
|
|
19
|
+
__decorate([
|
|
20
|
+
(0, class_transformer_1.Expose)(),
|
|
21
|
+
(0, class_validator_1.IsOptional)(),
|
|
22
|
+
(0, class_validator_1.IsString)(),
|
|
23
|
+
(0, class_validator_1.MaxLength)(80),
|
|
24
|
+
__metadata("design:type", String)
|
|
25
|
+
], UpdateUserFieldRequest.prototype, "label", void 0);
|
|
26
|
+
__decorate([
|
|
27
|
+
(0, class_transformer_1.Expose)(),
|
|
28
|
+
(0, class_validator_1.IsOptional)(),
|
|
29
|
+
(0, class_validator_1.IsArray)(),
|
|
30
|
+
(0, class_validator_1.ArrayNotEmpty)(),
|
|
31
|
+
(0, class_validator_1.IsString)({ each: true }),
|
|
32
|
+
__metadata("design:type", Array)
|
|
33
|
+
], UpdateUserFieldRequest.prototype, "options", void 0);
|
|
34
|
+
__decorate([
|
|
35
|
+
(0, class_transformer_1.Expose)(),
|
|
36
|
+
(0, class_validator_1.IsOptional)(),
|
|
37
|
+
(0, class_validator_1.IsBoolean)(),
|
|
38
|
+
__metadata("design:type", Boolean)
|
|
39
|
+
], UpdateUserFieldRequest.prototype, "required", void 0);
|
|
40
|
+
__decorate([
|
|
41
|
+
(0, class_transformer_1.Expose)(),
|
|
42
|
+
(0, class_validator_1.IsOptional)(),
|
|
43
|
+
(0, class_validator_1.IsBoolean)(),
|
|
44
|
+
__metadata("design:type", Boolean)
|
|
45
|
+
], UpdateUserFieldRequest.prototype, "injectToToken", void 0);
|
|
46
|
+
__decorate([
|
|
47
|
+
(0, class_transformer_1.Expose)(),
|
|
48
|
+
(0, class_validator_1.IsOptional)(),
|
|
49
|
+
(0, class_validator_1.IsBoolean)(),
|
|
50
|
+
__metadata("design:type", Boolean)
|
|
51
|
+
], UpdateUserFieldRequest.prototype, "enabled", void 0);
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import type { UserFieldType } from '../enums/UserFieldType';
|
|
2
|
+
/**
|
|
3
|
+
* Definición de un campo personalizado de usuario, embebida en PlatformTenantConfig.userFieldDefs.
|
|
4
|
+
* El `key` es inmutable (clave en el map de valores y en el claim). `enabled:false` = soft-disable.
|
|
5
|
+
* Timestamps inline: los setea el manager a mano (Dynamoose no mantiene sub-objetos inline). DEC-RBAC-016.
|
|
6
|
+
*/
|
|
7
|
+
export interface UserFieldDef {
|
|
8
|
+
key: string;
|
|
9
|
+
label: string;
|
|
10
|
+
type: UserFieldType;
|
|
11
|
+
options?: string[];
|
|
12
|
+
required: boolean;
|
|
13
|
+
injectToToken: boolean;
|
|
14
|
+
enabled: boolean;
|
|
15
|
+
createdAt: number;
|
|
16
|
+
updatedAt: number;
|
|
17
|
+
createdBy: string;
|
|
18
|
+
updatedBy: string;
|
|
19
|
+
}
|
|
@@ -51,6 +51,7 @@ export declare enum Permission {
|
|
|
51
51
|
PLATFORM_ROLE_UPDATE = "platform.role.update",
|
|
52
52
|
PLATFORM_ROLE_DELETE = "platform.role.delete",
|
|
53
53
|
PLATFORM_AUDIT_VIEW = "platform.audit.view",
|
|
54
|
+
PLATFORM_TENANT_USERFIELDS_MANAGE = "platform.tenant.userfields.manage",
|
|
54
55
|
TENANT_USER_CREATE = "tenant.user.create",
|
|
55
56
|
TENANT_USER_CREATE_LATERAL = "tenant.user.create.lateral",
|
|
56
57
|
TENANT_USER_READ = "tenant.user.read",
|
|
@@ -63,6 +63,7 @@ var Permission;
|
|
|
63
63
|
Permission["PLATFORM_ROLE_UPDATE"] = "platform.role.update";
|
|
64
64
|
Permission["PLATFORM_ROLE_DELETE"] = "platform.role.delete";
|
|
65
65
|
Permission["PLATFORM_AUDIT_VIEW"] = "platform.audit.view";
|
|
66
|
+
Permission["PLATFORM_TENANT_USERFIELDS_MANAGE"] = "platform.tenant.userfields.manage";
|
|
66
67
|
// ====================================================
|
|
67
68
|
// TENANT — operaciones dentro del silo de un tenant
|
|
68
69
|
// ====================================================
|
|
@@ -321,6 +322,10 @@ exports.PERMISSION_BIT_ORDER = [
|
|
|
321
322
|
// Append-only: nuevo permiso agregado 2026-06-18 (DEC-A2-02). Va al FINAL para no correr los bits
|
|
322
323
|
// existentes (PERMS_VERSION cambia, pero los índices previos se conservan).
|
|
323
324
|
Permission.AGENTS_PERSON_CREATE,
|
|
325
|
+
// Append-only 2026-06-18 (DEC-RBAC-017): catálogo de campos personalizados por tenant. Al FINAL para
|
|
326
|
+
// no correr bits existentes. (El bitset está deprecado por token-flaco, pero el orden se mantiene
|
|
327
|
+
// sincronizado con el enum para que el test de bits no rompa.)
|
|
328
|
+
Permission.PLATFORM_TENANT_USERFIELDS_MANAGE,
|
|
324
329
|
];
|
|
325
330
|
function djb2(input) {
|
|
326
331
|
let h = 5381;
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.UserFieldType = void 0;
|
|
4
|
+
/** Tipo de un campo personalizado de usuario. text = texto libre; select = lista cerrada de opciones. */
|
|
5
|
+
var UserFieldType;
|
|
6
|
+
(function (UserFieldType) {
|
|
7
|
+
UserFieldType["TEXT"] = "text";
|
|
8
|
+
UserFieldType["SELECT"] = "select";
|
|
9
|
+
})(UserFieldType || (exports.UserFieldType = UserFieldType = {}));
|
|
@@ -29,3 +29,8 @@ export type { CreateTenantResponse } from './dtos/CreateTenantResponse';
|
|
|
29
29
|
export * from './dtos/UpdateTenantSecurityPolicyRequest';
|
|
30
30
|
export type { TenantSecurityPolicyResponse } from './dtos/TenantSecurityPolicyResponse';
|
|
31
31
|
export { TenantType, TENANT_TYPES, levelsOf, tableSuffixForLevel, scopeRankOrder } from './tenantTypes';
|
|
32
|
+
export { UserFieldType } from './enums/UserFieldType';
|
|
33
|
+
export type { UserFieldDef } from './dtos/UserFieldDef';
|
|
34
|
+
export * from './dtos/CreateUserFieldRequest';
|
|
35
|
+
export * from './dtos/UpdateUserFieldRequest';
|
|
36
|
+
export type { InjectableUserAttributesResponse } from './dtos/InjectableUserAttributesResponse';
|
|
@@ -23,7 +23,7 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
23
23
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
24
24
|
};
|
|
25
25
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
26
|
-
exports.scopeRankOrder = exports.tableSuffixForLevel = exports.levelsOf = exports.TENANT_TYPES = exports.TenantType = exports.AuthorizeDenyReason = exports.PermissionCategory = exports.PermissionScope = exports.bitsToPermissions = exports.permissionsToBits = exports.PERMS_VERSION = exports.PERMISSION_BIT_ORDER = exports.Permission = void 0;
|
|
26
|
+
exports.UserFieldType = exports.scopeRankOrder = exports.tableSuffixForLevel = exports.levelsOf = exports.TENANT_TYPES = exports.TenantType = exports.AuthorizeDenyReason = exports.PermissionCategory = exports.PermissionScope = exports.bitsToPermissions = exports.permissionsToBits = exports.PERMS_VERSION = exports.PERMISSION_BIT_ORDER = exports.Permission = void 0;
|
|
27
27
|
var Permission_1 = require("./enums/Permission");
|
|
28
28
|
Object.defineProperty(exports, "Permission", { enumerable: true, get: function () { return Permission_1.Permission; } });
|
|
29
29
|
Object.defineProperty(exports, "PERMISSION_BIT_ORDER", { enumerable: true, get: function () { return Permission_1.PERMISSION_BIT_ORDER; } });
|
|
@@ -73,3 +73,11 @@ Object.defineProperty(exports, "TENANT_TYPES", { enumerable: true, get: function
|
|
|
73
73
|
Object.defineProperty(exports, "levelsOf", { enumerable: true, get: function () { return tenantTypes_1.levelsOf; } });
|
|
74
74
|
Object.defineProperty(exports, "tableSuffixForLevel", { enumerable: true, get: function () { return tenantTypes_1.tableSuffixForLevel; } });
|
|
75
75
|
Object.defineProperty(exports, "scopeRankOrder", { enumerable: true, get: function () { return tenantTypes_1.scopeRankOrder; } });
|
|
76
|
+
// Campos personalizados de usuario por tenant — embebidos en PlatformTenantConfig.userFieldDefs.
|
|
77
|
+
// UserFieldType es enum (export de valor); UserFieldDef es interface plain (type-only).
|
|
78
|
+
var UserFieldType_1 = require("./enums/UserFieldType");
|
|
79
|
+
Object.defineProperty(exports, "UserFieldType", { enumerable: true, get: function () { return UserFieldType_1.UserFieldType; } });
|
|
80
|
+
// DTOs de endpoints user-fields. Create/Update Request llevan decoradores class-validator → export de valor.
|
|
81
|
+
// InjectableUserAttributesResponse es interface plain (consumida por jwt-inyector) → type-only.
|
|
82
|
+
__exportStar(require("./dtos/CreateUserFieldRequest"), exports);
|
|
83
|
+
__exportStar(require("./dtos/UpdateUserFieldRequest"), exports);
|
package/package.json
CHANGED
|
@@ -25,4 +25,10 @@ export interface AuthContext {
|
|
|
25
25
|
permVer?: number;
|
|
26
26
|
/** @deprecated DEC-RBAC-008: epoch de permisos. El authorizer ya no lo chequea. */
|
|
27
27
|
permsEpoch?: number;
|
|
28
|
+
/**
|
|
29
|
+
* Metadata de negocio por-usuario inyectada por jwt-inyector (campos personalizados del tenant
|
|
30
|
+
* marcados injectToToken). NO es autorización: NUNCA usar en un guard/decisión de acceso (DEC-RBAC-020).
|
|
31
|
+
* El gateway-adapter (buildAuthContextFromToken) parsea el claim JSON a este objeto.
|
|
32
|
+
*/
|
|
33
|
+
customAttributes?: Record<string, string>;
|
|
28
34
|
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { Expose } from 'class-transformer';
|
|
2
|
+
import { ArrayNotEmpty, IsArray, IsBoolean, IsEnum, IsOptional, IsString, Matches, MaxLength } from 'class-validator';
|
|
3
|
+
import { UserFieldType } from '../enums/UserFieldType';
|
|
4
|
+
|
|
5
|
+
/** Body del POST /backoffice/tenants/{tenantId}/user-fields. La validación de `options` por `type` (no vacío si select) la hace el manager. */
|
|
6
|
+
export class CreateUserFieldRequest {
|
|
7
|
+
@Expose() @IsString() @Matches(/^[a-z][a-zA-Z0-9_]*$/, { message: 'key debe ser slug ^[a-z][a-zA-Z0-9_]*$' }) key!: string;
|
|
8
|
+
@Expose() @IsString() @MaxLength(80) label!: string;
|
|
9
|
+
@Expose() @IsEnum(UserFieldType) type!: UserFieldType;
|
|
10
|
+
@Expose() @IsOptional() @IsArray() @ArrayNotEmpty() @IsString({ each: true }) options?: string[];
|
|
11
|
+
@Expose() @IsBoolean() required!: boolean;
|
|
12
|
+
@Expose() @IsBoolean() injectToToken!: boolean;
|
|
13
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
/** Respuesta del GET /internal/users/{cognitoSub}/injectable-attributes (consumida por jwt-inyector). */
|
|
2
|
+
export interface InjectableUserAttributesResponse {
|
|
3
|
+
/** Solo los campos injectToToken && enabled del tenant que tengan valor en el usuario. */
|
|
4
|
+
customAttributes: Record<string, string>;
|
|
5
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { Expose } from 'class-transformer';
|
|
2
|
+
import { ArrayNotEmpty, IsArray, IsBoolean, IsOptional, IsString, MaxLength } from 'class-validator';
|
|
3
|
+
|
|
4
|
+
/** Body del PATCH /backoffice/tenants/{tenantId}/user-fields/{key}. `key` y `type` NO son editables (inmutables, DEC-RBAC-016). */
|
|
5
|
+
export class UpdateUserFieldRequest {
|
|
6
|
+
@Expose() @IsOptional() @IsString() @MaxLength(80) label?: string;
|
|
7
|
+
@Expose() @IsOptional() @IsArray() @ArrayNotEmpty() @IsString({ each: true }) options?: string[];
|
|
8
|
+
@Expose() @IsOptional() @IsBoolean() required?: boolean;
|
|
9
|
+
@Expose() @IsOptional() @IsBoolean() injectToToken?: boolean;
|
|
10
|
+
@Expose() @IsOptional() @IsBoolean() enabled?: boolean;
|
|
11
|
+
}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { UserFieldType } from '../enums/UserFieldType';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Definición de un campo personalizado de usuario, embebida en PlatformTenantConfig.userFieldDefs.
|
|
5
|
+
* El `key` es inmutable (clave en el map de valores y en el claim). `enabled:false` = soft-disable.
|
|
6
|
+
* Timestamps inline: los setea el manager a mano (Dynamoose no mantiene sub-objetos inline). DEC-RBAC-016.
|
|
7
|
+
*/
|
|
8
|
+
export interface UserFieldDef {
|
|
9
|
+
key: string;
|
|
10
|
+
label: string;
|
|
11
|
+
type: UserFieldType;
|
|
12
|
+
options?: string[];
|
|
13
|
+
required: boolean;
|
|
14
|
+
injectToToken: boolean;
|
|
15
|
+
enabled: boolean;
|
|
16
|
+
createdAt: number;
|
|
17
|
+
updatedAt: number;
|
|
18
|
+
createdBy: string;
|
|
19
|
+
updatedBy: string;
|
|
20
|
+
}
|
|
@@ -58,6 +58,7 @@ export enum Permission {
|
|
|
58
58
|
PLATFORM_ROLE_UPDATE = 'platform.role.update',
|
|
59
59
|
PLATFORM_ROLE_DELETE = 'platform.role.delete',
|
|
60
60
|
PLATFORM_AUDIT_VIEW = 'platform.audit.view',
|
|
61
|
+
PLATFORM_TENANT_USERFIELDS_MANAGE = 'platform.tenant.userfields.manage',
|
|
61
62
|
|
|
62
63
|
// ====================================================
|
|
63
64
|
// TENANT — operaciones dentro del silo de un tenant
|
|
@@ -323,6 +324,10 @@ export const PERMISSION_BIT_ORDER: readonly Permission[] = [
|
|
|
323
324
|
// Append-only: nuevo permiso agregado 2026-06-18 (DEC-A2-02). Va al FINAL para no correr los bits
|
|
324
325
|
// existentes (PERMS_VERSION cambia, pero los índices previos se conservan).
|
|
325
326
|
Permission.AGENTS_PERSON_CREATE,
|
|
327
|
+
// Append-only 2026-06-18 (DEC-RBAC-017): catálogo de campos personalizados por tenant. Al FINAL para
|
|
328
|
+
// no correr bits existentes. (El bitset está deprecado por token-flaco, pero el orden se mantiene
|
|
329
|
+
// sincronizado con el enum para que el test de bits no rompa.)
|
|
330
|
+
Permission.PLATFORM_TENANT_USERFIELDS_MANAGE,
|
|
326
331
|
] as const;
|
|
327
332
|
|
|
328
333
|
function djb2(input: string): number {
|
|
@@ -62,3 +62,14 @@ export type { TenantSecurityPolicyResponse } from './dtos/TenantSecurityPolicyRe
|
|
|
62
62
|
// Consumido por ScopeValidationService._rank vía scopeRankOrder() y por los seeds.
|
|
63
63
|
// Accesible bajo el namespace PlatformRbac (el index raíz hace export * as PlatformRbac).
|
|
64
64
|
export { TenantType, TENANT_TYPES, levelsOf, tableSuffixForLevel, scopeRankOrder } from './tenantTypes';
|
|
65
|
+
|
|
66
|
+
// Campos personalizados de usuario por tenant — embebidos en PlatformTenantConfig.userFieldDefs.
|
|
67
|
+
// UserFieldType es enum (export de valor); UserFieldDef es interface plain (type-only).
|
|
68
|
+
export { UserFieldType } from './enums/UserFieldType';
|
|
69
|
+
export type { UserFieldDef } from './dtos/UserFieldDef';
|
|
70
|
+
|
|
71
|
+
// DTOs de endpoints user-fields. Create/Update Request llevan decoradores class-validator → export de valor.
|
|
72
|
+
// InjectableUserAttributesResponse es interface plain (consumida por jwt-inyector) → type-only.
|
|
73
|
+
export * from './dtos/CreateUserFieldRequest';
|
|
74
|
+
export * from './dtos/UpdateUserFieldRequest';
|
|
75
|
+
export type { InjectableUserAttributesResponse } from './dtos/InjectableUserAttributesResponse';
|