Skip to content

Commit

Permalink
feat: Resolve system properties/environment variables while browsing the
Browse files Browse the repository at this point in the history
application.properties values

Fixes eclipse#448

Signed-off-by: azerr <azerr@redhat.com>
  • Loading branch information
angelozerr committed Aug 14, 2024
1 parent 228499f commit 94c085d
Show file tree
Hide file tree
Showing 6 changed files with 179 additions and 56 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -202,7 +202,10 @@ private synchronized void synchUpdateCustomProperties(PropertiesModel document)
// - a Java sources changes (document = null)
// - a microprofile-config.properties changes (document != null)
if (document != null || provider.isAvailable()) {
List<ItemMetadata> oldProperties = new ArrayList<>(provider.getProperties());
List<ItemMetadata> oldProperties = provider.getProperties();
if (oldProperties != null) {
oldProperties = new ArrayList<>(oldProperties);
}
provider.update(document);
List<ItemMetadata> newProperties = provider.getProperties();
if (!Objects.deepEquals(oldProperties, newProperties)) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
package org.eclipse.lsp4mp.extensions.sysenv;

import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import org.eclipse.lsp4mp.commons.metadata.ItemMetadata;
import org.eclipse.lsp4mp.commons.utils.StringUtils;
import org.eclipse.lsp4mp.extensions.ExtendedMicroProfileProjectInfo;
import org.eclipse.lsp4mp.extensions.ItemMetadataProvider;
import org.eclipse.lsp4mp.model.PropertiesModel;

/**
* Properties provider for Environment variables and System properties.
*/
public class SysEnvItemMetadataProvider implements ItemMetadataProvider {

private List<ItemMetadata> sysEnvProperties;

public SysEnvItemMetadataProvider(ExtendedMicroProfileProjectInfo projectInfo) {

}

@Override
public boolean isAvailable() {
return true;
}

@Override
public void update(PropertiesModel document) {
this.sysEnvProperties = collectSysEnvProperties();
}

@Override
public List<ItemMetadata> getProperties() {
return sysEnvProperties;
}

private static List<ItemMetadata> collectSysEnvProperties() {
Stream<ItemMetadata> sysProps = System.getProperties().entrySet().stream().map(e -> {
String name = e.getKey().toString();
String defaultValue = e.getValue() != null ? e.getValue().toString() : null;

ItemMetadata item = new ItemMetadata();
item.setExtensionName("System property");
item.setName(name);
item.setDefaultValue(defaultValue);
item.setType("java.lang.String");
return item;
});

Stream<ItemMetadata> envVars = System.getenv().entrySet().stream().map(e -> {
String name = e.getKey();
// Poor-man obfuscation of env var keys (*_KEY) and secrets (*_SECRET)
// Maybe later add configuration for suffixes and/or actual keys to obfuscate
String defaultValue = obfuscate(name, e.getValue());

ItemMetadata item = new ItemMetadata();
item.setExtensionName("Environment variable");
item.setName(name);
item.setDefaultValue(defaultValue);
item.setType("java.lang.String");
return item;
});

return Stream.concat(sysProps, envVars)//
.collect(Collectors.toList());

}

private static String obfuscate(String key, String value) {
if (StringUtils.isEmpty(key)) {
return key;
}
String upKey = key.toUpperCase().replace(".", "_");
return upKey.endsWith("_KEY") || upKey.endsWith("_SECRET") || upKey.endsWith("_PASSOWORD")
|| upKey.endsWith("_TOKEN") ? "*********" : value;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
/*******************************************************************************
* Copyright (c) 2024 Red Hat Inc. and others.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0, or the Apache License, Version 2.0
* which is available at https://www.apache.org/licenses/LICENSE-2.0.
*
* SPDX-License-Identifier: EPL-2.0 OR Apache-2.0
*
* Contributors:
* Red Hat Inc. - initial API and implementation
*******************************************************************************/
package org.eclipse.lsp4mp.extensions.sysenv;

import org.eclipse.lsp4mp.extensions.ExtendedMicroProfileProjectInfo;
import org.eclipse.lsp4mp.extensions.ItemMetadataProvider;
import org.eclipse.lsp4mp.extensions.ItemMetadataProviderFactory;

/**
* Factory for creating {@link ItemMetadataProvider} instance for System
* properties and Environment variables.
*
* @author Angelo ZERR
*
*/
public class SysEnvItemMetadataProviderFactory implements ItemMetadataProviderFactory {

@Override
public ItemMetadataProvider create(ExtendedMicroProfileProjectInfo projectInfo) {
return new SysEnvItemMetadataProvider(projectInfo);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,8 @@

import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.function.Predicate;
Expand All @@ -41,7 +39,6 @@
import org.eclipse.lsp4mp.commons.metadata.ConverterKind;
import org.eclipse.lsp4mp.commons.metadata.ItemMetadata;
import org.eclipse.lsp4mp.commons.metadata.ValueHint;
import org.eclipse.lsp4mp.commons.utils.ConfigSourcePropertiesProviderUtils;
import org.eclipse.lsp4mp.commons.utils.PropertyValueExpander;
import org.eclipse.lsp4mp.commons.utils.StringUtils;
import org.eclipse.lsp4mp.ls.commons.BadLocationException;
Expand Down Expand Up @@ -122,8 +119,8 @@ public CompletionList doComplete(PropertiesModel document, Position position, Mi
completionItemDefaults, list);
} else {
// other.test.property = ${|}
collectPropertyValueExpressionSuggestions(propExpr, document, projectInfo, completionCapabilities,
list, cancelChecker);
collectPropertyValueExpressionSuggestions(propExpr, document, projectInfo, completionCapabilities, list,
cancelChecker);
}
break;

Expand Down Expand Up @@ -327,7 +324,8 @@ private static void collectPropertyKeySuggestions(int offset, Node node, Propert
* was invoked
* @param key the property key
* @param model the properties model
* @param markdownSupported boolean determining if markdown is supported
* @param markdownSupported boolean determining if
* markdown is supported
* @param completionResolveDocumentationSupported true if completion resolve for
* documentation is supported
* @param completionCapabilities the completion capabilities
Expand Down Expand Up @@ -534,7 +532,8 @@ private static void collectPropertyValueExpressionSuggestions(PropertyValueExpre
// Add all properties not referenced in the properties file as completion
// options only the property has no default value
for (ItemMetadata candidateCompletion : projectInfo.getProperties()) {
if (candidateCompletion.getDefaultValue() == null) {
if (StringUtils.isEmpty(candidateCompletion.getSourceType())
|| candidateCompletion.getDefaultValue() == null) {
String candidateCompletionName = candidateCompletion.getName();
if (!model.hasKey(candidateCompletionName)) {
list.getItems().add(getPropertyCompletionItem(candidateCompletionName, node, model));
Expand All @@ -551,7 +550,8 @@ private static void collectPropertyValueExpressionSuggestions(PropertyValueExpre
* @param converterKinds the converter kinds.
* @param range the range for completion
* @param model the property model
* @param markdownSupported true if markdown is supported and false otherwise.
* @param markdownSupported true if markdown is supported and false
* otherwise.
* @param completionItemDefaults the completion itemDefaults
* @return the value completion item
*/
Expand Down
Loading

0 comments on commit 94c085d

Please sign in to comment.