-
Notifications
You must be signed in to change notification settings - Fork 15.4k
KAFKA-10570 Rename JMXReporter configs for KIP-629 #9367
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Closed
Closed
Changes from all commits
Commits
Show all changes
2 commits
Select commit
Hold shift + click to select a range
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
116 changes: 116 additions & 0 deletions
116
clients/src/main/java/org/apache/kafka/common/utils/ConfigUtils.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,116 @@ | ||
| /* | ||
| * Licensed to the Apache Software Foundation (ASF) under one or more | ||
| * contributor license agreements. See the NOTICE file distributed with | ||
| * this work for additional information regarding copyright ownership. | ||
| * The ASF licenses this file to You under the Apache License, Version 2.0 | ||
| * (the "License"); you may not use this file except in compliance with | ||
| * the License. You may obtain a copy of the License at | ||
| * | ||
| * http://www.apache.org/licenses/LICENSE-2.0 | ||
| * | ||
| * Unless required by applicable law or agreed to in writing, software | ||
| * distributed under the License is distributed on an "AS IS" BASIS, | ||
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| * See the License for the specific language governing permissions and | ||
| * limitations under the License. | ||
| */ | ||
|
|
||
| package org.apache.kafka.common.utils; | ||
|
|
||
| import org.slf4j.Logger; | ||
| import org.slf4j.LoggerFactory; | ||
|
|
||
| import java.util.Collection; | ||
| import java.util.List; | ||
| import java.util.Map; | ||
| import java.util.Objects; | ||
| import java.util.Set; | ||
| import java.util.stream.Collectors; | ||
| import java.util.stream.Stream; | ||
|
|
||
| public class ConfigUtils { | ||
|
|
||
| private static final Logger log = LoggerFactory.getLogger(ConfigUtils.class); | ||
|
|
||
| /** | ||
| * Translates deprecated configurations into their non-deprecated equivalents | ||
| * | ||
| * This is a convenience method for {@link ConfigUtils#translateDeprecatedConfigs(Map, Map)} | ||
| * until we can use Java 9+ {@code Map.of(..)} and {@code Set.of(...)} | ||
| * | ||
| * @param configs the input configuration | ||
| * @param aliasGroups An array of arrays of synonyms. Each synonym array begins with the non-deprecated synonym | ||
| * For example, new String[][] { { a, b }, { c, d, e} } | ||
| * would declare b as a deprecated synonym for a, | ||
| * and d and e as deprecated synonyms for c. | ||
| * The ordering of synonyms determines the order of precedence | ||
| * (e.g. the first synonym takes precedence over the second one) | ||
| * @return a new configuration map with deprecated keys translated to their non-deprecated equivalents | ||
| */ | ||
| public static <T> Map<String, T> translateDeprecatedConfigs(Map<String, T> configs, String[][] aliasGroups) { | ||
| return translateDeprecatedConfigs(configs, Stream.of(aliasGroups) | ||
| .collect(Collectors.toMap(x -> x[0], x -> Stream.of(x).skip(1).collect(Collectors.toList())))); | ||
| } | ||
|
|
||
| /** | ||
| * Translates deprecated configurations into their non-deprecated equivalents | ||
| * | ||
| * @param configs the input configuration | ||
| * @param aliasGroups A map of config to synonyms. Each key is the non-deprecated synonym | ||
| * For example, Map.of(a , Set.of(b), c, Set.of(d, e)) | ||
| * would declare b as a deprecated synonym for a, | ||
| * and d and e as deprecated synonyms for c. | ||
| * The ordering of synonyms determines the order of precedence | ||
| * (e.g. the first synonym takes precedence over the second one) | ||
| * @return a new configuration map with deprecated keys translated to their non-deprecated equivalents | ||
| */ | ||
| public static <T> Map<String, T> translateDeprecatedConfigs(Map<String, T> configs, | ||
| Map<String, List<String>> aliasGroups) { | ||
| Set<String> aliasSet = Stream.concat( | ||
| aliasGroups.keySet().stream(), | ||
| aliasGroups.values().stream().flatMap(Collection::stream)) | ||
| .collect(Collectors.toSet()); | ||
|
|
||
| // pass through all configurations without aliases | ||
| Map<String, T> newConfigs = configs.entrySet().stream() | ||
| .filter(e -> !aliasSet.contains(e.getKey())) | ||
| // filter out null values | ||
| .filter(e -> Objects.nonNull(e.getValue())) | ||
| .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)); | ||
|
|
||
| aliasGroups.forEach((target, aliases) -> { | ||
| List<String> deprecated = aliases.stream() | ||
| .filter(configs::containsKey) | ||
| .collect(Collectors.toList()); | ||
|
|
||
| if (deprecated.isEmpty()) { | ||
| // No deprecated key(s) found. | ||
| if (configs.containsKey(target)) { | ||
| newConfigs.put(target, configs.get(target)); | ||
| } | ||
| return; | ||
| } | ||
|
|
||
| String aliasString = String.join(", ", deprecated); | ||
|
|
||
| if (configs.containsKey(target)) { | ||
| // Ignore the deprecated key(s) because the actual key was set. | ||
| log.error(target + " was configured, as well as the deprecated alias(es) " + | ||
| aliasString + ". Using the value of " + target); | ||
| newConfigs.put(target, configs.get(target)); | ||
| } else if (deprecated.size() > 1) { | ||
| log.error("The configuration keys " + aliasString + " are deprecated and may be " + | ||
| "removed in the future. Additionally, this configuration is ambigous because " + | ||
| "these configuration keys are all aliases for " + target + ". Please update " + | ||
| "your configuration to have only " + target + " set."); | ||
| newConfigs.put(target, configs.get(deprecated.get(0))); | ||
| } else { | ||
| log.warn("Configuration key " + deprecated.get(0) + " is deprecated and may be removed " + | ||
| "in the future. Please update your configuration to use " + target + " instead."); | ||
| newConfigs.put(target, configs.get(deprecated.get(0))); | ||
| } | ||
| }); | ||
|
|
||
| return newConfigs; | ||
| } | ||
| } | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
143 changes: 143 additions & 0 deletions
143
clients/src/test/java/org/apache/kafka/common/utils/ConfigUtilsTest.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,143 @@ | ||
| /* | ||
| * Licensed to the Apache Software Foundation (ASF) under one or more | ||
| * contributor license agreements. See the NOTICE file distributed with | ||
| * this work for additional information regarding copyright ownership. | ||
| * The ASF licenses this file to You under the Apache License, Version 2.0 | ||
| * (the "License"); you may not use this file except in compliance with | ||
| * the License. You may obtain a copy of the License at | ||
| * | ||
| * http://www.apache.org/licenses/LICENSE-2.0 | ||
| * | ||
| * Unless required by applicable law or agreed to in writing, software | ||
| * distributed under the License is distributed on an "AS IS" BASIS, | ||
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| * See the License for the specific language governing permissions and | ||
| * limitations under the License. | ||
| */ | ||
|
|
||
| package org.apache.kafka.common.utils; | ||
|
|
||
| import org.junit.Test; | ||
|
|
||
| import java.util.HashMap; | ||
| import java.util.Map; | ||
|
|
||
| import static org.junit.Assert.assertEquals; | ||
| import static org.junit.Assert.assertNotNull; | ||
| import static org.junit.Assert.assertNull; | ||
|
|
||
| public class ConfigUtilsTest { | ||
|
|
||
| @Test | ||
| public void testTranslateDeprecated() { | ||
| Map<String, Object> config = new HashMap<>(); | ||
| config.put("foo.bar", "baz"); | ||
| config.put("foo.bar.deprecated", "quux"); | ||
| config.put("chicken", "1"); | ||
| config.put("rooster", "2"); | ||
| config.put("hen", "3"); | ||
| config.put("heifer", "moo"); | ||
| config.put("blah", "blah"); | ||
| config.put("unexpected.non.string.object", 42); | ||
| Map<String, Object> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated"}, | ||
| {"chicken", "rooster", "hen"}, | ||
| {"cow", "beef", "heifer", "steer"} | ||
| }); | ||
| assertEquals("baz", newConfig.get("foo.bar")); | ||
| assertEquals(null, newConfig.get("foobar.deprecated")); | ||
| assertEquals("1", newConfig.get("chicken")); | ||
| assertEquals(null, newConfig.get("rooster")); | ||
| assertEquals(null, newConfig.get("hen")); | ||
| assertEquals("moo", newConfig.get("cow")); | ||
| assertEquals(null, newConfig.get("beef")); | ||
| assertEquals(null, newConfig.get("heifer")); | ||
| assertEquals(null, newConfig.get("steer")); | ||
| assertEquals(null, config.get("cow")); | ||
| assertEquals("blah", config.get("blah")); | ||
| assertEquals("blah", newConfig.get("blah")); | ||
| assertEquals(42, newConfig.get("unexpected.non.string.object")); | ||
| assertEquals(42, config.get("unexpected.non.string.object")); | ||
|
|
||
| } | ||
|
|
||
| @Test | ||
| public void testAllowsNewKey() { | ||
| Map<String, String> config = new HashMap<>(); | ||
| config.put("foo.bar", "baz"); | ||
| Map<String, String> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated"}, | ||
| {"chicken", "rooster", "hen"}, | ||
| {"cow", "beef", "heifer", "steer"} | ||
| }); | ||
| assertNotNull(newConfig); | ||
| assertEquals("baz", newConfig.get("foo.bar")); | ||
| assertNull(newConfig.get("foo.bar.deprecated")); | ||
| } | ||
|
|
||
| @Test | ||
| public void testAllowDeprecatedNulls() { | ||
| Map<String, String> config = new HashMap<>(); | ||
| config.put("foo.bar.deprecated", null); | ||
| config.put("foo.bar", "baz"); | ||
| Map<String, String> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated"} | ||
| }); | ||
| assertNotNull(newConfig); | ||
| assertEquals("baz", newConfig.get("foo.bar")); | ||
| assertNull(newConfig.get("foo.bar.deprecated")); | ||
| } | ||
|
|
||
| @Test | ||
| public void testAllowNullOverride() { | ||
| Map<String, String> config = new HashMap<>(); | ||
| config.put("foo.bar.deprecated", "baz"); | ||
| config.put("foo.bar", null); | ||
| Map<String, String> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated"} | ||
| }); | ||
| assertNotNull(newConfig); | ||
| assertNull(newConfig.get("foo.bar")); | ||
| assertNull(newConfig.get("foo.bar.deprecated")); | ||
| } | ||
|
|
||
| @Test | ||
| public void testNullMapEntriesWithoutAliasesDoNotThrowNPE() { | ||
| Map<String, String> config = new HashMap<>(); | ||
| config.put("other", null); | ||
| Map<String, String> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated"} | ||
| }); | ||
| assertNotNull(newConfig); | ||
| assertNull(newConfig.get("other")); | ||
| } | ||
|
|
||
| @Test | ||
| public void testDuplicateSynonyms() { | ||
| Map<String, String> config = new HashMap<>(); | ||
| config.put("foo.bar", "baz"); | ||
| config.put("foo.bar.deprecated", "derp"); | ||
| Map<String, String> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated"}, | ||
| {"chicken", "foo.bar.deprecated"} | ||
| }); | ||
| assertNotNull(newConfig); | ||
| assertEquals("baz", newConfig.get("foo.bar")); | ||
| assertEquals("derp", newConfig.get("chicken")); | ||
| assertNull(newConfig.get("foo.bar.deprecated")); | ||
| } | ||
|
|
||
| @Test | ||
| public void testMultipleDeprecations() { | ||
| Map<String, String> config = new HashMap<>(); | ||
| config.put("foo.bar.deprecated", "derp"); | ||
| config.put("foo.bar.even.more.deprecated", "very old configuration"); | ||
| Map<String, String> newConfig = ConfigUtils.translateDeprecatedConfigs(config, new String[][]{ | ||
| {"foo.bar", "foo.bar.deprecated", "foo.bar.even.more.deprecated"} | ||
| }); | ||
| assertNotNull(newConfig); | ||
| assertEquals("derp", newConfig.get("foo.bar")); | ||
| assertNull(newConfig.get("foo.bar.deprecated")); | ||
| assertNull(newConfig.get("foo.bar.even.more.deprecated")); | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I like the extra-detailed error messages, thank you.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you have to thank @cmccabe for that ;)