in backend/actions/manager.cc [114:225]
void ActionRegistry::BuildActionRegistry() {
for (const Table* table : schema_->tables()) {
// Column value checks for all tables.
absl::flat_hash_set<std::string> placements;
for (const Placement* placement : schema_->placements()) {
placements.insert(placement->PlacementName());
}
table_validators_[table].emplace_back(
std::make_unique<ColumnValueValidator>(placements));
// Row existence checks for all tables.
table_validators_[table].emplace_back(
std::make_unique<RowExistenceValidator>());
// Interleave actions for child tables.
for (const Table* child : table->children()) {
table_validators_[table].emplace_back(
std::make_unique<InterleaveParentValidator>(table, child));
table_effectors_[table].emplace_back(
std::make_unique<InterleaveParentEffector>(table, child));
}
// Interleave actions for parent table.
if (table->parent() != nullptr) {
table_validators_[table].emplace_back(
std::make_unique<InterleaveChildValidator>(table->parent(), table));
}
// Actions for Index.
for (const Index* index : table->indexes()) {
// Index effects.
if (index->is_search_index()) {
continue;
}
table_effectors_[table].emplace_back(
std::make_unique<IndexEffector>(index));
// Index uniqueness checks.
if (index->is_unique()) {
table_verifiers_[index->index_data_table()].emplace_back(
std::make_unique<UniqueIndexVerifier>(index));
}
}
// Actions for foreign keys.
for (const ForeignKey* foreign_key : table->foreign_keys()) {
if (!foreign_key->enforced()) {
// Not enforced foreign keys doesn't verify referential integrity on
// data.
continue;
}
table_verifiers_[foreign_key->referencing_data_table()].emplace_back(
std::make_unique<ForeignKeyReferencingVerifier>(foreign_key));
}
for (const ForeignKey* foreign_key : table->referencing_foreign_keys()) {
if (!foreign_key->enforced()) {
// Not enforced foreign keys has no actions, and doesn't verify
// referential integrity on data.
continue;
}
table_verifiers_[foreign_key->referenced_data_table()].emplace_back(
std::make_unique<ForeignKeyReferencedVerifier>(foreign_key));
if (foreign_key->on_delete_action() == ForeignKey::Action::kCascade) {
table_effectors_[table].emplace_back(
std::make_unique<ForeignKeyActionEffector>(foreign_key));
}
}
// Actions for check constraints.
for (const CheckConstraint* check_constraint : table->check_constraints()) {
table_verifiers_[table].emplace_back(
std::make_unique<CheckConstraintVerifier>(
check_constraint,
MakeGoogleSqlAnalyzerOptions(schema_->default_time_zone()),
&catalog_));
}
// A set containing key columns with default/generated values.
absl::flat_hash_set<std::string> default_or_generated_key_columns;
// Effector for primary key default and generated columns.
for (const Column* column : table->columns()) {
if ((column->has_default_value()
|| column->is_generated()
) &&
table->FindKeyColumn(column->Name()) != nullptr) {
default_or_generated_key_columns.insert(column->Name());
table_generated_key_effectors_[table->Name()] =
std::make_unique<GeneratedColumnEffector>(
table,
MakeGoogleSqlAnalyzerOptions(schema_->default_time_zone()),
&catalog_,
/*for_keys=*/true);
break;
}
}
// Effector for non-key generated and default columns.
for (const Column* column : table->columns()) {
if (!default_or_generated_key_columns.contains(column->Name()) &&
(column->is_generated() || column->has_default_value())) {
table_effectors_[table].emplace_back(
std::make_unique<GeneratedColumnEffector>(
table,
MakeGoogleSqlAnalyzerOptions(schema_->default_time_zone()),
&catalog_));
break;
}
}
}
}