Skip to content
This repository was archived by the owner on Jun 28, 2022. It is now read-only.

Commit 5ecc799

Browse files
authored
Add ConfigV2 Validator (#2672)
1 parent 1214ae5 commit 5ecc799

File tree

2 files changed

+126
-0
lines changed

2 files changed

+126
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
/* Copyright 2019 Google LLC
2+
*
3+
* Licensed under the Apache License, Version 2.0 (the "License");
4+
* you may not use this file except in compliance with the License.
5+
* You may obtain a copy of the License at
6+
*
7+
* https://www.apache.org/licenses/LICENSE-2.0
8+
*
9+
* Unless required by applicable law or agreed to in writing, software
10+
* distributed under the License is distributed on an "AS IS" BASIS,
11+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
* See the License for the specific language governing permissions and
13+
* limitations under the License.
14+
*/
15+
package com.google.api.codegen.util;
16+
17+
import com.google.protobuf.DiscardUnknownFieldsParser;
18+
import com.google.protobuf.InvalidProtocolBufferException;
19+
import com.google.protobuf.Parser;
20+
import java.util.Arrays;
21+
import javax.annotation.Nonnull;
22+
23+
public class ConfigVersionValidator {
24+
25+
public static String CONFIG_V2_MAJOR_VERSION = "2";
26+
public static String CONFIG_V2_VERSION = CONFIG_V2_MAJOR_VERSION + ".0.0"; // "2.0.0"
27+
28+
/**
29+
* Throw {@link IllegalStateException} iff the given input contains fields unknown to the {@link
30+
* com.google.api.codegen.v2.ConfigProto} schema.
31+
*/
32+
public void validateV2Config(@Nonnull com.google.api.codegen.ConfigProto configV1Proto)
33+
throws IllegalStateException {
34+
if (!configV1Proto.getConfigSchemaVersion().startsWith(CONFIG_V2_MAJOR_VERSION + ".")
35+
&& !configV1Proto.getConfigSchemaVersion().equals(CONFIG_V2_MAJOR_VERSION)) {
36+
throw new IllegalStateException(
37+
String.format(
38+
"Provided ConfigProto version is %s but should be >= %s",
39+
configV1Proto.getConfigSchemaVersion(), CONFIG_V2_VERSION));
40+
}
41+
42+
try {
43+
// Serialize and deserialize the Config v1 proto under the Config v2 schema to remove fields
44+
// unknown to Config v2 schema.
45+
Parser<com.google.api.codegen.v2.ConfigProto> parser =
46+
DiscardUnknownFieldsParser.wrap(com.google.api.codegen.v2.ConfigProto.parser());
47+
com.google.api.codegen.v2.ConfigProto configV2 =
48+
parser.parseFrom(configV1Proto.toByteString());
49+
50+
// Compare the v1-serialized and v2-serialized strings of the same config proto object.
51+
if (!Arrays.equals(configV2.toByteArray(), configV1Proto.toByteArray())) {
52+
throw new IllegalStateException(
53+
String.format(
54+
"Unknown fields to ConfigProto v2 in configProto: %s", configV1Proto.toString()));
55+
}
56+
} catch (InvalidProtocolBufferException e) {
57+
throw new IllegalStateException(e);
58+
}
59+
}
60+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
/* Copyright 2019 Google LLC
2+
*
3+
* Licensed under the Apache License, Version 2.0 (the "License");
4+
* you may not use this file except in compliance with the License.
5+
* You may obtain a copy of the License at
6+
*
7+
* https://www.apache.org/licenses/LICENSE-2.0
8+
*
9+
* Unless required by applicable law or agreed to in writing, software
10+
* distributed under the License is distributed on an "AS IS" BASIS,
11+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
* See the License for the specific language governing permissions and
13+
* limitations under the License.
14+
*/
15+
package com.google.api.codegen.util;
16+
17+
import com.google.api.codegen.ConfigProto;
18+
import com.google.api.codegen.FlatteningConfigProto;
19+
import com.google.api.codegen.FlatteningGroupProto;
20+
import com.google.api.codegen.InterfaceConfigProto;
21+
import com.google.api.codegen.MethodConfigProto;
22+
import com.google.protobuf.BoolValue;
23+
import org.junit.Test;
24+
25+
public class ConfigValidatorTest {
26+
private static final ConfigProto validV2Proto =
27+
ConfigProto.newBuilder()
28+
.setConfigSchemaVersion("2.0.0")
29+
// This is a valid field for both Config v1 and Config v2.
30+
.setEnableStringFormatFunctionsOverride(BoolValue.of(true))
31+
.build();
32+
33+
private static final ConfigVersionValidator validator = new ConfigVersionValidator();
34+
35+
@Test(expected = IllegalStateException.class)
36+
public void testProtoIsNotConfigNextVersion() {
37+
ConfigProto smallProto = validV2Proto.toBuilder().setConfigSchemaVersion("1.0.0").build();
38+
validator.validateV2Config(smallProto);
39+
}
40+
41+
@Test(expected = IllegalStateException.class)
42+
public void testProtoIsNotValid() {
43+
ConfigProto smallProto =
44+
validV2Proto
45+
.toBuilder()
46+
.addInterfaces(
47+
InterfaceConfigProto.newBuilder()
48+
.addMethods(
49+
MethodConfigProto.newBuilder()
50+
.setFlattening(
51+
FlatteningConfigProto.newBuilder()
52+
.addGroups(
53+
FlatteningGroupProto.newBuilder()
54+
.addParameters("flattenedParam")
55+
.build())
56+
.build()))
57+
.build())
58+
.build();
59+
validator.validateV2Config(smallProto);
60+
}
61+
62+
@Test
63+
public void testProtoIsValid() {
64+
validator.validateV2Config(validV2Proto);
65+
}
66+
}

0 commit comments

Comments
 (0)