From b3754d44fe4bd6edce787f481bcf4c7ff8b95e95 Mon Sep 17 00:00:00 2001 From: Viacheslav Koryagin Date: Thu, 23 Jul 2026 15:17:49 +0300 Subject: [PATCH] THRIFT-6108: implemented exception documentation generation Client: cpp,haxe,java,netstd,py --- .../src/thrift/generate/t_c_glib_generator.cc | 12 ++++++ .../cpp/src/thrift/generate/t_cl_generator.cc | 6 +++ .../src/thrift/generate/t_cpp_generator.cc | 13 ++++++ .../cpp/src/thrift/generate/t_d_generator.cc | 8 ++++ .../src/thrift/generate/t_dart_generator.cc | 26 ++++-------- .../src/thrift/generate/t_delphi_generator.cc | 22 +++------- .../src/thrift/generate/t_haxe_generator.cc | 18 +++++++++ .../src/thrift/generate/t_java_generator.cc | 8 ++++ .../src/thrift/generate/t_javame_generator.cc | 35 ++++++---------- .../cpp/src/thrift/generate/t_js_generator.cc | 7 ++++ .../src/thrift/generate/t_kotlin_generator.cc | 17 ++++++++ .../src/thrift/generate/t_lua_generator.cc | 8 ++++ .../src/thrift/generate/t_netstd_generator.cc | 19 +++++++++ .../src/thrift/generate/t_netstd_generator.h | 3 ++ .../src/thrift/generate/t_ocaml_generator.cc | 8 ++++ .../cpp/src/thrift/generate/t_oop_generator.h | 40 +++++++++++++++++++ .../src/thrift/generate/t_perl_generator.cc | 12 ++++++ .../src/thrift/generate/t_php_generator.cc | 12 ++++++ .../cpp/src/thrift/generate/t_py_generator.cc | 36 +++++++++++++---- .../cpp/src/thrift/generate/t_rb_generator.cc | 7 ++++ .../cpp/src/thrift/generate/t_st_generator.cc | 7 ++++ lib/cpp/test/TTransportFactoryConfigTest.cpp | 3 +- test/ThriftTest.thrift | 6 ++- 23 files changed, 266 insertions(+), 67 deletions(-) diff --git a/compiler/cpp/src/thrift/generate/t_c_glib_generator.cc b/compiler/cpp/src/thrift/generate/t_c_glib_generator.cc index 3373908baf9..cabef15b2cf 100644 --- a/compiler/cpp/src/thrift/generate/t_c_glib_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_c_glib_generator.cc @@ -103,6 +103,8 @@ class t_c_glib_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; + std::string get_namespace(t_type* type) override; /* generation functions */ void generate_typedef(t_typedef* ttypedef) override; @@ -125,6 +127,8 @@ class t_c_glib_generator : public t_oop_generator { string nspace_uc; string nspace_lc; + const string gen_name_ = "c_glib"; + /* helper functions */ bool is_complex_type(t_type* ttype); bool is_numeric(t_type* ttype); @@ -215,6 +219,14 @@ class t_c_glib_generator : public t_oop_generator { string generate_cmp_func_from_type(t_type* ttype); }; +const string& t_c_glib_generator::get_gen_name() const { + return gen_name_; +} + +std::string t_c_glib_generator::get_namespace(t_type*) { + return nspace; +} + /** * Prepare for file generation by opening up the necessary file * output streams. diff --git a/compiler/cpp/src/thrift/generate/t_cl_generator.cc b/compiler/cpp/src/thrift/generate/t_cl_generator.cc index 409af1dd174..3b7742316ff 100644 --- a/compiler/cpp/src/thrift/generate/t_cl_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_cl_generator.cc @@ -73,6 +73,7 @@ class t_cl_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; void generate_typedef (t_typedef* ttypedef) override; void generate_enum (t_enum* tenum) override; @@ -116,8 +117,13 @@ class t_cl_generator : public t_oop_generator { bool no_asd; std::string system_prefix; + + const std::string gen_name_ = "cl"; }; +const std::string& t_cl_generator::get_gen_name() const { + return gen_name_; +} void t_cl_generator::init_generator() { MKDIR(get_out_dir().c_str()); diff --git a/compiler/cpp/src/thrift/generate/t_cpp_generator.cc b/compiler/cpp/src/thrift/generate/t_cpp_generator.cc index f468ea88d58..151b73124b4 100644 --- a/compiler/cpp/src/thrift/generate/t_cpp_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_cpp_generator.cc @@ -120,6 +120,8 @@ class t_cpp_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; + std::string get_namespace(t_type* type) override; void generate_consts(std::vector consts) override; @@ -434,6 +436,8 @@ class t_cpp_generator : public t_oop_generator { std::string ns_open_; std::string ns_close_; + const std::string gen_name_ = "cpp"; + /** * File streams, stored here to avoid passing them as parameters to every * function. @@ -455,6 +459,15 @@ class t_cpp_generator : public t_oop_generator { friend class ProcessorGenerator; }; +const std::string& t_cpp_generator::get_gen_name() const { + return gen_name_; +} + +std::string t_cpp_generator::get_namespace(t_type *type) { + std::string namespace_str = type->get_program()->get_namespace(get_gen_name()); + return replace_all(namespace_str, ".", "::") + "::"; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_d_generator.cc b/compiler/cpp/src/thrift/generate/t_d_generator.cc index 61988dfc491..efba37bde4b 100644 --- a/compiler/cpp/src/thrift/generate/t_d_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_d_generator.cc @@ -68,6 +68,7 @@ class t_d_generator : public t_oop_generator { out_dir_base_ = "gen-d"; } std::string display_name() const override; + const std::string& get_gen_name() const override; protected: @@ -367,6 +368,9 @@ class t_d_generator : public t_oop_generator { } private: + + const std::string gen_name_ = "d"; + /** * Writes a server skeleton for the passed service to out. */ @@ -779,4 +783,8 @@ std::string t_d_generator::display_name() const { } +const std::string& t_d_generator::get_gen_name() const { + return gen_name_; +} + THRIFT_REGISTER_GENERATOR(d, "D", "") diff --git a/compiler/cpp/src/thrift/generate/t_dart_generator.cc b/compiler/cpp/src/thrift/generate/t_dart_generator.cc index cb28bf54ae4..f7e39d36ab7 100644 --- a/compiler/cpp/src/thrift/generate/t_dart_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_dart_generator.cc @@ -95,25 +95,6 @@ class t_dart_generator : public t_oop_generator { indent(out) << "}" << postfix; } - string replace_all(string contents, string search, string repl) { - string str(contents); - - size_t slen = search.length(); - size_t rlen = repl.length(); - size_t incr = (rlen > 0) ? rlen : 1; - - if (slen > 0) { - size_t found = str.find(search); - while ((found != string::npos) && (found < str.length())) { - str.replace(found, slen, repl); - found = str.find(search, found + incr); - } - } - - return str; - } - - /** * Init and close methods */ @@ -121,6 +102,7 @@ class t_dart_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; void export_class_to_library(string file_name, string class_name); @@ -279,8 +261,14 @@ class t_dart_generator : public t_oop_generator { std::string base_dir_; std::string src_dir_; std::string library_exports_; + + const std::string gen_name_ = "dart"; }; +const std::string& t_dart_generator::get_gen_name() const { + return gen_name_; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_delphi_generator.cc b/compiler/cpp/src/thrift/generate/t_delphi_generator.cc index 8d7e11b463e..51345e8dcbd 100644 --- a/compiler/cpp/src/thrift/generate/t_delphi_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_delphi_generator.cc @@ -110,6 +110,7 @@ class t_delphi_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; void generate_consts(std::vector consts) override; @@ -359,7 +360,6 @@ class t_delphi_generator : public t_oop_generator { " *)\n"; } - string replace_all(string contents, string search, string replace); string xml_encode(string contents); string xmldoc_encode(string contents); string xmlattrib_encode(string contents); @@ -468,24 +468,12 @@ class t_delphi_generator : public t_oop_generator { return ind; }; std::ostream& indent_impl(std::ostream& os) { return os << indent_impl(); }; -}; - -string t_delphi_generator::replace_all(string contents, string search, string repl) { - string str(contents); - - size_t slen = search.length(); - size_t rlen = repl.length(); - size_t incr = (rlen > 0) ? rlen : 1; - if (slen > 0) { - size_t found = str.find(search); - while ((found != string::npos) && (found < str.length())) { - str.replace(found, slen, repl); - found = str.find(search, found + incr); - } - } + const std::string gen_name_ = "delphi"; +}; - return str; +const std::string& t_delphi_generator::get_gen_name() const { + return gen_name_; } // XML encoding diff --git a/compiler/cpp/src/thrift/generate/t_haxe_generator.cc b/compiler/cpp/src/thrift/generate/t_haxe_generator.cc index a05736d2c21..0019a96a7b9 100644 --- a/compiler/cpp/src/thrift/generate/t_haxe_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_haxe_generator.cc @@ -74,6 +74,7 @@ class t_haxe_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; void generate_consts(std::vector consts) override; @@ -253,8 +254,14 @@ class t_haxe_generator : public t_oop_generator { std::string package_name_; ofstream_with_content_based_conditional_update f_service_; std::string package_dir_; + + const std::string gen_name_ = "haxe"; }; +const std::string& t_haxe_generator::get_gen_name() const { + return gen_name_; +} + /** * Prepares for file generation by opening up the necessary file output * streams. @@ -3148,6 +3155,17 @@ void t_haxe_generator::generate_haxe_doc(ostream& out, t_function* tfunction) { ss << " " << p->get_doc(); } } + + const vector& exceptions = tfunction->get_xceptions()->get_members(); + vector::const_iterator e_iter; + for (e_iter = exceptions.begin(); e_iter != exceptions.end(); ++e_iter) { + t_field* e = *e_iter; + ss << "\n@throws " << type_name(e->get_type()) << " " << e->get_name(); + if (e->has_doc()) { + ss << " " << e->get_doc(); + } + } + generate_docstring_comment(out, "/**\n", " * ", ss.str(), " */\n"); } } diff --git a/compiler/cpp/src/thrift/generate/t_java_generator.cc b/compiler/cpp/src/thrift/generate/t_java_generator.cc index d583e4b1a33..bed7e031214 100644 --- a/compiler/cpp/src/thrift/generate/t_java_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_java_generator.cc @@ -148,6 +148,7 @@ class t_java_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; void generate_consts(std::vector consts) override; @@ -467,8 +468,15 @@ class t_java_generator : public t_oop_generator { bool unsafe_binaries_; bool annotations_as_metadata_; bool jakarta_annotations_; + + const std::string gen_name_ = "java"; }; + +const std::string& t_java_generator::get_gen_name() const { + return gen_name_; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_javame_generator.cc b/compiler/cpp/src/thrift/generate/t_javame_generator.cc index 9e7b459cd8d..c7c9df32898 100644 --- a/compiler/cpp/src/thrift/generate/t_javame_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_javame_generator.cc @@ -66,6 +66,8 @@ class t_javame_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; + std::string get_namespace(t_type* type) override; void generate_consts(std::vector consts) override; @@ -188,8 +190,6 @@ class t_javame_generator : public t_oop_generator { void generate_java_doc(std::ostream& out, t_doc* tdoc) override; - void generate_java_doc(std::ostream& out, t_function* tdoc) override; - void generate_java_docstring_comment(std::ostream& out, string contents) override; void generate_deep_copy_container(std::ostream& out, @@ -242,8 +242,19 @@ class t_javame_generator : public t_oop_generator { std::string package_name_; ofstream_with_content_based_conditional_update f_service_; std::string package_dir_; + + const std::string gen_name_ = "javame"; }; + +const std::string& t_javame_generator::get_gen_name() const { + return gen_name_; +} + +std::string t_javame_generator::get_namespace(t_type *type) { + return type->get_program()->get_namespace("java"); +} + /** * Prepares for file generation by opening up the necessary file output * streams. @@ -3054,26 +3065,6 @@ void t_javame_generator::generate_java_doc(ostream& out, t_doc* tdoc) { } } -/** - * Emits a JavaDoc comment if the provided function object has a doc in Thrift - */ -void t_javame_generator::generate_java_doc(ostream& out, t_function* tfunction) { - if (tfunction->has_doc()) { - stringstream ss; - ss << tfunction->get_doc(); - const vector& fields = tfunction->get_arglist()->get_members(); - vector::const_iterator p_iter; - for (p_iter = fields.begin(); p_iter != fields.end(); ++p_iter) { - t_field* p = *p_iter; - ss << "\n@param " << p->get_name(); - if (p->has_doc()) { - ss << " " << p->get_doc(); - } - } - generate_docstring_comment(out, "/**\n", " * ", ss.str(), " */\n"); - } -} - void t_javame_generator::generate_deep_copy_container(ostream& out, std::string source_name_p1, std::string source_name_p2, diff --git a/compiler/cpp/src/thrift/generate/t_js_generator.cc b/compiler/cpp/src/thrift/generate/t_js_generator.cc index c7281504b84..7ae0ebf84b4 100644 --- a/compiler/cpp/src/thrift/generate/t_js_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_js_generator.cc @@ -160,6 +160,7 @@ class t_js_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; /** * Program-level generation functions @@ -478,8 +479,14 @@ class t_js_generator : public t_oop_generator { ofstream_with_content_based_conditional_update f_service_; ofstream_with_content_based_conditional_update f_types_ts_; ofstream_with_content_based_conditional_update f_service_ts_; + + const std::string gen_name_ = "js"; }; +const std::string& t_js_generator::get_gen_name() const { + return gen_name_; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_kotlin_generator.cc b/compiler/cpp/src/thrift/generate/t_kotlin_generator.cc index 2e81909c48b..98e1fdfc04f 100644 --- a/compiler/cpp/src/thrift/generate/t_kotlin_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_kotlin_generator.cc @@ -77,6 +77,8 @@ class t_kotlin_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; + std::string get_namespace(t_type* type) override; void generate_consts(std::vector consts) override; @@ -171,8 +173,23 @@ class t_kotlin_generator : public t_oop_generator { void generate_deserialize_container(ostream& out, t_type* ttype); void generate_kotlin_union(t_struct* tstruct); + + const std::string gen_name_ = "kotlin"; }; +const std::string& t_kotlin_generator::get_gen_name() const { + return gen_name_; +} + +std::string t_kotlin_generator::get_namespace(t_type *type) { + std::string namespace_str = type->get_program()->get_namespace(get_gen_name()); + if (namespace_str.empty()) { + namespace_str = type->get_program()->get_namespace("java"); + } + + return namespace_str; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_lua_generator.cc b/compiler/cpp/src/thrift/generate/t_lua_generator.cc index 54c1fd7097f..49e6fd5425e 100644 --- a/compiler/cpp/src/thrift/generate/t_lua_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_lua_generator.cc @@ -18,6 +18,7 @@ */ #include +#include #include "thrift/platform.h" #include "thrift/generate/t_oop_generator.h" @@ -58,6 +59,7 @@ class t_lua_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; /** * Program-level generation functions @@ -167,8 +169,14 @@ class t_lua_generator : public t_oop_generator { ofstream_with_content_based_conditional_update f_types_; ofstream_with_content_based_conditional_update f_consts_; ofstream_with_content_based_conditional_update f_service_; + + const std::string gen_name_ = "lua"; }; +const std::string& t_lua_generator::get_gen_name() const { + return gen_name_; +} + /** * Init and close methods */ diff --git a/compiler/cpp/src/thrift/generate/t_netstd_generator.cc b/compiler/cpp/src/thrift/generate/t_netstd_generator.cc index 61e5bdeb0ff..d59c9e117fa 100644 --- a/compiler/cpp/src/thrift/generate/t_netstd_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_netstd_generator.cc @@ -47,6 +47,10 @@ using std::vector; //TODO: check for indentation //TODO: Do we need seqId_ in generation? +const std::string& t_netstd_generator::get_gen_name() const { + return gen_name_; +} + t_netstd_generator::t_netstd_generator(t_program* program, const map& parsed_options, const string& option_string) : t_oop_generator(program) { @@ -3960,6 +3964,21 @@ void t_netstd_generator::generate_netstd_doc(ostream& out, t_function* tfunction ps << ""; } + const vector& exceptions = tfunction->get_xceptions()->get_members(); + vector::const_iterator e_iter; + for (e_iter = exceptions.begin(); e_iter != exceptions.end(); ++e_iter) + { + t_field* e = *e_iter; + ps << '\n' << "get_type()) << "\">"; + if (e->has_doc()) + { + string str = e->get_doc(); + str.erase(remove(str.begin(), str.end(), '\n'), str.end()); + ps << str; + } + ps << ""; + } + docstring_comment(out, "", "/// ", diff --git a/compiler/cpp/src/thrift/generate/t_netstd_generator.h b/compiler/cpp/src/thrift/generate/t_netstd_generator.h index 4623b122862..969d49eeddd 100644 --- a/compiler/cpp/src/thrift/generate/t_netstd_generator.h +++ b/compiler/cpp/src/thrift/generate/t_netstd_generator.h @@ -78,6 +78,7 @@ class t_netstd_generator : public t_oop_generator void generate_struct(t_struct* tstruct) override; void generate_xception(t_struct* txception) override; void generate_service(t_service* tservice) override; + const std::string& get_gen_name() const override; // additional files void generate_extensions_file(); @@ -226,4 +227,6 @@ class t_netstd_generator : public t_oop_generator string nullable_field_suffix(t_field* tfield); // depends on field type string nullable_field_suffix(t_type* ttype); // depends on field type string nullable_value_access(t_type* ttype); // depends on field type + + const std::string gen_name_ = "netstd"; }; diff --git a/compiler/cpp/src/thrift/generate/t_ocaml_generator.cc b/compiler/cpp/src/thrift/generate/t_ocaml_generator.cc index 389abb98937..6df25e1a15a 100644 --- a/compiler/cpp/src/thrift/generate/t_ocaml_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_ocaml_generator.cc @@ -63,6 +63,7 @@ class t_ocaml_generator : public t_oop_generator { void init_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; /** * Program-level generation functions @@ -168,8 +169,15 @@ class t_ocaml_generator : public t_oop_generator { ofstream_with_content_based_conditional_update f_types_i_; ofstream_with_content_based_conditional_update f_service_i_; + +private: + const std::string gen_name_ = "ocaml"; }; +const std::string& t_ocaml_generator::get_gen_name() const { + return gen_name_; +} + /* * This is necessary because we want typedefs to appear later, * after all the types have been declared. diff --git a/compiler/cpp/src/thrift/generate/t_oop_generator.h b/compiler/cpp/src/thrift/generate/t_oop_generator.h index 07b621639f7..bf806f29c87 100644 --- a/compiler/cpp/src/thrift/generate/t_oop_generator.h +++ b/compiler/cpp/src/thrift/generate/t_oop_generator.h @@ -37,6 +37,12 @@ class t_oop_generator : public t_generator { public: t_oop_generator(t_program* program) : t_generator(program) {} + virtual const std::string& get_gen_name() const = 0; + + virtual std::string get_namespace(t_type* type) { + return type->get_program()->get_namespace(get_gen_name()) + "."; + } + /** * Scoping, using curly braces! */ @@ -104,9 +110,43 @@ class t_oop_generator : public t_generator { ss << " " << p->get_doc(); } } + + ss << '\n'; + + const std::vector& exceptions = tfunction->get_xceptions()->get_members(); + std::vector::const_iterator e_iter; + for (e_iter = exceptions.begin(); e_iter != exceptions.end(); ++e_iter) { + t_field* e = *e_iter; + ss << "\n@throws " << get_namespace(e->get_type()) << e->get_type()->get_name(); + if (e->has_doc()) { + std::string doc_string = e->get_doc(); + doc_string.erase(remove(doc_string.begin(), doc_string.end(), '\n'), doc_string.end()); + ss << " " << doc_string; + } + } generate_docstring_comment(out, "/**\n", " * ", ss.str(), " */\n"); } } + + + + static std::string replace_all(std::string contents, std::string search, std::string repl) { + std::string str(contents); + + size_t slen = search.length(); + size_t rlen = repl.length(); + size_t incr = (rlen > 0) ? rlen : 1; + + if (slen > 0) { + size_t found = str.find(search); + while ((found != std::string::npos) && (found < str.length())) { + str.replace(found, slen, repl); + found = str.find(search, found + incr); + } + } + + return str; + } }; #endif diff --git a/compiler/cpp/src/thrift/generate/t_perl_generator.cc b/compiler/cpp/src/thrift/generate/t_perl_generator.cc index ca632ea3d6b..3d3a10762fe 100644 --- a/compiler/cpp/src/thrift/generate/t_perl_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_perl_generator.cc @@ -67,6 +67,8 @@ class t_perl_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; + std::string get_namespace(t_type* type) override; /** * Program-level generation functions @@ -216,8 +218,18 @@ class t_perl_generator : public t_oop_generator { ofstream_with_content_based_conditional_update f_service_; bool f_types_use_includes_emitted_; + + const std::string gen_name_ = "perl"; }; +const std::string& t_perl_generator::get_gen_name() const { + return gen_name_; +} + +std::string t_perl_generator::get_namespace(t_type* type) { + return perl_namespace(type->get_program()); +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_php_generator.cc b/compiler/cpp/src/thrift/generate/t_php_generator.cc index 073bb9eb445..514293d2712 100644 --- a/compiler/cpp/src/thrift/generate/t_php_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_php_generator.cc @@ -158,6 +158,8 @@ class t_php_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; + std::string get_namespace(t_type* type) override; /** * Program-level generation functions @@ -470,8 +472,18 @@ class t_php_generator : public t_oop_generator { * Whether to generate getters and setters */ bool getters_setters_; + + const std::string gen_name_ = "php"; }; +const std::string& t_php_generator::get_gen_name() const { + return gen_name_; +} + +std::string t_php_generator::get_namespace(t_type *type) { + return php_namespace(type->get_program()); +} + std::set t_php_generator::lang_keywords_for_validation() const { std::string keywords[] = { "BEGIN", "END", "__CLASS__", "__DIR__", "__FILE__", "__FUNCTION__", "__LINE__", "__METHOD__", "__NAMESPACE__", "abstract", "alias", "and", "args", "as", diff --git a/compiler/cpp/src/thrift/generate/t_py_generator.cc b/compiler/cpp/src/thrift/generate/t_py_generator.cc index 4f82944a11c..f66e55ee147 100644 --- a/compiler/cpp/src/thrift/generate/t_py_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_py_generator.cc @@ -250,6 +250,10 @@ class t_py_generator : public t_generator { t_doc* tdoc, t_struct* tstruct, const char* subheader); + void generate_python_params_docstring(ostream& ss, + t_struct* tstruct, + bool* has_doc, + const char* subheader); void generate_python_docstring(std::ostream& out, t_doc* tdoc); @@ -2722,7 +2726,17 @@ void t_py_generator::generate_python_docstring(ostream& out, t_struct* tstruct) * Generates the docstring for a given function. */ void t_py_generator::generate_python_docstring(ostream& out, t_function* tfunction) { - generate_python_docstring(out, tfunction, tfunction->get_arglist(), "Parameters"); + bool has_doc = false; + stringstream ss; + if (tfunction->has_doc()) { + has_doc = true; + ss << tfunction->get_doc(); + } + generate_python_params_docstring(ss, tfunction->get_arglist(), &has_doc, "Parameters"); + generate_python_params_docstring(ss, tfunction->get_xceptions(), &has_doc, "Raises"); + if (has_doc) { + generate_docstring_comment(out, "\"\"\"\n", "", ss.str(), "\"\"\"\n"); + } } /** @@ -2738,18 +2752,30 @@ void t_py_generator::generate_python_docstring(ostream& out, has_doc = true; ss << tdoc->get_doc(); } + generate_python_params_docstring(ss, tstruct, &has_doc, subheader); + if (has_doc) { + generate_docstring_comment(out, "\"\"\"\n", "", ss.str(), "\"\"\"\n"); + } +} +void t_py_generator::generate_python_params_docstring(ostream& ss, + t_struct* tstruct, + bool* has_doc, + const char* subheader) { const vector& fields = tstruct->get_members(); if (fields.size() > 0) { - if (has_doc) { + if (*has_doc) { ss << '\n'; } - has_doc = true; + *has_doc = true; ss << subheader << ":\n"; vector::const_iterator p_iter; for (p_iter = fields.begin(); p_iter != fields.end(); ++p_iter) { t_field* p = *p_iter; ss << " - " << p->get_name(); + if (gen_type_hints_) { + ss << " (" << p->get_type()->get_name() << ")"; + } if (p->has_doc()) { ss << ": " << p->get_doc(); } else { @@ -2757,10 +2783,6 @@ void t_py_generator::generate_python_docstring(ostream& out, } } } - - if (has_doc) { - generate_docstring_comment(out, "\"\"\"\n", "", ss.str(), "\"\"\"\n"); - } } /** diff --git a/compiler/cpp/src/thrift/generate/t_rb_generator.cc b/compiler/cpp/src/thrift/generate/t_rb_generator.cc index 113ab89c4b4..a706fe3ca6a 100644 --- a/compiler/cpp/src/thrift/generate/t_rb_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_rb_generator.cc @@ -104,6 +104,7 @@ class t_rb_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; /** * Program-level generation functions @@ -252,8 +253,14 @@ class t_rb_generator : public t_oop_generator { bool types_need_separator_; bool consts_need_separator_; bool service_need_separator_; + + const std::string gen_name_ = "rb"; }; +const std::string& t_rb_generator::get_gen_name() const { + return gen_name_; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/compiler/cpp/src/thrift/generate/t_st_generator.cc b/compiler/cpp/src/thrift/generate/t_st_generator.cc index 140f8cdefcf..05cb9a5b131 100644 --- a/compiler/cpp/src/thrift/generate/t_st_generator.cc +++ b/compiler/cpp/src/thrift/generate/t_st_generator.cc @@ -72,6 +72,7 @@ class t_st_generator : public t_oop_generator { void init_generator() override; void close_generator() override; std::string display_name() const override; + const std::string& get_gen_name() const override; /** * Program-level generation functions @@ -156,8 +157,14 @@ class t_st_generator : public t_oop_generator { */ int temporary_var; ofstream_with_content_based_conditional_update f_; + + const std::string gen_name_ = "st"; }; +const std::string& t_st_generator::get_gen_name() const { + return gen_name_; +} + /** * Prepares for file generation by opening up the necessary file output * streams. diff --git a/lib/cpp/test/TTransportFactoryConfigTest.cpp b/lib/cpp/test/TTransportFactoryConfigTest.cpp index b771b537cab..25c4a8252e6 100644 --- a/lib/cpp/test/TTransportFactoryConfigTest.cpp +++ b/lib/cpp/test/TTransportFactoryConfigTest.cpp @@ -104,7 +104,8 @@ BOOST_AUTO_TEST_CASE(test_piped_transport_factory_preserves_configuration) { // failing on a truncated buffer. BOOST_AUTO_TEST_CASE(test_framed_transport_factory_enforces_custom_max_frame_size) { const int kMaxFrameSize = 64; - auto config = std::make_shared(TConfiguration::DEFAULT_MAX_MESSAGE_SIZE, kMaxFrameSize); + const int kMaxMessageSize = TConfiguration::DEFAULT_MAX_MESSAGE_SIZE; + auto config = std::make_shared(kMaxMessageSize, kMaxFrameSize); // A 4-byte big-endian frame-length prefix declaring a 1024-byte frame, // well beyond kMaxFrameSize, followed by 1024 bytes of payload. diff --git a/test/ThriftTest.thrift b/test/ThriftTest.thrift index 42607cc3544..4b0cdb998e3 100644 --- a/test/ThriftTest.thrift +++ b/test/ThriftTest.thrift @@ -314,7 +314,11 @@ service ThriftTest * else do not throw anything * @return Xtruct - an Xtruct with string_thing = arg1 */ - Xtruct testMultiException(1: string arg0, 2: string arg1) throws(1: Xception err1, 2: Xception2 err2) + Xtruct testMultiException(1: string arg0, 2: string arg1) throws( + /** Thrown when a bad thing happens */ + 1: Xception err1, + /** Thrown when the input is in incorrect format, for example */ + 2: Xception2 err2) /** * Print 'testOneway(%d): Sleeping...' with secondsToSleep as '%d'