/*
 * Copyright 2020 Google Inc. All rights reserved.
 *
 * Licensed 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.
 */

#include <cctype>
#include <unordered_set>

#include "flatbuffers/code_generators.h"
#include "flatbuffers/flatbuffers.h"
#include "flatbuffers/idl.h"
#include "flatbuffers/util.h"

namespace flatbuffers {

namespace swift {

inline std::string GenIndirect(const std::string &reading) {
  return "{{ACCESS}}.indirect(" + reading + ")";
}

inline std::string GenArrayMainBody(const std::string &optional) {
  return "{{ACCESS_TYPE}} func {{VALUENAME}}(at index: Int32) -> "
         "{{VALUETYPE}}" +
         optional + " { ";
}

class SwiftGenerator : public BaseGenerator {
 private:
  CodeWriter code_;
  std::unordered_set<std::string> keywords_;
  int namespace_depth;

 public:
  SwiftGenerator(const Parser &parser, const std::string &path,
                 const std::string &file_name)
      : BaseGenerator(parser, path, file_name, "", "_", "swift") {
    namespace_depth = 0;
    code_.SetPadding("    ");
    static const char *const keywords[] = {
      "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",
      nullptr,
    };
    for (auto kw = keywords; *kw; kw++) keywords_.insert(*kw);
  }

  bool generate() {
    code_.Clear();
    code_.SetValue("ACCESS", "_accessor");
    code_.SetValue("TABLEOFFSET", "VTOFFSET");
    code_ += "// " + std::string(FlatBuffersGeneratedWarning());
    code_ += "// swiftlint:disable all\n";
    code_ += "import FlatBuffers\n";
    // Generate code for all the enum declarations.

    for (auto it = parser_.enums_.vec.begin(); it != parser_.enums_.vec.end();
         ++it) {
      const auto &enum_def = **it;
      if (!enum_def.generated) { GenEnum(enum_def); }
    }

    for (auto it = parser_.structs_.vec.begin();
         it != parser_.structs_.vec.end(); ++it) {
      const auto &struct_def = **it;
      if (struct_def.fixed && !struct_def.generated) {
        GenStructReader(struct_def);
        if (parser_.opts.generate_object_based_api) {
          GenObjectAPI(struct_def);
        }
      }
    }

    for (auto it = parser_.structs_.vec.begin();
         it != parser_.structs_.vec.end(); ++it) {
      const auto &struct_def = **it;
      if (struct_def.fixed && !struct_def.generated) {
        GenStructWriter(struct_def);
      }
    }

    for (auto it = parser_.structs_.vec.begin();
         it != parser_.structs_.vec.end(); ++it) {
      const auto &struct_def = **it;
      if (!struct_def.fixed && !struct_def.generated) {
        GenTable(struct_def);
        if (parser_.opts.generate_object_based_api) {
          GenObjectAPI(struct_def);
        }
      }
    }

    const auto filename = GeneratedFileName(path_, file_name_, parser_.opts);
    const auto final_code = code_.ToString();
    return SaveFile(filename.c_str(), final_code, false);
  }

  void mark(const std::string &str) {
    code_.SetValue("MARKVALUE", str);
    code_ += "\n// MARK: - {{MARKVALUE}}\n";
  }

  // Generates the create function for swift
  void GenStructWriter(const StructDef &struct_def) {
    auto is_private_access = struct_def.attributes.Lookup("private");
    code_.SetValue("ACCESS_TYPE", is_private_access ? "internal" : "public");
    code_.SetValue("STRUCTNAME", NameWrappedInNameSpace(struct_def));
    code_.SetValue("SHORT_STRUCTNAME", Name(struct_def));
    code_ += "extension {{STRUCTNAME}} {";
    Indent();
    code_ += "@discardableResult";
    code_ +=
        "{{ACCESS_TYPE}} static func create{{SHORT_STRUCTNAME}}(builder: inout "
        "FlatBufferBuilder, \\";
    std::string func_header = "";
    GenerateStructArgs(struct_def, &func_header, "", "");
    code_ += func_header.substr(0, func_header.size() - 2) + "\\";
    code_ += ") -> Offset<UOffset> {";
    Indent();
    code_ +=
        "builder.createStructOf(size: {{STRUCTNAME}}.size, alignment: "
        "{{STRUCTNAME}}.alignment)";
    GenerateStructBody(struct_def, "");
    code_ += "return builder.endStruct()";
    Outdent();
    code_ += "}\n";
    Outdent();
    code_ += "}\n";
  }

  void GenerateStructBody(const StructDef &struct_def,
                          const std::string &nameprefix, int offset = 0) {
    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      auto name = nameprefix + Name(field);
      const auto &field_type = field.value.type;
      auto type = GenTypeBasic(field_type, false);
      if (IsStruct(field.value.type)) {
        GenerateStructBody(*field_type.struct_def, (nameprefix + field.name),
                           static_cast<int>(field.value.offset));
      } else {
        auto off = NumToString(offset + field.value.offset);
        code_ += "builder.reverseAdd(v: " + name +
                 (field_type.enum_def ? ".rawValue" : "") +
                 ", postion: " + off + ")";
      }
    }
  }

  void GenerateStructArgs(const StructDef &struct_def, std::string *code_ptr,
                          const std::string &nameprefix,
                          const std::string &object_name,
                          const std::string &obj_api_named = "",
                          bool is_obj_api = false) {
    auto &code = *code_ptr;
    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      const auto &field_type = field.value.type;
      if (IsStruct(field.value.type)) {
        GenerateStructArgs(
            *field_type.struct_def, code_ptr, (nameprefix + field.name),
            (object_name + "." + field.name), obj_api_named, is_obj_api);
      } else {
        auto name = Name(field);
        auto type = GenType(field.value.type);
        if (!is_obj_api) {
          code += nameprefix + name + ": " + type;
          if (!IsEnum(field.value.type)) {
            code += " = ";
            auto is_bool = IsBool(field.value.type.base_type);
            auto constant =
                is_bool ? ("0" == field.value.constant ? "false" : "true")
                        : field.value.constant;
            code += constant;
          }
          code += ", ";
          continue;
        }
        code +=
            nameprefix + name + ": " + obj_api_named + object_name + "." + name;
        code += ", ";
      }
    }
  }

  void GenObjectHeader(const StructDef &struct_def) {
    GenComment(struct_def.doc_comment);
    code_.SetValue("SHORT_STRUCTNAME", Name(struct_def));
    code_.SetValue("STRUCTNAME", NameWrappedInNameSpace(struct_def));
    code_.SetValue("PROTOCOL",
                   struct_def.fixed ? "Readable" : "FlatBufferObject");
    code_.SetValue("OBJECTTYPE", struct_def.fixed ? "Struct" : "Table");
    code_ += "{{ACCESS_TYPE}} struct {{STRUCTNAME}}: {{PROTOCOL}}\\";
    if (!struct_def.fixed && parser_.opts.generate_object_based_api)
      code_ += ", ObjectAPI\\";
    code_ += " {\n";
    Indent();
    code_ += ValidateFunc();
    code_ +=
        "{{ACCESS_TYPE}} var __buffer: ByteBuffer! { return {{ACCESS}}.bb }";
    code_ += "private var {{ACCESS}}: {{OBJECTTYPE}}\n";
    if (struct_def.fixed) {
      code_.SetValue("BYTESIZE", NumToString(struct_def.bytesize));
      code_.SetValue("MINALIGN", NumToString(struct_def.minalign));
      code_ += "{{ACCESS_TYPE}} static var size = {{BYTESIZE}}";
      code_ += "{{ACCESS_TYPE}} static var alignment = {{MINALIGN}}";
    } else {
      if (parser_.file_identifier_.length()) {
        code_.SetValue("FILENAME", parser_.file_identifier_);
        code_ +=
            "{{ACCESS_TYPE}} static func finish(_ fbb: inout "
            "FlatBufferBuilder, end: "
            "Offset<UOffset>, prefix: Bool = false) { fbb.finish(offset: end, "
            "fileId: "
            "\"{{FILENAME}}\", addPrefix: prefix) }";
      }
      code_ +=
          "{{ACCESS_TYPE}} static func getRootAs{{SHORT_STRUCTNAME}}(bb: "
          "ByteBuffer) -> "
          "{{STRUCTNAME}} { return {{STRUCTNAME}}(Table(bb: bb, position: "
          "Int32(bb.read(def: UOffset.self, position: bb.reader)) + "
          "Int32(bb.reader))) }\n";
      code_ += "private init(_ t: Table) { {{ACCESS}} = t }";
    }
    code_ +=
        "{{ACCESS_TYPE}} init(_ bb: ByteBuffer, o: Int32) { {{ACCESS}} = "
        "{{OBJECTTYPE}}(bb: "
        "bb, position: o) }";
    code_ += "";
  }

  // Generates the reader for swift
  void GenTable(const StructDef &struct_def) {
    auto is_private_access = struct_def.attributes.Lookup("private");
    code_.SetValue("ACCESS_TYPE", is_private_access ? "internal" : "public");

    GenObjectHeader(struct_def);
    GenTableAccessors(struct_def);
    GenTableReader(struct_def);
    GenTableWriter(struct_def);
    if (parser_.opts.generate_object_based_api)
      GenerateObjectAPITableExtension(struct_def);
    Outdent();
    code_ += "}\n";
  }

  // Generates the reader for swift
  void GenTableAccessors(const StructDef &struct_def) {
    // Generate field id constants.
    if (struct_def.fields.vec.size() > 0) {
      code_ += "private enum {{TABLEOFFSET}}: VOffset {";
      Indent();
      for (auto it = struct_def.fields.vec.begin();
           it != struct_def.fields.vec.end(); ++it) {
        const auto &field = **it;
        if (field.deprecated) { continue; }
        code_.SetValue("OFFSET_NAME", Name(field));
        code_.SetValue("OFFSET_VALUE", NumToString(field.value.offset));
        code_ += "case {{OFFSET_NAME}} = {{OFFSET_VALUE}}";
      }
      code_ += "var v: Int32 { Int32(self.rawValue) }";
      code_ += "var p: VOffset { self.rawValue }";
      Outdent();
      code_ += "}";
      code_ += "";
    }
  }

  void GenerateObjectAPIExtensionHeader() {
    code_ += "\n";
    code_ += "{{ACCESS_TYPE}} mutating func unpack() -> " +
             ObjectAPIName("{{STRUCTNAME}}") + " {";
    Indent();
    code_ += "return " + ObjectAPIName("{{STRUCTNAME}}") + "(&self)";
    Outdent();
    code_ += "}";
    code_ +=
        "{{ACCESS_TYPE}} static func pack(_ builder: inout FlatBufferBuilder, "
        "obj: "
        "inout " +
        ObjectAPIName("{{STRUCTNAME}}") + "?) -> Offset<UOffset> {";
    Indent();
    code_ += "guard var obj = obj else { return Offset<UOffset>() }";
    code_ += "return pack(&builder, obj: &obj)";
    Outdent();
    code_ += "}";
    code_ += "";
    code_ +=
        "{{ACCESS_TYPE}} static func pack(_ builder: inout FlatBufferBuilder, "
        "obj: "
        "inout " +
        ObjectAPIName("{{STRUCTNAME}}") + ") -> Offset<UOffset> {";
    Indent();
  }

  void GenerateObjectAPIStructExtension(const StructDef &struct_def) {
    GenerateObjectAPIExtensionHeader();
    std::string code;
    GenerateStructArgs(struct_def, &code, "", "", "obj", true);
    code_ += "return create{{SHORT_STRUCTNAME}}(builder: &builder, \\";
    code_ += code.substr(0, code.size() - 2) + "\\";
    code_ += ")";
    Outdent();
    code_ += "}";
  }

  void GenTableReader(const StructDef &struct_def) {
    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      GenTableReaderFields(field);
    }
  }

  void GenTableWriter(const StructDef &struct_def) {
    flatbuffers::FieldDef *key_field = nullptr;
    std::vector<std::string> require_fields;
    std::vector<std::string> create_func_body;
    std::vector<std::string> create_func_header;
    auto should_generate_create = struct_def.fields.vec.size() != 0;

    code_.SetValue("NUMBEROFFIELDS", NumToString(struct_def.fields.vec.size()));
    code_ +=
        "{{ACCESS_TYPE}} static func start{{SHORT_STRUCTNAME}}(_ fbb: inout "
        "FlatBufferBuilder) -> "
        "UOffset { fbb.startTable(with: {{NUMBEROFFIELDS}}) }";

    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      if (field.key) key_field = &field;
      if (field.required)
        require_fields.push_back(NumToString(field.value.offset));

      GenTableWriterFields(field, &create_func_body, &create_func_header,
                           should_generate_create);
    }
    code_ +=
        "{{ACCESS_TYPE}} static func end{{SHORT_STRUCTNAME}}(_ fbb: inout "
        "FlatBufferBuilder, "
        "start: "
        "UOffset) -> Offset<UOffset> { let end = Offset<UOffset>(offset: "
        "fbb.endTable(at: start))\\";
    if (require_fields.capacity() != 0) {
      std::string fields = "";
      for (auto it = require_fields.begin(); it != require_fields.end(); ++it)
        fields += *it + ", ";
      code_.SetValue("FIELDS", fields.substr(0, fields.size() - 2));
      code_ += "; fbb.require(table: end, fields: [{{FIELDS}}])\\";
    }
    code_ += "; return end }";

    if (should_generate_create) {
      code_ += "{{ACCESS_TYPE}} static func create{{SHORT_STRUCTNAME}}(";
      Indent();
      code_ += "_ fbb: inout FlatBufferBuilder,";
      for (auto it = create_func_header.begin(); it < create_func_header.end();
           ++it) {
        code_ += *it + "\\";
        if (it < create_func_header.end() - 1) code_ += ",";
      }
      code_ += "";
      Outdent();
      code_ += ") -> Offset<UOffset> {";
      Indent();
      code_ += "let __start = {{STRUCTNAME}}.start{{SHORT_STRUCTNAME}}(&fbb)";
      for (auto it = create_func_body.begin(); it < create_func_body.end();
           ++it) {
        code_ += *it;
      }
      code_ +=
          "return {{STRUCTNAME}}.end{{SHORT_STRUCTNAME}}(&fbb, start: __start)";
      Outdent();
      code_ += "}";
    }

    std::string spacing = "";

    if (key_field != nullptr && !struct_def.fixed && struct_def.has_key) {
      code_.SetValue("VALUENAME", NameWrappedInNameSpace(struct_def));
      code_.SetValue("SHORT_VALUENAME", Name(struct_def));
      code_.SetValue("VOFFSET", NumToString(key_field->value.offset));

      code_ +=
          "{{ACCESS_TYPE}} static func "
          "sortVectorOf{{SHORT_VALUENAME}}(offsets:[Offset<UOffset>], "
          "_ fbb: inout FlatBufferBuilder) -> Offset<UOffset> {";
      Indent();
      code_ += spacing + "var off = offsets";
      code_ +=
          spacing +
          "off.sort { Table.compare(Table.offset(Int32($1.o), vOffset: "
          "{{VOFFSET}}, fbb: fbb.buffer), Table.offset(Int32($0.o), vOffset: "
          "{{VOFFSET}}, fbb: fbb.buffer), fbb: fbb.buffer) < 0 } ";
      code_ += spacing + "return fbb.createVector(ofOffsets: off)";
      Outdent();
      code_ += "}";
      GenLookup(*key_field);
    }
  }

  void GenTableWriterFields(const FieldDef &field,
                            std::vector<std::string> *create_body,
                            std::vector<std::string> *create_header,
                            bool &contains_structs) {
    std::string builder_string = ", _ fbb: inout FlatBufferBuilder) { ";
    auto &create_func_body = *create_body;
    auto &create_func_header = *create_header;
    auto name = Name(field);
    auto type = GenType(field.value.type);
    bool opt_scalar = field.optional && IsScalar(field.value.type.base_type);
    auto nullable_type = opt_scalar ? type + "?" : type;
    code_.SetValue("VALUENAME", name);
    code_.SetValue("VALUETYPE", nullable_type);
    code_.SetValue("OFFSET", name);
    code_.SetValue("CONSTANT", field.value.constant);
    std::string check_if_vector =
        (IsVector(field.value.type) ||
         IsArray(field.value.type))
            ? "VectorOf("
            : "(";
    auto body = "add" + check_if_vector + name + ": ";
    code_ += "{{ACCESS_TYPE}} static func " + body + "\\";

    create_func_body.push_back("{{STRUCTNAME}}." + body + name + ", &fbb)");

    if (IsScalar(field.value.type.base_type) &&
        !IsBool(field.value.type.base_type)) {
      std::string is_enum = IsEnum(field.value.type) ? ".rawValue" : "";
      std::string optional_enum =
          IsEnum(field.value.type) ? ("?" + is_enum) : "";
      code_ +=
          "{{VALUETYPE}}" + builder_string + "fbb.add(element: {{VALUENAME}}\\";

      code_ += field.optional ? (optional_enum + "\\")
                              : (is_enum + ", def: {{CONSTANT}}\\");

      code_ += ", at: {{TABLEOFFSET}}.{{OFFSET}}.p) }";

      auto default_value =
          IsEnum(field.value.type)
              ? (field.optional ? "nil" : GenEnumDefaultValue(field))
              : field.value.constant;
      create_func_header.push_back("" + name + ": " + nullable_type + " = " +
                                   (field.optional ? "nil" : default_value));
      return;
    }

    if (IsBool(field.value.type.base_type)) {
      std::string default_value =
          "0" == field.value.constant ? "false" : "true";

      code_.SetValue("CONSTANT", default_value);
      code_.SetValue("VALUETYPE", field.optional ? "Bool?" : "Bool");
      code_ += "{{VALUETYPE}}" + builder_string +
               "fbb.add(element: {{VALUENAME}},\\";
      code_ += field.optional ? "\\" : " def: {{CONSTANT}},";
      code_ += " at: {{TABLEOFFSET}}.{{OFFSET}}.p) }";
      create_func_header.push_back(name + ": " + nullable_type + " = " +
                                   (field.optional ? "nil" : default_value));
      return;
    }

    if (IsStruct(field.value.type)) {
      contains_structs = false;
      auto struct_type = "Offset<UOffset>?";
      auto camel_case_name = "structOf" + MakeCamel(name, true);
      auto reader_type =
          "fbb.add(structOffset: {{TABLEOFFSET}}.{{OFFSET}}.p) }";
      auto create_struct = "guard {{VALUENAME}} != nil else { return }; ";
      code_ += struct_type + builder_string + create_struct + reader_type;
      return;
    }

    auto offset_type = IsString(field.value.type)
                           ? "Offset<String>"
                           : "Offset<UOffset>";
    auto camel_case_name =
        (IsVector(field.value.type) ||
                 IsArray(field.value.type)
             ? "vectorOf"
             : "offsetOf") +
        MakeCamel(name, true);
    create_func_header.push_back(camel_case_name + " " + name + ": " +
                                 offset_type + " = Offset()");
    auto reader_type =
        IsStruct(field.value.type) && field.value.type.struct_def->fixed
            ? "structOffset: {{TABLEOFFSET}}.{{OFFSET}}.p) }"
            : "offset: {{VALUENAME}}, at: {{TABLEOFFSET}}.{{OFFSET}}.p) }";
    code_ += offset_type + builder_string + "fbb.add(" + reader_type;

    auto vectortype = field.value.type.VectorType();

    if ((vectortype.base_type == BASE_TYPE_STRUCT &&
         field.value.type.struct_def->fixed) &&
        (IsVector(field.value.type) ||
         IsArray(field.value.type))) {
      auto field_name = NameWrappedInNameSpace(*vectortype.struct_def);
      code_ += "public static func startVectorOf" + MakeCamel(name, true) +
               "(_ size: Int, in builder: inout "
               "FlatBufferBuilder) {";
      Indent();
      code_ += "builder.startVectorOfStructs(count: size, size: " + field_name +
               ".size, "
               "alignment: " +
               field_name + ".alignment)";
      Outdent();
      code_ += "}";
    }
  }

  void GenTableReaderFields(const FieldDef &field) {
    auto offset = NumToString(field.value.offset);
    auto name = Name(field);
    auto type = GenType(field.value.type);
    code_.SetValue("VALUENAME", name);
    code_.SetValue("VALUETYPE", type);
    code_.SetValue("OFFSET", name);
    code_.SetValue("CONSTANT", field.value.constant);
    bool opt_scalar = field.optional && IsScalar(field.value.type.base_type);
    std::string def_Val = opt_scalar ? "nil" : "{{CONSTANT}}";
    std::string optional = opt_scalar ? "?" : "";
    auto const_string = "return o == 0 ? " + def_Val + " : ";
    GenComment(field.doc_comment);
    if (IsScalar(field.value.type.base_type) && !IsEnum(field.value.type) &&
        !IsBool(field.value.type.base_type)) {
      code_ += GenReaderMainBody(optional) + GenOffset() + const_string +
               GenReader("VALUETYPE", "o") + " }";
      if (parser_.opts.mutable_buffer) code_ += GenMutate("o", GenOffset());
      return;
    }

    if (IsBool(field.value.type.base_type)) {
      std::string default_value =
          "0" == field.value.constant ? "false" : "true";
      code_.SetValue("CONSTANT", default_value);
      code_.SetValue("VALUETYPE", "Bool");
      code_ += GenReaderMainBody(optional) + "\\";
      code_.SetValue("VALUETYPE", "Byte");
      code_ += GenOffset() + "return o == 0 ? {{CONSTANT}} : 0 != " +
               GenReader("VALUETYPE", "o") + " }";
      if (parser_.opts.mutable_buffer) code_ += GenMutate("o", GenOffset());
      return;
    }

    if (IsEnum(field.value.type)) {
      auto default_value = field.optional ? "nil" : GenEnumDefaultValue(field);
      code_.SetValue("BASEVALUE", GenTypeBasic(field.value.type, false));
      code_ += GenReaderMainBody(optional) + "\\";
      code_ += GenOffset() + "return o == 0 ? " + default_value + " : " +
               GenEnumConstructor("o") + "?? " + default_value + " }";
      if (parser_.opts.mutable_buffer && !IsUnion(field.value.type))
        code_ += GenMutate("o", GenOffset(), true);
      return;
    }

    std::string is_required = field.required ? "!" : "?";
    auto required_reader = field.required ? "return " : const_string;

    if (IsStruct(field.value.type) && field.value.type.struct_def->fixed) {
      code_.SetValue("VALUETYPE", GenType(field.value.type));
      code_.SetValue("CONSTANT", "nil");
      code_ += GenReaderMainBody(is_required) + GenOffset() + required_reader +
               GenConstructor("o + {{ACCESS}}.postion");
      return;
    }
    switch (field.value.type.base_type) {
      case BASE_TYPE_STRUCT:
        code_.SetValue("VALUETYPE", GenType(field.value.type));
        code_.SetValue("CONSTANT", "nil");
        code_ += GenReaderMainBody(is_required) + GenOffset() +
                 required_reader +
                 GenConstructor(GenIndirect("o + {{ACCESS}}.postion"));
        break;

      case BASE_TYPE_STRING:
        code_.SetValue("VALUETYPE", GenType(field.value.type));
        code_.SetValue("CONSTANT", "nil");
        code_ += GenReaderMainBody(is_required) + GenOffset() +
                 required_reader + "{{ACCESS}}.string(at: o) }";
        code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}SegmentArray: [UInt8]" +
                 is_required +
                 " { return "
                 "{{ACCESS}}.getVector(at: {{TABLEOFFSET}}.{{OFFSET}}.v) }";
        break;

      case BASE_TYPE_ARRAY: FLATBUFFERS_FALLTHROUGH();  // fall thru
      case BASE_TYPE_VECTOR:
        GenTableReaderVectorFields(field, const_string);
        break;
      case BASE_TYPE_UNION:
        code_.SetValue("CONSTANT", "nil");
        code_ +=
            "{{ACCESS_TYPE}} func {{VALUENAME}}<T: FlatBufferObject>(type: "
            "T.Type) -> T" +
            is_required + " { " + GenOffset() + required_reader +
            "{{ACCESS}}.union(o) }";
        break;
      default: FLATBUFFERS_ASSERT(0);
    }
  }

  void GenTableReaderVectorFields(const FieldDef &field,
                                  const std::string &const_string) {
    auto vectortype = field.value.type.VectorType();
    code_.SetValue("SIZE", NumToString(InlineSize(vectortype)));
    code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}Count: Int32 { " + GenOffset() +
             const_string + "{{ACCESS}}.vector(count: o) }";
    code_.SetValue("CONSTANT", IsScalar(vectortype.base_type) == true
                                   ? field.value.constant
                                   : "nil");
    auto nullable = IsScalar(vectortype.base_type) == true ? "" : "?";
    nullable = IsEnum(vectortype) == true ? "?" : nullable;
    if (vectortype.base_type != BASE_TYPE_UNION) {
      code_ += GenArrayMainBody(nullable) + GenOffset() + "\\";
    } else {
      code_ +=
          "{{ACCESS_TYPE}} func {{VALUENAME}}<T: FlatBufferObject>(at index: "
          "Int32, type: T.Type) -> T? { " +
          GenOffset() + "\\";
    }

    if (IsBool(vectortype.base_type)) {
      code_.SetValue("CONSTANT", field.value.offset == 0 ? "false" : "true");
      code_.SetValue("VALUETYPE", "Byte");
    }
    if (!IsEnum(vectortype))
      code_ +=
          const_string + (IsBool(vectortype.base_type) ? "0 != " : "") + "\\";

    if (IsScalar(vectortype.base_type) && !IsEnum(vectortype) &&
        !IsBool(field.value.type.base_type)) {
      code_ +=
          "{{ACCESS}}.directRead(of: {{VALUETYPE}}.self, offset: "
          "{{ACCESS}}.vector(at: o) + index * {{SIZE}}) }";
      code_ +=
          "{{ACCESS_TYPE}} var {{VALUENAME}}: [{{VALUETYPE}}] { return "
          "{{ACCESS}}.getVector(at: {{TABLEOFFSET}}.{{OFFSET}}.v) ?? [] }";
      if (parser_.opts.mutable_buffer) code_ += GenMutateArray();
      return;
    }
    if (vectortype.base_type == BASE_TYPE_STRUCT &&
        field.value.type.struct_def->fixed) {
      code_ += GenConstructor("{{ACCESS}}.vector(at: o) + index * {{SIZE}}");
      return;
    }

    if (IsString(vectortype)) {
      code_ +=
          "{{ACCESS}}.directString(at: {{ACCESS}}.vector(at: o) + "
          "index * {{SIZE}}) }";
      return;
    }

    if (IsEnum(vectortype)) {
      code_.SetValue("BASEVALUE", GenTypeBasic(vectortype, false));
      code_ += "return o == 0 ? {{VALUETYPE}}" + GenEnumDefaultValue(field) +
               " : {{VALUETYPE}}(rawValue: {{ACCESS}}.directRead(of: "
               "{{BASEVALUE}}.self, offset: {{ACCESS}}.vector(at: o) + "
               "index * {{SIZE}})) }";
      return;
    }
    if (vectortype.base_type == BASE_TYPE_UNION) {
      code_ +=
          "{{ACCESS}}.directUnion({{ACCESS}}.vector(at: o) + "
          "index * {{SIZE}}) }";
      return;
    }

    if (vectortype.base_type == BASE_TYPE_STRUCT &&
        !field.value.type.struct_def->fixed) {
      code_ += GenConstructor(
          "{{ACCESS}}.indirect({{ACCESS}}.vector(at: o) + index * "
          "{{SIZE}})");
      auto &sd = *field.value.type.struct_def;
      auto &fields = sd.fields.vec;
      for (auto kit = fields.begin(); kit != fields.end(); ++kit) {
        auto &key_field = **kit;
        if (key_field.key) {
          GenByKeyFunctions(key_field);
          break;
        }
      }
    }
  }

  void GenByKeyFunctions(const FieldDef &key_field) {
    code_.SetValue("TYPE", GenType(key_field.value.type));
    code_ +=
        "{{ACCESS_TYPE}} func {{VALUENAME}}By(key: {{TYPE}}) -> {{VALUETYPE}}? "
        "{ \\";
    code_ += GenOffset() +
             "return o == 0 ? nil : {{VALUETYPE}}.lookupByKey(vector: "
             "{{ACCESS}}.vector(at: o), key: key, fbb: {{ACCESS}}.bb) }";
  }

  // Generates the reader for swift
  void GenStructReader(const StructDef &struct_def) {
    auto is_private_access = struct_def.attributes.Lookup("private");
    code_.SetValue("ACCESS_TYPE", is_private_access ? "internal" : "public");

    GenObjectHeader(struct_def);
    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      auto offset = NumToString(field.value.offset);
      auto name = Name(field);
      auto type = GenType(field.value.type);
      code_.SetValue("VALUENAME", name);
      code_.SetValue("VALUETYPE", type);
      code_.SetValue("OFFSET", offset);
      GenComment(field.doc_comment);
      if (IsScalar(field.value.type.base_type) && !IsEnum(field.value.type)) {
        code_ +=
            GenReaderMainBody() + "return " + GenReader("VALUETYPE") + " }";
        if (parser_.opts.mutable_buffer) code_ += GenMutate("{{OFFSET}}", "");
      } else if (IsEnum(field.value.type)) {
        code_.SetValue("BASEVALUE", GenTypeBasic(field.value.type, false));
        code_ += GenReaderMainBody() + "return " +
                 GenEnumConstructor("{{OFFSET}}") + "?? " +
                 GenEnumDefaultValue(field) + " }";
      } else if (IsStruct(field.value.type)) {
        code_.SetValue("VALUETYPE", GenType(field.value.type));
        code_ += GenReaderMainBody() + "return " +
                 GenConstructor("{{ACCESS}}.postion + {{OFFSET}}");
      }
    }
    if (parser_.opts.generate_object_based_api)
      GenerateObjectAPIStructExtension(struct_def);
    Outdent();
    code_ += "}\n";
  }

  void GenEnum(const EnumDef &enum_def) {
    if (enum_def.generated) return;
    auto is_private_access = enum_def.attributes.Lookup("private");
    code_.SetValue("ACCESS_TYPE", is_private_access ? "internal" : "public");
    code_.SetValue("ENUM_NAME", NameWrappedInNameSpace(enum_def));
    code_.SetValue("BASE_TYPE", GenTypeBasic(enum_def.underlying_type, false));
    GenComment(enum_def.doc_comment);
    code_ += "{{ACCESS_TYPE}} enum {{ENUM_NAME}}: {{BASE_TYPE}}, Enum { ";
    Indent();
    code_ += "{{ACCESS_TYPE}} typealias T = {{BASE_TYPE}}";
    code_ +=
        "{{ACCESS_TYPE}} static var byteSize: Int { return "
        "MemoryLayout<{{BASE_TYPE}}>.size "
        "}";
    code_ +=
        "{{ACCESS_TYPE}} var value: {{BASE_TYPE}} { return self.rawValue }";
    for (auto it = enum_def.Vals().begin(); it != enum_def.Vals().end(); ++it) {
      const auto &ev = **it;
      auto name = Name(ev);
      code_.SetValue("KEY", name);
      code_.SetValue("VALUE", enum_def.ToString(ev));
      GenComment(ev.doc_comment);
      code_ += "case {{KEY}} = {{VALUE}}";
    }
    code_ += "\n";
    AddMinOrMaxEnumValue(Name(*enum_def.MaxValue()), "max");
    AddMinOrMaxEnumValue(Name(*enum_def.MinValue()), "min");
    Outdent();
    code_ += "}\n";
    if (parser_.opts.generate_object_based_api && enum_def.is_union) {
      code_ += "{{ACCESS_TYPE}} struct {{ENUM_NAME}}Union {";
      Indent();
      code_ += "{{ACCESS_TYPE}} var type: {{ENUM_NAME}}";
      code_ += "{{ACCESS_TYPE}} var value: NativeTable?";
      code_ += "{{ACCESS_TYPE}} init(_ v: NativeTable?, type: {{ENUM_NAME}}) {";
      Indent();
      code_ += "self.type = type";
      code_ += "self.value = v";
      Outdent();
      code_ += "}";
      code_ +=
          "{{ACCESS_TYPE}} func pack(builder: inout FlatBufferBuilder) -> "
          "Offset<UOffset> {";
      Indent();
      BuildUnionEnumSwitchCaseWritter(enum_def);
      Outdent();
      code_ += "}";
      Outdent();
      code_ += "}";
    }
  }

  void GenObjectAPI(const StructDef &struct_def) {
    code_ += "{{ACCESS_TYPE}} class " + ObjectAPIName("{{STRUCTNAME}}") +
             ": NativeTable {\n";
    std::vector<std::string> buffer_constructor;
    std::vector<std::string> base_constructor;
    Indent();
    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      BuildObjectAPIConstructorBody(field, struct_def.fixed, buffer_constructor,
                                    base_constructor);
    }
    code_ += "";
    BuildObjectAPIConstructor(
        buffer_constructor,
        "_ _t: inout " + NameWrappedInNameSpace(struct_def));
    BuildObjectAPIConstructor(base_constructor);
    if (!struct_def.fixed)
      code_ +=
          "{{ACCESS_TYPE}} func serialize() -> ByteBuffer { return "
          "serialize(type: "
          "{{STRUCTNAME}}.self) }\n";
    Outdent();
    code_ += "}";
  }

  void GenerateObjectAPITableExtension(const StructDef &struct_def) {
    GenerateObjectAPIExtensionHeader();
    std::vector<std::string> unpack_body;
    std::string builder = ", &builder)";
    for (auto it = struct_def.fields.vec.begin();
         it != struct_def.fields.vec.end(); ++it) {
      auto &field = **it;
      if (field.deprecated) continue;
      auto name = Name(field);
      auto type = GenType(field.value.type);
      std::string check_if_vector =
          (IsVector(field.value.type) ||
           IsArray(field.value.type))
              ? "VectorOf("
              : "(";
      std::string body = "add" + check_if_vector + name + ": ";
      switch (field.value.type.base_type) {
        case BASE_TYPE_ARRAY: FLATBUFFERS_FALLTHROUGH();
        case BASE_TYPE_VECTOR: {
          GenerateVectorObjectAPITableExtension(field, name, type);
          unpack_body.push_back("{{STRUCTNAME}}." + body + "__" + name +
                                builder);
          break;
        }
        case BASE_TYPE_UNION: {
          code_ += "let __" + name + " = obj." + name +
                   "?.pack(builder: &builder) ?? Offset()";
          unpack_body.push_back("if let o = obj." + name + "?.type {");
          unpack_body.push_back("  {{STRUCTNAME}}.add(" + name + "Type: o" +
                                builder);
          unpack_body.push_back("  {{STRUCTNAME}}." + body + "__" + name +
                                builder);
          unpack_body.push_back("}\n");
          break;
        }
        case BASE_TYPE_STRUCT: {
          if (field.value.type.struct_def &&
              field.value.type.struct_def->fixed) {
            // This is a Struct (IsStruct), not a table. We create
            // UnsafeMutableRawPointer in this case.
            std::string code;
            GenerateStructArgs(*field.value.type.struct_def, &code, "", "",
                               "$0", true);
            code = code.substr(0, code.size() - 2);
            unpack_body.push_back(
                "{{STRUCTNAME}}." + body + "obj." + name + ".map { " +
                NameWrappedInNameSpace(*field.value.type.struct_def) +
                ".create" + Name(*field.value.type.struct_def) +
                "(builder: &builder, " + code + ") }" + builder);
          } else {
            code_ += "let __" + name + " = " + type +
                     ".pack(&builder, obj: &obj." + name + ")";
            unpack_body.push_back("{{STRUCTNAME}}." + body + "__" + name +
                                  builder);
          }
          break;
        }
        case BASE_TYPE_STRING: {
          unpack_body.push_back("{{STRUCTNAME}}." + body + "__" + name +
                                builder);
          if (field.required) {
            code_ +=
                "let __" + name + " = builder.create(string: obj." + name + ")";
          } else {
            BuildingOptionalObjects(name, "String",
                                    "builder.create(string: s)");
          }
          break;
        }
        case BASE_TYPE_UTYPE: break;
        default:
          unpack_body.push_back("{{STRUCTNAME}}." + body + "obj." + name +
                                builder);
      }
    }
    code_ += "let __root = {{STRUCTNAME}}.start{{SHORT_STRUCTNAME}}(&builder)";
    for (auto it = unpack_body.begin(); it < unpack_body.end(); it++)
      code_ += *it;
    code_ +=
        "return {{STRUCTNAME}}.end{{SHORT_STRUCTNAME}}(&builder, start: "
        "__root)";
    Outdent();
    code_ += "}";
  }

  void GenerateVectorObjectAPITableExtension(const FieldDef &field,
                                             const std::string &name,
                                             const std::string &type) {
    auto vectortype = field.value.type.VectorType();
    switch (vectortype.base_type) {
      case BASE_TYPE_UNION: {
        code_ += "var __" + name + "__: [Offset<UOffset>] = []";
        code_ += "for i in obj." + name + " {";
        Indent();
        code_ += "guard let off = i?.pack(builder: &builder) else { continue }";
        code_ += "__" + name + "__.append(off)";
        Outdent();
        code_ += "}";
        code_ += "let __" + name + " = builder.createVector(ofOffsets: __" +
                 name + "__)";
        code_ += "let __" + name + "Type = builder.createVector(obj." + name +
                 ".compactMap { $0?.type })";
        break;
      }
      case BASE_TYPE_UTYPE: break;
      case BASE_TYPE_STRUCT: {
        if (field.value.type.struct_def &&
            !field.value.type.struct_def->fixed) {
          code_ += "var __" + name + "__: [Offset<UOffset>] = []";
          code_ += "for var i in obj." + name + " {";
          Indent();
          code_ +=
              "__" + name + "__.append(" + type + ".pack(&builder, obj: &i))";
          Outdent();
          code_ += "}";
          code_ += "let __" + name + " = builder.createVector(ofOffsets: __" +
                   name + "__)";
        } else {
          code_ += "{{STRUCTNAME}}.startVectorOf" + MakeCamel(name, true) +
                   "(obj." + name + ".count, in: &builder)";
          std::string code;
          GenerateStructArgs(*field.value.type.struct_def, &code, "", "", "_o",
                             true);
          code = code.substr(0, code.size() - 2);
          code_ += "for i in obj." + name + " {";
          Indent();
          code_ += "guard let _o = i else { continue }";
          code_ += NameWrappedInNameSpace(*field.value.type.struct_def) +
                   ".create" + Name(*field.value.type.struct_def) +
                   "(builder: &builder, " + code + ")";
          Outdent();
          code_ += "}";
          code_ += "let __" + name +
                   " = builder.endVectorOfStructs(count: obj." + name +
                   ".count)";
        }
        break;
      }
      case BASE_TYPE_STRING: {
        code_ += "let __" + name + " = builder.createVector(ofStrings: obj." +
                 name + ".compactMap({ $0 }) )";
        break;
      }
      default: {
        code_ += "let __" + name + " = builder.createVector(obj." + name + ")";
        break;
      }
    }
  }

  void BuildingOptionalObjects(const std::string &name,
                               const std::string &object_type,
                               const std::string &body_front) {
    code_ += "let __" + name + ": Offset<" + object_type + ">";
    code_ += "if let s = obj." + name + " {";
    Indent();
    code_ += "__" + name + " = " + body_front;
    Outdent();
    code_ += "} else {";
    Indent();
    code_ += "__" + name + " = Offset<" + object_type + ">()";
    Outdent();
    code_ += "}";
    code_ += "";
  }

  void BuildObjectAPIConstructor(const std::vector<std::string> &body,
                                 const std::string &header = "") {
    code_.SetValue("HEADER", header);
    code_ += "{{ACCESS_TYPE}} init({{HEADER}}) {";
    Indent();
    for (auto it = body.begin(); it < body.end(); ++it) code_ += *it;
    Outdent();
    code_ += "}\n";
  }

  void BuildObjectAPIConstructorBody(
      const FieldDef &field, bool is_fixed,
      std::vector<std::string> &buffer_constructor,
      std::vector<std::string> &base_constructor) {
    auto name = Name(field);
    auto type = GenType(field.value.type);
    code_.SetValue("VALUENAME", name);
    code_.SetValue("VALUETYPE", type);
    std::string is_required = field.required ? "" : "?";

    switch (field.value.type.base_type) {
      case BASE_TYPE_STRUCT: {
        type = GenType(field.value.type, true);
        code_.SetValue("VALUETYPE", type);
        buffer_constructor.push_back("var __" + name + " = _t." + name);
        auto optional =
            (field.value.type.struct_def && field.value.type.struct_def->fixed);
        std::string question_mark =
            (field.required || (optional && is_fixed) ? "" : "?");

        code_ +=
            "{{ACCESS_TYPE}} var {{VALUENAME}}: {{VALUETYPE}}" + question_mark;
        buffer_constructor.push_back("" + name + " = __" + name +
                                     (field.required ? "!" : question_mark) +
                                     ".unpack()");
        base_constructor.push_back("" + name + " = " + type + "()");
        break;
      }
      case BASE_TYPE_ARRAY: FLATBUFFERS_FALLTHROUGH();
      case BASE_TYPE_VECTOR: {
        BuildObjectAPIConstructorBodyVectors(field, name, buffer_constructor,
                                             base_constructor, "    ");
        break;
      }
      case BASE_TYPE_STRING: {
        code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}: String" + is_required;
        buffer_constructor.push_back(name + " = _t." + name);
        if (field.required) base_constructor.push_back(name + " = \"\"");
        break;
      }
      case BASE_TYPE_UTYPE: break;
      case BASE_TYPE_UNION: {
        BuildUnionEnumSwitchCase(*field.value.type.enum_def, name,
                                 buffer_constructor);
        break;
      }
      default: {
        buffer_constructor.push_back(name + " = _t." + name);
        std::string nullable = field.optional ? "?" : "";
        if (IsScalar(field.value.type.base_type) &&
            !IsBool(field.value.type.base_type) && !IsEnum(field.value.type)) {
          code_ +=
              "{{ACCESS_TYPE}} var {{VALUENAME}}: {{VALUETYPE}}" + nullable;
          if (!field.optional)
            base_constructor.push_back(name + " = " + field.value.constant);
          break;
        }

        if (IsEnum(field.value.type)) {
          auto default_value = IsEnum(field.value.type)
                                   ? GenEnumDefaultValue(field)
                                   : field.value.constant;
          code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}: {{VALUETYPE}}";
          base_constructor.push_back(name + " = " + default_value);
          break;
        }

        if (IsBool(field.value.type.base_type)) {
          code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}: Bool" + nullable;
          std::string default_value =
              "0" == field.value.constant ? "false" : "true";
          if (!field.optional)
            base_constructor.push_back(name + " = " + default_value);
        }
      }
    }
  }

  void BuildObjectAPIConstructorBodyVectors(
      const FieldDef &field, const std::string &name,
      std::vector<std::string> &buffer_constructor,
      std::vector<std::string> &base_constructor,
      const std::string &indentation) {
    auto vectortype = field.value.type.VectorType();

    if (vectortype.base_type != BASE_TYPE_UTYPE) {
      buffer_constructor.push_back(name + " = []");
      buffer_constructor.push_back("for index in 0..<_t." + name + "Count {");
      base_constructor.push_back(name + " = []");
    }

    switch (vectortype.base_type) {
      case BASE_TYPE_STRUCT: {
        code_.SetValue("VALUETYPE", GenType(vectortype, true));
        code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}: [{{VALUETYPE}}?]";
        buffer_constructor.push_back(indentation + "var __v_ = _t." + name +
                                     "(at: index)");
        buffer_constructor.push_back(indentation + name +
                                     ".append(__v_?.unpack())");
        break;
      }
      case BASE_TYPE_ARRAY: FLATBUFFERS_FALLTHROUGH();
      case BASE_TYPE_VECTOR: {
        break;
      }
      case BASE_TYPE_UNION: {
        BuildUnionEnumSwitchCase(*field.value.type.enum_def, name,
                                 buffer_constructor, indentation, true);
        break;
      }
      case BASE_TYPE_UTYPE: break;
      default: {
        code_.SetValue("VALUETYPE", (IsString(vectortype)
                                         ? "String?"
                                         : GenType(vectortype)));
        code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}: [{{VALUETYPE}}]";

        if (IsEnum(vectortype) && vectortype.base_type != BASE_TYPE_UNION) {
          auto default_value = IsEnum(field.value.type)
                                   ? GenEnumDefaultValue(field)
                                   : field.value.constant;
          buffer_constructor.push_back(indentation + name + ".append(_t." +
                                       name + "(at: index)!)");
          break;
        }
        buffer_constructor.push_back(indentation + name + ".append(_t." + name +
                                     "(at: index))");
        break;
      }
    }
    if (vectortype.base_type != BASE_TYPE_UTYPE)
      buffer_constructor.push_back("}");
  }

  void BuildUnionEnumSwitchCaseWritter(const EnumDef &ev) {
    auto field_name = Name(ev);
    code_.SetValue("VALUETYPE", field_name);
    code_ += "switch type {";
    for (auto it = ev.Vals().begin(); it < ev.Vals().end(); ++it) {
      auto field = **it;
      auto ev_name = Name(field);
      auto type = GenType(field.union_type);

      if (field.union_type.base_type == BASE_TYPE_NONE ||
          IsString(field.union_type)) {
        continue;
      }
      code_ += "case ." + ev_name + ":";
      Indent();
      code_ += "var __obj = value as? " + GenType(field.union_type, true);
      code_ += "return " + type + ".pack(&builder, obj: &__obj)";
      Outdent();
    }
    code_ += "default: return Offset()";
    code_ += "}";
  }

  void BuildUnionEnumSwitchCase(const EnumDef &ev, const std::string &name,
                                std::vector<std::string> &buffer_constructor,
                                const std::string &indentation = "",
                                const bool is_vector = false) {
    auto field_name = NameWrappedInNameSpace(ev);
    code_.SetValue("VALUETYPE", field_name);
    code_ += "{{ACCESS_TYPE}} var {{VALUENAME}}: \\";
    code_ += is_vector ? "[{{VALUETYPE}}Union?]" : "{{VALUETYPE}}Union?";

    auto vector_reader = is_vector ? "(at: index" : "";
    buffer_constructor.push_back(indentation + "switch _t." + name + "Type" +
                                 vector_reader + (is_vector ? ")" : "") + " {");

    for (auto it = ev.Vals().begin(); it < ev.Vals().end(); ++it) {
      auto field = **it;
      auto ev_name = Name(field);
      if (field.union_type.base_type == BASE_TYPE_NONE ||
          IsString(field.union_type)) {
        continue;
      }
      buffer_constructor.push_back(indentation + "case ." + ev_name + ":");
      buffer_constructor.push_back(
          indentation + "    var _v = _t." + name + (is_vector ? "" : "(") +
          vector_reader + (is_vector ? ", " : "") +
          "type: " + GenType(field.union_type) + ".self)");
      auto constructor =
          field_name + "Union(_v?.unpack(), type: ." + ev_name + ")";
      buffer_constructor.push_back(
          indentation + "    " + name +
          (is_vector ? ".append(" + constructor + ")" : " = " + constructor));
    }
    buffer_constructor.push_back(indentation + "default: break");
    buffer_constructor.push_back(indentation + "}");
  }

  void AddMinOrMaxEnumValue(const std::string &str, const std::string &type) {
    auto current_value = str;
    code_.SetValue(type, current_value);
    code_ += "{{ACCESS_TYPE}} static var " + type +
             ": {{ENUM_NAME}} { return .{{" + type + "}} }";
  }

  void GenLookup(const FieldDef &key_field) {
    code_.SetValue("OFFSET", NumToString(key_field.value.offset));
    std::string offset_reader =
        "Table.offset(Int32(fbb.capacity) - tableOffset, vOffset: {{OFFSET}}, "
        "fbb: fbb)";

    code_.SetValue("TYPE", GenType(key_field.value.type));
    code_ +=
        "fileprivate static func lookupByKey(vector: Int32, key: {{TYPE}}, "
        "fbb: "
        "ByteBuffer) -> {{VALUENAME}}? {";
    Indent();
    if (IsString(key_field.value.type))
      code_ += "let key = key.utf8.map { $0 }";
    code_ += "var span = fbb.read(def: Int32.self, position: Int(vector - 4))";
    code_ += "var start: Int32 = 0";
    code_ += "while span != 0 {";
    Indent();
    code_ += "var middle = span / 2";
    code_ +=
        "let tableOffset = Table.indirect(vector + 4 * (start + middle), fbb)";
    if (IsString(key_field.value.type)) {
      code_ += "let comp = Table.compare(" + offset_reader + ", key, fbb: fbb)";
    } else {
      code_ += "let comp = fbb.read(def: {{TYPE}}.self, position: Int(" +
               offset_reader + "))";
    }

    code_ += "if comp > 0 {";
    Indent();
    code_ += "span = middle";
    Outdent();
    code_ += "} else if comp < 0 {";
    Indent();
    code_ += "middle += 1";
    code_ += "start += middle";
    code_ += "span -= middle";
    Outdent();
    code_ += "} else {";
    Indent();
    code_ += "return {{VALUENAME}}(fbb, o: tableOffset)";
    Outdent();
    code_ += "}";
    Outdent();
    code_ += "}";
    code_ += "return nil";
    Outdent();
    code_ += "}";
  }

  void GenComment(const std::vector<std::string> &dc) {
    if (dc.begin() == dc.end()) {
      // Don't output empty comment blocks with 0 lines of comment content.
      return;
    }
    for (auto it = dc.begin(); it != dc.end(); ++it) { code_ += "/// " + *it; }
  }

  std::string GenOffset() {
    return "let o = {{ACCESS}}.offset({{TABLEOFFSET}}.{{OFFSET}}.v); ";
  }

  std::string GenReaderMainBody(const std::string &optional = "") {
    return "{{ACCESS_TYPE}} var {{VALUENAME}}: {{VALUETYPE}}" + optional +
           " { ";
  }

  std::string GenReader(const std::string &type,
                        const std::string &at = "{{OFFSET}}") {
    return "{{ACCESS}}.readBuffer(of: {{" + type + "}}.self, at: " + at + ")";
  }

  std::string GenConstructor(const std::string &offset) {
    return "{{VALUETYPE}}({{ACCESS}}.bb, o: " + offset + ") }";
  }

  std::string GenMutate(const std::string &offset,
                        const std::string &get_offset, bool isRaw = false) {
    return "@discardableResult {{ACCESS_TYPE}} func mutate({{VALUENAME}}: "
           "{{VALUETYPE}}) -> Bool {" +
           get_offset + " return {{ACCESS}}.mutate({{VALUENAME}}" +
           (isRaw ? ".rawValue" : "") + ", index: " + offset + ") }";
  }

  std::string GenMutateArray() {
    return "{{ACCESS_TYPE}} func mutate({{VALUENAME}}: {{VALUETYPE}}, at "
           "index: "
           "Int32) -> Bool { " +
           GenOffset() +
           "return {{ACCESS}}.directMutate({{VALUENAME}}, index: "
           "{{ACCESS}}.vector(at: o) + index * {{SIZE}}) }";
  }

  std::string GenEnumDefaultValue(const FieldDef &field) {
    auto &value = field.value;
    FLATBUFFERS_ASSERT(value.type.enum_def);
    auto &enum_def = *value.type.enum_def;
    auto enum_val = enum_def.FindByValue(value.constant);
    std::string name;
    if (enum_val) {
      name = Name(*enum_val);
    } else {
      const auto &ev = **enum_def.Vals().begin();
      name = Name(ev);
    }
    std::transform(name.begin(), name.end(), name.begin(), CharToLower);
    return "." + name;
  }

  std::string GenEnumConstructor(const std::string &at) {
    return "{{VALUETYPE}}(rawValue: " + GenReader("BASEVALUE", at) + ") ";
  }

  std::string ValidateFunc() {
    return "static func validateVersion() { FlatBuffersVersion_1_12_0() }";
  }

  std::string GenType(const Type &type,
                      const bool should_consider_suffix = false) const {
    return IsScalar(type.base_type)
               ? GenTypeBasic(type)
               : (IsArray(type) ? GenType(type.VectorType())
                                : GenTypePointer(type, should_consider_suffix));
  }

  std::string GenTypePointer(const Type &type,
                             const bool should_consider_suffix) const {
    switch (type.base_type) {
      case BASE_TYPE_STRING: return "String";
      case BASE_TYPE_VECTOR: return GenType(type.VectorType());
      case BASE_TYPE_STRUCT: {
        auto &struct_ = *type.struct_def;
        if (should_consider_suffix) {
          return WrapInNameSpace(struct_.defined_namespace,
                                 ObjectAPIName(Name(struct_)));
        }
        return WrapInNameSpace(struct_.defined_namespace, Name(struct_));
      }
      case BASE_TYPE_UNION:
      default: return "FlatBufferObject";
    }
  }

  std::string GenTypeBasic(const Type &type) const {
    return GenTypeBasic(type, true);
  }

  std::string ObjectAPIName(const std::string &name) const {
    return parser_.opts.object_prefix + name + parser_.opts.object_suffix;
  }

  void Indent() { code_.IncrementIdentLevel(); }

  void Outdent() { code_.DecrementIdentLevel(); }

  std::string NameWrappedInNameSpace(const EnumDef &enum_def) const {
    return WrapInNameSpace(enum_def.defined_namespace, Name(enum_def));
  }

  std::string NameWrappedInNameSpace(const StructDef &struct_def) const {
    return WrapInNameSpace(struct_def.defined_namespace, Name(struct_def));
  }

  std::string GenTypeBasic(const Type &type, bool can_override) const {
    // clang-format off
    static const char * const swift_type[] = {
      #define FLATBUFFERS_TD(ENUM, IDLTYPE, \
              CTYPE, JTYPE, GTYPE, NTYPE, PTYPE, RTYPE, KTYPE, STYPE) \
        #STYPE,
        FLATBUFFERS_GEN_TYPES(FLATBUFFERS_TD)
      #undef FLATBUFFERS_TD
    };
    // clang-format on
    if (can_override) {
      if (type.enum_def) return NameWrappedInNameSpace(*type.enum_def);
      if (type.base_type == BASE_TYPE_BOOL) return "Bool";
    }
    return swift_type[static_cast<int>(type.base_type)];
  }

  std::string EscapeKeyword(const std::string &name) const {
    return keywords_.find(name) == keywords_.end() ? name : name + "_";
  }

  std::string Name(const EnumVal &ev) const {
    auto name = ev.name;
    if (isupper(name.front())) {
      std::transform(name.begin(), name.end(), name.begin(), CharToLower);
    }
    return EscapeKeyword(MakeCamel(name, false));
  }

  std::string Name(const Definition &def) const {
    return EscapeKeyword(MakeCamel(def.name, false));
  }
};
}  // namespace swift
bool GenerateSwift(const Parser &parser, const std::string &path,
                   const std::string &file_name) {
  swift::SwiftGenerator generator(parser, path, file_name);
  return generator.generate();
}
}  // namespace flatbuffers
