Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
45 commits
Select commit Hold shift + click to select a range
757ca49
init files
nafees87n Dec 22, 2025
0f8cb7a
added external secrets manager interfaces
nafees87n Dec 22, 2025
7b4d869
fix: config type
nafees87n Dec 23, 2025
fa080d0
added method
nafees87n Dec 23, 2025
0caccc0
refactor
nafees87n Dec 24, 2025
a965650
refactor folder name
nafees87n Dec 25, 2025
e68e69f
Merge branch 'master' of github.com:requestly/requestly-desktop-app i…
nafees87n Dec 25, 2025
2f38597
fix: interface reusability
nafees87n Dec 27, 2025
bbefd3f
fix
nafees87n Dec 30, 2025
a808ba9
added caching service
nafees87n Jan 9, 2026
aa26c49
refactored providerRegistry
nafees87n Jan 12, 2026
13f5131
fix: types
nafees87n Jan 12, 2026
2bb53a6
fix
nafees87n Jan 13, 2026
36e1b45
poc code
nafees87n Jan 14, 2026
3b34f7d
added initilization flow
nafees87n Jan 14, 2026
bdb67fb
remove unused code
nafees87n Jan 15, 2026
b597f38
Merge branch 'master' of github.com:requestly/requestly-desktop-app i…
nafees87n Jan 15, 2026
6968919
fix
nafees87n Jan 16, 2026
1756a21
fix: encrypted storage init
nafees87n Jan 20, 2026
e603899
fix: error
nafees87n Jan 20, 2026
4375589
fix: type
nafees87n Jan 20, 2026
0468284
fix: schemas
nafees87n Jan 20, 2026
c0b5a93
fix: config read/write
nafees87n Jan 20, 2026
3faf236
fix: provider reading
nafees87n Jan 20, 2026
ae99164
added key sanitization
nafees87n Jan 20, 2026
d8b7462
fix: deletion result
nafees87n Jan 20, 2026
9ae079b
fix: orphaned indexes in manifest
nafees87n Jan 20, 2026
8de1756
use electron-store
nafees87n Jan 21, 2026
56c2b4b
fix: initialization
nafees87n Jan 21, 2026
0f93b01
fix: file name
nafees87n Jan 21, 2026
11f1ede
fix: encryption code
nafees87n Jan 21, 2026
8ff48a7
cleanup unncessary changes
nafees87n Jan 21, 2026
2a4ca6d
Merge branch 'master' of github.com:requestly/requestly-desktop-app i…
nafees87n Jan 21, 2026
04f496b
wrap in trycatch
nafees87n Jan 21, 2026
cbec03c
removed linting changes
nafees87n Jan 28, 2026
555f2f0
Merge branch 'master' of github.com:requestly/requestly-desktop-app i…
nafees87n Jan 28, 2026
63a10fc
fix: new line
nafees87n Jan 28, 2026
88fb8fb
[DB-21] added variable fetching flow and awsSecretsManagerProvider (#…
nafees87n Jan 29, 2026
e95012d
convert into generic types
wrongsahil Jan 30, 2026
caaf624
fix: types
nafees87n Jan 30, 2026
7bce339
readded vault types
nafees87n Jan 30, 2026
20c9454
Merge branch 'master' of github.com:requestly/requestly-desktop-app i…
nafees87n Feb 25, 2026
75cd56c
adds support for listener in secretsManager (#273)
nafees87n Mar 9, 2026
acf3121
[DB-29] added IPC methods for secretsManager (#277)
nafees87n Mar 9, 2026
312b1f6
Merge branch 'master' of github.com:requestly/requestly-desktop-app i…
nafees87n Mar 9, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25,431 changes: 14,190 additions & 11,241 deletions package-lock.json

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -272,6 +272,7 @@
"webpack-merge": "^5.8.0"
},
"dependencies": {
"@aws-sdk/client-secrets-manager": "^3.969.0",
"@devicefarmer/adbkit": "^3.2.6",
"@electron/remote": "^2.1.2",
"@requestly/requestly-core": "1.1.1",
Expand Down
366 changes: 366 additions & 0 deletions src/lib/secretsManager/USAGE_EXAMPLES.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,366 @@
/**
* Usage Examples for Type-Safe Secrets Manager
*
* This file demonstrates how TypeScript automatically infers types
* throughout the secrets manager system.
*/

import {
SecretProviderType,
AWSSecretProviderConfig,
HashicorpVaultProviderConfig,
AwsSecretReference,
VaultSecretReference,
} from "./types";
import { createProviderInstance } from "./providerService/providerFactory";
import { AWSSecretsManagerProvider } from "./providerService/awsSecretManagerProvider";
Comment thread
nafees87n marked this conversation as resolved.
// import { HashicorpVaultProvider } from "./providerService/hashicorpVaultProvider";

Comment thread
nafees87n marked this conversation as resolved.
// ============================================================================
// Example 1: Creating Provider Configurations (Type-Safe)
// ============================================================================

// AWS Provider Config - TypeScript enforces correct config structure
const awsConfig: AWSSecretProviderConfig = {
id: "aws-prod",
type: SecretProviderType.AWS_SECRETS_MANAGER,
name: "AWS Production",
createdAt: Date.now(),
updatedAt: Date.now(),
credentials: {
accessKeyId: "AKIA...",
secretAccessKey: "...",
region: "us-east-1",
sessionToken: "...", // optional
},
};

// HashiCorp Vault Config - TypeScript enforces correct config structure
const vaultConfig: HashicorpVaultProviderConfig = {
id: "vault-dev",
type: SecretProviderType.HASHICORP_VAULT,
name: "Vault Development",
createdAt: Date.now(),
updatedAt: Date.now(),
credentials: {
address: "https://vault.example.com",
token: "s.xyz...",
namespace: "admin", // optional
},
};

// ❌ This will cause a TypeScript error - wrong config type for provider type
// const invalidConfig: AWSSecretProviderConfig = {
// id: "invalid",
// type: SecretProviderType.HASHICORP_VAULT, // ❌ Error: type mismatch
// ...
// };

// ============================================================================
// Example 2: Creating Provider Instances (Type-Safe Factory)
// ============================================================================

async function example2() {
// Generic factory - returns AbstractSecretProvider<SecretProviderType>
const awsProvider = createProviderInstance(awsConfig);
const vaultProvider = createProviderInstance(vaultConfig);

// TypeScript knows the provider type from the instance
console.log(awsProvider.type); // SecretProviderType.AWS_SECRETS_MANAGER
console.log(vaultProvider.type); // SecretProviderType.HASHICORP_VAULT

Comment thread
nafees87n marked this conversation as resolved.
// Strongly-typed factory - returns specific provider type
const typedAwsProvider = createTypedProviderInstance(awsConfig);
// typedAwsProvider is AbstractSecretProvider<SecretProviderType.AWS_SECRETS_MANAGER>

const typedVaultProvider = createTypedProviderInstance(vaultConfig);
// typedVaultProvider is AbstractSecretProvider<SecretProviderType.HASHICORP_VAULT>
}

// ============================================================================
// Example 3: Working with Secret References (Type-Safe)
// ============================================================================

async function example3() {
const awsProvider = new AWSSecretsManagerProvider(awsConfig);
const vaultProvider = new HashicorpVaultProvider(vaultConfig);

// AWS Secret Reference - TypeScript enforces correct structure
const awsRef: AwsSecretReference = {
type: SecretProviderType.AWS_SECRETS_MANAGER,
identifier: "arn:aws:secretsmanager:us-east-1:123456789:secret:myapp/config",
version: "AWSCURRENT", // optional
};

// Vault Secret Reference - TypeScript enforces correct structure
const vaultRef: VaultSecretReference = {
type: SecretProviderType.HASHICORP_VAULT,
path: "secret/data/myapp/config",
version: 2, // optional - KV v2 version number
};

// TypeScript ensures you pass the correct reference type to each provider
const awsSecret = await awsProvider.getSecret(awsRef); // ✅ Correct
const vaultSecret = await vaultProvider.getSecret(vaultRef); // ✅ Correct

// ❌ These would cause TypeScript errors:
// await awsProvider.getSecret(vaultRef); // ❌ Error: wrong reference type
// await vaultProvider.getSecret(awsRef); // ❌ Error: wrong reference type

// TypeScript knows the exact return types
if (awsSecret) {
console.log(awsSecret.ARN); // ✅ ARN exists on AwsSecretValue
console.log(awsSecret.value); // ✅ value is string | undefined
// console.log(awsSecret.data); // ❌ Error: data doesn't exist on AwsSecretValue
}

if (vaultSecret) {
console.log(vaultSecret.data); // ✅ data exists on VaultSecretValue
console.log(vaultSecret.metadata?.version); // ✅ metadata is optional
// console.log(vaultSecret.ARN); // ❌ Error: ARN doesn't exist on VaultSecretValue
}
}

// ============================================================================
// Example 4: Batch Operations (Type-Safe)
// ============================================================================

async function example4() {
const awsProvider = new AWSSecretsManagerProvider(awsConfig);
const vaultProvider = new HashicorpVaultProvider(vaultConfig);

// Get multiple secrets - types are preserved
const awsRefs: AwsSecretReference[] = [
{
type: SecretProviderType.AWS_SECRETS_MANAGER,
identifier: "secret-1",
},
{
type: SecretProviderType.AWS_SECRETS_MANAGER,
identifier: "secret-2",
},
];

const vaultRefs: VaultSecretReference[] = [
{
type: SecretProviderType.HASHICORP_VAULT,
path: "secret/data/app1",
},
{
type: SecretProviderType.HASHICORP_VAULT,
path: "secret/data/app2",
},
];

const awsSecrets = await awsProvider.getSecrets(awsRefs);
// TypeScript knows: awsSecrets is (AwsSecretValue | null)[]

const vaultSecrets = await vaultProvider.getSecrets(vaultRefs);
// TypeScript knows: vaultSecrets is (VaultSecretValue | null)[]

// Type-safe iteration
awsSecrets.forEach((secret) => {
if (secret) {
console.log(secret.ARN); // ✅ ARN exists
console.log(secret.versionId); // ✅ versionId exists
}
});

vaultSecrets.forEach((secret) => {
if (secret) {
console.log(secret.path); // ✅ path exists
console.log(secret.data); // ✅ data exists
}
});
}

// ============================================================================
// Example 5: Setting Secrets (Type-Safe)
// ============================================================================

async function example5() {
const awsProvider = new AWSSecretsManagerProvider(awsConfig);
const vaultProvider = new HashicorpVaultProvider(vaultConfig);

const awsRef: AwsSecretReference = {
type: SecretProviderType.AWS_SECRETS_MANAGER,
identifier: "my-secret",
};

const vaultRef: VaultSecretReference = {
type: SecretProviderType.HASHICORP_VAULT,
path: "secret/data/myapp/config",
};

// Set a single secret - both string and object values are supported
await awsProvider.setSecret(awsRef, "my-secret-value");
await vaultProvider.setSecret(vaultRef, {
database: "postgres://...",
apiKey: "xyz...",
});

// Batch set
await awsProvider.setSecrets([
{ ref: awsRef, value: "value1" },
]);

await vaultProvider.setSecrets([
{
ref: { type: SecretProviderType.HASHICORP_VAULT, path: "secret/data/app1" },
value: { key1: "value1" },
},
{
ref: { type: SecretProviderType.HASHICORP_VAULT, path: "secret/data/app2" },
value: { key2: "value2" },
},
]);
}
Comment thread
nafees87n marked this conversation as resolved.

// ============================================================================
// Example 6: Using the Registry (Type-Safe)
// ============================================================================

async function example6() {
// Assume we have a registry instance
const registry: any = null; // FileBasedProviderRegistry instance

// Get a provider without knowing its type
const provider = registry.getProvider("aws-prod");
if (provider) {
// provider is AbstractSecretProvider<SecretProviderType>
console.log(provider.type);
}

// Get a provider with a specific type (type-safe)
const awsProvider = registry.getTypedProvider(
"aws-prod",
SecretProviderType.AWS_SECRETS_MANAGER
);

if (awsProvider) {
// TypeScript knows: awsProvider is AbstractSecretProvider<SecretProviderType.AWS_SECRETS_MANAGER>
const ref: AwsSecretReference = {
type: SecretProviderType.AWS_SECRETS_MANAGER,
identifier: "my-secret",
};

const secret = await awsProvider.getSecret(ref);
// TypeScript knows: secret is AwsSecretValue | null

if (secret) {
console.log(secret.ARN); // ✅ Type-safe access to AWS-specific fields
}
}
}

// ============================================================================
// Example 7: Type Guards and Runtime Checks
// ============================================================================

async function example7() {
const registry: any = null; // FileBasedProviderRegistry instance

// Get a provider and use type guards
const provider = registry.getProvider("some-provider-id");

if (provider) {
// Runtime check with type narrowing
if (provider.type === SecretProviderType.AWS_SECRETS_MANAGER) {
// TypeScript narrows the type here
const awsProvider = provider as AWSSecretsManagerProvider;
// Now you have full access to AWS-specific methods if any
} else if (provider.type === SecretProviderType.HASHICORP_VAULT) {
const vaultProvider = provider as HashicorpVaultProvider;
// Now you have full access to Vault-specific methods if any
}
}
}

// ============================================================================
// Example 8: Adding a New Provider (Easy Extension)
// ============================================================================

/**
* To add a new provider (e.g., Azure Key Vault):
*
* 1. Add the provider type to the enum in types.ts:
* ```
* export enum SecretProviderType {
* AWS_SECRETS_MANAGER = "aws",
* HASHICORP_VAULT = "vault",
* AZURE_KEY_VAULT = "azure", // ← Add this
* }
* ```
*
* 2. Add the config interface in types.ts:
* ```
* export interface AzureKeyVaultConfig {
* vaultUrl: string;
* tenantId: string;
* clientId: string;
* clientSecret: string;
* }
* ```
*
* 3. Add to the discriminated unions in types.ts:
* ```
* export type AzureKeyVaultProviderConfig = ProviderConfig<
* SecretProviderType.AZURE_KEY_VAULT,
* AzureKeyVaultConfig
* >;
*
* export type SecretProviderConfig =
* | AWSSecretProviderConfig
* | HashicorpVaultProviderConfig
* | AzureKeyVaultProviderConfig; // ← Add this
* ```
*
* 4. Add reference and value types in types.ts:
* ```
* export interface AzureSecretReference extends BaseSecretReference<...> {
* name: string;
* version?: string;
* }
*
* export interface AzureSecretValue extends BaseSecretValue<...> {
* value: string;
* id: string;
* // ... other Azure-specific fields
* }
* ```
*
* 5. Add to the type map in types.ts:
* ```
* export interface ProviderTypeMap {
* [SecretProviderType.AWS_SECRETS_MANAGER]: { ... };
* [SecretProviderType.HASHICORP_VAULT]: { ... };
* [SecretProviderType.AZURE_KEY_VAULT]: { // ← Add this
* config: AzureKeyVaultConfig;
* providerConfig: AzureKeyVaultProviderConfig;
* reference: AzureSecretReference;
* value: AzureSecretValue;
* };
* }
* ```
*
* 6. Create the provider class (azureKeyVaultProvider.ts):
* ```
* export class AzureKeyVaultProvider extends AbstractSecretProvider<
* SecretProviderType.AZURE_KEY_VAULT
* > {
* readonly type = SecretProviderType.AZURE_KEY_VAULT as const;
* // ... implement abstract methods
* }
* ```
*
* 7. Add to the factory in providerFactory.ts:
* ```
* case SecretProviderType.AZURE_KEY_VAULT:
* return new AzureKeyVaultProvider(config as AzureKeyVaultProviderConfig);
* ```
*
* That's it! TypeScript will now enforce type safety for your new provider
* throughout the entire system.
*/

export {};
Loading