mirror of
https://github.com/awatertrevi/infisical.git
synced 2026-10-06 14:27:59 +00:00
Fix folder path and environment on secret imports
This commit is contained in:
@@ -59,7 +59,7 @@ type TSecretReplicationServiceFactoryDep = {
|
|||||||
TSecretVersionV2DALFactory,
|
TSecretVersionV2DALFactory,
|
||||||
"find" | "insertMany" | "update" | "findLatestVersionMany"
|
"find" | "insertMany" | "update" | "findLatestVersionMany"
|
||||||
>;
|
>;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "updateById" | "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "updateById" | "findByFolderIds" | "findById">;
|
||||||
folderDAL: Pick<
|
folderDAL: Pick<
|
||||||
TSecretFolderDALFactory,
|
TSecretFolderDALFactory,
|
||||||
"findSecretPathByFolderIds" | "findBySecretPath" | "create" | "findOne" | "findByManySecretPath"
|
"findSecretPathByFolderIds" | "findBySecretPath" | "create" | "findOne" | "findByManySecretPath"
|
||||||
|
|||||||
@@ -39,7 +39,7 @@ const getIntegrationSecretsV2 = async (
|
|||||||
},
|
},
|
||||||
secretV2BridgeDAL: Pick<TSecretV2BridgeDALFactory, "find" | "findByFolderId">,
|
secretV2BridgeDAL: Pick<TSecretV2BridgeDALFactory, "find" | "findByFolderId">,
|
||||||
folderDAL: Pick<TSecretFolderDALFactory, "findByManySecretPath">,
|
folderDAL: Pick<TSecretFolderDALFactory, "findByManySecretPath">,
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds">
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds" | "findById">
|
||||||
) => {
|
) => {
|
||||||
const content: Record<string, boolean> = {};
|
const content: Record<string, boolean> = {};
|
||||||
if (dto.depth > MAX_SYNC_SECRET_DEPTH) {
|
if (dto.depth > MAX_SYNC_SECRET_DEPTH) {
|
||||||
@@ -300,7 +300,7 @@ export const deleteIntegrationSecrets = async ({
|
|||||||
projectBotService: Pick<TProjectBotServiceFactory, "getBotKey">;
|
projectBotService: Pick<TProjectBotServiceFactory, "getBotKey">;
|
||||||
secretV2BridgeDAL: Pick<TSecretV2BridgeDALFactory, "find" | "findByFolderId">;
|
secretV2BridgeDAL: Pick<TSecretV2BridgeDALFactory, "find" | "findByFolderId">;
|
||||||
folderDAL: Pick<TSecretFolderDALFactory, "findByManySecretPath" | "findBySecretPath">;
|
folderDAL: Pick<TSecretFolderDALFactory, "findByManySecretPath" | "findBySecretPath">;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds" | "findById">;
|
||||||
secretDAL: Pick<TSecretDALFactory, "findByFolderId">;
|
secretDAL: Pick<TSecretDALFactory, "findByFolderId">;
|
||||||
kmsService: Pick<TKmsServiceFactory, "createCipherPairWithDataKey">;
|
kmsService: Pick<TKmsServiceFactory, "createCipherPairWithDataKey">;
|
||||||
}) => {
|
}) => {
|
||||||
|
|||||||
@@ -40,7 +40,7 @@ type TIntegrationServiceFactoryDep = {
|
|||||||
projectBotService: TProjectBotServiceFactory;
|
projectBotService: TProjectBotServiceFactory;
|
||||||
secretQueueService: Pick<TSecretQueueFactory, "syncIntegrations">;
|
secretQueueService: Pick<TSecretQueueFactory, "syncIntegrations">;
|
||||||
secretV2BridgeDAL: Pick<TSecretV2BridgeDALFactory, "find" | "findByFolderId">;
|
secretV2BridgeDAL: Pick<TSecretV2BridgeDALFactory, "find" | "findByFolderId">;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds" | "findById">;
|
||||||
kmsService: Pick<TKmsServiceFactory, "createCipherPairWithDataKey">;
|
kmsService: Pick<TKmsServiceFactory, "createCipherPairWithDataKey">;
|
||||||
secretDAL: Pick<TSecretDALFactory, "findByFolderId">;
|
secretDAL: Pick<TSecretDALFactory, "findByFolderId">;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import RE2 from "re2";
|
||||||
|
|
||||||
import { SecretType, TSecretImports, TSecrets, TSecretsV2 } from "@app/db/schemas";
|
import { SecretType, TSecretImports, TSecrets, TSecretsV2 } from "@app/db/schemas";
|
||||||
import { groupBy, unique } from "@app/lib/fn";
|
import { groupBy, unique } from "@app/lib/fn";
|
||||||
|
|
||||||
@@ -54,6 +56,77 @@ type TSecretImportSecretsV2 = {
|
|||||||
|
|
||||||
const LEVEL_BREAK = 10;
|
const LEVEL_BREAK = 10;
|
||||||
const getImportUniqKey = (envSlug: string, path: string) => `${envSlug}=${path}`;
|
const getImportUniqKey = (envSlug: string, path: string) => `${envSlug}=${path}`;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Processes reserved imports by resolving them to their replication source.
|
||||||
|
*/
|
||||||
|
const processReservedImports = async <
|
||||||
|
T extends {
|
||||||
|
isReserved?: boolean | null;
|
||||||
|
importPath: string;
|
||||||
|
importEnv: { id: string; slug: string; name: string };
|
||||||
|
folderId: string;
|
||||||
|
}
|
||||||
|
>(
|
||||||
|
imports: T[],
|
||||||
|
secretImportDAL: Pick<TSecretImportDALFactory, "findById">
|
||||||
|
): Promise<T[]> => {
|
||||||
|
const reservedImportIds: string[] = [];
|
||||||
|
|
||||||
|
imports.forEach((secretImport) => {
|
||||||
|
if (secretImport.isReserved) {
|
||||||
|
const reservedMatch = new RE2("/__reserve_replication_([a-f0-9-]{36})").exec(secretImport.importPath);
|
||||||
|
if (reservedMatch) {
|
||||||
|
const referencedImportId = reservedMatch[1];
|
||||||
|
reservedImportIds.push(referencedImportId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
if (reservedImportIds.length === 0) {
|
||||||
|
return imports;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
const importDetailsMap = new Map<
|
||||||
|
string,
|
||||||
|
{ importPath: string; importEnv: { id: string; slug: string; name: string } }
|
||||||
|
>();
|
||||||
|
|
||||||
|
/* eslint-disable no-await-in-loop */
|
||||||
|
for (const importId of reservedImportIds) {
|
||||||
|
const referencedImport = await secretImportDAL.findById(importId);
|
||||||
|
if (referencedImport) {
|
||||||
|
importDetailsMap.set(importId, {
|
||||||
|
importPath: referencedImport.importPath,
|
||||||
|
importEnv: referencedImport.importEnv
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/* eslint-enable no-await-in-loop */
|
||||||
|
|
||||||
|
return imports.map((secretImport) => {
|
||||||
|
if (secretImport.isReserved) {
|
||||||
|
const reservedMatch = new RE2("/__reserve_replication_([a-f0-9-]{36})").exec(secretImport.importPath);
|
||||||
|
if (reservedMatch) {
|
||||||
|
const referencedImportId = reservedMatch[1];
|
||||||
|
const referencedDetails = importDetailsMap.get(referencedImportId);
|
||||||
|
|
||||||
|
if (referencedDetails) {
|
||||||
|
return {
|
||||||
|
...secretImport,
|
||||||
|
importPath: referencedDetails.importPath,
|
||||||
|
importEnv: referencedDetails.importEnv
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return secretImport;
|
||||||
|
});
|
||||||
|
} catch (error) {
|
||||||
|
return imports;
|
||||||
|
}
|
||||||
|
};
|
||||||
export const fnSecretsFromImports = async ({
|
export const fnSecretsFromImports = async ({
|
||||||
allowedImports: possibleCyclicImports,
|
allowedImports: possibleCyclicImports,
|
||||||
folderDAL,
|
folderDAL,
|
||||||
@@ -167,7 +240,7 @@ export const fnSecretsV2FromImports = async ({
|
|||||||
folderDAL: Pick<TSecretFolderDALFactory, "findByManySecretPath">;
|
folderDAL: Pick<TSecretFolderDALFactory, "findByManySecretPath">;
|
||||||
viewSecretValue: boolean;
|
viewSecretValue: boolean;
|
||||||
secretDAL: Pick<TSecretV2BridgeDALFactory, "find">;
|
secretDAL: Pick<TSecretV2BridgeDALFactory, "find">;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "findByFolderIds" | "findById">;
|
||||||
decryptor: (value?: Buffer | null) => string;
|
decryptor: (value?: Buffer | null) => string;
|
||||||
expandSecretReferences?: (inputSecret: {
|
expandSecretReferences?: (inputSecret: {
|
||||||
value?: string;
|
value?: string;
|
||||||
@@ -188,6 +261,10 @@ export const fnSecretsV2FromImports = async ({
|
|||||||
})[];
|
})[];
|
||||||
}[] = [{ secretImports: rootSecretImports, depth: 0, parentImportedSecrets: [] }];
|
}[] = [{ secretImports: rootSecretImports, depth: 0, parentImportedSecrets: [] }];
|
||||||
|
|
||||||
|
const processedSecretImports = await processReservedImports(rootSecretImports, secretImportDAL);
|
||||||
|
|
||||||
|
stack[0] = { secretImports: processedSecretImports, depth: 0, parentImportedSecrets: [] };
|
||||||
|
|
||||||
const processedImports: TSecretImportSecretsV2[] = [];
|
const processedImports: TSecretImportSecretsV2[] = [];
|
||||||
|
|
||||||
while (stack.length) {
|
while (stack.length) {
|
||||||
|
|||||||
@@ -80,7 +80,7 @@ type TSecretSyncQueueFactoryDep = {
|
|||||||
| "deleteMany"
|
| "deleteMany"
|
||||||
| "invalidateSecretCacheByProjectId"
|
| "invalidateSecretCacheByProjectId"
|
||||||
>;
|
>;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds" | "findById">;
|
||||||
secretSyncDAL: Pick<TSecretSyncDALFactory, "findById" | "find" | "updateById" | "deleteById">;
|
secretSyncDAL: Pick<TSecretSyncDALFactory, "findById" | "find" | "updateById" | "deleteById">;
|
||||||
auditLogService: Pick<TAuditLogServiceFactory, "createAuditLog">;
|
auditLogService: Pick<TAuditLogServiceFactory, "createAuditLog">;
|
||||||
projectMembershipDAL: Pick<TProjectMembershipDALFactory, "findAllProjectMembers">;
|
projectMembershipDAL: Pick<TProjectMembershipDALFactory, "findAllProjectMembers">;
|
||||||
|
|||||||
@@ -108,7 +108,7 @@ type TSecretV2BridgeServiceFactoryDep = {
|
|||||||
| "findBySecretPathMultiEnv"
|
| "findBySecretPathMultiEnv"
|
||||||
| "findSecretPathByFolderIds"
|
| "findSecretPathByFolderIds"
|
||||||
>;
|
>;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds" | "findById">;
|
||||||
secretQueueService: Pick<TSecretQueueFactory, "syncSecrets" | "handleSecretReminder" | "removeSecretReminder">;
|
secretQueueService: Pick<TSecretQueueFactory, "syncSecrets" | "handleSecretReminder" | "removeSecretReminder">;
|
||||||
secretApprovalPolicyService: Pick<TSecretApprovalPolicyServiceFactory, "getSecretApprovalPolicy">;
|
secretApprovalPolicyService: Pick<TSecretApprovalPolicyServiceFactory, "getSecretApprovalPolicy">;
|
||||||
secretApprovalRequestDAL: Pick<TSecretApprovalRequestDALFactory, "create" | "transaction">;
|
secretApprovalRequestDAL: Pick<TSecretApprovalRequestDALFactory, "create" | "transaction">;
|
||||||
|
|||||||
@@ -86,7 +86,7 @@ type TSecretQueueFactoryDep = {
|
|||||||
integrationAuthService: Pick<TIntegrationAuthServiceFactory, "getIntegrationAccessToken">;
|
integrationAuthService: Pick<TIntegrationAuthServiceFactory, "getIntegrationAccessToken">;
|
||||||
folderDAL: TSecretFolderDALFactory;
|
folderDAL: TSecretFolderDALFactory;
|
||||||
secretDAL: TSecretDALFactory;
|
secretDAL: TSecretDALFactory;
|
||||||
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds">;
|
secretImportDAL: Pick<TSecretImportDALFactory, "find" | "findByFolderIds" | "findById">;
|
||||||
webhookDAL: Pick<TWebhookDALFactory, "findAllWebhooks" | "transaction" | "update" | "bulkUpdate">;
|
webhookDAL: Pick<TWebhookDALFactory, "findAllWebhooks" | "transaction" | "update" | "bulkUpdate">;
|
||||||
projectEnvDAL: Pick<TProjectEnvDALFactory, "findOne" | "find">;
|
projectEnvDAL: Pick<TProjectEnvDALFactory, "findOne" | "find">;
|
||||||
projectDAL: TProjectDALFactory;
|
projectDAL: TProjectDALFactory;
|
||||||
|
|||||||
Reference in New Issue
Block a user