Skip to content

Conversation

@shachibista
Copy link
Contributor

@shachibista shachibista commented Jan 9, 2026

Summary

Adds support for User Defined Functions.

Checklist

Delete items not relevant to your PR:

  • Unit and integration tests covering the common scenarios were added
  • A human-readable description of the changes was provided to include in CHANGELOG
  • For significant changes, documentation in https://github.com/ClickHouse/clickhouse-docs was updated with further explanations or tutorials

Note

Adds first-class support for dbt User Defined Functions and aligns the adapter with dbt-core 1.11.

  • Introduces Function relation type in dbt/adapters/clickhouse/relation.py
  • New scalar function materialization macros: include/clickhouse/macros/materializations/functions/scalar.sql (create/replace signature and body)
  • Integration test for UDF creation/execution: tests/integration/adapter/udf/test_udf.py
  • Version bump to 1.11.0 and dependency updates: dbt-core>=1.11.0, dbt-adapters>=1.17.0; setup.py dbt_minor_version="1.11"
  • CHANGELOG updated to note UDF support

Written by Cursor Bugbot for commit 2a75b23. This will update automatically on new commits. Configure here.

@koletzilla
Copy link
Contributor

Related to #590

@koletzilla
Copy link
Contributor

Hi @shachibista! Thanks for the contribution. This is a really interesting functionality and I just started checking the implementation details, so I still don't have a full picture of the work needed. I'm sorry I can't give complete feedback yet, but I wanted to ask a few questions to get your opinion:

  • Can you walk through all the changes you needed to make to the materialization function macro? It looks like we should be able to use practically the same implementation as the default in dbt. Why did you need to apply these changes?
  • Were you able to later call this function from a model? I'm getting different errors when I try to use it. Can you add a test to assert that the function can be called from a model?
  • It looks like we may need to update dbt-adapters to the latest version to be able to use UDFs, but you didn't do it. Is there a reason not to do it?
  • dbt usually releases tests in the dbt-tests-adapter package that we can call from this adapter like this: https://github.com/dbt-labs/dbt-adapters/tree/main/dbt-tests-adapter/src/dbt/tests/adapter/functions. Have you checked if we can reuse these tests?

@shachibista
Copy link
Contributor Author

shachibista commented Jan 14, 2026

It looks like we may need to update dbt-adapters to the latest version to be able to use UDFs, but you didn't do it. Is there a reason not to do it?

Ah yes, I missed that.

Can you walk through all the changes you needed to make to the materialization function macro? It looks like we should be able to use practically the same implementation as the default in dbt. Why did you need to apply these changes?

You are correct, I tried to use the default implementation but did not realise that dbt-adapters needed to be updated too. Should be unnecessary after update.

dbt usually releases tests in the dbt-tests-adapter package that we can call from this adapter like this: https://github.com/dbt-labs/dbt-adapters/tree/main/dbt-tests-adapter/src/dbt/tests/adapter/functions. Have you checked if we can reuse these tests?

Unfortunately we cannot use them because ClickHouse functions expect an expression:

CREATE [OR REPLACE] FUNCTION name [ON CLUSTER cluster] AS (parameter0, ...) -> expression

However the tests defined in the adapters repo expect the function body to be a SELECT statement.

Were you able to later call this function from a model? I'm getting different errors when I try to use it. Can you add a test to assert that the function can be called from a model?

What errors are you getting? I did not try to run it from a model but I currently get the following when trying to run from a model.

 'SourceQuotingBaseConfig' object has no attribute 'credentials'

I am not sure what the reason is.

{% endmacro %}

{% macro clickhouse__scalar_function_create_replace_signature_sql(target_relation) %}
CREATE OR REPLACE FUNCTION {{ target_relation.include(database=false, schema=false) }} {{ on_cluster_clause(this) }} AS ({{ clickhouse__formatted_scalar_function_args_sql() }}) ->
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Inconsistent relation used for cluster clause

Medium Severity

The clickhouse__scalar_function_create_replace_signature_sql macro receives target_relation as a parameter and uses it for the function name, but then uses the global this variable for on_cluster_clause(this). This is inconsistent with the established pattern throughout the codebase where the same relation is used for both the identifier and the cluster clause. If target_relation and this ever differ, the ON CLUSTER clause may be generated incorrectly or omitted unexpectedly.

Fix in Cursor Fix in Web

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants