THRIFT-3214 Add Erlang option for using maps instead of dicts
Client: Erlang
Patch: Michael Oliver <mikemboliver@gmail.com>
This closes #535
diff --git a/compiler/cpp/src/generate/t_erl_generator.cc b/compiler/cpp/src/generate/t_erl_generator.cc
index 342c581..8af5da2 100644
--- a/compiler/cpp/src/generate/t_erl_generator.cc
+++ b/compiler/cpp/src/generate/t_erl_generator.cc
@@ -55,6 +55,7 @@
out_dir_base_ = "gen-erl";
legacy_names_ = (parsed_options.find("legacynames") != parsed_options.end());
+ maps_ = (parsed_options.find("maps") != parsed_options.end());
}
/**
@@ -152,6 +153,9 @@
/* if true retain pre 0.9.2 naming scheme for functions, atoms and consts */
bool legacy_names_;
+ /* if true use maps instead of dicts in generated code */
+ bool maps_;
+
/**
* add function to export list
*/
@@ -430,7 +434,11 @@
t_type* ktype = ((t_map*)type)->get_key_type();
t_type* vtype = ((t_map*)type)->get_val_type();
- out << "dict:from_list([";
+ if (maps_) {
+ out << "maps:from_list([";
+ } else {
+ out << "dict:from_list([";
+ }
map<t_const_value*, t_const_value*>::const_iterator i, end = value->get_map().end();
for (i = value->get_map().begin(); i != end;) {
out << "{" << render_const_value(ktype, i->first) << ","
@@ -479,7 +487,11 @@
if (type->is_struct() || type->is_xception()) {
return "#" + atomify(type->get_name()) + "{}";
} else if (type->is_map()) {
- return "dict:new()";
+ if (maps_) {
+ return "#{}";
+ } else {
+ return "dict:new()";
+ }
} else if (type->is_set()) {
return "sets:new()";
} else if (type->is_list()) {
@@ -513,7 +525,11 @@
} else if (type->is_struct() || type->is_xception()) {
return atomify(type->get_name()) + "()";
} else if (type->is_map()) {
- return "dict:dict()";
+ if (maps_) {
+ return "#{}";
+ } else {
+ return "dict:dict()";
+ }
} else if (type->is_set()) {
return "sets:set()";
} else if (type->is_list()) {
@@ -1010,4 +1026,5 @@
THRIFT_REGISTER_GENERATOR(
erl,
"Erlang",
- " legacynames: Output files retain naming conventions of Thrift 0.9.1 and earlier.\n")
+ " legacynames: Output files retain naming conventions of Thrift 0.9.1 and earlier.\n"
+ " maps: Generate maps instead of dicts.\n")
diff --git a/lib/erl/Makefile.am b/lib/erl/Makefile.am
index 60c7e5a..1f65a24 100644
--- a/lib/erl/Makefile.am
+++ b/lib/erl/Makefile.am
@@ -25,6 +25,7 @@
for f in $(THRIFT_FILES) ; do \
$(THRIFT) --gen erl -o test $$f ; \
done ; \
+ $(THRIFT) --gen erl:maps -o test test/Thrift3214.thrift ; \
touch .generated
all: .generated
diff --git a/lib/erl/test/Thrift3214.thrift b/lib/erl/test/Thrift3214.thrift
new file mode 100644
index 0000000..a9110ce
--- /dev/null
+++ b/lib/erl/test/Thrift3214.thrift
@@ -0,0 +1,23 @@
+/*
+ * 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.
+ */
+
+struct StringMap
+{
+ 1: map<i32, string> data = {1: "a", 2: "b"};
+}
diff --git a/lib/erl/test/test_thrift_3214.erl b/lib/erl/test/test_thrift_3214.erl
new file mode 100644
index 0000000..118e779
--- /dev/null
+++ b/lib/erl/test/test_thrift_3214.erl
@@ -0,0 +1,58 @@
+%%
+%% 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.
+%%
+
+-module(test_thrift_3214).
+-compile(export_all).
+
+-include("gen-erl/thrift3214_types.hrl").
+
+-ifdef(TEST).
+-include_lib("eunit/include/eunit.hrl").
+
+record_generation_test_() ->
+ [
+ {"StringMap record", ?_assertMatch(
+ {'StringMap', _},
+ #'StringMap'{data=#{50 => "foo"}}
+ )},
+ {"StringMap record defaults", ?_assertEqual(
+ {'StringMap', #{1 => "a", 2 => "b"}},
+ #'StringMap'{}
+ )},
+ {"StringMap record dict from list", ?_assertNotEqual(
+ {'StringMap', dict:from_list([{1, "a"}, {2, "b"}])},
+ #'StringMap'{}
+ )},
+ {"StringMap record map from list", ?_assertEqual(
+ {'StringMap', maps:from_list([{1, "a"}, {2, "b"}])},
+ #'StringMap'{}
+ )}
+ ].
+
+struct_info_test_() ->
+ [
+ {"StringMap extended definition", ?_assertEqual(
+ {struct, [
+ {1, undefined, {map, i32, string}, 'data', #{1 => "a", 2 => "b"}}
+ ]},
+ thrift3214_types:struct_info_ext('StringMap')
+ )}
+ ].
+
+-endif.