void PGCatalog::FillPGClassTable()

in backend/query/pg_catalog.cc [815:1365]


void PGCatalog::FillPGClassTable() {
  auto pg_class = tables_by_name_.at(kPGClass).get();
  std::vector<std::vector<zetasql::Value>> rows;
  // Add tables.
  for (const Table* table : default_schema_->tables()) {
    const auto& [table_schema_part, table_name_part] =
        GetSchemaAndNameForPGCatalog(table->Name());
    int namespace_oid = 0;
    if (kHardCodedNamedSchemaOid.contains(table_schema_part)) {
      namespace_oid = kHardCodedNamedSchemaOid.at(table_schema_part);
    } else {
      const NamedSchema* named_schema =
          default_schema_->FindNamedSchema(table_schema_part);
      if (!named_schema->postgresql_oid().has_value()) {
        ZETASQL_VLOG(1) << "Named schema " << table_schema_part
                << " does not have a PostgreSQL OID.";
        continue;
      }
      namespace_oid = named_schema->postgresql_oid().value();
    }
    if (!table->postgresql_oid().has_value()) {
      ZETASQL_VLOG(1) << "Table " << table->Name()
              << " does not have a PostgreSQL OID.";
      continue;
    }
    if (!table->primary_key_index_postgresql_oid().has_value()) {
      ZETASQL_VLOG(1) << "PK for " << table->Name()
              << " does not have a PostgreSQL OID.";
      continue;
    }
    rows.push_back({
        // oid
        CreatePgOidValue(table->postgresql_oid().value()).value(),
        // relname
        String(table_name_part),
        // relnamespace
        CreatePgOidValue(namespace_oid).value(),
        // reltype
        NullPgOid(),
        // reloftype
        NullPgOid(),
        // relowner
        NullPgOid(),
        // relam
        CreatePgOidValue(75001).value(),
        // relfilenode
        NullPgOid(),
        // reltablespace
        NullPgOid(),
        // relpages
        NullInt64(),
        // reltuples
        NullDouble(),
        // relallvisible
        NullInt64(),
        // reltoastrelid
        NullPgOid(),
        // relhasindex
        Bool(!table->indexes().empty()),
        // relisshared
        NullBool(),
        // relpersistence
        String("p"),
        // relkind
        String("r"),
        // relnatts
        Int64(table->columns().size()),
        // relchecks
        Int64(table->check_constraints().size()),
        // relhasrules
        NullBool(),
        // relhastriggers
        NullBool(),
        // relhassubclass
        NullBool(),
        // relrowsecurity
        NullBool(),
        // relforcerowsecurity
        NullBool(),
        // relispopulated
        Bool(true),
        // relreplident
        NullString(),
        // relispartition
        NullBool(),
        // relrewrite
        NullPgOid(),
        // relfrozenxid
        NullInt64(),
        // relminmxid
        NullInt64(),
        // reloptions
        NullString(),
        // relpartbound
        NullString(),
    });

    // Add primary key.
    rows.push_back({
        // oid
        CreatePgOidValue(table->primary_key_index_postgresql_oid().value())
            .value(),
        // relname
        String(PrimaryKeyName(table)),
        // relnamespace
        CreatePgOidValue(namespace_oid).value(),
        // reltype
        NullPgOid(),
        // reloftype
        NullPgOid(),
        // relowner
        NullPgOid(),
        // relam
        CreatePgOidValue(75002).value(),
        // relfilenode
        NullPgOid(),
        // reltablespace
        NullPgOid(),
        // relpages
        NullInt64(),
        // reltuples
        NullDouble(),
        // relallvisible
        NullInt64(),
        // reltoastrelid
        NullPgOid(),
        // relhasindex
        Bool(false),
        // relisshared
        NullBool(),
        // relpersistence
        String("p"),
        // relkind
        String("i"),
        // relnatts
        Int64(table->primary_key().size()),
        // relchecks
        Int64(0),
        // relhasrules
        NullBool(),
        // relhastriggers
        NullBool(),
        // relhassubclass
        NullBool(),
        // relrowsecurity
        NullBool(),
        // relforcerowsecurity
        NullBool(),
        // relispopulated
        Bool(true),
        // relreplident
        NullString(),
        // relispartition
        NullBool(),
        // relrewrite
        NullPgOid(),
        // relfrozenxid
        NullInt64(),
        // relminmxid
        NullInt64(),
        // reloptions
        NullString(),
        // relpartbound
        NullString(),
    });

    // Add indexes.
    for (const Index* index : table->indexes()) {
      const auto& [index_schema_part, index_name_part] =
          GetSchemaAndNameForPGCatalog(index->Name());
      if (!index->postgresql_oid().has_value()) {
        ZETASQL_VLOG(1) << "Index " << index->Name()
                << " does not have a PostgreSQL OID.";
        continue;
      }
      rows.push_back({
          // oid
          CreatePgOidValue(index->postgresql_oid().value()).value(),
          // relname
          String(index_name_part),
          // relnamespace
          CreatePgOidValue(namespace_oid).value(),
          // reltype
          NullPgOid(),
          // reloftype
          NullPgOid(),
          // relowner
          NullPgOid(),
          // relam
          CreatePgOidValue(75002).value(),
          // relfilenode
          NullPgOid(),
          // reltablespace
          NullPgOid(),
          // relpages
          NullInt64(),
          // reltuples
          NullDouble(),
          // relallvisible
          NullInt64(),
          // reltoastrelid
          NullPgOid(),
          // relhasindex
          Bool(false),
          // relisshared
          NullBool(),
          // relpersistence
          String("p"),
          // relkind
          String("i"),
          // relnatts
          Int64(index->key_columns().size() + index->stored_columns().size()),
          // relchecks
          Int64(0),
          // relhasrules
          NullBool(),
          // relhastriggers
          NullBool(),
          // relhassubclass
          NullBool(),
          // relrowsecurity
          NullBool(),
          // relforcerowsecurity
          NullBool(),
          // relispopulated
          Bool(true),
          // relreplident
          NullString(),
          // relispartition
          NullBool(),
          // relrewrite
          NullPgOid(),
          // relfrozenxid
          NullInt64(),
          // relminmxid
          NullInt64(),
          // reloptions
          NullString(),
          // relpartbound
          NullString(),
      });
    }
  }
  // Add sequences.
  for (const Sequence* sequence : default_schema_->sequences()) {
    if (sequence->is_internal_use()) {
      // Skip internal sequences.
      continue;
    }
    const auto& [sequence_schema_part, sequence_name_part] =
        GetSchemaAndNameForPGCatalog(sequence->Name());
    int namespace_oid = 0;
    if (kHardCodedNamedSchemaOid.contains(sequence_schema_part)) {
      namespace_oid = kHardCodedNamedSchemaOid.at(sequence_schema_part);
    } else {
      const NamedSchema* named_schema =
          default_schema_->FindNamedSchema(sequence_schema_part);
      if (!named_schema->postgresql_oid().has_value()) {
        ZETASQL_VLOG(1) << "Named schema " << sequence_schema_part
                << " does not have a PostgreSQL OID.";
        continue;
      }
      namespace_oid = named_schema->postgresql_oid().value();
    }
    if (!sequence->postgresql_oid().has_value()) {
      ZETASQL_VLOG(1) << "Sequence " << sequence->Name()
              << " does not have a PostgreSQL OID.";
      continue;
    }
    rows.push_back({
        // oid
        CreatePgOidValue(sequence->postgresql_oid().value()).value(),
        // relname
        String(sequence_name_part),
        // relnamespace
        CreatePgOidValue(namespace_oid).value(),
        // reltype
        NullPgOid(),
        // reloftype
        NullPgOid(),
        // relowner
        NullPgOid(),
        // relam
        CreatePgOidValue(0).value(),
        // relfilenode
        NullPgOid(),
        // reltablespace
        NullPgOid(),
        // relpages
        NullInt64(),
        // reltuples
        NullDouble(),
        // relallvisible
        NullInt64(),
        // reltoastrelid
        NullPgOid(),
        // relhasindex
        Bool(false),
        // relisshared
        NullBool(),
        // relpersistence
        String("p"),
        // relkind
        String("S"),
        // relnatts
        NullInt64(),
        // relchecks
        Int64(0),
        // relhasrules
        NullBool(),
        // relhastriggers
        NullBool(),
        // relhassubclass
        NullBool(),
        // relrowsecurity
        NullBool(),
        // relforcerowsecurity
        NullBool(),
        // relispopulated
        Bool(true),
        // relreplident
        NullString(),
        // relispartition
        NullBool(),
        // relrewrite
        NullPgOid(),
        // relfrozenxid
        NullInt64(),
        // relminmxid
        NullInt64(),
        // reloptions
        NullString(),
        // relpartbound
        NullString(),
    });
  }
  // Add views.
  for (const View* view : default_schema_->views()) {
    const auto& [view_schema_part, view_name_part] =
        GetSchemaAndNameForPGCatalog(view->Name());
    int namespace_oid = 0;
    if (kHardCodedNamedSchemaOid.contains(view_schema_part)) {
      namespace_oid = kHardCodedNamedSchemaOid.at(view_schema_part);
    } else {
      const NamedSchema* named_schema =
          default_schema_->FindNamedSchema(view_schema_part);
      if (!named_schema->postgresql_oid().has_value()) {
        ZETASQL_VLOG(1) << "Named schema " << view_schema_part
                << " does not have a PostgreSQL OID.";
        continue;
      }
      namespace_oid = named_schema->postgresql_oid().value();
    }
    if (!view->postgresql_oid().has_value()) {
      ZETASQL_VLOG(1) << "View " << view->Name() << " does not have a PostgreSQL OID.";
      continue;
    }
    rows.push_back({
        // oid
        CreatePgOidValue(view->postgresql_oid().value()).value(),
        // relname
        String(view_name_part),
        // relnamespace
        CreatePgOidValue(namespace_oid).value(),
        // reltype
        NullPgOid(),
        // reloftype
        NullPgOid(),
        // relowner
        NullPgOid(),
        // relam
        CreatePgOidValue(0).value(),
        // relfilenode
        NullPgOid(),
        // reltablespace
        NullPgOid(),
        // relpages
        NullInt64(),
        // reltuples
        NullDouble(),
        // relallvisible
        NullInt64(),
        // reltoastrelid
        NullPgOid(),
        // relhasindex
        Bool(false),
        // relisshared
        NullBool(),
        // relpersistence
        String("p"),
        // relkind
        String("v"),
        // relnatts
        Int64(view->columns().size()),
        // relchecks
        Int64(0),
        // relhasrules
        NullBool(),
        // relhastriggers
        NullBool(),
        // relhassubclass
        NullBool(),
        // relrowsecurity
        NullBool(),
        // relforcerowsecurity
        NullBool(),
        // relispopulated
        Bool(true),
        // relreplident
        NullString(),
        // relispartition
        NullBool(),
        // relrewrite
        NullPgOid(),
        // relfrozenxid
        NullInt64(),
        // relminmxid
        NullInt64(),
        // reloptions
        NullString(),
        // relpartbound
        NullString(),
    });
  }

  std::vector<PgClassSystemTableMetadata> system_tables_metadata;
  for (const auto& [table_name, metadata] :
       info_schema_table_name_to_column_metadata_) {
    auto full_table_name = absl::StrCat("information_schema.", table_name);
    if (!kHardCodedSystemViewOid.contains(full_table_name)) {
      ZETASQL_VLOG(1) << "Missing oid for " << full_table_name;
      continue;
    }
    int table_oid = kHardCodedSystemViewOid.at(full_table_name);
    int namespace_oid = kHardCodedNamedSchemaOid.at("information_schema");
    system_tables_metadata.push_back(PgClassSystemTableMetadata{
        table_name, table_oid, namespace_oid,
        /*column_count=*/static_cast<int>(metadata.size()), /*is_view=*/true});
  }
  for (const auto& [table_name, metadata] :
       pg_catalog_table_name_to_column_metadata_) {
    int table_oid = 0;
    bool is_view;
    auto full_table_name = absl::StrCat("pg_catalog.", table_name);
    if (kHardCodedSystemViewOid.contains(full_table_name)) {
      table_oid = kHardCodedSystemViewOid.at(full_table_name);
      is_view = true;
    } else if (kHardCodedPgCatalogTableOid.contains(full_table_name)) {
      table_oid = kHardCodedPgCatalogTableOid.at(full_table_name);
      is_view = false;
    } else {
      continue;
    }
    int namespace_oid = kHardCodedNamedSchemaOid.at("pg_catalog");
    system_tables_metadata.push_back(PgClassSystemTableMetadata{
        table_name, table_oid, namespace_oid,
        /*column_count=*/static_cast<int>(metadata.size()), is_view});
  }
  for (const auto& [uppercase_table_name, metadata] :
       spanner_sys_table_name_to_column_metadata_) {
    auto table_name = absl::AsciiStrToLower(uppercase_table_name);
    auto full_table_name = absl::StrCat("spanner_sys.", table_name);
    if (!kHardCodedSystemViewOid.contains(full_table_name)) {
      ZETASQL_VLOG(1) << "Missing oid for " << full_table_name;
      continue;
    }
    int table_oid = kHardCodedSystemViewOid.at(full_table_name);
    int namespace_oid = kHardCodedNamedSchemaOid.at("spanner_sys");
    int column_count = 0;
    for (const auto& column_metadata : metadata) {
      if (absl::StrContains(column_metadata.spanner_type, "STRUCT")) {
        // STRUCT columns are not supported in PG.
        continue;
      }
      ++column_count;
    }
    system_tables_metadata.push_back(PgClassSystemTableMetadata{
        table_name, table_oid, namespace_oid, column_count, /*is_view=*/true});
  }

  for (const auto& metadata : system_tables_metadata) {
    rows.push_back({
        // oid
        CreatePgOidValue(metadata.table_oid).value(),
        // relname
        String(metadata.table_name),
        // relnamespace
        CreatePgOidValue(metadata.namespace_oid).value(),
        // reltype
        NullPgOid(),
        // reloftype
        NullPgOid(),
        // relowner
        NullPgOid(),
        // relam
        CreatePgOidValue(metadata.is_view ? 0 : 75001).value(),
        // relfilenode
        NullPgOid(),
        // reltablespace
        NullPgOid(),
        // relpages
        NullInt64(),
        // reltuples
        NullDouble(),
        // relallvisible
        NullInt64(),
        // reltoastrelid
        NullPgOid(),
        // relhasindex
        Bool(false),
        // relisshared
        NullBool(),
        // relpersistence
        String("p"),
        // relkind
        String(metadata.is_view ? "v" : "r"),
        // relnatts
        Int64(metadata.column_count),
        // relchecks
        Int64(0),
        // relhasrules
        NullBool(),
        // relhastriggers
        NullBool(),
        // relhassubclass
        NullBool(),
        // relrowsecurity
        NullBool(),
        // relforcerowsecurity
        NullBool(),
        // relispopulated
        Bool(true),
        // relreplident
        NullString(),
        // relispartition
        NullBool(),
        // relrewrite
        NullPgOid(),
        // relfrozenxid
        NullInt64(),
        // relminmxid
        NullInt64(),
        // reloptions
        NullString(),
        // relpartbound
        NullString(),
    });
  }

  pg_class->SetContents(rows);
}