chainlesschain 0.143.0 → 0.152.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/package.json +1 -1
- package/src/commands/a2a.js +196 -28
- package/src/commands/activitypub.js +364 -27
- package/src/commands/agent-network.js +217 -0
- package/src/commands/agent.js +587 -103
- package/src/commands/audit.js +206 -0
- package/src/commands/automation.js +201 -0
- package/src/commands/bi.js +355 -27
- package/src/commands/bm25.js +111 -27
- package/src/commands/browse.js +403 -29
- package/src/commands/ccron.js +128 -28
- package/src/commands/chat.js +207 -0
- package/src/commands/codegen.js +207 -0
- package/src/commands/collab.js +211 -0
- package/src/commands/compliance.js +824 -34
- package/src/commands/compt.js +127 -29
- package/src/commands/consol.js +8 -2
- package/src/commands/cowork.js +783 -34
- package/src/commands/crosschain.js +182 -28
- package/src/commands/dao.js +182 -28
- package/src/commands/dbevo.js +227 -0
- package/src/commands/dev.js +207 -0
- package/src/commands/did-v2.js +217 -0
- package/src/commands/did.js +221 -0
- package/src/commands/dlp.js +385 -27
- package/src/commands/economy.js +205 -50
- package/src/commands/evolution.js +203 -50
- package/src/commands/evomap.js +387 -27
- package/src/commands/export.js +213 -0
- package/src/commands/federation.js +209 -0
- package/src/commands/fflag.js +74 -22
- package/src/commands/fusion.js +205 -0
- package/src/commands/git.js +177 -37
- package/src/commands/governance.js +209 -0
- package/src/commands/hardening.js +209 -0
- package/src/commands/hmemory.js +204 -50
- package/src/commands/hook.js +209 -0
- package/src/commands/import.js +209 -0
- package/src/commands/incentive.js +209 -0
- package/src/commands/inference.js +170 -34
- package/src/commands/infra.js +203 -0
- package/src/commands/instinct.js +209 -0
- package/src/commands/ipfs.js +207 -0
- package/src/commands/itbudget.js +149 -33
- package/src/commands/kg.js +206 -0
- package/src/commands/llm.js +217 -0
- package/src/commands/lowcode.js +195 -38
- package/src/commands/marketplace.js +206 -0
- package/src/commands/matrix.js +386 -27
- package/src/commands/mcp.js +217 -0
- package/src/commands/mcpscaf.js +145 -33
- package/src/commands/meminj.js +145 -33
- package/src/commands/memory.js +209 -0
- package/src/commands/multimodal.js +203 -0
- package/src/commands/nlprog.js +225 -0
- package/src/commands/nostr.js +387 -27
- package/src/commands/note.js +205 -0
- package/src/commands/ops.js +219 -0
- package/src/commands/orchestrate.js +217 -0
- package/src/commands/orchgov.js +144 -33
- package/src/commands/org.js +209 -0
- package/src/commands/p2p.js +209 -0
- package/src/commands/pdfp.js +109 -27
- package/src/commands/perception.js +209 -0
- package/src/commands/perf.js +169 -32
- package/src/commands/perm.js +144 -33
- package/src/commands/permmem.js +203 -0
- package/src/commands/pipeline.js +207 -52
- package/src/commands/planmode.js +141 -32
- package/src/commands/plugin-ecosystem.js +209 -0
- package/src/commands/pqc.js +213 -0
- package/src/commands/privacy.js +203 -0
- package/src/commands/promcomp.js +111 -27
- package/src/commands/quantization.js +207 -0
- package/src/commands/rcache.js +205 -0
- package/src/commands/recommend.js +410 -34
- package/src/commands/reputation.js +208 -0
- package/src/commands/runtime.js +205 -0
- package/src/commands/sandbox.js +206 -0
- package/src/commands/scim.js +209 -0
- package/src/commands/seshhook.js +145 -33
- package/src/commands/seshsearch.js +141 -33
- package/src/commands/seshtail.js +144 -33
- package/src/commands/seshu.js +152 -33
- package/src/commands/session.js +209 -0
- package/src/commands/sganal.js +123 -29
- package/src/commands/siem.js +201 -34
- package/src/commands/skill.js +207 -0
- package/src/commands/sla.js +212 -0
- package/src/commands/slotfill.js +146 -33
- package/src/commands/social.js +358 -32
- package/src/commands/sso.js +209 -0
- package/src/commands/stress.js +206 -0
- package/src/commands/svccont.js +145 -33
- package/src/commands/sync.js +209 -0
- package/src/commands/tech.js +209 -0
- package/src/commands/tenant.js +217 -0
- package/src/commands/terraform.js +206 -0
- package/src/commands/tms.js +171 -33
- package/src/commands/tokens.js +209 -0
- package/src/commands/topiccls.js +146 -33
- package/src/commands/trust.js +217 -0
- package/src/commands/uprof.js +141 -32
- package/src/commands/vcheck.js +122 -28
- package/src/commands/wallet.js +209 -0
- package/src/commands/webfetch.js +141 -32
- package/src/commands/workflow.js +203 -0
- package/src/commands/zkp.js +184 -28
- package/src/index.js +180 -0
- package/src/lib/a2a-protocol.js +319 -51
- package/src/lib/activitypub-bridge.js +622 -50
- package/src/lib/agent-economy.js +304 -51
- package/src/lib/agent-network.js +341 -0
- package/src/lib/aiops.js +346 -0
- package/src/lib/app-builder.js +279 -46
- package/src/lib/audit-logger.js +321 -0
- package/src/lib/automation-engine.js +335 -0
- package/src/lib/autonomous-agent.js +284 -48
- package/src/lib/autonomous-developer.js +332 -0
- package/src/lib/bi-engine.js +616 -49
- package/src/lib/bm25-search.js +301 -49
- package/src/lib/browser-automation.js +630 -49
- package/src/lib/chat-core.js +336 -0
- package/src/lib/claude-code-bridge.js +341 -0
- package/src/lib/code-agent.js +339 -0
- package/src/lib/collaboration-governance.js +334 -0
- package/src/lib/community-governance.js +346 -0
- package/src/lib/compliance-framework-reporter.js +305 -51
- package/src/lib/compliance-manager.js +330 -0
- package/src/lib/compression-telemetry.js +301 -49
- package/src/lib/content-recommendation.js +351 -0
- package/src/lib/content-recommender.js +317 -52
- package/src/lib/cowork-cron.js +298 -49
- package/src/lib/cowork-learning.js +333 -0
- package/src/lib/cowork-share.js +338 -0
- package/src/lib/cowork-task-runner.js +308 -51
- package/src/lib/cowork-workflow.js +327 -0
- package/src/lib/cross-chain.js +311 -51
- package/src/lib/dao-governance.js +280 -46
- package/src/lib/dbevo.js +351 -0
- package/src/lib/decentral-infra.js +330 -0
- package/src/lib/did-manager.js +341 -0
- package/src/lib/did-v2-manager.js +341 -0
- package/src/lib/dlp-engine.js +626 -49
- package/src/lib/evolution-system.js +278 -47
- package/src/lib/evomap-governance.js +334 -0
- package/src/lib/evomap-manager.js +280 -46
- package/src/lib/execution-backend.js +294 -48
- package/src/lib/feature-flags.js +294 -49
- package/src/lib/federation-hardening.js +340 -0
- package/src/lib/git-integration.js +285 -47
- package/src/lib/hardening-manager.js +341 -0
- package/src/lib/hierarchical-memory.js +284 -48
- package/src/lib/hook-manager.js +341 -0
- package/src/lib/inference-network.js +308 -51
- package/src/lib/instinct-manager.js +346 -0
- package/src/lib/ipfs-storage.js +334 -0
- package/src/lib/iteration-budget.js +302 -50
- package/src/lib/knowledge-exporter.js +341 -0
- package/src/lib/knowledge-graph.js +333 -0
- package/src/lib/knowledge-importer.js +341 -0
- package/src/lib/llm-providers.js +346 -0
- package/src/lib/matrix-bridge.js +620 -47
- package/src/lib/mcp-registry.js +346 -0
- package/src/lib/mcp-scaffold.js +318 -54
- package/src/lib/memory-injection.js +288 -49
- package/src/lib/memory-manager.js +336 -0
- package/src/lib/multimodal.js +330 -0
- package/src/lib/nl-programming.js +341 -0
- package/src/lib/nostr-bridge.js +622 -49
- package/src/lib/note-versioning.js +339 -0
- package/src/lib/orchestrator.js +293 -48
- package/src/lib/org-manager.js +336 -0
- package/src/lib/p2p-manager.js +341 -0
- package/src/lib/pdf-parser.js +298 -49
- package/src/lib/perception.js +346 -0
- package/src/lib/perf-tuning.js +309 -50
- package/src/lib/permanent-memory.js +327 -0
- package/src/lib/permission-engine.js +287 -49
- package/src/lib/pipeline-orchestrator.js +289 -49
- package/src/lib/plan-mode.js +298 -51
- package/src/lib/plugin-ecosystem.js +346 -0
- package/src/lib/pqc-manager.js +346 -0
- package/src/lib/privacy-computing.js +335 -0
- package/src/lib/protocol-fusion.js +338 -0
- package/src/lib/quantization.js +337 -0
- package/src/lib/reputation-optimizer.js +340 -0
- package/src/lib/response-cache.js +333 -0
- package/src/lib/sandbox-v2.js +327 -0
- package/src/lib/scim-manager.js +346 -0
- package/src/lib/service-container.js +313 -52
- package/src/lib/session-consolidator.js +296 -49
- package/src/lib/session-hooks.js +312 -53
- package/src/lib/session-manager.js +334 -0
- package/src/lib/session-search.js +304 -51
- package/src/lib/session-tail.js +288 -49
- package/src/lib/session-usage.js +298 -52
- package/src/lib/siem-exporter.js +298 -51
- package/src/lib/skill-loader.js +334 -0
- package/src/lib/skill-marketplace.js +345 -0
- package/src/lib/sla-manager.js +341 -0
- package/src/lib/slot-filler.js +303 -51
- package/src/lib/social-graph-analytics.js +295 -49
- package/src/lib/social-graph.js +272 -49
- package/src/lib/social-manager.js +330 -0
- package/src/lib/sso-manager.js +340 -0
- package/src/lib/stress-tester.js +342 -0
- package/src/lib/sub-agent-registry.js +302 -53
- package/src/lib/sync-manager.js +336 -0
- package/src/lib/task-model-selector.js +302 -50
- package/src/lib/tech-learning-engine.js +341 -0
- package/src/lib/tenant-saas.js +341 -0
- package/src/lib/terraform-manager.js +333 -0
- package/src/lib/threat-intel.js +330 -0
- package/src/lib/todo-manager.js +281 -47
- package/src/lib/token-incentive.js +341 -0
- package/src/lib/token-tracker.js +336 -0
- package/src/lib/topic-classifier.js +297 -49
- package/src/lib/trust-security.js +343 -0
- package/src/lib/ueba.js +340 -0
- package/src/lib/universal-runtime.js +330 -0
- package/src/lib/user-profile.js +294 -50
- package/src/lib/version-checker.js +304 -50
- package/src/lib/wallet-manager.js +336 -0
- package/src/lib/web-fetch.js +292 -51
- package/src/lib/workflow-engine.js +330 -0
- package/src/lib/zkp-engine.js +286 -49
package/src/lib/dlp-engine.js
CHANGED
|
@@ -692,25 +692,50 @@ export function getHighestUnresolvedSeverity() {
|
|
|
692
692
|
|
|
693
693
|
export { _v2PolicyMeta, _v2IncidentMeta, _builtinPolicyTemplates };
|
|
694
694
|
|
|
695
|
-
|
|
696
695
|
// ===== V2 Surface: DLP Engine governance overlay (CLI v0.135.0) =====
|
|
697
696
|
export const DLP_POLICY_MATURITY_V2 = Object.freeze({
|
|
698
|
-
PENDING: "pending",
|
|
697
|
+
PENDING: "pending",
|
|
698
|
+
ACTIVE: "active",
|
|
699
|
+
SUSPENDED: "suspended",
|
|
700
|
+
RETIRED: "retired",
|
|
699
701
|
});
|
|
700
702
|
export const DLP_SCAN_LIFECYCLE_V2 = Object.freeze({
|
|
701
|
-
QUEUED: "queued",
|
|
703
|
+
QUEUED: "queued",
|
|
704
|
+
SCANNING: "scanning",
|
|
705
|
+
COMPLETED: "completed",
|
|
706
|
+
FAILED: "failed",
|
|
707
|
+
CANCELLED: "cancelled",
|
|
702
708
|
});
|
|
703
709
|
|
|
704
710
|
const _dlpPolTrans = new Map([
|
|
705
|
-
[
|
|
706
|
-
|
|
707
|
-
|
|
711
|
+
[
|
|
712
|
+
DLP_POLICY_MATURITY_V2.PENDING,
|
|
713
|
+
new Set([DLP_POLICY_MATURITY_V2.ACTIVE, DLP_POLICY_MATURITY_V2.RETIRED]),
|
|
714
|
+
],
|
|
715
|
+
[
|
|
716
|
+
DLP_POLICY_MATURITY_V2.ACTIVE,
|
|
717
|
+
new Set([DLP_POLICY_MATURITY_V2.SUSPENDED, DLP_POLICY_MATURITY_V2.RETIRED]),
|
|
718
|
+
],
|
|
719
|
+
[
|
|
720
|
+
DLP_POLICY_MATURITY_V2.SUSPENDED,
|
|
721
|
+
new Set([DLP_POLICY_MATURITY_V2.ACTIVE, DLP_POLICY_MATURITY_V2.RETIRED]),
|
|
722
|
+
],
|
|
708
723
|
[DLP_POLICY_MATURITY_V2.RETIRED, new Set()],
|
|
709
724
|
]);
|
|
710
725
|
const _dlpPolTerminal = new Set([DLP_POLICY_MATURITY_V2.RETIRED]);
|
|
711
726
|
const _dlpScanTrans = new Map([
|
|
712
|
-
[
|
|
713
|
-
|
|
727
|
+
[
|
|
728
|
+
DLP_SCAN_LIFECYCLE_V2.QUEUED,
|
|
729
|
+
new Set([DLP_SCAN_LIFECYCLE_V2.SCANNING, DLP_SCAN_LIFECYCLE_V2.CANCELLED]),
|
|
730
|
+
],
|
|
731
|
+
[
|
|
732
|
+
DLP_SCAN_LIFECYCLE_V2.SCANNING,
|
|
733
|
+
new Set([
|
|
734
|
+
DLP_SCAN_LIFECYCLE_V2.COMPLETED,
|
|
735
|
+
DLP_SCAN_LIFECYCLE_V2.FAILED,
|
|
736
|
+
DLP_SCAN_LIFECYCLE_V2.CANCELLED,
|
|
737
|
+
]),
|
|
738
|
+
],
|
|
714
739
|
[DLP_SCAN_LIFECYCLE_V2.COMPLETED, new Set()],
|
|
715
740
|
[DLP_SCAN_LIFECYCLE_V2.FAILED, new Set()],
|
|
716
741
|
[DLP_SCAN_LIFECYCLE_V2.CANCELLED, new Set()],
|
|
@@ -723,76 +748,628 @@ let _dlpMaxPendingPerPol = 20;
|
|
|
723
748
|
let _dlpPolIdleMs = 12 * 60 * 60 * 1000;
|
|
724
749
|
let _dlpScanStuckMs = 5 * 60 * 1000;
|
|
725
750
|
|
|
726
|
-
function _dlpPos(n, lbl) {
|
|
751
|
+
function _dlpPos(n, lbl) {
|
|
752
|
+
const v = Math.floor(Number(n));
|
|
753
|
+
if (!Number.isFinite(v) || v <= 0)
|
|
754
|
+
throw new Error(`${lbl} must be positive integer`);
|
|
755
|
+
return v;
|
|
756
|
+
}
|
|
727
757
|
|
|
728
|
-
export function setMaxActiveDlpPoliciesPerOwnerV2(n) {
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
export function
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
export function
|
|
735
|
-
|
|
758
|
+
export function setMaxActiveDlpPoliciesPerOwnerV2(n) {
|
|
759
|
+
_dlpMaxActivePerOwner = _dlpPos(n, "maxActiveDlpPoliciesPerOwner");
|
|
760
|
+
}
|
|
761
|
+
export function getMaxActiveDlpPoliciesPerOwnerV2() {
|
|
762
|
+
return _dlpMaxActivePerOwner;
|
|
763
|
+
}
|
|
764
|
+
export function setMaxPendingDlpScansPerPolicyV2(n) {
|
|
765
|
+
_dlpMaxPendingPerPol = _dlpPos(n, "maxPendingDlpScansPerPolicy");
|
|
766
|
+
}
|
|
767
|
+
export function getMaxPendingDlpScansPerPolicyV2() {
|
|
768
|
+
return _dlpMaxPendingPerPol;
|
|
769
|
+
}
|
|
770
|
+
export function setDlpPolicyIdleMsV2(n) {
|
|
771
|
+
_dlpPolIdleMs = _dlpPos(n, "dlpPolicyIdleMs");
|
|
772
|
+
}
|
|
773
|
+
export function getDlpPolicyIdleMsV2() {
|
|
774
|
+
return _dlpPolIdleMs;
|
|
775
|
+
}
|
|
776
|
+
export function setDlpScanStuckMsV2(n) {
|
|
777
|
+
_dlpScanStuckMs = _dlpPos(n, "dlpScanStuckMs");
|
|
778
|
+
}
|
|
779
|
+
export function getDlpScanStuckMsV2() {
|
|
780
|
+
return _dlpScanStuckMs;
|
|
781
|
+
}
|
|
736
782
|
|
|
737
783
|
export function _resetStateDlpEngineV2() {
|
|
738
|
-
_dlpPols.clear();
|
|
739
|
-
|
|
740
|
-
|
|
784
|
+
_dlpPols.clear();
|
|
785
|
+
_dlpScans.clear();
|
|
786
|
+
_dlpMaxActivePerOwner = 16;
|
|
787
|
+
_dlpMaxPendingPerPol = 20;
|
|
788
|
+
_dlpPolIdleMs = 12 * 60 * 60 * 1000;
|
|
789
|
+
_dlpScanStuckMs = 5 * 60 * 1000;
|
|
741
790
|
}
|
|
742
791
|
|
|
743
|
-
export function registerDlpPolicyV2({
|
|
792
|
+
export function registerDlpPolicyV2({
|
|
793
|
+
id,
|
|
794
|
+
owner,
|
|
795
|
+
classification,
|
|
796
|
+
metadata,
|
|
797
|
+
} = {}) {
|
|
744
798
|
if (!id || typeof id !== "string") throw new Error("id is required");
|
|
745
799
|
if (!owner || typeof owner !== "string") throw new Error("owner is required");
|
|
746
800
|
if (_dlpPols.has(id)) throw new Error(`dlp policy ${id} already registered`);
|
|
747
801
|
const now = Date.now();
|
|
748
|
-
const p = {
|
|
802
|
+
const p = {
|
|
803
|
+
id,
|
|
804
|
+
owner,
|
|
805
|
+
classification: classification || "internal",
|
|
806
|
+
status: DLP_POLICY_MATURITY_V2.PENDING,
|
|
807
|
+
createdAt: now,
|
|
808
|
+
updatedAt: now,
|
|
809
|
+
activatedAt: null,
|
|
810
|
+
retiredAt: null,
|
|
811
|
+
lastTouchedAt: now,
|
|
812
|
+
metadata: { ...(metadata || {}) },
|
|
813
|
+
};
|
|
749
814
|
_dlpPols.set(id, p);
|
|
750
815
|
return { ...p, metadata: { ...p.metadata } };
|
|
751
816
|
}
|
|
752
|
-
function _dlpCheckP(from, to) {
|
|
753
|
-
|
|
817
|
+
function _dlpCheckP(from, to) {
|
|
818
|
+
const a = _dlpPolTrans.get(from);
|
|
819
|
+
if (!a || !a.has(to))
|
|
820
|
+
throw new Error(`invalid dlp policy transition ${from} → ${to}`);
|
|
821
|
+
}
|
|
822
|
+
function _dlpCountActive(owner) {
|
|
823
|
+
let n = 0;
|
|
824
|
+
for (const p of _dlpPols.values())
|
|
825
|
+
if (p.owner === owner && p.status === DLP_POLICY_MATURITY_V2.ACTIVE) n++;
|
|
826
|
+
return n;
|
|
827
|
+
}
|
|
754
828
|
|
|
755
829
|
export function activateDlpPolicyV2(id) {
|
|
756
|
-
const p = _dlpPols.get(id);
|
|
830
|
+
const p = _dlpPols.get(id);
|
|
831
|
+
if (!p) throw new Error(`dlp policy ${id} not found`);
|
|
757
832
|
_dlpCheckP(p.status, DLP_POLICY_MATURITY_V2.ACTIVE);
|
|
758
833
|
const recovery = p.status === DLP_POLICY_MATURITY_V2.SUSPENDED;
|
|
759
|
-
if (!recovery) {
|
|
760
|
-
|
|
834
|
+
if (!recovery) {
|
|
835
|
+
const a = _dlpCountActive(p.owner);
|
|
836
|
+
if (a >= _dlpMaxActivePerOwner)
|
|
837
|
+
throw new Error(
|
|
838
|
+
`max active dlp policies per owner (${_dlpMaxActivePerOwner}) reached for ${p.owner}`,
|
|
839
|
+
);
|
|
840
|
+
}
|
|
841
|
+
const now = Date.now();
|
|
842
|
+
p.status = DLP_POLICY_MATURITY_V2.ACTIVE;
|
|
843
|
+
p.updatedAt = now;
|
|
844
|
+
p.lastTouchedAt = now;
|
|
845
|
+
if (!p.activatedAt) p.activatedAt = now;
|
|
846
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
847
|
+
}
|
|
848
|
+
export function suspendDlpPolicyV2(id) {
|
|
849
|
+
const p = _dlpPols.get(id);
|
|
850
|
+
if (!p) throw new Error(`dlp policy ${id} not found`);
|
|
851
|
+
_dlpCheckP(p.status, DLP_POLICY_MATURITY_V2.SUSPENDED);
|
|
852
|
+
p.status = DLP_POLICY_MATURITY_V2.SUSPENDED;
|
|
853
|
+
p.updatedAt = Date.now();
|
|
854
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
855
|
+
}
|
|
856
|
+
export function retireDlpPolicyV2(id) {
|
|
857
|
+
const p = _dlpPols.get(id);
|
|
858
|
+
if (!p) throw new Error(`dlp policy ${id} not found`);
|
|
859
|
+
_dlpCheckP(p.status, DLP_POLICY_MATURITY_V2.RETIRED);
|
|
860
|
+
const now = Date.now();
|
|
861
|
+
p.status = DLP_POLICY_MATURITY_V2.RETIRED;
|
|
862
|
+
p.updatedAt = now;
|
|
863
|
+
if (!p.retiredAt) p.retiredAt = now;
|
|
864
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
865
|
+
}
|
|
866
|
+
export function touchDlpPolicyV2(id) {
|
|
867
|
+
const p = _dlpPols.get(id);
|
|
868
|
+
if (!p) throw new Error(`dlp policy ${id} not found`);
|
|
869
|
+
if (_dlpPolTerminal.has(p.status))
|
|
870
|
+
throw new Error(`cannot touch terminal dlp policy ${id}`);
|
|
871
|
+
const now = Date.now();
|
|
872
|
+
p.lastTouchedAt = now;
|
|
873
|
+
p.updatedAt = now;
|
|
761
874
|
return { ...p, metadata: { ...p.metadata } };
|
|
762
875
|
}
|
|
763
|
-
export function
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
876
|
+
export function getDlpPolicyV2(id) {
|
|
877
|
+
const p = _dlpPols.get(id);
|
|
878
|
+
if (!p) return null;
|
|
879
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
880
|
+
}
|
|
881
|
+
export function listDlpPoliciesV2() {
|
|
882
|
+
return [..._dlpPols.values()].map((p) => ({
|
|
883
|
+
...p,
|
|
884
|
+
metadata: { ...p.metadata },
|
|
885
|
+
}));
|
|
886
|
+
}
|
|
768
887
|
|
|
769
|
-
function _dlpCountPending(pid) {
|
|
888
|
+
function _dlpCountPending(pid) {
|
|
889
|
+
let n = 0;
|
|
890
|
+
for (const s of _dlpScans.values())
|
|
891
|
+
if (
|
|
892
|
+
s.policyId === pid &&
|
|
893
|
+
(s.status === DLP_SCAN_LIFECYCLE_V2.QUEUED ||
|
|
894
|
+
s.status === DLP_SCAN_LIFECYCLE_V2.SCANNING)
|
|
895
|
+
)
|
|
896
|
+
n++;
|
|
897
|
+
return n;
|
|
898
|
+
}
|
|
770
899
|
|
|
771
900
|
export function createDlpScanV2({ id, policyId, target, metadata } = {}) {
|
|
772
901
|
if (!id || typeof id !== "string") throw new Error("id is required");
|
|
773
|
-
if (!policyId || typeof policyId !== "string")
|
|
902
|
+
if (!policyId || typeof policyId !== "string")
|
|
903
|
+
throw new Error("policyId is required");
|
|
774
904
|
if (_dlpScans.has(id)) throw new Error(`dlp scan ${id} already exists`);
|
|
775
|
-
if (!_dlpPols.has(policyId))
|
|
905
|
+
if (!_dlpPols.has(policyId))
|
|
906
|
+
throw new Error(`dlp policy ${policyId} not found`);
|
|
776
907
|
const pending = _dlpCountPending(policyId);
|
|
777
|
-
if (pending >= _dlpMaxPendingPerPol)
|
|
908
|
+
if (pending >= _dlpMaxPendingPerPol)
|
|
909
|
+
throw new Error(
|
|
910
|
+
`max pending dlp scans per policy (${_dlpMaxPendingPerPol}) reached for ${policyId}`,
|
|
911
|
+
);
|
|
778
912
|
const now = Date.now();
|
|
779
|
-
const s = {
|
|
913
|
+
const s = {
|
|
914
|
+
id,
|
|
915
|
+
policyId,
|
|
916
|
+
target: target || "",
|
|
917
|
+
status: DLP_SCAN_LIFECYCLE_V2.QUEUED,
|
|
918
|
+
createdAt: now,
|
|
919
|
+
updatedAt: now,
|
|
920
|
+
startedAt: null,
|
|
921
|
+
settledAt: null,
|
|
922
|
+
metadata: { ...(metadata || {}) },
|
|
923
|
+
};
|
|
780
924
|
_dlpScans.set(id, s);
|
|
781
925
|
return { ...s, metadata: { ...s.metadata } };
|
|
782
926
|
}
|
|
783
|
-
function _dlpCheckS(from, to) {
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
export function
|
|
789
|
-
|
|
927
|
+
function _dlpCheckS(from, to) {
|
|
928
|
+
const a = _dlpScanTrans.get(from);
|
|
929
|
+
if (!a || !a.has(to))
|
|
930
|
+
throw new Error(`invalid dlp scan transition ${from} → ${to}`);
|
|
931
|
+
}
|
|
932
|
+
export function startDlpScanV2(id) {
|
|
933
|
+
const s = _dlpScans.get(id);
|
|
934
|
+
if (!s) throw new Error(`dlp scan ${id} not found`);
|
|
935
|
+
_dlpCheckS(s.status, DLP_SCAN_LIFECYCLE_V2.SCANNING);
|
|
936
|
+
const now = Date.now();
|
|
937
|
+
s.status = DLP_SCAN_LIFECYCLE_V2.SCANNING;
|
|
938
|
+
s.updatedAt = now;
|
|
939
|
+
if (!s.startedAt) s.startedAt = now;
|
|
940
|
+
return { ...s, metadata: { ...s.metadata } };
|
|
941
|
+
}
|
|
942
|
+
export function completeDlpScanV2(id) {
|
|
943
|
+
const s = _dlpScans.get(id);
|
|
944
|
+
if (!s) throw new Error(`dlp scan ${id} not found`);
|
|
945
|
+
_dlpCheckS(s.status, DLP_SCAN_LIFECYCLE_V2.COMPLETED);
|
|
946
|
+
const now = Date.now();
|
|
947
|
+
s.status = DLP_SCAN_LIFECYCLE_V2.COMPLETED;
|
|
948
|
+
s.updatedAt = now;
|
|
949
|
+
if (!s.settledAt) s.settledAt = now;
|
|
950
|
+
return { ...s, metadata: { ...s.metadata } };
|
|
951
|
+
}
|
|
952
|
+
export function failDlpScanV2(id, reason) {
|
|
953
|
+
const s = _dlpScans.get(id);
|
|
954
|
+
if (!s) throw new Error(`dlp scan ${id} not found`);
|
|
955
|
+
_dlpCheckS(s.status, DLP_SCAN_LIFECYCLE_V2.FAILED);
|
|
956
|
+
const now = Date.now();
|
|
957
|
+
s.status = DLP_SCAN_LIFECYCLE_V2.FAILED;
|
|
958
|
+
s.updatedAt = now;
|
|
959
|
+
if (!s.settledAt) s.settledAt = now;
|
|
960
|
+
if (reason) s.metadata.failReason = String(reason);
|
|
961
|
+
return { ...s, metadata: { ...s.metadata } };
|
|
962
|
+
}
|
|
963
|
+
export function cancelDlpScanV2(id, reason) {
|
|
964
|
+
const s = _dlpScans.get(id);
|
|
965
|
+
if (!s) throw new Error(`dlp scan ${id} not found`);
|
|
966
|
+
_dlpCheckS(s.status, DLP_SCAN_LIFECYCLE_V2.CANCELLED);
|
|
967
|
+
const now = Date.now();
|
|
968
|
+
s.status = DLP_SCAN_LIFECYCLE_V2.CANCELLED;
|
|
969
|
+
s.updatedAt = now;
|
|
970
|
+
if (!s.settledAt) s.settledAt = now;
|
|
971
|
+
if (reason) s.metadata.cancelReason = String(reason);
|
|
972
|
+
return { ...s, metadata: { ...s.metadata } };
|
|
973
|
+
}
|
|
974
|
+
export function getDlpScanV2(id) {
|
|
975
|
+
const s = _dlpScans.get(id);
|
|
976
|
+
if (!s) return null;
|
|
977
|
+
return { ...s, metadata: { ...s.metadata } };
|
|
978
|
+
}
|
|
979
|
+
export function listDlpScansV2() {
|
|
980
|
+
return [..._dlpScans.values()].map((s) => ({
|
|
981
|
+
...s,
|
|
982
|
+
metadata: { ...s.metadata },
|
|
983
|
+
}));
|
|
984
|
+
}
|
|
790
985
|
|
|
791
|
-
export function autoSuspendIdleDlpPoliciesV2({ now } = {}) {
|
|
792
|
-
|
|
986
|
+
export function autoSuspendIdleDlpPoliciesV2({ now } = {}) {
|
|
987
|
+
const t = now ?? Date.now();
|
|
988
|
+
const flipped = [];
|
|
989
|
+
for (const p of _dlpPols.values())
|
|
990
|
+
if (
|
|
991
|
+
p.status === DLP_POLICY_MATURITY_V2.ACTIVE &&
|
|
992
|
+
t - p.lastTouchedAt >= _dlpPolIdleMs
|
|
993
|
+
) {
|
|
994
|
+
p.status = DLP_POLICY_MATURITY_V2.SUSPENDED;
|
|
995
|
+
p.updatedAt = t;
|
|
996
|
+
flipped.push(p.id);
|
|
997
|
+
}
|
|
998
|
+
return { flipped, count: flipped.length };
|
|
999
|
+
}
|
|
1000
|
+
export function autoFailStuckDlpScansV2({ now } = {}) {
|
|
1001
|
+
const t = now ?? Date.now();
|
|
1002
|
+
const flipped = [];
|
|
1003
|
+
for (const s of _dlpScans.values())
|
|
1004
|
+
if (
|
|
1005
|
+
s.status === DLP_SCAN_LIFECYCLE_V2.SCANNING &&
|
|
1006
|
+
s.startedAt != null &&
|
|
1007
|
+
t - s.startedAt >= _dlpScanStuckMs
|
|
1008
|
+
) {
|
|
1009
|
+
s.status = DLP_SCAN_LIFECYCLE_V2.FAILED;
|
|
1010
|
+
s.updatedAt = t;
|
|
1011
|
+
if (!s.settledAt) s.settledAt = t;
|
|
1012
|
+
s.metadata.failReason = "auto-fail-stuck";
|
|
1013
|
+
flipped.push(s.id);
|
|
1014
|
+
}
|
|
1015
|
+
return { flipped, count: flipped.length };
|
|
1016
|
+
}
|
|
793
1017
|
|
|
794
1018
|
export function getDlpEngineStatsV2() {
|
|
795
|
-
const policiesByStatus = {};
|
|
796
|
-
|
|
797
|
-
|
|
1019
|
+
const policiesByStatus = {};
|
|
1020
|
+
for (const s of Object.values(DLP_POLICY_MATURITY_V2))
|
|
1021
|
+
policiesByStatus[s] = 0;
|
|
1022
|
+
for (const p of _dlpPols.values()) policiesByStatus[p.status]++;
|
|
1023
|
+
const scansByStatus = {};
|
|
1024
|
+
for (const s of Object.values(DLP_SCAN_LIFECYCLE_V2)) scansByStatus[s] = 0;
|
|
1025
|
+
for (const sc of _dlpScans.values()) scansByStatus[sc.status]++;
|
|
1026
|
+
return {
|
|
1027
|
+
totalPoliciesV2: _dlpPols.size,
|
|
1028
|
+
totalScansV2: _dlpScans.size,
|
|
1029
|
+
maxActiveDlpPoliciesPerOwner: _dlpMaxActivePerOwner,
|
|
1030
|
+
maxPendingDlpScansPerPolicy: _dlpMaxPendingPerPol,
|
|
1031
|
+
dlpPolicyIdleMs: _dlpPolIdleMs,
|
|
1032
|
+
dlpScanStuckMs: _dlpScanStuckMs,
|
|
1033
|
+
policiesByStatus,
|
|
1034
|
+
scansByStatus,
|
|
1035
|
+
};
|
|
1036
|
+
}
|
|
1037
|
+
|
|
1038
|
+
// =====================================================================
|
|
1039
|
+
// dlp-engine V2 governance overlay (iter20)
|
|
1040
|
+
// =====================================================================
|
|
1041
|
+
export const DLPGOV_PROFILE_MATURITY_V2 = Object.freeze({
|
|
1042
|
+
PENDING: "pending",
|
|
1043
|
+
ACTIVE: "active",
|
|
1044
|
+
SUSPENDED: "suspended",
|
|
1045
|
+
ARCHIVED: "archived",
|
|
1046
|
+
});
|
|
1047
|
+
export const DLPGOV_SCAN_LIFECYCLE_V2 = Object.freeze({
|
|
1048
|
+
QUEUED: "queued",
|
|
1049
|
+
SCANNING: "scanning",
|
|
1050
|
+
SCANNED: "scanned",
|
|
1051
|
+
FAILED: "failed",
|
|
1052
|
+
CANCELLED: "cancelled",
|
|
1053
|
+
});
|
|
1054
|
+
const _dlpgovPTrans = new Map([
|
|
1055
|
+
[
|
|
1056
|
+
DLPGOV_PROFILE_MATURITY_V2.PENDING,
|
|
1057
|
+
new Set([
|
|
1058
|
+
DLPGOV_PROFILE_MATURITY_V2.ACTIVE,
|
|
1059
|
+
DLPGOV_PROFILE_MATURITY_V2.ARCHIVED,
|
|
1060
|
+
]),
|
|
1061
|
+
],
|
|
1062
|
+
[
|
|
1063
|
+
DLPGOV_PROFILE_MATURITY_V2.ACTIVE,
|
|
1064
|
+
new Set([
|
|
1065
|
+
DLPGOV_PROFILE_MATURITY_V2.SUSPENDED,
|
|
1066
|
+
DLPGOV_PROFILE_MATURITY_V2.ARCHIVED,
|
|
1067
|
+
]),
|
|
1068
|
+
],
|
|
1069
|
+
[
|
|
1070
|
+
DLPGOV_PROFILE_MATURITY_V2.SUSPENDED,
|
|
1071
|
+
new Set([
|
|
1072
|
+
DLPGOV_PROFILE_MATURITY_V2.ACTIVE,
|
|
1073
|
+
DLPGOV_PROFILE_MATURITY_V2.ARCHIVED,
|
|
1074
|
+
]),
|
|
1075
|
+
],
|
|
1076
|
+
[DLPGOV_PROFILE_MATURITY_V2.ARCHIVED, new Set()],
|
|
1077
|
+
]);
|
|
1078
|
+
const _dlpgovPTerminal = new Set([DLPGOV_PROFILE_MATURITY_V2.ARCHIVED]);
|
|
1079
|
+
const _dlpgovJTrans = new Map([
|
|
1080
|
+
[
|
|
1081
|
+
DLPGOV_SCAN_LIFECYCLE_V2.QUEUED,
|
|
1082
|
+
new Set([
|
|
1083
|
+
DLPGOV_SCAN_LIFECYCLE_V2.SCANNING,
|
|
1084
|
+
DLPGOV_SCAN_LIFECYCLE_V2.CANCELLED,
|
|
1085
|
+
]),
|
|
1086
|
+
],
|
|
1087
|
+
[
|
|
1088
|
+
DLPGOV_SCAN_LIFECYCLE_V2.SCANNING,
|
|
1089
|
+
new Set([
|
|
1090
|
+
DLPGOV_SCAN_LIFECYCLE_V2.SCANNED,
|
|
1091
|
+
DLPGOV_SCAN_LIFECYCLE_V2.FAILED,
|
|
1092
|
+
DLPGOV_SCAN_LIFECYCLE_V2.CANCELLED,
|
|
1093
|
+
]),
|
|
1094
|
+
],
|
|
1095
|
+
[DLPGOV_SCAN_LIFECYCLE_V2.SCANNED, new Set()],
|
|
1096
|
+
[DLPGOV_SCAN_LIFECYCLE_V2.FAILED, new Set()],
|
|
1097
|
+
[DLPGOV_SCAN_LIFECYCLE_V2.CANCELLED, new Set()],
|
|
1098
|
+
]);
|
|
1099
|
+
const _dlpgovPsV2 = new Map();
|
|
1100
|
+
const _dlpgovJsV2 = new Map();
|
|
1101
|
+
let _dlpgovMaxActive = 8,
|
|
1102
|
+
_dlpgovMaxPending = 20,
|
|
1103
|
+
_dlpgovIdleMs = 30 * 24 * 60 * 60 * 1000,
|
|
1104
|
+
_dlpgovStuckMs = 60 * 1000;
|
|
1105
|
+
function _dlpgovPos(n, label) {
|
|
1106
|
+
const v = Math.floor(Number(n));
|
|
1107
|
+
if (!Number.isFinite(v) || v <= 0)
|
|
1108
|
+
throw new Error(`${label} must be positive integer`);
|
|
1109
|
+
return v;
|
|
1110
|
+
}
|
|
1111
|
+
function _dlpgovCheckP(from, to) {
|
|
1112
|
+
const a = _dlpgovPTrans.get(from);
|
|
1113
|
+
if (!a || !a.has(to))
|
|
1114
|
+
throw new Error(`invalid dlpgov profile transition ${from} → ${to}`);
|
|
1115
|
+
}
|
|
1116
|
+
function _dlpgovCheckJ(from, to) {
|
|
1117
|
+
const a = _dlpgovJTrans.get(from);
|
|
1118
|
+
if (!a || !a.has(to))
|
|
1119
|
+
throw new Error(`invalid dlpgov scan transition ${from} → ${to}`);
|
|
1120
|
+
}
|
|
1121
|
+
function _dlpgovCountActive(owner) {
|
|
1122
|
+
let c = 0;
|
|
1123
|
+
for (const p of _dlpgovPsV2.values())
|
|
1124
|
+
if (p.owner === owner && p.status === DLPGOV_PROFILE_MATURITY_V2.ACTIVE)
|
|
1125
|
+
c++;
|
|
1126
|
+
return c;
|
|
1127
|
+
}
|
|
1128
|
+
function _dlpgovCountPending(profileId) {
|
|
1129
|
+
let c = 0;
|
|
1130
|
+
for (const j of _dlpgovJsV2.values())
|
|
1131
|
+
if (
|
|
1132
|
+
j.profileId === profileId &&
|
|
1133
|
+
(j.status === DLPGOV_SCAN_LIFECYCLE_V2.QUEUED ||
|
|
1134
|
+
j.status === DLPGOV_SCAN_LIFECYCLE_V2.SCANNING)
|
|
1135
|
+
)
|
|
1136
|
+
c++;
|
|
1137
|
+
return c;
|
|
1138
|
+
}
|
|
1139
|
+
export function setMaxActiveDlpgovProfilesPerOwnerV2(n) {
|
|
1140
|
+
_dlpgovMaxActive = _dlpgovPos(n, "maxActiveDlpgovProfilesPerOwner");
|
|
1141
|
+
}
|
|
1142
|
+
export function getMaxActiveDlpgovProfilesPerOwnerV2() {
|
|
1143
|
+
return _dlpgovMaxActive;
|
|
1144
|
+
}
|
|
1145
|
+
export function setMaxPendingDlpgovScansPerProfileV2(n) {
|
|
1146
|
+
_dlpgovMaxPending = _dlpgovPos(n, "maxPendingDlpgovScansPerProfile");
|
|
1147
|
+
}
|
|
1148
|
+
export function getMaxPendingDlpgovScansPerProfileV2() {
|
|
1149
|
+
return _dlpgovMaxPending;
|
|
1150
|
+
}
|
|
1151
|
+
export function setDlpgovProfileIdleMsV2(n) {
|
|
1152
|
+
_dlpgovIdleMs = _dlpgovPos(n, "dlpgovProfileIdleMs");
|
|
1153
|
+
}
|
|
1154
|
+
export function getDlpgovProfileIdleMsV2() {
|
|
1155
|
+
return _dlpgovIdleMs;
|
|
1156
|
+
}
|
|
1157
|
+
export function setDlpgovScanStuckMsV2(n) {
|
|
1158
|
+
_dlpgovStuckMs = _dlpgovPos(n, "dlpgovScanStuckMs");
|
|
1159
|
+
}
|
|
1160
|
+
export function getDlpgovScanStuckMsV2() {
|
|
1161
|
+
return _dlpgovStuckMs;
|
|
1162
|
+
}
|
|
1163
|
+
export function _resetStateDlpEngineGovV2() {
|
|
1164
|
+
_dlpgovPsV2.clear();
|
|
1165
|
+
_dlpgovJsV2.clear();
|
|
1166
|
+
_dlpgovMaxActive = 8;
|
|
1167
|
+
_dlpgovMaxPending = 20;
|
|
1168
|
+
_dlpgovIdleMs = 30 * 24 * 60 * 60 * 1000;
|
|
1169
|
+
_dlpgovStuckMs = 60 * 1000;
|
|
1170
|
+
}
|
|
1171
|
+
export function registerDlpgovProfileV2({
|
|
1172
|
+
id,
|
|
1173
|
+
owner,
|
|
1174
|
+
classification,
|
|
1175
|
+
metadata,
|
|
1176
|
+
} = {}) {
|
|
1177
|
+
if (!id || !owner) throw new Error("id and owner required");
|
|
1178
|
+
if (_dlpgovPsV2.has(id))
|
|
1179
|
+
throw new Error(`dlpgov profile ${id} already exists`);
|
|
1180
|
+
const now = Date.now();
|
|
1181
|
+
const p = {
|
|
1182
|
+
id,
|
|
1183
|
+
owner,
|
|
1184
|
+
classification: classification || "internal",
|
|
1185
|
+
status: DLPGOV_PROFILE_MATURITY_V2.PENDING,
|
|
1186
|
+
createdAt: now,
|
|
1187
|
+
updatedAt: now,
|
|
1188
|
+
lastTouchedAt: now,
|
|
1189
|
+
activatedAt: null,
|
|
1190
|
+
archivedAt: null,
|
|
1191
|
+
metadata: { ...(metadata || {}) },
|
|
1192
|
+
};
|
|
1193
|
+
_dlpgovPsV2.set(id, p);
|
|
1194
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
1195
|
+
}
|
|
1196
|
+
export function activateDlpgovProfileV2(id) {
|
|
1197
|
+
const p = _dlpgovPsV2.get(id);
|
|
1198
|
+
if (!p) throw new Error(`dlpgov profile ${id} not found`);
|
|
1199
|
+
const isInitial = p.status === DLPGOV_PROFILE_MATURITY_V2.PENDING;
|
|
1200
|
+
_dlpgovCheckP(p.status, DLPGOV_PROFILE_MATURITY_V2.ACTIVE);
|
|
1201
|
+
if (isInitial && _dlpgovCountActive(p.owner) >= _dlpgovMaxActive)
|
|
1202
|
+
throw new Error(`max active dlpgov profiles for owner ${p.owner} reached`);
|
|
1203
|
+
const now = Date.now();
|
|
1204
|
+
p.status = DLPGOV_PROFILE_MATURITY_V2.ACTIVE;
|
|
1205
|
+
p.updatedAt = now;
|
|
1206
|
+
p.lastTouchedAt = now;
|
|
1207
|
+
if (!p.activatedAt) p.activatedAt = now;
|
|
1208
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
1209
|
+
}
|
|
1210
|
+
export function suspendDlpgovProfileV2(id) {
|
|
1211
|
+
const p = _dlpgovPsV2.get(id);
|
|
1212
|
+
if (!p) throw new Error(`dlpgov profile ${id} not found`);
|
|
1213
|
+
_dlpgovCheckP(p.status, DLPGOV_PROFILE_MATURITY_V2.SUSPENDED);
|
|
1214
|
+
p.status = DLPGOV_PROFILE_MATURITY_V2.SUSPENDED;
|
|
1215
|
+
p.updatedAt = Date.now();
|
|
1216
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
1217
|
+
}
|
|
1218
|
+
export function archiveDlpgovProfileV2(id) {
|
|
1219
|
+
const p = _dlpgovPsV2.get(id);
|
|
1220
|
+
if (!p) throw new Error(`dlpgov profile ${id} not found`);
|
|
1221
|
+
_dlpgovCheckP(p.status, DLPGOV_PROFILE_MATURITY_V2.ARCHIVED);
|
|
1222
|
+
const now = Date.now();
|
|
1223
|
+
p.status = DLPGOV_PROFILE_MATURITY_V2.ARCHIVED;
|
|
1224
|
+
p.updatedAt = now;
|
|
1225
|
+
if (!p.archivedAt) p.archivedAt = now;
|
|
1226
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
1227
|
+
}
|
|
1228
|
+
export function touchDlpgovProfileV2(id) {
|
|
1229
|
+
const p = _dlpgovPsV2.get(id);
|
|
1230
|
+
if (!p) throw new Error(`dlpgov profile ${id} not found`);
|
|
1231
|
+
if (_dlpgovPTerminal.has(p.status))
|
|
1232
|
+
throw new Error(`cannot touch terminal dlpgov profile ${id}`);
|
|
1233
|
+
const now = Date.now();
|
|
1234
|
+
p.lastTouchedAt = now;
|
|
1235
|
+
p.updatedAt = now;
|
|
1236
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
1237
|
+
}
|
|
1238
|
+
export function getDlpgovProfileV2(id) {
|
|
1239
|
+
const p = _dlpgovPsV2.get(id);
|
|
1240
|
+
if (!p) return null;
|
|
1241
|
+
return { ...p, metadata: { ...p.metadata } };
|
|
1242
|
+
}
|
|
1243
|
+
export function listDlpgovProfilesV2() {
|
|
1244
|
+
return [..._dlpgovPsV2.values()].map((p) => ({
|
|
1245
|
+
...p,
|
|
1246
|
+
metadata: { ...p.metadata },
|
|
1247
|
+
}));
|
|
1248
|
+
}
|
|
1249
|
+
export function createDlpgovScanV2({ id, profileId, resource, metadata } = {}) {
|
|
1250
|
+
if (!id || !profileId) throw new Error("id and profileId required");
|
|
1251
|
+
if (_dlpgovJsV2.has(id)) throw new Error(`dlpgov scan ${id} already exists`);
|
|
1252
|
+
if (!_dlpgovPsV2.has(profileId))
|
|
1253
|
+
throw new Error(`dlpgov profile ${profileId} not found`);
|
|
1254
|
+
if (_dlpgovCountPending(profileId) >= _dlpgovMaxPending)
|
|
1255
|
+
throw new Error(
|
|
1256
|
+
`max pending dlpgov scans for profile ${profileId} reached`,
|
|
1257
|
+
);
|
|
1258
|
+
const now = Date.now();
|
|
1259
|
+
const j = {
|
|
1260
|
+
id,
|
|
1261
|
+
profileId,
|
|
1262
|
+
resource: resource || "",
|
|
1263
|
+
status: DLPGOV_SCAN_LIFECYCLE_V2.QUEUED,
|
|
1264
|
+
createdAt: now,
|
|
1265
|
+
updatedAt: now,
|
|
1266
|
+
startedAt: null,
|
|
1267
|
+
settledAt: null,
|
|
1268
|
+
metadata: { ...(metadata || {}) },
|
|
1269
|
+
};
|
|
1270
|
+
_dlpgovJsV2.set(id, j);
|
|
1271
|
+
return { ...j, metadata: { ...j.metadata } };
|
|
1272
|
+
}
|
|
1273
|
+
export function scanningDlpgovScanV2(id) {
|
|
1274
|
+
const j = _dlpgovJsV2.get(id);
|
|
1275
|
+
if (!j) throw new Error(`dlpgov scan ${id} not found`);
|
|
1276
|
+
_dlpgovCheckJ(j.status, DLPGOV_SCAN_LIFECYCLE_V2.SCANNING);
|
|
1277
|
+
const now = Date.now();
|
|
1278
|
+
j.status = DLPGOV_SCAN_LIFECYCLE_V2.SCANNING;
|
|
1279
|
+
j.updatedAt = now;
|
|
1280
|
+
if (!j.startedAt) j.startedAt = now;
|
|
1281
|
+
return { ...j, metadata: { ...j.metadata } };
|
|
1282
|
+
}
|
|
1283
|
+
export function completeScanDlpgovV2(id) {
|
|
1284
|
+
const j = _dlpgovJsV2.get(id);
|
|
1285
|
+
if (!j) throw new Error(`dlpgov scan ${id} not found`);
|
|
1286
|
+
_dlpgovCheckJ(j.status, DLPGOV_SCAN_LIFECYCLE_V2.SCANNED);
|
|
1287
|
+
const now = Date.now();
|
|
1288
|
+
j.status = DLPGOV_SCAN_LIFECYCLE_V2.SCANNED;
|
|
1289
|
+
j.updatedAt = now;
|
|
1290
|
+
if (!j.settledAt) j.settledAt = now;
|
|
1291
|
+
return { ...j, metadata: { ...j.metadata } };
|
|
1292
|
+
}
|
|
1293
|
+
export function failDlpgovScanV2(id, reason) {
|
|
1294
|
+
const j = _dlpgovJsV2.get(id);
|
|
1295
|
+
if (!j) throw new Error(`dlpgov scan ${id} not found`);
|
|
1296
|
+
_dlpgovCheckJ(j.status, DLPGOV_SCAN_LIFECYCLE_V2.FAILED);
|
|
1297
|
+
const now = Date.now();
|
|
1298
|
+
j.status = DLPGOV_SCAN_LIFECYCLE_V2.FAILED;
|
|
1299
|
+
j.updatedAt = now;
|
|
1300
|
+
if (!j.settledAt) j.settledAt = now;
|
|
1301
|
+
if (reason) j.metadata.failReason = String(reason);
|
|
1302
|
+
return { ...j, metadata: { ...j.metadata } };
|
|
1303
|
+
}
|
|
1304
|
+
export function cancelDlpgovScanV2(id, reason) {
|
|
1305
|
+
const j = _dlpgovJsV2.get(id);
|
|
1306
|
+
if (!j) throw new Error(`dlpgov scan ${id} not found`);
|
|
1307
|
+
_dlpgovCheckJ(j.status, DLPGOV_SCAN_LIFECYCLE_V2.CANCELLED);
|
|
1308
|
+
const now = Date.now();
|
|
1309
|
+
j.status = DLPGOV_SCAN_LIFECYCLE_V2.CANCELLED;
|
|
1310
|
+
j.updatedAt = now;
|
|
1311
|
+
if (!j.settledAt) j.settledAt = now;
|
|
1312
|
+
if (reason) j.metadata.cancelReason = String(reason);
|
|
1313
|
+
return { ...j, metadata: { ...j.metadata } };
|
|
1314
|
+
}
|
|
1315
|
+
export function getDlpgovScanV2(id) {
|
|
1316
|
+
const j = _dlpgovJsV2.get(id);
|
|
1317
|
+
if (!j) return null;
|
|
1318
|
+
return { ...j, metadata: { ...j.metadata } };
|
|
1319
|
+
}
|
|
1320
|
+
export function listDlpgovScansV2() {
|
|
1321
|
+
return [..._dlpgovJsV2.values()].map((j) => ({
|
|
1322
|
+
...j,
|
|
1323
|
+
metadata: { ...j.metadata },
|
|
1324
|
+
}));
|
|
1325
|
+
}
|
|
1326
|
+
export function autoSuspendIdleDlpgovProfilesV2({ now } = {}) {
|
|
1327
|
+
const t = now ?? Date.now();
|
|
1328
|
+
const flipped = [];
|
|
1329
|
+
for (const p of _dlpgovPsV2.values())
|
|
1330
|
+
if (
|
|
1331
|
+
p.status === DLPGOV_PROFILE_MATURITY_V2.ACTIVE &&
|
|
1332
|
+
t - p.lastTouchedAt >= _dlpgovIdleMs
|
|
1333
|
+
) {
|
|
1334
|
+
p.status = DLPGOV_PROFILE_MATURITY_V2.SUSPENDED;
|
|
1335
|
+
p.updatedAt = t;
|
|
1336
|
+
flipped.push(p.id);
|
|
1337
|
+
}
|
|
1338
|
+
return { flipped, count: flipped.length };
|
|
1339
|
+
}
|
|
1340
|
+
export function autoFailStuckDlpgovScansV2({ now } = {}) {
|
|
1341
|
+
const t = now ?? Date.now();
|
|
1342
|
+
const flipped = [];
|
|
1343
|
+
for (const j of _dlpgovJsV2.values())
|
|
1344
|
+
if (
|
|
1345
|
+
j.status === DLPGOV_SCAN_LIFECYCLE_V2.SCANNING &&
|
|
1346
|
+
j.startedAt != null &&
|
|
1347
|
+
t - j.startedAt >= _dlpgovStuckMs
|
|
1348
|
+
) {
|
|
1349
|
+
j.status = DLPGOV_SCAN_LIFECYCLE_V2.FAILED;
|
|
1350
|
+
j.updatedAt = t;
|
|
1351
|
+
if (!j.settledAt) j.settledAt = t;
|
|
1352
|
+
j.metadata.failReason = "auto-fail-stuck";
|
|
1353
|
+
flipped.push(j.id);
|
|
1354
|
+
}
|
|
1355
|
+
return { flipped, count: flipped.length };
|
|
1356
|
+
}
|
|
1357
|
+
export function getDlpEngineGovStatsV2() {
|
|
1358
|
+
const profilesByStatus = {};
|
|
1359
|
+
for (const v of Object.values(DLPGOV_PROFILE_MATURITY_V2))
|
|
1360
|
+
profilesByStatus[v] = 0;
|
|
1361
|
+
for (const p of _dlpgovPsV2.values()) profilesByStatus[p.status]++;
|
|
1362
|
+
const scansByStatus = {};
|
|
1363
|
+
for (const v of Object.values(DLPGOV_SCAN_LIFECYCLE_V2)) scansByStatus[v] = 0;
|
|
1364
|
+
for (const j of _dlpgovJsV2.values()) scansByStatus[j.status]++;
|
|
1365
|
+
return {
|
|
1366
|
+
totalDlpgovProfilesV2: _dlpgovPsV2.size,
|
|
1367
|
+
totalDlpgovScansV2: _dlpgovJsV2.size,
|
|
1368
|
+
maxActiveDlpgovProfilesPerOwner: _dlpgovMaxActive,
|
|
1369
|
+
maxPendingDlpgovScansPerProfile: _dlpgovMaxPending,
|
|
1370
|
+
dlpgovProfileIdleMs: _dlpgovIdleMs,
|
|
1371
|
+
dlpgovScanStuckMs: _dlpgovStuckMs,
|
|
1372
|
+
profilesByStatus,
|
|
1373
|
+
scansByStatus,
|
|
1374
|
+
};
|
|
798
1375
|
}
|