Fix application variable issue (#20500)

Fixes wrong formatting converting secret value to ******** before saving
Issued by
https://discord.com/channels/1130383047699738754/1423290797079662602/1502674904770936903
This commit is contained in:
martmull
2026-05-12 20:52:17 +02:00
committed by GitHub
parent c4e897a7b5
commit 7ade9e3aab
4 changed files with 61 additions and 7 deletions
@@ -12,6 +12,7 @@ import {
import { SECRET_APPLICATION_VARIABLE_MASK } from 'src/engine/core-modules/application/application-variable/constants/secret-application-variable-mask.constant';
import { SecretEncryptionService } from 'src/engine/core-modules/secret-encryption/secret-encryption.service';
import { WorkspaceCacheService } from 'src/engine/workspace-cache/services/workspace-cache.service';
import { isNonEmptyString } from '@sniptt/guards';
@Injectable()
export class ApplicationVariableEntityService {
@@ -27,6 +28,10 @@ export class ApplicationVariableEntityService {
return applicationVariable.value;
}
if (!isNonEmptyString(applicationVariable.value)) {
return '';
}
return this.secretEncryptionService.decryptAndMask({
value: applicationVariable.value,
mask: SECRET_APPLICATION_VARIABLE_MASK,
@@ -1,5 +1,6 @@
import { type FlatApplicationVariable } from 'src/engine/metadata-modules/flat-application-variable/types/flat-application-variable.type';
import { type SecretEncryptionService } from 'src/engine/core-modules/secret-encryption/secret-encryption.service';
import { isNonEmptyString } from '@sniptt/guards';
export const buildEnvVar = (
flatApplicationVariables: FlatApplicationVariable[],
@@ -9,9 +10,10 @@ export const buildEnvVar = (
(acc, flatApplicationVariable) => {
const value = String(flatApplicationVariable.value ?? '');
acc[flatApplicationVariable.key] = flatApplicationVariable.isSecret
? secretEncryptionService.decrypt(value)
: value;
acc[flatApplicationVariable.key] =
flatApplicationVariable.isSecret && isNonEmptyString(value)
? secretEncryptionService.decrypt(value)
: value;
return acc;
},
@@ -1,5 +1,6 @@
import { FieldMetadataType } from 'twenty-shared/types';
import { type FlatApplicationVariable } from 'src/engine/metadata-modules/flat-application-variable/types/flat-application-variable.type';
import { getFlatFieldMetadataMock } from 'src/engine/metadata-modules/flat-field-metadata/__mocks__/get-flat-field-metadata.mock';
import { flatEntityToScalarFlatEntity } from 'src/engine/workspace-manager/workspace-migration/workspace-migration-runner/utils/flat-entity-to-scalar-flat-entity.util';
@@ -77,4 +78,54 @@ describe('flatEntityToScalarFlatEntity', () => {
}
`);
});
it('should preserve secret application variable value instead of masking it', () => {
const encryptedValue = 'dGVzdC1lbmNyeXB0ZWQtdmFsdWUtd2l0aC1pdi1wcmVmaXg=';
const flatEntity = {
id: 'app-var-id',
workspaceId: 'workspace-id',
applicationId: 'application-id',
universalIdentifier: 'app-var-universal-id',
applicationUniversalIdentifier: 'app-universal-id',
key: 'API_SECRET',
value: encryptedValue,
description: 'An API secret key',
isSecret: true,
createdAt: '2025-01-01T00:00:00.000Z',
updatedAt: '2025-01-01T00:00:00.000Z',
} as unknown as FlatApplicationVariable;
const result = flatEntityToScalarFlatEntity({
metadataName: 'applicationVariable',
flatEntity,
});
expect(result.value).toBe(encryptedValue);
});
it('should preserve non-secret application variable value', () => {
const plainValue = 'https://example.com';
const flatEntity = {
id: 'app-var-id',
workspaceId: 'workspace-id',
applicationId: 'application-id',
universalIdentifier: 'app-var-universal-id',
applicationUniversalIdentifier: 'app-universal-id',
key: 'PUBLIC_URL',
value: plainValue,
description: 'A public URL',
isSecret: false,
createdAt: '2025-01-01T00:00:00.000Z',
updatedAt: '2025-01-01T00:00:00.000Z',
} as unknown as FlatApplicationVariable;
const result = flatEntityToScalarFlatEntity({
metadataName: 'applicationVariable',
flatEntity,
});
expect(result.value).toBe(plainValue);
});
});
@@ -26,9 +26,5 @@ export const flatEntityToScalarFlatEntity = <T extends AllMetadataName>({
result.applicationId = flatEntityRecord.applicationId;
result.universalIdentifier = flatEntityRecord.universalIdentifier;
if (metadataName === 'applicationVariable' && result.isSecret === true) {
result.value = '********';
}
return result as ScalarFlatEntity<MetadataEntity<T>>;
};