Repository: ClickHouse/ClickHouse
File: src/Databases/DDLDependencyVisitor.cpp (C++)

Code before:
            if (!as_table.table.empty())
            {
                /// AS table_name
                if (as_table.database.empty())
                    as_table.database = current_database;
                dependencies.emplace(as_table);
            }

            /// Visit nested select query only for views, for other cases it's not
            /// an actual dependency as it will be executed only once to fill the table.
            if (create.select)
            {
                if (create.isView())
                {
                    if (create.is_materialized_view)
                    {
                        auto select_copy = create.select->clone();
                        ApplyWithSubqueryVisitor(global_context).visit(select_copy);

                        /// Use the database where the materialized view is created to resolve nested views
                        ContextMutablePtr mv_db_context = Context::createCopy(global_context);
                        /// During bootstrap/restore scenarios, the database may not exist yet, so we provide a way to skip this validation
                        if (validate_current_database)
                            mv_db_context->setCurrentDatabase(table_name.database);
                        else
                            mv_db_context->setCurrentDatabaseUnchecked(table_name.database);
                        auto select_query = SelectQueryDescription::getSelectQueryFromASTForMatView(select_copy, create.refresh_strategy != nullptr /*refresheable*/, mv_db_context);
                        if (!select_query.select_table_id.empty())
                        {
                            mv_from_dependency = select_query.select_table_id;

                            /// Keepeing UUID is problematic
                            mv_from_dependency->uuid = UUIDHelpers::Nil;
                        }
                    }
                }
                else
                    skip_asts.insert(create.select);
            }

        }

        /// The definition of a dictionary: SOURCE(CLICKHOUSE(...)) LAYOUT(...) LIFETIME(...)
        void visitDictionaryDef(const ASTDictionary & dictionary)
        {
            if (!dictionary.source || dictionary.source->name != "clickhouse" || !dictionary.source->elements)
                return;

            auto config = getDictionaryConfigurationFromAST(create_query->as<ASTCreateQuery &>(), global_context);
            auto info = getInfoIfClickHouseDictionarySource(config, global_context);


Review comment (refactor):
This context creation and conditional database setting logic is duplicated from StorageMaterializedView.cpp. Consider centralizing this pattern into a shared helper function to maintain consistency and reduce duplication.

Code after:
            if (!as_table.table.empty())
            {
                /// AS table_name
                if (as_table.database.empty())
                    as_table.database = current_database;
                dependencies.emplace(as_table);
            }

            /// Visit nested select query only for views, for other cases it's not
            /// an actual dependency as it will be executed only once to fill the table.
            if (create.select)
            {
                if (create.isView())
                {
                    if (create.is_materialized_view)
                    {
                        auto select_copy = create.select->clone();
                        ApplyWithSubqueryVisitor(global_context).visit(select_copy);

                        /// Use the database where the materialized view is created to resolve nested views.
                        /// The database name can be empty when the AST has been mutated by SharedDatabaseCatalog::serializeCreateQuery
                        /// (which strips the database before serialization). In that case, keep the global context's current database.
                        ContextMutablePtr mv_db_context = Context::createCopy(global_context);
                        if (!table_name.database.empty())
                        {
                            /// During bootstrap/restore scenarios, the database may not exist yet, so we provide a way to skip this validation
                            if (validate_current_database)
                                mv_db_context->setCurrentDatabase(table_name.database);
                            else
                                mv_db_context->setCurrentDatabaseUnchecked(table_name.database);
                        }
                        auto select_query = SelectQueryDescription::getSelectQueryFromASTForMatView(select_copy, create.refresh_strategy != nullptr /*refresheable*/, mv_db_context);
                        if (!select_query.select_table_id.empty())
                        {
                            mv_from_dependency = select_query.select_table_id;

                            /// Keepeing UUID is problematic
                            mv_from_dependency->uuid = UUIDHelpers::Nil;
                        }
                    }
                }
                else
                    skip_asts.insert(create.select);
            }

        }

        /// The definition of a dictionary: SOURCE(CLICKHOUSE(...)) LAYOUT(...) LIFETIME(...)
        void visitDictionaryDef(const ASTDictionary & dictionary)
        {
            if (!dictionary.source || dictionary.source->name != "clickhouse" || !dictionary.source->elements)