-
Notifications
You must be signed in to change notification settings - Fork 71
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
normalization: add normalization of the options
The options could be of different types: 1. string 2. boolean 3. number 4. enum 5. map 6. list 7. option Here I've added an example for each one of them: Sure! Here are examples for each type of option in Protobuf: 1. STRING: ``` option example_option = "hello world"; ``` 2. BOOLEAN: ``` option example_option = true; ``` 3. NUMBER: ``` option example_option = 42; ``` 4. ENUM: ``` enum ExampleEnum { OPTION_ONE = 1; OPTION_TWO = 2; } option example_option = OPTION_ONE; ``` 5. MAP: ``` message ExampleMessage { map<string, int32> example_map = 1; } option (map_option) = { key: "key1" value: 42 }; ``` 6. LIST: ``` message ExampleMessage { repeated string example_list = 1; } option (list_option) = [ "item1", "item2", "item3" ]; ``` 7. OPTION: ``` option (custom_option) = { string_option: "hello world", enum_option: OPTION_ONE, boolean_option: true }; ``` The goal of this pr its to start the process of normalization of the schemas initially just for the options in the protobuf types. For the reviewers: I'm not completely familiar with protobuf nor the normalizations, please read each line of documentation (of the code and of the pr) and if anything doesn't sound right or you found something that seems wrong please discuss about it!
- Loading branch information
Showing
6 changed files
with
171 additions
and
2 deletions.
There are no files selected for viewing
This file contains 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
This file contains 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,36 @@ | ||
""" | ||
Copyright (c) 2024 Aiven Ltd | ||
See LICENSE for details | ||
""" | ||
from karapace.protobuf.proto_file_element import ProtoFileElement | ||
from karapace.typing import StrEnum | ||
|
||
|
||
class ProtobufNormalisationOptions(StrEnum): | ||
sort_options = "sort_options" | ||
|
||
|
||
def normalize_options_ordered(proto_file_element: ProtoFileElement) -> ProtoFileElement: | ||
sorted_options = ( | ||
None if proto_file_element.options is None else list(sorted(proto_file_element.options, key=lambda x: x.name)) | ||
) | ||
return ProtoFileElement( | ||
location=proto_file_element.location, | ||
package_name=proto_file_element.package_name, | ||
syntax=proto_file_element.syntax, | ||
imports=proto_file_element.imports, | ||
public_imports=proto_file_element.public_imports, | ||
types=proto_file_element.types, | ||
services=proto_file_element.services, | ||
extend_declarations=proto_file_element.extend_declarations, | ||
options=sorted_options, | ||
) | ||
|
||
|
||
# if other normalizations are added we will switch to a more generic approach: | ||
# def normalize_parsed_file(proto_file_element: ProtoFileElement, | ||
# normalization: ProtobufNormalisationOptions) -> ProtoFileElement: | ||
# if normalization == ProtobufNormalisationOptions.sort_options: | ||
# return normalize_options_ordered(proto_file_element) | ||
# else: | ||
# assert_never(normalization) |
This file contains 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
This file contains 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
This file contains 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
This file contains 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,71 @@ | ||
""" | ||
Copyright (c) 2024 Aiven Ltd | ||
See LICENSE for details | ||
""" | ||
from karapace.protobuf.compare_result import CompareResult | ||
from karapace.protobuf.location import Location | ||
from karapace.protobuf.proto_normalizations import normalize_options_ordered | ||
from karapace.protobuf.proto_parser import ProtoParser | ||
|
||
location: Location = Location("some/folder", "file.proto") | ||
|
||
|
||
def test_different_options_order_its_correctly_normalized() -> None: | ||
ordered_schema = """\ | ||
syntax = "proto3"; | ||
package pkg; | ||
option cc_generic_services = true; | ||
option java_generate_equals_and_hash = true; | ||
option java_generic_services = true; | ||
option java_multiple_files = true; | ||
option java_outer_classname = "FooProto"; | ||
option java_package = "com.example.foo"; | ||
option java_string_check_utf8 = true; | ||
option optimize_for = SPEED; | ||
message Foo { | ||
string fieldA = 1; | ||
string fieldB = 2; | ||
string fieldC = 3; | ||
string fieldX = 4; | ||
} | ||
""" | ||
|
||
unordered_schema = """\ | ||
syntax = "proto3"; | ||
package pkg; | ||
option java_generic_services = true; | ||
option java_generate_equals_and_hash = true; | ||
option java_package = "com.example.foo"; | ||
option java_outer_classname = "FooProto"; | ||
option optimize_for = SPEED; | ||
option cc_generic_services = true; | ||
option java_multiple_files = true; | ||
option java_string_check_utf8 = true; | ||
message Foo { | ||
string fieldA = 1; | ||
string fieldB = 2; | ||
string fieldC = 3; | ||
string fieldX = 4; | ||
} | ||
""" | ||
|
||
ordered_proto = ProtoParser.parse(location, ordered_schema) | ||
unordered_proto = ProtoParser.parse(location, unordered_schema) | ||
|
||
result = CompareResult() | ||
assert result.is_compatible() | ||
normalize_options_ordered(ordered_proto).compare(normalize_options_ordered(unordered_proto), result) | ||
assert result.is_compatible() | ||
assert normalize_options_ordered(ordered_proto).to_schema() == normalize_options_ordered(unordered_proto).to_schema() |