Skip to content

Commit ef6c1db

Browse files
authored
compatibility with dbt 1.2.0rc1 (#24)
* reorganize Dockerfile and use docker in github CI * in dbt-core 1.2.x, commit is now being done in SQLAdapter.drop_schema(), so there's no need for it here anymore. see this PR: dbt-labs/dbt-core#5198 * rm file on disk on DROP SCHEMA * load text.so sqlean extension to get split_parts fn * add math.so for functions needed by datediff
1 parent 815af9e commit ef6c1db

File tree

22 files changed

+609
-67
lines changed

22 files changed

+609
-67
lines changed

.dockerignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
*.log

.github/workflows/ci.yml

Lines changed: 7 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -5,27 +5,15 @@ on: [push]
55

66
jobs:
77
build:
8-
9-
runs-on: ubuntu-latest
108
strategy:
119
matrix:
12-
python-version: ["3.7", "3.8", "3.9"]
10+
python_version: ["3.8", "3.9", "3.10"]
11+
12+
runs-on: ubuntu-latest
1313

1414
steps:
1515
- uses: actions/checkout@v3
16-
- name: Set up Python ${{ matrix.python-version }}
17-
uses: actions/setup-python@v3
18-
with:
19-
python-version: ${{ matrix.python-version }}
20-
- name: Install from requirements.txt
21-
run: |
22-
python -m pip install --upgrade pip
23-
pip install pytest pytest-dotenv dbt-tests-adapter==1.1.0
24-
if [ -f requirements.txt ]; then pip install -r requirements.txt; fi
25-
- name: Create data directory and install crypto.so
26-
run: |
27-
mkdir -p /tmp/dbt-sqlite-tests
28-
cd /tmp/dbt-sqlite-tests && wget https://github.com/nalgeon/sqlean/releases/download/0.12.2/crypto.so
29-
- name: Run test script
30-
run: |
31-
./run_tests.sh
16+
- name: Build docker image
17+
run: docker build --build-arg PYTHON_VERSION=${{ matrix.python_version }} --tag dbt-sqlite:$GITHUB_SHA .
18+
- name: Run tests
19+
run: docker run dbt-sqlite:$GITHUB_SHA run_tests.sh

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,3 +14,5 @@ env/
1414
*.sublime-*
1515

1616
.idea/
17+
18+
*.log

Dockerfile

Lines changed: 24 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,33 @@
11

2-
FROM ubuntu:20.04
2+
ARG PYTHON_VERSION=3.9
33

4-
RUN apt-get update && apt-get -y install git make python3 python3-pip python3-venv sqlite3 vim virtualenvwrapper wget
4+
FROM python:${PYTHON_VERSION}-bullseye
55

6-
RUN mkdir /root/dbt-sqlite
6+
RUN apt-get update && apt-get -y install git python3 python3-pip python3-venv sqlite3 vim virtualenvwrapper wget
77

8-
WORKDIR /root/dbt-sqlite
8+
WORKDIR /opt/dbt-sqlite
99

10-
RUN mkdir -p /tmp/dbt-sqlite-tests
10+
RUN python3 -m pip install --upgrade pip \
11+
&& python3 -m pip install pytest pytest-dotenv dbt-core~=1.2.0 dbt-tests-adapter~=1.2.0
1112

12-
RUN cd /tmp/dbt-sqlite-tests && wget https://github.com/nalgeon/sqlean/releases/download/0.12.2/crypto.so
13+
RUN wget -q https://github.com/nalgeon/sqlean/releases/download/0.15.2/crypto.so
14+
RUN wget -q https://github.com/nalgeon/sqlean/releases/download/0.15.2/math.so
15+
RUN wget -q https://github.com/nalgeon/sqlean/releases/download/0.15.2/text.so
1316

14-
RUN pip install dbt-core~=1.1.0
17+
WORKDIR /opt/dbt-sqlite/src
1518

16-
RUN pip install pytest pytest-dotenv dbt-tests-adapter==1.1.0
19+
COPY . .
1720

18-
ENTRYPOINT ["./run_tests.sh"]
21+
RUN pip install .
22+
23+
ENV TESTDATA=/opt/dbt-sqlite/testdata
24+
25+
RUN mkdir $TESTDATA
26+
27+
VOLUME /opt/dbt-sqlite/testdata
28+
29+
WORKDIR /opt/dbt-sqlite/project
30+
31+
ENV PATH=$PATH:/opt/dbt-sqlite/src
32+
33+
VOLUME /opt/dbt-sqlite/project

README.md

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -80,10 +80,14 @@ dbt_sqlite:
8080
# files in schemas_and_paths as long as there's no conflicts.
8181
schema_directory: '/my_project/data'
8282

83-
# optional: list of file paths of SQLite extensions to load.
84-
# crypto.so is needed for snapshots to work; see README
83+
# optional: list of file paths of SQLite extensions to load. see README.
84+
# crypto.so is needed for snapshots to work
85+
# math.so is needed for ceil function
86+
# text.so is needed for split_part macro to work
8587
extensions:
8688
- "/path/to/sqlean/crypto.so"
89+
- "/path/to/sqlean/math.so"
90+
- "/path/to/sqlean/text.so"
8791

8892
```
8993

@@ -126,12 +130,14 @@ not worth the effort.
126130

127131
## SQLite Extensions
128132

129-
For snapshots to work, you'll need the `crypto` module from SQLean to get an `md5()`
130-
function. It's recommended that you install all the SQLean modules, as they provide
131-
many common SQL functions missing from SQLite.
133+
These modules from SQLean are needed for certain functionality to work:
134+
- `crypto`: provides `md5()` function needed for snapshots
135+
- `math`: provides `ceil` and `floor` needed for the datediff macro to work
136+
- `text`: provides `split_part` function
132137

133138
Precompiled binaries are available for download from the [SQLean github repository page](https://github.com/nalgeon/sqlean).
134-
You can also compile them yourself if you want.
139+
You can also compile them yourself if you want. Note that some modules depend on other libraries
140+
(`math` for example depends on GLIBC); if an extension fails to load, you may want to try building it yourself.
135141

136142
Point to these module files in your profile config as shown in the example above.
137143

@@ -177,10 +183,22 @@ git push --tags
177183

178184
## Running Tests
179185

186+
This runs the test suite and cleans up after itself:
180187
```
181188
./run_tests_docker.sh
182189
```
183190

191+
To run tests interactively and be able to examine test artifacts:
192+
```
193+
docker build . -t dbt-sqlite
194+
195+
docker run --rm -it dbt-sqlite bash
196+
197+
# see output for the locations of artifacts
198+
run_tests.sh -s
199+
```
200+
201+
184202
## Credits
185203

186204
Inspired by this initial work by stephen1000: https://github.com/stephen1000/dbt_sqlite

dbt/adapters/sqlite/impl.py

Lines changed: 36 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11

2+
import datetime
23
import decimal
4+
import os
5+
import os.path
36
from typing import List, Optional, Set
47

58
import agate
@@ -21,6 +24,33 @@ class SQLiteAdapter(SQLAdapter):
2124
def date_function(cls):
2225
return 'date()'
2326

27+
# sqlite reports the exact string (including case) used when declaring a column of a certain type
28+
29+
@classmethod
30+
def convert_text_type(cls, agate_table: agate.Table, col_idx: int) -> str:
31+
return "TEXT"
32+
33+
@classmethod
34+
def convert_number_type(cls, agate_table: agate.Table, col_idx: int) -> str:
35+
decimals = agate_table.aggregate(agate.MaxPrecision(col_idx)) # type: ignore[attr-defined]
36+
return "NUMERIC" if decimals else "INT"
37+
38+
@classmethod
39+
def convert_boolean_type(cls, agate_table: agate.Table, col_idx: int) -> str:
40+
return "BOOLEAN"
41+
42+
@classmethod
43+
def convert_datetime_type(cls, agate_table: agate.Table, col_idx: int) -> str:
44+
return "TIMESTAMP WITHOUT TIMEZONE"
45+
46+
@classmethod
47+
def convert_date_type(cls, agate_table: agate.Table, col_idx: int) -> str:
48+
return "DATE"
49+
50+
@classmethod
51+
def convert_time_type(cls, agate_table: agate.Table, col_idx: int) -> str:
52+
return "TIME"
53+
2454
def get_live_relation_type(self, relation):
2555
"""
2656
returns the type of relation (table, view) from the live database
@@ -244,11 +274,13 @@ def timestamp_add_sql(
244274
def drop_schema(self, relation: BaseRelation) -> None:
245275
super().drop_schema(relation)
246276

247-
# can't detach a database in the middle of a transaction, so commit first.
248-
# I wonder if drop_schema() in SQLAdapter should do this, since create_schema() does.
249-
self.commit_if_has_connection()
250-
251277
# never detach main
252278
if relation.schema != 'main':
253279
if self.check_schema_exists(relation.database, relation.schema):
254280
self.connections.execute(f"DETACH DATABASE {relation.schema}")
281+
282+
if relation.schema in self.config.credentials.schemas_and_paths:
283+
path = self.config.credentials.schemas_and_paths[relation.schema]
284+
else:
285+
path = os.path.join(self.config.credentials.schema_directory, relation.schema + ".db")
286+
os.remove(path)
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{% macro sqlite__get_binding_char() %}
2+
{{ return('?') }}
3+
{% endmacro %}

dbt/include/sqlite/macros/materializations/seed/seed.sql

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,7 @@
1919
insert into {{ this.schema }}.{{ this.identifier}} ({{ cols_sql }}) values
2020
{% for row in chunk -%}
2121
({%- for column in agate_table.column_names -%}
22-
{# sqlite uses ? as placeholder character #}
23-
?
22+
{{ get_binding_char() }}
2423
{%- if not loop.last%},{%- endif %}
2524
{%- endfor -%})
2625
{%- if not loop.last%},{%- endif %}
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{% macro sqlite__any_value(expression) -%}
2+
3+
min({{ expression }})
4+
5+
{%- endmacro %}
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{% macro sqlite__bool_or(expression) -%}
2+
3+
max({{ expression }})
4+
5+
{%- endmacro %}

0 commit comments

Comments
 (0)