dremio dbt 集成nessie分支扩展说明
dremio dbt 的集成我以前简单说过玩法,同时与nessie 的集成也有说明过(主要是关于配置以及简单使用的)
以下我说明下nessie 分支特性集成的一些可能玩法
nessie 分支简单说明
nessie 基于元数据的分支特性可以很好的辅助我们进行数据模型的开发,而且不需要多份数据,可以使用类似git 的模式进行
数据开发(branch,merge,commit,tag)可以极大的提示我们数据开发的信心(提供稳健的数据模型)
dbt-dremio 目前提供的能力
dbt-dremio 实际上属于一个标准的dbt adapter 扩展,对于nessie 这类支持类似git 模式进行数据开发的缺少比较好的支持,主要原因还是
nessie sql 查询的特殊性,里边可以包含branch,commit ,tag 等查询标识
解决方法
- 自定义变量
我们可以基于变量控制我们查询的模型使用那个branch 或者tag 的数据,可以通过var 进行处理,当让env 也是一种选择 - 自定义macro
这个属于一个比较标准的做法,可以通过自定义relation 实现处理,主要是基于api.Relation.create ,创建自定义的relation 这样dbt 就可以识别了
参考
{%- macro refv1(schema,table,branch ) -%}
{% if schema %}
{%- set relation = api.Relation.create(schema=schema,identifier=table) -%}
{{return (relation ~ ' AT ' ~ 'branch ' ~ branch) }}
{% else %}
{{return (table ~ ' AT ' ~ 'branch ' ~ branch) }}
{% endif %}
{%- endmacro %}
- 自定义source 以及ref(对于buildin 的覆盖)
实际上也属于自定义macro,但是更加标准,更加符合dbt 的玩法,对于用户使用友好,可以还是以前的模式
参考定义ref
{% macro ref(model_name, v=None)%}
{%- set relation = builtins.ref(model_name, v=v) -%}
{{log('user my ref' ~ relation , info=True)}}
{% if execute %}
# 为了简单演示,结合了model config 进行数据获取,实际上graph 也是一个很不错的选择,注意execute 的使用,dbt 包含了编译以及执行会有不同的阶段,之后基于api.Relation.create 创建新的relation
{{log("my ref model " ~ model.config,info=True)}}
{% set my_source = model.config %}
{%- set relation2 = api.Relation.create(schema=my_source.schema, identifier=my_source.table) -%}
{{log('user my ref ' ~ relation2, info=True)}}
{% if my_source.branch %}
{{ return (relation2 ~ ' AT ' ~ ' branch ' ~ my_source.branch) }}
{% else %}
{{ return (relation2) }}
{% endif %}
{% endif %}
{{return (relation)}}
{% endmacro %}
参考使用
注意此时ref 里边的一个model name 实际上主要存在就行,属于一个占位符,核心是自定义ref 进行了替换以及branch 的附加
{{
config(
branch='prod',
schema = "dbtv4",
table = "dalongdemoapp"
)
}}
select * from {{ref("nessiev3")}}
参考自定义source
此处利用了graph source 以及config 能力,然后基于api.Relation.create 创建新的relation , 当然也可以与ref 的类似使用model 的config
{%- macro source(source_name, table_name) -%}
{%- set relation = builtins.source(source_name, table_name) -%}
{{log('user my source relation default' ~ relation, info=True)}}
{%- if execute -%}
{{log("my source model config " ~ model.config,info=True)}}
{%- set source = graph.sources.values() | selectattr("source_name", "equalto", source_name) | selectattr("name", "equalto", table_name) | list | first -%}
{{log("my source model " ~ tojson(source),info=True)}}
{% set my_source = source.config %}
{%- set relation2 = api.Relation.create(schema=my_source.schema, identifier=my_source.table) -%}
{{log('user my source relation2 ' ~ relation2, info=True)}}
{% if my_source.branch %}
{{ return (relation2 ~ ' AT ' ~ ' branch ' ~ my_source.branch) }}
{% else %}
{{ return (relation) }}
{% endif %}
{%- else -%}
{{ return (relation) }}
{%- endif -%}
{%- endmacro -%}
参考使用
source 定义
version: 2
sources:
- name: public # this is the source_name
database: pg
tables:
- name: sensor # this is the table_name
config:
branch: prod
table: dalongdemoapp
schema: dbtv4
- name: sensor_data_store
使用
{{
config(
branch='prod',
schema = "dbtv4",
table = "dalongdemoapp"
)
}}
select * from {{source("public","sensor")}}
- 自定义扩展dbt adapter 的relation 创建
这种方法就需要进行dbt dremio adapter 内部的处理了,并不是很建议,不利于后期的维护升级,基于dbt package 反而是一个很不错的方法
说明
以上只是简单的说明,包含了一些可选的集成nessie 分支特性的方法,从实际上来说还是推荐开发dbt package 进行维护同时利用好dbt 提供的一些方便的上下文数据,可以实现比较灵活的数据模型处理
参考资料
https://github.com/dremio/dbt-dremio/blob/main/dbt/include/dremio/macros/builtins/builtins.sql
https://www.cnblogs.com/rongfengliang/p/17958669
https://docs.getdbt.com/docs/build/sources
https://docs.getdbt.com/reference/dbt-classes
https://docs.getdbt.com/reference/dbt-jinja-functions/ref
https://docs.getdbt.com/reference/dbt-jinja-functions/graph
https://docs.getdbt.com/reference/dbt-jinja-functions/model
https://docs.getdbt.com/reference/dbt-jinja-functions/builtins
https://docs.getdbt.com/reference/dbt-jinja-functions/var