mirror of
https://github.com/google/flatbuffers.git
synced 2026-06-02 04:04:19 +00:00
[Lua] Apply Namer to Lua (#7171)
* Apply Namer to Lua bfbs code gen * refactor namer into IdlNamer to keep idl includes separate * remove commented out code * added bfbs_namer * remove Enum case * add to bazel
This commit is contained in:
@@ -158,10 +158,13 @@ set(FlatBuffers_Compiler_SRCS
|
||||
src/idl_gen_grpc.cpp
|
||||
src/idl_gen_json_schema.cpp
|
||||
src/idl_gen_swift.cpp
|
||||
src/idl_namer.h
|
||||
src/namer.h
|
||||
src/flatc.cpp
|
||||
src/flatc_main.cpp
|
||||
src/bfbs_gen.h
|
||||
src/bfbs_gen_lua.h
|
||||
src/bfbs_namer.h
|
||||
include/flatbuffers/code_generators.h
|
||||
src/bfbs_gen_lua.cpp
|
||||
src/code_generators.cpp
|
||||
|
||||
@@ -37,7 +37,9 @@ cc_library(
|
||||
"bfbs_gen.h",
|
||||
"bfbs_gen_lua.cpp",
|
||||
"bfbs_gen_lua.h",
|
||||
"bfbs_namer.h",
|
||||
"flatc.cpp",
|
||||
"namer.h",
|
||||
],
|
||||
hdrs = [
|
||||
"//:flatc_headers",
|
||||
@@ -56,6 +58,7 @@ cc_library(
|
||||
"bfbs_gen.h",
|
||||
"bfbs_gen_lua.cpp",
|
||||
"bfbs_gen_lua.h",
|
||||
"bfbs_namer.h",
|
||||
"flatc_main.cpp",
|
||||
"idl_gen_cpp.cpp",
|
||||
"idl_gen_csharp.cpp",
|
||||
@@ -73,6 +76,7 @@ cc_library(
|
||||
"idl_gen_swift.cpp",
|
||||
"idl_gen_text.cpp",
|
||||
"idl_gen_ts.cpp",
|
||||
"idl_namer.h",
|
||||
"namer.h",
|
||||
"util.cpp",
|
||||
],
|
||||
|
||||
@@ -73,10 +73,6 @@ static bool IsStructOrTable(const reflection::BaseType base_type) {
|
||||
return base_type == reflection::Obj;
|
||||
}
|
||||
|
||||
static bool IsScalar(const reflection::BaseType base_type) {
|
||||
return base_type >= reflection::UType && base_type <= reflection::Double;
|
||||
}
|
||||
|
||||
static bool IsFloatingPoint(const reflection::BaseType base_type) {
|
||||
return base_type == reflection::Float || base_type == reflection::Double;
|
||||
}
|
||||
@@ -93,22 +89,6 @@ static bool IsVector(const reflection::BaseType base_type) {
|
||||
return base_type == reflection::Vector;
|
||||
}
|
||||
|
||||
static std::string Denamespace(const flatbuffers::String *name,
|
||||
std::string &ns) {
|
||||
const size_t pos = name->str().find_last_of('.');
|
||||
if (pos == std::string::npos) {
|
||||
ns = "";
|
||||
return name->str();
|
||||
}
|
||||
ns = name->str().substr(0, pos);
|
||||
return name->str().substr(pos + 1);
|
||||
}
|
||||
|
||||
static std::string Denamespace(const flatbuffers::String *name) {
|
||||
std::string ns;
|
||||
return Denamespace(name, ns);
|
||||
}
|
||||
|
||||
// A concrete base Flatbuffer Generator that specific language generators can
|
||||
// derive from.
|
||||
class BaseBfbsGenerator : public BfbsGenerator {
|
||||
|
||||
@@ -25,9 +25,11 @@
|
||||
|
||||
// Ensure no includes to flatc internals. bfbs_gen.h and generator.h are OK.
|
||||
#include "bfbs_gen.h"
|
||||
#include "bfbs_namer.h"
|
||||
#include "flatbuffers/bfbs_generator.h"
|
||||
|
||||
// The intermediate representation schema.
|
||||
#include "flatbuffers/reflection.h"
|
||||
#include "flatbuffers/reflection_generated.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
@@ -36,6 +38,36 @@ namespace {
|
||||
// To reduce typing
|
||||
namespace r = ::reflection;
|
||||
|
||||
std::set<std::string> LuaKeywords() {
|
||||
return { "and", "break", "do", "else", "elseif", "end",
|
||||
"false", "for", "function", "goto", "if", "in",
|
||||
"local", "nil", "not", "or", "repeat", "return",
|
||||
"then", "true", "until", "while" };
|
||||
}
|
||||
|
||||
Namer::Config LuaDefaultConfig() {
|
||||
return { /*types=*/Case::kUpperCamel,
|
||||
/*constants=*/Case::kUnknown,
|
||||
/*methods=*/Case::kUpperCamel,
|
||||
/*functions=*/Case::kUpperCamel,
|
||||
/*fields=*/Case::kUpperCamel,
|
||||
/*variables=*/Case::kLowerCamel,
|
||||
/*variants=*/Case::kKeep,
|
||||
/*enum_variant_seperator=*/"",
|
||||
/*escape_keywords=*/Namer::Config::Escape::AfterConvertingCase,
|
||||
/*namespaces=*/Case::kKeep,
|
||||
/*namespace_seperator=*/"__",
|
||||
/*object_prefix=*/"",
|
||||
/*object_suffix=*/"",
|
||||
/*keyword_prefix=*/"",
|
||||
/*keyword_suffix=*/"_",
|
||||
/*filenames=*/Case::kKeep,
|
||||
/*directories=*/Case::kKeep,
|
||||
/*output_path=*/"",
|
||||
/*filename_suffix=*/"",
|
||||
/*filename_extension=*/".lua" };
|
||||
}
|
||||
|
||||
class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
public:
|
||||
explicit LuaBfbsGenerator(const std::string &flatc_version)
|
||||
@@ -44,14 +76,8 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
requires_(),
|
||||
current_obj_(nullptr),
|
||||
current_enum_(nullptr),
|
||||
flatc_version_(flatc_version) {
|
||||
static const char *const keywords[] = {
|
||||
"and", "break", "do", "else", "elseif", "end", "false", "for",
|
||||
"function", "goto", "if", "in", "local", "nil", "not", "or",
|
||||
"repeat", "return", "then", "true", "until", "while"
|
||||
};
|
||||
keywords_.insert(std::begin(keywords), std::end(keywords));
|
||||
}
|
||||
flatc_version_(flatc_version),
|
||||
namer_(LuaDefaultConfig(), LuaKeywords()) {}
|
||||
|
||||
GeneratorStatus GenerateFromSchema(const r::Schema *schema)
|
||||
FLATBUFFERS_OVERRIDE {
|
||||
@@ -76,14 +102,14 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
|
||||
std::string ns;
|
||||
const std::string enum_name =
|
||||
NormalizeName(Denamespace(enum_def->name(), ns));
|
||||
namer_.Type(namer_.Denamespace(enum_def, ns));
|
||||
|
||||
GenerateDocumentation(enum_def->documentation(), "", code);
|
||||
code += "local " + enum_name + " = {\n";
|
||||
|
||||
ForAllEnumValues(enum_def, [&](const reflection::EnumVal *enum_val) {
|
||||
GenerateDocumentation(enum_val->documentation(), " ", code);
|
||||
code += " " + NormalizeName(enum_val->name()) + " = " +
|
||||
code += " " + namer_.Variant(enum_val->name()->str()) + " = " +
|
||||
NumToString(enum_val->value()) + ",\n";
|
||||
});
|
||||
code += "}\n";
|
||||
@@ -107,7 +133,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
|
||||
std::string ns;
|
||||
const std::string object_name =
|
||||
NormalizeName(Denamespace(object->name(), ns));
|
||||
namer_.Type(namer_.Denamespace(object, ns));
|
||||
|
||||
GenerateDocumentation(object->documentation(), "", code);
|
||||
|
||||
@@ -149,14 +175,12 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
// Skip writing deprecated fields altogether.
|
||||
if (field->deprecated()) { return; }
|
||||
|
||||
const std::string field_name = NormalizeName(field->name());
|
||||
const std::string field_name_camel_case =
|
||||
ConvertCase(field_name, Case::kUpperCamel);
|
||||
const std::string field_name = namer_.Field(field->name()->str());
|
||||
const r::BaseType base_type = field->type()->base_type();
|
||||
|
||||
// Generate some fixed strings so we don't repeat outselves later.
|
||||
const std::string getter_signature =
|
||||
"function mt:" + field_name_camel_case + "()\n";
|
||||
"function mt:" + field_name + "()\n";
|
||||
const std::string offset_prefix = "local o = self.view:Offset(" +
|
||||
NumToString(field->offset()) + ")\n";
|
||||
const std::string offset_prefix_2 = "if o ~= 0 then\n";
|
||||
@@ -201,7 +225,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
}
|
||||
case r::Obj: {
|
||||
if (object->is_struct()) {
|
||||
code += "function mt:" + field_name_camel_case + "(obj)\n";
|
||||
code += "function mt:" + field_name + "(obj)\n";
|
||||
code += " obj:Init(self.view.bytes, self.view.pos + " +
|
||||
NumToString(field->offset()) + ")\n";
|
||||
code += " return obj\n";
|
||||
@@ -252,7 +276,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
case r::Vector: {
|
||||
const r::BaseType vector_base_type = field->type()->element();
|
||||
int32_t element_size = field->type()->element_size();
|
||||
code += "function mt:" + field_name_camel_case + "(j)\n";
|
||||
code += "function mt:" + field_name + "(j)\n";
|
||||
code += " " + offset_prefix;
|
||||
code += " " + offset_prefix_2;
|
||||
|
||||
@@ -297,8 +321,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
// generate a helper function to get it as a byte string in
|
||||
// Lua.
|
||||
if (IsSingleByte(vector_base_type)) {
|
||||
code += "function mt:" + field_name_camel_case +
|
||||
"AsString(start, stop)\n";
|
||||
code += "function mt:" + field_name + "AsString(start, stop)\n";
|
||||
code += " return self.view:VectorAsString(" +
|
||||
NumToString(field->offset()) + ", start, stop)\n";
|
||||
code += "end\n";
|
||||
@@ -307,7 +330,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
|
||||
// We also make a new accessor to query just the length of the
|
||||
// vector.
|
||||
code += "function mt:" + field_name_camel_case + "Length()\n";
|
||||
code += "function mt:" + field_name + "Length()\n";
|
||||
code += " " + offset_prefix;
|
||||
code += " " + offset_prefix_2;
|
||||
code += " return self.view:VectorLen(o)\n";
|
||||
@@ -344,21 +367,20 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
ForAllFields(object, /*reverse=*/false, [&](const r::Field *field) {
|
||||
if (field->deprecated()) { return; }
|
||||
|
||||
const std::string field_name = NormalizeName(field->name());
|
||||
const std::string field_name = namer_.Field(field->name()->str());
|
||||
const std::string variable_name =
|
||||
namer_.Variable(field->name()->str());
|
||||
|
||||
code += "function " + object_name + ".Add" +
|
||||
ConvertCase(field_name, Case::kUpperCamel) + "(builder, " +
|
||||
ConvertCase(field_name, Case::kLowerCamel) + ")\n";
|
||||
code += "function " + object_name + ".Add" + field_name +
|
||||
"(builder, " + variable_name + ")\n";
|
||||
code += " builder:Prepend" + GenerateMethod(field) + "Slot(" +
|
||||
NumToString(field->id()) + ", " +
|
||||
ConvertCase(field_name, Case::kLowerCamel) + ", " +
|
||||
NumToString(field->id()) + ", " + variable_name + ", " +
|
||||
DefaultValue(field) + ")\n";
|
||||
code += "end\n";
|
||||
code += "\n";
|
||||
|
||||
if (IsVector(field->type()->base_type())) {
|
||||
code += "function " + object_name + ".Start" +
|
||||
ConvertCase(field_name, Case::kUpperCamel) +
|
||||
code += "function " + object_name + ".Start" + field_name +
|
||||
"Vector(builder, numElems)\n";
|
||||
|
||||
const int32_t element_size = field->type()->element_size();
|
||||
@@ -406,11 +428,9 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
if (IsStructOrTable(field->type()->base_type())) {
|
||||
const r::Object *field_object = GetObject(field->type());
|
||||
signature += GenerateStructBuilderArgs(
|
||||
field_object, prefix + NormalizeName(field->name()) + "_");
|
||||
field_object, prefix + namer_.Variable(field->name()->str()) + "_");
|
||||
} else {
|
||||
signature +=
|
||||
", " + prefix +
|
||||
ConvertCase(NormalizeName(field->name()), Case::kLowerCamel);
|
||||
signature += ", " + prefix + namer_.Variable(field->name()->str());
|
||||
}
|
||||
});
|
||||
return signature;
|
||||
@@ -432,11 +452,10 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
if (IsStructOrTable(field->type()->base_type())) {
|
||||
const r::Object *field_object = GetObject(field->type());
|
||||
code += AppendStructBuilderBody(
|
||||
field_object, prefix + NormalizeName(field->name()) + "_");
|
||||
field_object, prefix + namer_.Variable(field->name()->str()) + "_");
|
||||
} else {
|
||||
code += " builder:Prepend" + GenerateMethod(field) + "(" + prefix +
|
||||
ConvertCase(NormalizeName(field->name()), Case::kLowerCamel) +
|
||||
")\n";
|
||||
namer_.Variable(field->name()->str()) + ")\n";
|
||||
}
|
||||
});
|
||||
|
||||
@@ -445,9 +464,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
|
||||
std::string GenerateMethod(const r::Field *field) const {
|
||||
const r::BaseType base_type = field->type()->base_type();
|
||||
if (IsScalar(base_type)) {
|
||||
return ConvertCase(GenerateType(base_type), Case::kUpperCamel);
|
||||
}
|
||||
if (IsScalar(base_type)) { return namer_.Type(GenerateType(base_type)); }
|
||||
if (IsStructOrTable(base_type)) { return "Struct"; }
|
||||
return "UOffsetTRelative";
|
||||
}
|
||||
@@ -460,9 +477,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
case r::Vector: return GenerateGetter(type, true);
|
||||
default:
|
||||
return "self.view:Get(flatbuffers.N." +
|
||||
ConvertCase(GenerateType(type, element_type),
|
||||
Case::kUpperCamel) +
|
||||
", ";
|
||||
namer_.Type(GenerateType(type, element_type)) + ", ";
|
||||
}
|
||||
}
|
||||
|
||||
@@ -474,10 +489,8 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
switch (base_type) {
|
||||
case r::String: return "string";
|
||||
case r::Vector: return GenerateGetter(type, true);
|
||||
case r::Obj: {
|
||||
const r::Object *obj = GetObject(type);
|
||||
return NormalizeName(Denamespace(obj->name()));
|
||||
};
|
||||
case r::Obj: return namer_.Type(namer_.Denamespace(GetObject(type)));
|
||||
|
||||
default: return "*flatbuffers.Table";
|
||||
}
|
||||
}
|
||||
@@ -515,14 +528,6 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
return "0";
|
||||
}
|
||||
|
||||
std::string NormalizeName(const std::string name) const {
|
||||
return keywords_.find(name) == keywords_.end() ? name : "_" + name;
|
||||
}
|
||||
|
||||
std::string NormalizeName(const flatbuffers::String *name) const {
|
||||
return NormalizeName(name->str());
|
||||
}
|
||||
|
||||
void StartCodeBlock(const reflection::Enum *enum_def) {
|
||||
current_enum_ = enum_def;
|
||||
current_obj_ = nullptr;
|
||||
@@ -544,11 +549,11 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
|
||||
if (IsStructOrTable(type)) {
|
||||
const r::Object *object = GetObjectByIndex(field->type()->index());
|
||||
if (object == current_obj_) { return Denamespace(object->name()); }
|
||||
if (object == current_obj_) { return namer_.Denamespace(object); }
|
||||
type_name = object->name()->str();
|
||||
} else {
|
||||
const r::Enum *enum_def = GetEnumByIndex(field->type()->index());
|
||||
if (enum_def == current_enum_) { return Denamespace(enum_def->name()); }
|
||||
if (enum_def == current_enum_) { return namer_.Denamespace(enum_def); }
|
||||
type_name = enum_def->name()->str();
|
||||
}
|
||||
|
||||
@@ -600,7 +605,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
// Namespaces are '.' deliminted, so replace it with the path separator.
|
||||
std::string path = ns;
|
||||
|
||||
if (path.empty()) {
|
||||
if (ns.empty()) {
|
||||
path = ".";
|
||||
} else {
|
||||
std::replace(path.begin(), path.end(), '.', '/');
|
||||
@@ -608,7 +613,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
|
||||
// TODO(derekbailey): figure out a save file without depending on util.h
|
||||
EnsureDirExists(path);
|
||||
const std::string file_name = path + "/" + name + ".lua";
|
||||
const std::string file_name = path + "/" + namer_.File(name);
|
||||
SaveFile(file_name.c_str(), code, false);
|
||||
}
|
||||
|
||||
@@ -617,6 +622,7 @@ class LuaBfbsGenerator : public BaseBfbsGenerator {
|
||||
const r::Object *current_obj_;
|
||||
const r::Enum *current_enum_;
|
||||
const std::string flatc_version_;
|
||||
const BfbsNamer namer_;
|
||||
};
|
||||
} // namespace
|
||||
|
||||
|
||||
43
src/bfbs_namer.h
Normal file
43
src/bfbs_namer.h
Normal file
@@ -0,0 +1,43 @@
|
||||
#ifndef FLATBUFFERS_BFBS_NAMER
|
||||
#define FLATBUFFERS_BFBS_NAMER
|
||||
|
||||
#include "flatbuffers/reflection.h"
|
||||
#include "namer.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
|
||||
// Provides Namer capabilities to types defined in the flatbuffers reflection.
|
||||
class BfbsNamer : public Namer {
|
||||
public:
|
||||
explicit BfbsNamer(Config config, std::set<std::string> keywords)
|
||||
: Namer(config, std::move(keywords)) {}
|
||||
|
||||
using Namer::Constant;
|
||||
using Namer::Denamespace;
|
||||
using Namer::Directories;
|
||||
using Namer::Field;
|
||||
using Namer::File;
|
||||
using Namer::Function;
|
||||
using Namer::Method;
|
||||
using Namer::Namespace;
|
||||
using Namer::NamespacedType;
|
||||
using Namer::ObjectType;
|
||||
using Namer::Type;
|
||||
using Namer::Variable;
|
||||
using Namer::Variant;
|
||||
|
||||
template<typename T>
|
||||
std::string Denamespace(T t, std::string &namespace_prefix,
|
||||
const char delimiter = '.') const {
|
||||
return Namer::Denamespace(t->name()->c_str(), namespace_prefix, delimiter);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
std::string Denamespace(T t, const char delimiter = '.') const {
|
||||
return Namer::Denamespace(t->name()->c_str(), delimiter);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace flatbuffers
|
||||
|
||||
#endif // FLATBUFFERS_BFBS_NAMER
|
||||
@@ -23,7 +23,7 @@
|
||||
#include "flatbuffers/flatbuffers.h"
|
||||
#include "flatbuffers/idl.h"
|
||||
#include "flatbuffers/util.h"
|
||||
#include "namer.h"
|
||||
#include "idl_namer.h"
|
||||
|
||||
#ifdef _WIN32
|
||||
# include <direct.h>
|
||||
@@ -82,8 +82,8 @@ class GoGenerator : public BaseGenerator {
|
||||
: BaseGenerator(parser, path, file_name, "" /* not used*/,
|
||||
"" /* not used */, "go"),
|
||||
cur_name_space_(nullptr),
|
||||
namer_({ GoDefaultConfig().WithFlagOptions(parser.opts, path),
|
||||
GoKeywords() }) {
|
||||
namer_(WithFlagOptions(GoDefaultConfig(), parser.opts, path),
|
||||
GoKeywords()) {
|
||||
std::istringstream iss(go_namespace);
|
||||
std::string component;
|
||||
while (std::getline(iss, component, '.')) {
|
||||
@@ -141,7 +141,7 @@ class GoGenerator : public BaseGenerator {
|
||||
private:
|
||||
Namespace go_namespace_;
|
||||
Namespace *cur_name_space_;
|
||||
const Namer namer_;
|
||||
const IdlNamer namer_;
|
||||
|
||||
struct NamespacePtrLess {
|
||||
bool operator()(const Namespace *a, const Namespace *b) const {
|
||||
@@ -385,9 +385,7 @@ class GoGenerator : public BaseGenerator {
|
||||
code += "\t\treturn ";
|
||||
}
|
||||
code += CastToEnum(field.value.type, getter + "(o + rcv._tab.Pos)");
|
||||
if (field.IsScalarOptional()) {
|
||||
code += "\n\t\treturn &v";
|
||||
}
|
||||
if (field.IsScalarOptional()) { code += "\n\t\treturn &v"; }
|
||||
code += "\n\t}\n";
|
||||
code += "\treturn " + GenConstant(field) + "\n";
|
||||
code += "}\n\n";
|
||||
@@ -709,7 +707,8 @@ class GoGenerator : public BaseGenerator {
|
||||
"rcv._tab.Mutate" + namer_.Method(GenTypeBasic(field.value.type));
|
||||
GenReceiver(struct_def, code_ptr);
|
||||
code += " Mutate" + namer_.Function(field);
|
||||
code += "(n " + GenTypeGet(field.value.type) + ") bool {\n\treturn " + setter;
|
||||
code +=
|
||||
"(n " + GenTypeGet(field.value.type) + ") bool {\n\treturn " + setter;
|
||||
code += "(rcv._tab.Pos+flatbuffers.UOffsetT(";
|
||||
code += NumToString(field.value.offset) + "), ";
|
||||
code += CastToBaseType(field.value.type, "n") + ")\n}\n\n";
|
||||
@@ -842,9 +841,7 @@ class GoGenerator : public BaseGenerator {
|
||||
field.value.type.enum_def->is_union)
|
||||
continue;
|
||||
code += "\t" + namer_.Field(field) + " ";
|
||||
if (field.IsScalarOptional()) {
|
||||
code += "*";
|
||||
}
|
||||
if (field.IsScalarOptional()) { code += "*"; }
|
||||
code += NativeType(field.value.type) + "\n";
|
||||
}
|
||||
code += "}\n\n";
|
||||
@@ -1011,9 +1008,7 @@ class GoGenerator : public BaseGenerator {
|
||||
code += "\t" + struct_type + "Add" + field_fn + "(builder, " +
|
||||
prefix + "t." + field_field + ")\n";
|
||||
}
|
||||
if (field.IsScalarOptional()) {
|
||||
code += "\t}\n";
|
||||
}
|
||||
if (field.IsScalarOptional()) { code += "\t}\n"; }
|
||||
} else {
|
||||
if (field.value.type.base_type == BASE_TYPE_STRUCT &&
|
||||
field.value.type.struct_def->fixed) {
|
||||
@@ -1247,9 +1242,7 @@ class GoGenerator : public BaseGenerator {
|
||||
|
||||
std::string TypeName(const FieldDef &field) {
|
||||
std::string prefix;
|
||||
if (field.IsScalarOptional()) {
|
||||
prefix = "*";
|
||||
}
|
||||
if (field.IsScalarOptional()) { prefix = "*"; }
|
||||
return prefix + GenTypeGet(field.value.type);
|
||||
}
|
||||
|
||||
@@ -1274,9 +1267,7 @@ class GoGenerator : public BaseGenerator {
|
||||
}
|
||||
|
||||
std::string GenConstant(const FieldDef &field) {
|
||||
if (field.IsScalarOptional()) {
|
||||
return "nil";
|
||||
}
|
||||
if (field.IsScalarOptional()) { return "nil"; }
|
||||
switch (field.value.type.base_type) {
|
||||
case BASE_TYPE_BOOL:
|
||||
return field.value.constant == "0" ? "false" : "true";
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
#include "flatbuffers/flatbuffers.h"
|
||||
#include "flatbuffers/idl.h"
|
||||
#include "flatbuffers/util.h"
|
||||
#include "namer.h"
|
||||
#include "idl_namer.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
namespace python {
|
||||
@@ -74,8 +74,8 @@ class PythonGenerator : public BaseGenerator {
|
||||
: BaseGenerator(parser, path, file_name, "" /* not used */,
|
||||
"" /* not used */, "py"),
|
||||
float_const_gen_("float('nan')", "float('inf')", "float('-inf')"),
|
||||
namer_({ PythonDefaultConfig().WithFlagOptions(parser.opts, path),
|
||||
PythonKeywords() }) {}
|
||||
namer_(WithFlagOptions(PythonDefaultConfig(), parser.opts, path),
|
||||
PythonKeywords()) {}
|
||||
|
||||
// Most field accessors need to retrieve and test the field offset first,
|
||||
// this is the prefix code for that.
|
||||
@@ -414,7 +414,7 @@ class PythonGenerator : public BaseGenerator {
|
||||
}
|
||||
|
||||
std::string NestedFlatbufferType(std::string unqualified_name) const {
|
||||
StructDef* nested_root = parser_.LookupStruct(unqualified_name);
|
||||
StructDef *nested_root = parser_.LookupStruct(unqualified_name);
|
||||
std::string qualified_name;
|
||||
if (nested_root == nullptr) {
|
||||
qualified_name = namer_.NamespacedType(
|
||||
@@ -1548,8 +1548,8 @@ class PythonGenerator : public BaseGenerator {
|
||||
const auto variant = namer_.Variant(ev);
|
||||
auto field_type = namer_.ObjectType(*ev.union_type.struct_def);
|
||||
|
||||
code += GenIndents(1) + "if unionType == " + union_type + "()." +
|
||||
variant + ":";
|
||||
code +=
|
||||
GenIndents(1) + "if unionType == " + union_type + "()." + variant + ":";
|
||||
if (parser_.opts.include_dependence_headers) {
|
||||
auto package_reference = GenPackageReference(ev.union_type);
|
||||
code += GenIndents(2) + "import " + package_reference;
|
||||
@@ -1565,8 +1565,8 @@ class PythonGenerator : public BaseGenerator {
|
||||
const auto union_type = namer_.Type(enum_def);
|
||||
const auto variant = namer_.Variant(ev);
|
||||
|
||||
code += GenIndents(1) + "if unionType == " + union_type + "()." +
|
||||
variant + ":";
|
||||
code +=
|
||||
GenIndents(1) + "if unionType == " + union_type + "()." + variant + ":";
|
||||
code += GenIndents(2) + "tab = Table(table.Bytes, table.Pos)";
|
||||
code += GenIndents(2) + "union = tab.String(table.Pos)";
|
||||
code += GenIndents(2) + "return union";
|
||||
@@ -1778,7 +1778,7 @@ class PythonGenerator : public BaseGenerator {
|
||||
|
||||
private:
|
||||
const SimpleFloatConstantGenerator float_const_gen_;
|
||||
const Namer namer_;
|
||||
const IdlNamer namer_;
|
||||
};
|
||||
|
||||
} // namespace python
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
#include "flatbuffers/flatbuffers.h"
|
||||
#include "flatbuffers/idl.h"
|
||||
#include "flatbuffers/util.h"
|
||||
#include "namer.h"
|
||||
#include "idl_namer.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
|
||||
@@ -280,7 +280,7 @@ bool GenerateRustModuleRootFile(const Parser &parser,
|
||||
// so return true.
|
||||
return true;
|
||||
}
|
||||
Namer namer(RustDefaultConfig().WithFlagOptions(parser.opts, output_dir),
|
||||
Namer namer(WithFlagOptions(RustDefaultConfig(), parser.opts, output_dir),
|
||||
RustKeywords());
|
||||
// We gather the symbols into a tree of namespaces (which are rust mods) and
|
||||
// generate a file that gathers them all.
|
||||
@@ -345,8 +345,8 @@ class RustGenerator : public BaseGenerator {
|
||||
const std::string &file_name)
|
||||
: BaseGenerator(parser, path, file_name, "", "::", "rs"),
|
||||
cur_name_space_(nullptr),
|
||||
namer_({ RustDefaultConfig().WithFlagOptions(parser.opts, path),
|
||||
RustKeywords() }) {
|
||||
namer_(WithFlagOptions(RustDefaultConfig(), parser.opts, path),
|
||||
RustKeywords()) {
|
||||
// TODO: Namer flag overrides should be in flatc or flatc_main.
|
||||
code_.SetPadding(" ");
|
||||
}
|
||||
@@ -2959,7 +2959,7 @@ class RustGenerator : public BaseGenerator {
|
||||
}
|
||||
|
||||
private:
|
||||
Namer namer_;
|
||||
IdlNamer namer_;
|
||||
};
|
||||
|
||||
} // namespace rust
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
#include "flatbuffers/flatbuffers.h"
|
||||
#include "flatbuffers/idl.h"
|
||||
#include "flatbuffers/util.h"
|
||||
#include "namer.h"
|
||||
#include "idl_namer.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
|
||||
@@ -52,21 +52,88 @@ Namer::Config SwiftDefaultConfig() {
|
||||
|
||||
std::set<std::string> SwiftKeywords() {
|
||||
return {
|
||||
"associatedtype", "class", "deinit", "enum", "extension", "fileprivate",
|
||||
"func", "import", "init", "inout", "internal", "let", "open", "operator",
|
||||
"private", "protocol", "public", "rethrows", "static", "struct",
|
||||
"subscript", "typealias", "var", "break", "case", "continue", "default",
|
||||
"defer", "do", "else", "fallthrough", "for", "guard", "if", "in", "repeat",
|
||||
"return", "switch", "where", "while", "Any", "catch", "false", "is", "nil",
|
||||
"super", "self", "Self", "throw", "throws", "true", "try", "associativity",
|
||||
"convenience", "dynamic", "didSet", "final", "get", "infix", "indirect",
|
||||
"lazy", "left", "mutating", "none", "nonmutating", "optional", "override",
|
||||
"postfix", "precedence", "prefix", "Protocol", "required", "right", "set",
|
||||
"Type", "unowned", "weak", "willSet", "Void",
|
||||
"associatedtype",
|
||||
"class",
|
||||
"deinit",
|
||||
"enum",
|
||||
"extension",
|
||||
"fileprivate",
|
||||
"func",
|
||||
"import",
|
||||
"init",
|
||||
"inout",
|
||||
"internal",
|
||||
"let",
|
||||
"open",
|
||||
"operator",
|
||||
"private",
|
||||
"protocol",
|
||||
"public",
|
||||
"rethrows",
|
||||
"static",
|
||||
"struct",
|
||||
"subscript",
|
||||
"typealias",
|
||||
"var",
|
||||
"break",
|
||||
"case",
|
||||
"continue",
|
||||
"default",
|
||||
"defer",
|
||||
"do",
|
||||
"else",
|
||||
"fallthrough",
|
||||
"for",
|
||||
"guard",
|
||||
"if",
|
||||
"in",
|
||||
"repeat",
|
||||
"return",
|
||||
"switch",
|
||||
"where",
|
||||
"while",
|
||||
"Any",
|
||||
"catch",
|
||||
"false",
|
||||
"is",
|
||||
"nil",
|
||||
"super",
|
||||
"self",
|
||||
"Self",
|
||||
"throw",
|
||||
"throws",
|
||||
"true",
|
||||
"try",
|
||||
"associativity",
|
||||
"convenience",
|
||||
"dynamic",
|
||||
"didSet",
|
||||
"final",
|
||||
"get",
|
||||
"infix",
|
||||
"indirect",
|
||||
"lazy",
|
||||
"left",
|
||||
"mutating",
|
||||
"none",
|
||||
"nonmutating",
|
||||
"optional",
|
||||
"override",
|
||||
"postfix",
|
||||
"precedence",
|
||||
"prefix",
|
||||
"Protocol",
|
||||
"required",
|
||||
"right",
|
||||
"set",
|
||||
"Type",
|
||||
"unowned",
|
||||
"weak",
|
||||
"willSet",
|
||||
"Void",
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
inline std::string GenIndirect(const std::string &reading) {
|
||||
return "{{ACCESS}}.indirect(" + reading + ")";
|
||||
}
|
||||
@@ -87,7 +154,7 @@ class SwiftGenerator : public BaseGenerator {
|
||||
SwiftGenerator(const Parser &parser, const std::string &path,
|
||||
const std::string &file_name)
|
||||
: BaseGenerator(parser, path, file_name, "", "_", "swift"),
|
||||
namer_(SwiftDefaultConfig().WithFlagOptions(parser.opts, path),
|
||||
namer_(WithFlagOptions(SwiftDefaultConfig(), parser.opts, path),
|
||||
SwiftKeywords()) {
|
||||
namespace_depth = 0;
|
||||
code_.SetPadding(" ");
|
||||
@@ -187,7 +254,8 @@ class SwiftGenerator : public BaseGenerator {
|
||||
: is_bool ? ("0" == field.value.constant ? "false" : "true")
|
||||
: field.value.constant;
|
||||
|
||||
main_constructor.push_back("_" + field_var + " = " + field_var + accessing_value);
|
||||
main_constructor.push_back("_" + field_var + " = " + field_var +
|
||||
accessing_value);
|
||||
base_constructor.push_back("_" + field_var + " = " + base_value);
|
||||
|
||||
if (field.padding) { GenPadding(field, &padding_id); }
|
||||
@@ -359,8 +427,8 @@ class SwiftGenerator : public BaseGenerator {
|
||||
code += ", ";
|
||||
continue;
|
||||
}
|
||||
code +=
|
||||
nameprefix + field_var + ": " + obj_api_named + object_name + "." + field_field;
|
||||
code += nameprefix + field_var + ": " + obj_api_named + object_name +
|
||||
"." + field_field;
|
||||
code += ", ";
|
||||
}
|
||||
}
|
||||
@@ -1144,8 +1212,10 @@ class SwiftGenerator : public BaseGenerator {
|
||||
code_ += "case {{KEY}} = {{VALUE}}";
|
||||
}
|
||||
code_ += "";
|
||||
AddMinOrMaxEnumValue(namer_.LegacySwiftVariant(*enum_def.MaxValue()), "max");
|
||||
AddMinOrMaxEnumValue(namer_.LegacySwiftVariant(*enum_def.MinValue()), "min");
|
||||
AddMinOrMaxEnumValue(namer_.LegacySwiftVariant(*enum_def.MaxValue()),
|
||||
"max");
|
||||
AddMinOrMaxEnumValue(namer_.LegacySwiftVariant(*enum_def.MinValue()),
|
||||
"min");
|
||||
Outdent();
|
||||
code_ += "}\n";
|
||||
if (parser_.opts.gen_json_coders) EnumEncoder(enum_def);
|
||||
@@ -1838,7 +1908,7 @@ class SwiftGenerator : public BaseGenerator {
|
||||
|
||||
std::string Mutable() const { return "_Mutable"; }
|
||||
|
||||
Namer namer_;
|
||||
IdlNamer namer_;
|
||||
};
|
||||
} // namespace swift
|
||||
bool GenerateSwift(const Parser &parser, const std::string &path,
|
||||
|
||||
114
src/idl_namer.h
Normal file
114
src/idl_namer.h
Normal file
@@ -0,0 +1,114 @@
|
||||
#ifndef FLATBUFFERS_IDL_NAMER
|
||||
#define FLATBUFFERS_IDL_NAMER
|
||||
|
||||
#include "flatbuffers/idl.h"
|
||||
#include "namer.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
|
||||
// Provides Namer capabilities to types defined in the flatbuffers IDL.
|
||||
class IdlNamer : public Namer {
|
||||
public:
|
||||
explicit IdlNamer(Config config, std::set<std::string> keywords)
|
||||
: Namer(config, std::move(keywords)) {}
|
||||
|
||||
using Namer::Constant;
|
||||
using Namer::Directories;
|
||||
using Namer::Field;
|
||||
using Namer::File;
|
||||
using Namer::Function;
|
||||
using Namer::Method;
|
||||
using Namer::Namespace;
|
||||
using Namer::NamespacedType;
|
||||
using Namer::ObjectType;
|
||||
using Namer::Type;
|
||||
using Namer::Variable;
|
||||
using Namer::Variant;
|
||||
|
||||
// Types are always structs or enums so we can only expose these two
|
||||
// overloads.
|
||||
std::string Type(const StructDef &d) const { return Type(d.name); }
|
||||
std::string Type(const EnumDef &d) const { return Type(d.name); }
|
||||
|
||||
std::string Function(const Definition &s) const { return Function(s.name); }
|
||||
|
||||
std::string Field(const FieldDef &s) const { return Field(s.name); }
|
||||
|
||||
std::string Variable(const FieldDef &s) const { return Variable(s.name); }
|
||||
|
||||
std::string Variable(const StructDef &s) const { return Variable(s.name); }
|
||||
|
||||
std::string Variant(const EnumVal &s) const { return Variant(s.name); }
|
||||
|
||||
std::string EnumVariant(const EnumDef &e, const EnumVal &v) const {
|
||||
return Type(e) + config_.enum_variant_seperator + Variant(v);
|
||||
}
|
||||
|
||||
std::string ObjectType(const StructDef &d) const {
|
||||
return ObjectType(d.name);
|
||||
}
|
||||
std::string ObjectType(const EnumDef &d) const { return ObjectType(d.name); }
|
||||
|
||||
std::string Namespace(const struct Namespace &ns) const {
|
||||
return Namespace(ns.components);
|
||||
}
|
||||
|
||||
std::string NamespacedType(const Definition &def) const {
|
||||
return NamespacedString(def.defined_namespace, Type(def.name));
|
||||
}
|
||||
|
||||
std::string NamespacedObjectType(const Definition &def) const {
|
||||
return NamespacedString(def.defined_namespace, ObjectType(def.name));
|
||||
}
|
||||
|
||||
std::string Directories(const struct Namespace &ns,
|
||||
SkipDir skips = SkipDir::None) const {
|
||||
return Directories(ns.components, skips);
|
||||
}
|
||||
|
||||
// Legacy fields do not really follow the usual config and should be
|
||||
// considered for deprecation.
|
||||
|
||||
std::string LegacyRustNativeVariant(const EnumVal &v) const {
|
||||
return ConvertCase(EscapeKeyword(v.name), Case::kUpperCamel);
|
||||
}
|
||||
|
||||
std::string LegacyRustFieldOffsetName(const FieldDef &field) const {
|
||||
return "VT_" + ConvertCase(EscapeKeyword(field.name), Case::kAllUpper);
|
||||
}
|
||||
|
||||
// TODO(caspern): What's up with this case style?
|
||||
std::string LegacySwiftVariant(const EnumVal &ev) const {
|
||||
auto name = ev.name;
|
||||
if (isupper(name.front())) {
|
||||
std::transform(name.begin(), name.end(), name.begin(), CharToLower);
|
||||
}
|
||||
return EscapeKeyword(ConvertCase(name, Case::kLowerCamel));
|
||||
}
|
||||
|
||||
private:
|
||||
std::string NamespacedString(const struct Namespace *ns,
|
||||
const std::string &str) const {
|
||||
std::string ret;
|
||||
if (ns != nullptr) { ret += Namespace(ns->components); }
|
||||
if (!ret.empty()) ret += config_.namespace_seperator;
|
||||
return ret + str;
|
||||
}
|
||||
};
|
||||
|
||||
// This is a temporary helper function for code generators to call until all
|
||||
// flag-overriding logic into flatc.cpp
|
||||
inline Namer::Config WithFlagOptions(const Namer::Config &input,
|
||||
const IDLOptions &opts,
|
||||
const std::string &path) {
|
||||
Namer::Config result = input;
|
||||
result.object_prefix = opts.object_prefix;
|
||||
result.object_suffix = opts.object_suffix;
|
||||
result.output_path = path;
|
||||
result.filename_suffix = opts.filename_suffix;
|
||||
return result;
|
||||
}
|
||||
|
||||
} // namespace flatbuffers
|
||||
|
||||
#endif // FLATBUFFERS_IDL_NAMER
|
||||
144
src/namer.h
144
src/namer.h
@@ -1,7 +1,6 @@
|
||||
#ifndef FLATBUFFERS_NAMER
|
||||
#define FLATBUFFERS_NAMER
|
||||
|
||||
#include "flatbuffers/idl.h"
|
||||
#include "flatbuffers/util.h"
|
||||
|
||||
namespace flatbuffers {
|
||||
@@ -105,72 +104,35 @@ class Namer {
|
||||
std::string filename_suffix;
|
||||
// Extension for generated files, e.g. ".cpp" or ".rs".
|
||||
std::string filename_extension;
|
||||
|
||||
// This is a temporary helper function for code generators to call until all
|
||||
// code generators are using `Namer`. After that point, we can centralize
|
||||
// flag-overriding logic into flatc.cpp
|
||||
Config WithFlagOptions(const IDLOptions &opts,
|
||||
const std::string &path) const {
|
||||
Config result = *this;
|
||||
result.object_prefix = opts.object_prefix;
|
||||
result.object_suffix = opts.object_suffix;
|
||||
result.output_path = path;
|
||||
result.filename_suffix = opts.filename_suffix;
|
||||
return result;
|
||||
}
|
||||
};
|
||||
Namer(Config config, std::set<std::string> keywords)
|
||||
: config_(config), keywords_(std::move(keywords)) {}
|
||||
|
||||
// Types are always structs or enums so we can only expose these two
|
||||
// overloads.
|
||||
std::string Type(const StructDef &d) const { return Type(d.name); }
|
||||
std::string Type(const EnumDef &d) const { return Type(d.name); }
|
||||
|
||||
template<typename T> std::string Method(const T &s) const {
|
||||
return Method(s.name);
|
||||
}
|
||||
|
||||
std::string Method(const std::string &s) const {
|
||||
virtual std::string Method(const std::string &s) const {
|
||||
return Format(s, config_.methods);
|
||||
}
|
||||
|
||||
std::string Constant(const std::string &s) const {
|
||||
virtual std::string Constant(const std::string &s) const {
|
||||
return Format(s, config_.constants);
|
||||
}
|
||||
|
||||
std::string Function(const std::string &s) const {
|
||||
virtual std::string Function(const std::string &s) const {
|
||||
return Format(s, config_.functions);
|
||||
}
|
||||
|
||||
std::string Function(const Definition &s) const { return Function(s.name); }
|
||||
|
||||
std::string Field(const FieldDef &s) const { return Field(s.name); }
|
||||
|
||||
std::string Variable(const FieldDef &s) const { return Variable(s.name); }
|
||||
|
||||
std::string Variable(const StructDef &s) const { return Variable(s.name); }
|
||||
|
||||
std::string Variable(const std::string &s) const {
|
||||
virtual std::string Variable(const std::string &s) const {
|
||||
return Format(s, config_.variables);
|
||||
}
|
||||
|
||||
std::string Variant(const EnumVal &s) const { return Variant(s.name); }
|
||||
|
||||
std::string EnumVariant(const EnumDef &e, const EnumVal &v) const {
|
||||
return Type(e) + config_.enum_variant_seperator + Variant(v);
|
||||
}
|
||||
|
||||
std::string ObjectType(const StructDef &d) const {
|
||||
return ObjectType(d.name);
|
||||
}
|
||||
std::string ObjectType(const EnumDef &d) const { return ObjectType(d.name); }
|
||||
|
||||
std::string Namespace(const std::string &s) const {
|
||||
virtual std::string Namespace(const std::string &s) const {
|
||||
return Format(s, config_.namespaces);
|
||||
}
|
||||
|
||||
std::string Namespace(const std::vector<std::string> &ns) const {
|
||||
virtual std::string Namespace(const std::vector<std::string> &ns) const {
|
||||
std::string result;
|
||||
for (auto it = ns.begin(); it != ns.end(); it++) {
|
||||
if (it != ns.begin()) result += config_.namespace_seperator;
|
||||
@@ -179,27 +141,15 @@ class Namer {
|
||||
return result;
|
||||
}
|
||||
|
||||
std::string Namespace(const struct Namespace &ns) const {
|
||||
return Namespace(ns.components);
|
||||
}
|
||||
|
||||
std::string NamespacedType(const Definition &def) const {
|
||||
return NamespacedString(def.defined_namespace, Type(def.name));
|
||||
}
|
||||
|
||||
std::string NamespacedType(const std::vector<std::string> &ns,
|
||||
const std::string &s) const {
|
||||
virtual std::string NamespacedType(const std::vector<std::string> &ns,
|
||||
const std::string &s) const {
|
||||
return (ns.empty() ? "" : (Namespace(ns) + config_.namespace_seperator)) +
|
||||
Type(s);
|
||||
}
|
||||
|
||||
std::string NamespacedObjectType(const Definition &def) const {
|
||||
return NamespacedString(def.defined_namespace, ObjectType(def.name));
|
||||
}
|
||||
|
||||
// Returns `filename` with the right casing, suffix, and extension.
|
||||
std::string File(const std::string &filename,
|
||||
SkipFile skips = SkipFile::None) const {
|
||||
virtual std::string File(const std::string &filename,
|
||||
SkipFile skips = SkipFile::None) const {
|
||||
const bool skip_suffix = (skips & SkipFile::Suffix) != SkipFile::None;
|
||||
const bool skip_ext = (skips & SkipFile::Extension) != SkipFile::None;
|
||||
return ConvertCase(filename, config_.filenames, Case::kUpperCamel) +
|
||||
@@ -215,8 +165,8 @@ class Namer {
|
||||
// right seperator. Output path prefixing and the trailing separator may be
|
||||
// skiped using `skips`.
|
||||
// Callers may want to use `EnsureDirExists` with the result.
|
||||
std::string Directories(const std::vector<std::string> &directories,
|
||||
SkipDir skips = SkipDir::None) const {
|
||||
virtual std::string Directories(const std::vector<std::string> &directories,
|
||||
SkipDir skips = SkipDir::None) const {
|
||||
const bool skip_output_path =
|
||||
(skips & SkipDir::OutputPath) != SkipDir::None;
|
||||
const bool skip_trailing_seperator =
|
||||
@@ -230,12 +180,7 @@ class Namer {
|
||||
return result;
|
||||
}
|
||||
|
||||
std::string Directories(const struct Namespace &ns,
|
||||
SkipDir skips = SkipDir::None) const {
|
||||
return Directories(ns.components, skips);
|
||||
}
|
||||
|
||||
std::string EscapeKeyword(const std::string &name) const {
|
||||
virtual std::string EscapeKeyword(const std::string &name) const {
|
||||
if (keywords_.find(name) == keywords_.end()) {
|
||||
return name;
|
||||
} else {
|
||||
@@ -243,59 +188,52 @@ class Namer {
|
||||
}
|
||||
}
|
||||
|
||||
// Legacy fields do not really follow the usual config and should be
|
||||
// considered for deprecation.
|
||||
|
||||
std::string LegacyRustNativeVariant(const EnumVal &v) const {
|
||||
return ConvertCase(EscapeKeyword(v.name), Case::kUpperCamel);
|
||||
}
|
||||
|
||||
std::string LegacyRustFieldOffsetName(const FieldDef& field) const {
|
||||
|
||||
return "VT_" + ConvertCase(EscapeKeyword(field.name), Case::kAllUpper);
|
||||
}
|
||||
|
||||
// TODO(caspern): What's up with this case style?
|
||||
std::string LegacySwiftVariant(const EnumVal &ev) const {
|
||||
auto name = ev.name;
|
||||
if (isupper(name.front())) {
|
||||
std::transform(name.begin(), name.end(), name.begin(), CharToLower);
|
||||
}
|
||||
return EscapeKeyword(ConvertCase(name, Case::kLowerCamel));
|
||||
}
|
||||
|
||||
private:
|
||||
std::string Type(const std::string &s) const {
|
||||
virtual std::string Type(const std::string &s) const {
|
||||
return Format(s, config_.types);
|
||||
}
|
||||
|
||||
std::string ObjectType(const std::string &s) const {
|
||||
virtual std::string ObjectType(const std::string &s) const {
|
||||
return config_.object_prefix + Type(s) + config_.object_suffix;
|
||||
}
|
||||
|
||||
std::string Field(const std::string &s) const {
|
||||
virtual std::string Field(const std::string &s) const {
|
||||
return Format(s, config_.fields);
|
||||
}
|
||||
|
||||
std::string Variant(const std::string &s) const {
|
||||
virtual std::string Variant(const std::string &s) const {
|
||||
return Format(s, config_.variants);
|
||||
}
|
||||
|
||||
std::string NamespacedString(const struct Namespace *ns,
|
||||
const std::string &str) const {
|
||||
std::string ret;
|
||||
if (ns != nullptr) { ret += Namespace(ns->components); }
|
||||
if (!ret.empty()) ret += config_.namespace_seperator;
|
||||
return ret + str;
|
||||
}
|
||||
|
||||
std::string Format(const std::string &s, Case casing) const {
|
||||
virtual std::string Format(const std::string &s, Case casing) const {
|
||||
if (config_.escape_keywords == Config::Escape::BeforeConvertingCase) {
|
||||
return ConvertCase(EscapeKeyword(s), casing, Case::kLowerCamel);
|
||||
} else {
|
||||
return EscapeKeyword(ConvertCase(s, casing, Case::kLowerCamel));
|
||||
}
|
||||
}
|
||||
|
||||
// Denamespaces a string (e.g. The.Quick.Brown.Fox) by returning the last part
|
||||
// after the `delimiter` (Fox) and placing the rest in `namespace_prefix`
|
||||
// (The.Quick.Brown).
|
||||
virtual std::string Denamespace(const std::string &s,
|
||||
std::string &namespace_prefix,
|
||||
const char delimiter = '.') const {
|
||||
const size_t pos = s.find_last_of(delimiter);
|
||||
if (pos == std::string::npos) {
|
||||
namespace_prefix = "";
|
||||
return s;
|
||||
}
|
||||
namespace_prefix = s.substr(0, pos);
|
||||
return s.substr(pos + 1);
|
||||
}
|
||||
|
||||
// Same as above, but disregards the prefix.
|
||||
virtual std::string Denamespace(const std::string &s,
|
||||
const char delimiter = '.') const {
|
||||
std::string prefix;
|
||||
return Denamespace(s, prefix, delimiter);
|
||||
}
|
||||
|
||||
const Config config_;
|
||||
const std::set<std::string> keywords_;
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user