This is an automated email from the ASF dual-hosted git repository.
pvillard31 pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/nifi.git
The following commit(s) were added to refs/heads/main by this push:
new 1644ae795e6 NIFI-16431 Allow HashiCorp Vault Parameter Provider to
list secrets under a path prefix (#11763)
1644ae795e6 is described below
commit 1644ae795e6ec95402a83346b2c0974b543fb395
Author: Fabian Grosch <[email protected]>
AuthorDate: Tue Oct 6 17:33:25 2026 +0200
NIFI-16431 Allow HashiCorp Vault Parameter Provider to list secrets under a
path prefix (#11763)
---
.../HashiCorpVaultCommunicationService.java | 15 +++
...StandardHashiCorpVaultCommunicationService.java | 14 +-
...StandardHashiCorpVaultCommunicationService.java | 146 +++++++++++++++++++++
.../hashicorp/HashiCorpVaultParameterProvider.java | 11 +-
.../TestHashiCorpVaultParameterProvider.java | 62 ++++++++-
5 files changed, 241 insertions(+), 7 deletions(-)
diff --git
a/nifi-commons/nifi-hashicorp-vault-api/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultCommunicationService.java
b/nifi-commons/nifi-hashicorp-vault-api/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultCommunicationService.java
index 33ab496f667..e2aa4fa7092 100644
---
a/nifi-commons/nifi-hashicorp-vault-api/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultCommunicationService.java
+++
b/nifi-commons/nifi-hashicorp-vault-api/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultCommunicationService.java
@@ -114,4 +114,19 @@ public interface HashiCorpVaultCommunicationService {
* @return The list of secret names
*/
List<String> listKeyValueSecrets(String keyValuePath, String version);
+
+ /**
+ * Lists the secrets under the given path in the Key/Value Secrets Engine.
+ * @param keyValuePath The mount path of the Key/Value Secrets Engine
+ * @param version the Key/Value Secrets engine version
+ * @param secretPathPrefix The path within the Key/Value Secrets Engine
mount to list
+ * @return The list of secret names
+ * @throws UnsupportedOperationException if a non-empty prefix is not
supported by the implementation
+ */
+ default List<String> listKeyValueSecrets(final String keyValuePath, final
String version, final String secretPathPrefix) {
+ if (secretPathPrefix == null || secretPathPrefix.isEmpty()) {
+ return listKeyValueSecrets(keyValuePath, version);
+ }
+ throw new UnsupportedOperationException("Secret path prefixes are not
supported by this implementation");
+ }
}
diff --git
a/nifi-commons/nifi-hashicorp-vault/src/main/java/org/apache/nifi/vault/hashicorp/StandardHashiCorpVaultCommunicationService.java
b/nifi-commons/nifi-hashicorp-vault/src/main/java/org/apache/nifi/vault/hashicorp/StandardHashiCorpVaultCommunicationService.java
index 7b10615f5c3..a08e7649122 100644
---
a/nifi-commons/nifi-hashicorp-vault/src/main/java/org/apache/nifi/vault/hashicorp/StandardHashiCorpVaultCommunicationService.java
+++
b/nifi-commons/nifi-hashicorp-vault/src/main/java/org/apache/nifi/vault/hashicorp/StandardHashiCorpVaultCommunicationService.java
@@ -217,8 +217,20 @@ public class StandardHashiCorpVaultCommunicationService
implements HashiCorpVaul
@Override
public List<String> listKeyValueSecrets(final String keyValuePath, final
String version) {
+ return listKeyValueSecrets(keyValuePath, version, "");
+ }
+
+ @Override
+ public List<String> listKeyValueSecrets(final String keyValuePath, final
String version, final String secretPathPrefix) {
final VaultKeyValueOperations keyValueOperations =
vaultTemplate.opsForKeyValue(keyValuePath, KeyValueBackend.valueOf(version));
- return listKeyValueSecrets(keyValueOperations, "");
+ String path = secretPathPrefix == null ? "" : secretPathPrefix;
+ if (path.startsWith("/")) {
+ path = path.substring(1);
+ }
+ if (!path.isEmpty() && !path.endsWith("/")) {
+ path = path + "/";
+ }
+ return listKeyValueSecrets(keyValueOperations, path);
}
private List<String> listKeyValueSecrets(final VaultKeyValueOperations
keyValueOperations, final String path) {
diff --git
a/nifi-commons/nifi-hashicorp-vault/src/test/java/org/apache/nifi/vault/hashicorp/TestStandardHashiCorpVaultCommunicationService.java
b/nifi-commons/nifi-hashicorp-vault/src/test/java/org/apache/nifi/vault/hashicorp/TestStandardHashiCorpVaultCommunicationService.java
index d9de2fbcc2a..9c422e6bb39 100644
---
a/nifi-commons/nifi-hashicorp-vault/src/test/java/org/apache/nifi/vault/hashicorp/TestStandardHashiCorpVaultCommunicationService.java
+++
b/nifi-commons/nifi-hashicorp-vault/src/test/java/org/apache/nifi/vault/hashicorp/TestStandardHashiCorpVaultCommunicationService.java
@@ -20,7 +20,10 @@ import
org.apache.nifi.vault.hashicorp.config.HashiCorpVaultProperties;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
+import org.junit.jupiter.params.ParameterizedTest;
+import org.junit.jupiter.params.provider.EnumSource;
import org.mockito.Mockito;
+import org.springframework.vault.VaultException;
import org.springframework.vault.core.VaultKeyValueOperations;
import
org.springframework.vault.core.VaultKeyValueOperationsSupport.KeyValueBackend;
import org.springframework.vault.core.VaultTemplate;
@@ -34,6 +37,10 @@ import java.util.List;
import java.util.Optional;
import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertThrows;
+import static org.mockito.ArgumentMatchers.anyString;
+import static org.mockito.ArgumentMatchers.eq;
+import static org.mockito.Mockito.doCallRealMethod;
import static org.mockito.Mockito.when;
public class TestStandardHashiCorpVaultCommunicationService {
@@ -62,6 +69,17 @@ public class TestStandardHashiCorpVaultCommunicationService {
return new StandardHashiCorpVaultCommunicationService(properties);
}
+ @Test
+ public void
testDefaultSecretPathPrefixMethodPreservesExistingImplementations() {
+ final HashiCorpVaultCommunicationService communicationService =
Mockito.mock(HashiCorpVaultCommunicationService.class);
+ when(communicationService.listKeyValueSecrets("kv",
KeyValueBackend.KV_1.name())).thenReturn(List.of("secret"));
+
doCallRealMethod().when(communicationService).listKeyValueSecrets(eq("kv"),
eq(KeyValueBackend.KV_1.name()), anyString());
+
+ assertEquals(List.of("secret"),
communicationService.listKeyValueSecrets("kv", KeyValueBackend.KV_1.name(),
""));
+ assertThrows(UnsupportedOperationException.class,
+ () -> communicationService.listKeyValueSecrets("kv",
KeyValueBackend.KV_1.name(), "nested"));
+ }
+
@Test
public void testBasicConfiguration() {
try (StandardHashiCorpVaultCommunicationService ignored =
this.configureService()) {
@@ -107,4 +125,132 @@ public class
TestStandardHashiCorpVaultCommunicationService {
assertEquals(Arrays.asList("test", "nested/nifi"), secrets);
}
}
+
+ @ParameterizedTest
+ @EnumSource(KeyValueBackend.class)
+ public void testListKeyValueSecretsStartsAtSecretPathPrefix(final
KeyValueBackend backend) throws Exception {
+ when(properties.getKvVersion()).thenReturn(backend ==
KeyValueBackend.KV_1 ? 1 : 2);
+
+ try (StandardHashiCorpVaultCommunicationService service =
this.configureService()) {
+
+ final VaultTemplate vaultTemplate =
Mockito.mock(VaultTemplate.class);
+ final VaultKeyValueOperations keyValueOperations =
Mockito.mock(VaultKeyValueOperations.class);
+
+ final Field vaultTemplateField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("vaultTemplate");
+ vaultTemplateField.setAccessible(true);
+ vaultTemplateField.set(service, vaultTemplate);
+
+ final Field keyValueBackendField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("keyValueBackend");
+ keyValueBackendField.setAccessible(true);
+ final KeyValueBackend keyValueBackend = (KeyValueBackend)
keyValueBackendField.get(service);
+
+ when(vaultTemplate.opsForKeyValue("kv",
keyValueBackend)).thenReturn(keyValueOperations);
+
when(keyValueOperations.list("groups/my-group/")).thenReturn(Arrays.asList("app",
"nested/"));
+
when(keyValueOperations.list("groups/my-group/nested/")).thenReturn(List.of("nifi"));
+
+ final List<String> secrets = service.listKeyValueSecrets("kv",
keyValueBackend.name(), "groups/my-group");
+ assertEquals(Arrays.asList("groups/my-group/app",
"groups/my-group/nested/nifi"), secrets);
+ Mockito.verify(keyValueOperations, Mockito.never()).list("/");
+ Mockito.verify(keyValueOperations,
Mockito.never()).list("groups/");
+ Mockito.verify(keyValueOperations).list("groups/my-group/");
+ Mockito.verify(keyValueOperations).list("groups/my-group/nested/");
+ Mockito.verifyNoMoreInteractions(keyValueOperations);
+ }
+ }
+
+ @ParameterizedTest
+ @EnumSource(KeyValueBackend.class)
+ public void testListKeyValueSecretsNormalizesSecretPathPrefixSlashes(final
KeyValueBackend backend) throws Exception {
+ when(properties.getKvVersion()).thenReturn(backend ==
KeyValueBackend.KV_1 ? 1 : 2);
+
+ try (StandardHashiCorpVaultCommunicationService service =
this.configureService()) {
+
+ final VaultTemplate vaultTemplate =
Mockito.mock(VaultTemplate.class);
+ final VaultKeyValueOperations keyValueOperations =
Mockito.mock(VaultKeyValueOperations.class);
+
+ final Field vaultTemplateField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("vaultTemplate");
+ vaultTemplateField.setAccessible(true);
+ vaultTemplateField.set(service, vaultTemplate);
+
+ final Field keyValueBackendField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("keyValueBackend");
+ keyValueBackendField.setAccessible(true);
+ final KeyValueBackend keyValueBackend = (KeyValueBackend)
keyValueBackendField.get(service);
+
+ when(vaultTemplate.opsForKeyValue("kv",
keyValueBackend)).thenReturn(keyValueOperations);
+
when(keyValueOperations.list("groups/my-group/")).thenReturn(List.of("app"));
+
+ for (final String prefix : List.of("groups/my-group",
"groups/my-group/", "/groups/my-group", "/groups/my-group/")) {
+ assertEquals(List.of("groups/my-group/app"),
service.listKeyValueSecrets("kv", keyValueBackend.name(), prefix));
+ }
+ }
+ }
+
+ @Test
+ public void testListKeyValueSecretsBlankSecretPathPrefixListsRoot() throws
Exception {
+ try (StandardHashiCorpVaultCommunicationService service =
this.configureService()) {
+
+ final VaultTemplate vaultTemplate =
Mockito.mock(VaultTemplate.class);
+ final VaultKeyValueOperations keyValueOperations =
Mockito.mock(VaultKeyValueOperations.class);
+
+ final Field vaultTemplateField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("vaultTemplate");
+ vaultTemplateField.setAccessible(true);
+ vaultTemplateField.set(service, vaultTemplate);
+
+ final Field keyValueBackendField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("keyValueBackend");
+ keyValueBackendField.setAccessible(true);
+ final KeyValueBackend keyValueBackend = (KeyValueBackend)
keyValueBackendField.get(service);
+
+ when(vaultTemplate.opsForKeyValue("kv",
keyValueBackend)).thenReturn(keyValueOperations);
+ when(keyValueOperations.list("/")).thenReturn(List.of("test"));
+
+ assertEquals(List.of("test"), service.listKeyValueSecrets("kv",
keyValueBackend.name(), null));
+ assertEquals(List.of("test"), service.listKeyValueSecrets("kv",
keyValueBackend.name(), ""));
+ assertEquals(List.of("test"), service.listKeyValueSecrets("kv",
keyValueBackend.name(), "/"));
+ }
+ }
+
+ @Test
+ public void testListKeyValueSecretsMissingSecretPathPrefixReturnsEmpty()
throws Exception {
+ try (StandardHashiCorpVaultCommunicationService service =
this.configureService()) {
+
+ final VaultTemplate vaultTemplate =
Mockito.mock(VaultTemplate.class);
+ final VaultKeyValueOperations keyValueOperations =
Mockito.mock(VaultKeyValueOperations.class);
+
+ final Field vaultTemplateField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("vaultTemplate");
+ vaultTemplateField.setAccessible(true);
+ vaultTemplateField.set(service, vaultTemplate);
+
+ final Field keyValueBackendField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("keyValueBackend");
+ keyValueBackendField.setAccessible(true);
+ final KeyValueBackend keyValueBackend = (KeyValueBackend)
keyValueBackendField.get(service);
+
+ when(vaultTemplate.opsForKeyValue("kv",
keyValueBackend)).thenReturn(keyValueOperations);
+ when(keyValueOperations.list("groups/unknown/")).thenReturn(null);
+
+ assertEquals(List.of(), service.listKeyValueSecrets("kv",
keyValueBackend.name(), "groups/unknown"));
+ }
+ }
+
+ @Test
+ public void
testListKeyValueSecretsDeniedSecretPathPrefixDoesNotFallBackToRoot() throws
Exception {
+ try (StandardHashiCorpVaultCommunicationService service =
this.configureService()) {
+ final VaultTemplate vaultTemplate =
Mockito.mock(VaultTemplate.class);
+ final VaultKeyValueOperations keyValueOperations =
Mockito.mock(VaultKeyValueOperations.class);
+
+ final Field vaultTemplateField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("vaultTemplate");
+ vaultTemplateField.setAccessible(true);
+ vaultTemplateField.set(service, vaultTemplate);
+
+ final Field keyValueBackendField =
StandardHashiCorpVaultCommunicationService.class.getDeclaredField("keyValueBackend");
+ keyValueBackendField.setAccessible(true);
+ final KeyValueBackend keyValueBackend = (KeyValueBackend)
keyValueBackendField.get(service);
+
+ when(vaultTemplate.opsForKeyValue("kv",
keyValueBackend)).thenReturn(keyValueOperations);
+ when(keyValueOperations.list("groups/my-group/")).thenThrow(new
VaultException("Permission denied"));
+
+ assertThrows(VaultException.class, () ->
service.listKeyValueSecrets("kv", keyValueBackend.name(), "groups/my-group"));
+ Mockito.verify(keyValueOperations).list("groups/my-group/");
+ Mockito.verifyNoMoreInteractions(keyValueOperations);
+ }
+ }
}
diff --git
a/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultParameterProvider.java
b/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultParameterProvider.java
index 0d9f44a51a2..5544ff21888 100644
---
a/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultParameterProvider.java
+++
b/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/main/java/org/apache/nifi/vault/hashicorp/HashiCorpVaultParameterProvider.java
@@ -70,6 +70,13 @@ public class HashiCorpVaultParameterProvider extends
AbstractParameterProvider i
.allowableValues(KV_1, KV_2)
.defaultValue(KV_1)
.build();
+ public static final PropertyDescriptor SECRET_PATH_PREFIX = new
PropertyDescriptor.Builder()
+ .name("secret-path-prefix")
+ .displayName("Secret Path Prefix")
+ .description("Optional path prefix relative to the Key/Value
Secrets Engine mount. When set, only secrets under this path are listed (for
example, 'nested/path').")
+ .addValidator(StandardValidators.NON_EMPTY_VALIDATOR)
+ .required(false)
+ .build();
public static final PropertyDescriptor SECRET_NAME_PATTERN = new
PropertyDescriptor.Builder()
.name("secret-name-pattern")
.displayName("Secret Name Pattern")
@@ -83,6 +90,7 @@ public class HashiCorpVaultParameterProvider extends
AbstractParameterProvider i
VAULT_CLIENT_SERVICE,
KV_PATH,
KV_VERSION,
+ SECRET_PATH_PREFIX,
SECRET_NAME_PATTERN
);
@@ -104,8 +112,9 @@ public class HashiCorpVaultParameterProvider extends
AbstractParameterProvider i
final
ConfigurationContext context) {
final String kvPath = context.getProperty(KV_PATH).getValue();
final String kvVersion = context.getProperty(KV_VERSION).getValue();
+ final String secretPathPrefix =
context.getProperty(SECRET_PATH_PREFIX).getValue();
final String secretIncludeRegex =
context.getProperty(SECRET_NAME_PATTERN).getValue();
- final List<String> allSecretNames =
vaultCommunicationService.listKeyValueSecrets(kvPath, kvVersion);
+ final List<String> allSecretNames =
vaultCommunicationService.listKeyValueSecrets(kvPath, kvVersion,
secretPathPrefix);
final List<String> secretNames = allSecretNames.stream()
.filter(name -> name.matches(secretIncludeRegex))
.collect(Collectors.toList());
diff --git
a/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/test/java/org/apache/nifi/vault/hashicorp/TestHashiCorpVaultParameterProvider.java
b/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/test/java/org/apache/nifi/vault/hashicorp/TestHashiCorpVaultParameterProvider.java
index 023152a95cb..9ba2d98b886 100644
---
a/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/test/java/org/apache/nifi/vault/hashicorp/TestHashiCorpVaultParameterProvider.java
+++
b/nifi-extension-bundles/nifi-hashicorp-vault-bundle/nifi-hashicorp-vault-parameter-provider/src/test/java/org/apache/nifi/vault/hashicorp/TestHashiCorpVaultParameterProvider.java
@@ -52,6 +52,8 @@ public class TestHashiCorpVaultParameterProvider {
private List<ParameterGroup> mockedGroups;
+ private String mockedSecretPathPrefix;
+
@BeforeEach
public void init() {
vaultCommunicationService =
mock(HashiCorpVaultCommunicationService.class);
@@ -67,6 +69,7 @@ public class TestHashiCorpVaultParameterProvider {
return mock(ComponentLog.class);
}
};
+ mockedSecretPathPrefix = "";
mockedGroups = new ArrayList<>();
mockedGroups.add(new ParameterGroup("groupA", Arrays.asList(
createParameter("paramA", "valueA"),
@@ -85,12 +88,13 @@ public class TestHashiCorpVaultParameterProvider {
@Test
public void testFetchParameters() {
final String kvVersion = "KV_1";
- mockSecrets("kv2", kvVersion, mockedGroups);
+ mockSecrets("kv2", kvVersion, mockedSecretPathPrefix, mockedGroups);
final Map<PropertyDescriptor, String> properties = new HashMap<>();
properties.put(HashiCorpVaultParameterProvider.KV_PATH, "kv2");
properties.put(HashiCorpVaultParameterProvider.KV_VERSION, kvVersion);
properties.put(HashiCorpVaultParameterProvider.VAULT_CLIENT_SERVICE,
"service");
+ properties.put(HashiCorpVaultParameterProvider.SECRET_PATH_PREFIX,
mockedSecretPathPrefix);
properties.put(HashiCorpVaultParameterProvider.SECRET_NAME_PATTERN,
".*");
final ConfigurationContext context = mockContext(properties);
@@ -104,12 +108,13 @@ public class TestHashiCorpVaultParameterProvider {
@Test
public void testFetchParametersSecretRegex() {
final String kvVersion = "KV_2";
- mockSecrets("kv2", kvVersion, mockedGroups);
+ mockSecrets("kv2", kvVersion, mockedSecretPathPrefix, mockedGroups);
final Map<PropertyDescriptor, String> properties = new HashMap<>();
properties.put(HashiCorpVaultParameterProvider.KV_PATH, "kv2");
properties.put(HashiCorpVaultParameterProvider.KV_VERSION, kvVersion);
properties.put(HashiCorpVaultParameterProvider.VAULT_CLIENT_SERVICE,
"service");
+ properties.put(HashiCorpVaultParameterProvider.SECRET_PATH_PREFIX,
mockedSecretPathPrefix);
properties.put(HashiCorpVaultParameterProvider.SECRET_NAME_PATTERN,
".*A");
final ConfigurationContext context = mockContext(properties);
@@ -120,15 +125,62 @@ public class TestHashiCorpVaultParameterProvider {
});
}
+ @Test
+ public void testFetchParametersSecretPathPrefix() {
+ final String kvVersion = "KV_2";
+ final String secretPathPrefix = "groups/my-group";
+ final List<ParameterGroup> prefixedGroups = Arrays.asList(
+ new ParameterGroup("groups/my-group/app",
List.of(createParameter("paramA", "valueA"))),
+ new ParameterGroup("groups/my-group/nested/nifi",
List.of(createParameter("paramB", "valueB"))));
+ mockSecrets("kv", kvVersion, secretPathPrefix, prefixedGroups);
+
+ final Map<PropertyDescriptor, String> properties = new HashMap<>();
+ properties.put(HashiCorpVaultParameterProvider.KV_PATH, "kv");
+ properties.put(HashiCorpVaultParameterProvider.KV_VERSION, kvVersion);
+ properties.put(HashiCorpVaultParameterProvider.VAULT_CLIENT_SERVICE,
"service");
+ properties.put(HashiCorpVaultParameterProvider.SECRET_PATH_PREFIX,
secretPathPrefix);
+ properties.put(HashiCorpVaultParameterProvider.SECRET_NAME_PATTERN,
".*");
+ final ConfigurationContext context = mockContext(properties);
+
+ final List<ParameterGroup> results =
parameterProvider.fetchParameters(context);
+
+ assertEquals(List.of("groups/my-group/app",
"groups/my-group/nested/nifi"),
+
results.stream().map(ParameterGroup::getGroupName).collect(Collectors.toList()));
+ }
+
+ @Test
+ public void testFetchParametersSecretPathPrefixWithSecretRegex() {
+ final String kvVersion = "KV_2";
+ final String secretPathPrefix = "groups/my-group";
+ final List<ParameterGroup> prefixedGroups = Arrays.asList(
+ new ParameterGroup("groups/my-group/app",
List.of(createParameter("paramA", "valueA"))),
+ new ParameterGroup("groups/my-group/nested/nifi",
List.of(createParameter("paramB", "valueB"))));
+ mockSecrets("kv", kvVersion, secretPathPrefix, prefixedGroups);
+
+ final Map<PropertyDescriptor, String> properties = new HashMap<>();
+ properties.put(HashiCorpVaultParameterProvider.KV_PATH, "kv");
+ properties.put(HashiCorpVaultParameterProvider.KV_VERSION, kvVersion);
+ properties.put(HashiCorpVaultParameterProvider.VAULT_CLIENT_SERVICE,
"service");
+ properties.put(HashiCorpVaultParameterProvider.SECRET_PATH_PREFIX,
secretPathPrefix);
+ properties.put(HashiCorpVaultParameterProvider.SECRET_NAME_PATTERN,
".*/nested/.*");
+ final ConfigurationContext context = mockContext(properties);
+
+ final List<ParameterGroup> results =
parameterProvider.fetchParameters(context);
+
+ assertEquals(List.of("groups/my-group/nested/nifi"),
+
results.stream().map(ParameterGroup::getGroupName).collect(Collectors.toList()));
+ }
+
@Test
public void testVerifyParameters() {
final String kvVersion = "KV_1";
- mockSecrets("kv2", kvVersion, mockedGroups);
+ mockSecrets("kv2", kvVersion, mockedSecretPathPrefix, mockedGroups);
final Map<PropertyDescriptor, String> properties = new HashMap<>();
properties.put(HashiCorpVaultParameterProvider.KV_PATH, "kv2");
properties.put(HashiCorpVaultParameterProvider.KV_VERSION, kvVersion);
properties.put(HashiCorpVaultParameterProvider.VAULT_CLIENT_SERVICE,
"service");
+ properties.put(HashiCorpVaultParameterProvider.SECRET_PATH_PREFIX,
mockedSecretPathPrefix);
properties.put(HashiCorpVaultParameterProvider.SECRET_NAME_PATTERN,
".*");
final ConfigurationContext context = mockContext(properties);
@@ -151,8 +203,8 @@ public class TestHashiCorpVaultParameterProvider {
lenient().when(context.getProperty(descriptor)).thenReturn(propertyValue);
}
- private void mockSecrets(final String kvPath, final String kvVersion,
final List<ParameterGroup> parameterGroups) {
- when(vaultCommunicationService.listKeyValueSecrets(kvPath, kvVersion))
+ private void mockSecrets(final String kvPath, final String kvVersion,
final String secretPathPrefix, final List<ParameterGroup> parameterGroups) {
+ when(vaultCommunicationService.listKeyValueSecrets(kvPath, kvVersion,
secretPathPrefix))
.thenReturn(parameterGroups.stream().map(group ->
group.getGroupName()).collect(Collectors.toList()));
for (final ParameterGroup parameterGroup : parameterGroups) {
final Map<String, String> keyValues =
parameterGroup.getParameters().stream()