etlplus 0.7.1__py3-none-any.whl → 0.8.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
etlplus/cli/app.py CHANGED
@@ -60,7 +60,6 @@ from ..utils import json_type
60
60
  from .handlers import check_handler
61
61
  from .handlers import extract_handler
62
62
  from .handlers import load_handler
63
- from .handlers import pipeline_handler
64
63
  from .handlers import render_handler
65
64
  from .handlers import run_handler
66
65
  from .handlers import transform_handler
@@ -1010,60 +1009,6 @@ def load_cmd(
1010
1009
  return int(load_handler(ns))
1011
1010
 
1012
1011
 
1013
- @app.command('pipeline')
1014
- def pipeline_cmd(
1015
- ctx: typer.Context,
1016
- config: PipelineConfigOption,
1017
- job: str | None = typer.Option(
1018
- None,
1019
- '--job',
1020
- metavar='JOB',
1021
- help='Run a specific job by name',
1022
- ),
1023
- jobs: bool = typer.Option(
1024
- False,
1025
- '--jobs',
1026
- help='List available job names and exit',
1027
- ),
1028
- pipeline: str | None = typer.Option(
1029
- None,
1030
- '--pipeline',
1031
- help='Run a specific pipeline by name',
1032
- ),
1033
- ) -> int:
1034
- """
1035
- Deprecated wrapper to inspect or run a pipeline YAML configuration.
1036
-
1037
- Parameters
1038
- ----------
1039
- ctx : typer.Context
1040
- Typer execution context provided to the command.
1041
- config : PipelineConfigOption
1042
- Path to pipeline YAML configuration file.
1043
- job : str | None, optional
1044
- Name of a specific job to run.
1045
- jobs : bool, optional
1046
- If True, list available job names and exit.
1047
- pipeline : str | None, optional
1048
- Name of a specific pipeline to run.
1049
-
1050
- Returns
1051
- -------
1052
- int
1053
- Zero on success.
1054
- """
1055
- state = _ensure_state(ctx)
1056
- run_target = job or pipeline
1057
- ns = _stateful_namespace(
1058
- state,
1059
- command='pipeline',
1060
- config=config,
1061
- list=jobs,
1062
- run=run_target,
1063
- )
1064
- return int(pipeline_handler(ns))
1065
-
1066
-
1067
1012
  @app.command('render')
1068
1013
  def render_cmd(
1069
1014
  ctx: typer.Context,
etlplus/cli/handlers.py CHANGED
@@ -27,6 +27,7 @@ from ..load import load
27
27
  from ..run import run
28
28
  from ..transform import transform
29
29
  from ..types import JSONData
30
+ from ..types import TemplateKey
30
31
  from ..utils import json_type
31
32
  from ..utils import print_json
32
33
  from ..validate import validate
@@ -39,7 +40,6 @@ __all__ = [
39
40
  'extract_handler',
40
41
  'check_handler',
41
42
  'load_handler',
42
- 'pipeline_handler',
43
43
  'render_handler',
44
44
  'run_handler',
45
45
  'transform_handler',
@@ -72,7 +72,7 @@ def _collect_table_specs(
72
72
  specs: list[dict[str, Any]] = []
73
73
 
74
74
  if spec_path:
75
- specs.append(load_table_spec(Path(spec_path)))
75
+ specs.append(dict(load_table_spec(Path(spec_path))))
76
76
 
77
77
  if config_path:
78
78
  cfg = load_pipeline_config(config_path, substitute=True)
@@ -552,57 +552,13 @@ def load_handler(
552
552
  return 0
553
553
 
554
554
 
555
- def pipeline_handler(
556
- args: argparse.Namespace,
557
- ) -> int:
558
- """
559
- Inspect or run a pipeline YAML configuration.
560
-
561
- Parameters
562
- ----------
563
- args : argparse.Namespace
564
- Parsed command-line arguments.
565
-
566
- Returns
567
- -------
568
- int
569
- Zero on success.
570
- """
571
- print(
572
- 'DEPRECATED: use "etlplus check --summary|--jobs" or '
573
- '"etlplus run --job/--pipeline" instead of "etlplus pipeline".',
574
- file=sys.stderr,
575
- )
576
-
577
- cfg = load_pipeline_config(args.config, substitute=True)
578
-
579
- list_flag = getattr(args, 'list', False) or getattr(args, 'jobs', False)
580
- run_target = (
581
- getattr(args, 'run', None)
582
- or getattr(args, 'job', None)
583
- or getattr(args, 'pipeline', None)
584
- )
585
-
586
- if list_flag and not run_target:
587
- print_json({'jobs': _pipeline_summary(cfg)['jobs']})
588
- return 0
589
-
590
- if run_target:
591
- result = run(job=run_target, config_path=args.config)
592
- print_json({'status': 'ok', 'result': result})
593
- return 0
594
-
595
- print_json(_pipeline_summary(cfg))
596
- return 0
597
-
598
-
599
555
  def render_handler(
600
556
  args: argparse.Namespace,
601
557
  ) -> int:
602
558
  """Render SQL DDL statements from table schema specs."""
603
559
  _, quiet = _presentation_flags(args)
604
560
 
605
- template_value = getattr(args, 'template', 'ddl') or 'ddl'
561
+ template_value: TemplateKey = getattr(args, 'template', 'ddl') or 'ddl'
606
562
  template_path = getattr(args, 'template_path', None)
607
563
  table_filter = getattr(args, 'table', None)
608
564
  spec_path = getattr(args, 'spec', None)
@@ -610,7 +566,7 @@ def render_handler(
610
566
 
611
567
  # If the provided template points to a file, treat it as a path override.
612
568
  file_override = template_path
613
- template_key = template_value
569
+ template_key: TemplateKey | None = template_value
614
570
  if template_path is None:
615
571
  candidate_path = Path(template_value)
616
572
  if candidate_path.exists():
etlplus/cli/main.py CHANGED
@@ -27,7 +27,6 @@ from .app import app
27
27
  from .handlers import check_handler
28
28
  from .handlers import extract_handler
29
29
  from .handlers import load_handler
30
- from .handlers import pipeline_handler
31
30
  from .handlers import render_handler
32
31
  from .handlers import run_handler
33
32
  from .handlers import transform_handler
@@ -420,28 +419,6 @@ def create_parser() -> argparse.ArgumentParser:
420
419
  _add_format_options(load_parser, context='target')
421
420
  load_parser.set_defaults(func=load_handler)
422
421
 
423
- pipe_parser = subparsers.add_parser(
424
- 'pipeline',
425
- help=(
426
- 'DEPRECATED: use "list" (for summary/jobs) or "run" (to execute); '
427
- 'see '
428
- f'{PROJECT_URL}/blob/main/docs/pipeline-guide.md'
429
- ),
430
- formatter_class=argparse.ArgumentDefaultsHelpFormatter,
431
- )
432
- _add_config_option(pipe_parser)
433
- pipe_parser.add_argument(
434
- '--list',
435
- action='store_true',
436
- help='List available job names and exit',
437
- )
438
- pipe_parser.add_argument(
439
- '--run',
440
- metavar='JOB',
441
- help='Run a specific job by name',
442
- )
443
- pipe_parser.set_defaults(func=pipeline_handler)
444
-
445
422
  render_parser = subparsers.add_parser(
446
423
  'render',
447
424
  help='Render SQL DDL from table schema specs',
@@ -18,6 +18,7 @@ from .engine import engine
18
18
  from .engine import load_database_url_from_config
19
19
  from .engine import make_engine
20
20
  from .engine import session
21
+ from .orm import Base
21
22
  from .orm import build_models
22
23
  from .orm import load_and_build_models
23
24
  from .schema import load_table_specs
@@ -36,6 +37,7 @@ __all__ = [
36
37
  'render_table_sql',
37
38
  'render_tables',
38
39
  'render_tables_to_string',
40
+ 'Base',
39
41
  # Singletons
40
42
  'engine',
41
43
  'session',
etlplus/database/ddl.py CHANGED
@@ -15,7 +15,6 @@ import os
15
15
  from collections.abc import Iterable
16
16
  from collections.abc import Mapping
17
17
  from pathlib import Path
18
- from typing import Any
19
18
  from typing import Final
20
19
 
21
20
  from jinja2 import DictLoader
@@ -24,6 +23,9 @@ from jinja2 import FileSystemLoader
24
23
  from jinja2 import StrictUndefined
25
24
 
26
25
  from ..file import File
26
+ from ..types import StrAnyMap
27
+ from ..types import StrPath
28
+ from ..types import TemplateKey
27
29
 
28
30
  # SECTION: EXPORTS ========================================================== #
29
31
 
@@ -52,7 +54,7 @@ _SUPPORTED_SPEC_SUFFIXES: Final[frozenset[str]] = frozenset(
52
54
  # SECTION: CONSTANTS ======================================================== #
53
55
 
54
56
 
55
- TEMPLATES: Final[dict[str, str]] = {
57
+ TEMPLATES: Final[dict[TemplateKey, str]] = {
56
58
  'ddl': 'ddl.sql.j2',
57
59
  'view': 'view.sql.j2',
58
60
  }
@@ -64,7 +66,8 @@ TEMPLATES: Final[dict[str, str]] = {
64
66
  def _load_template_text(
65
67
  filename: str,
66
68
  ) -> str:
67
- """Return the bundled template text.
69
+ """
70
+ Return the bundled template text.
68
71
 
69
72
  Parameters
70
73
  ----------
@@ -99,16 +102,17 @@ def _load_template_text(
99
102
 
100
103
  def _resolve_template(
101
104
  *,
102
- template_key: str | None,
103
- template_path: str | None,
105
+ template_key: TemplateKey | None,
106
+ template_path: StrPath | None,
104
107
  ) -> tuple[Environment, str]:
105
- """Return environment and template name for rendering.
108
+ """
109
+ Return environment and template name for rendering.
106
110
 
107
111
  Parameters
108
112
  ----------
109
- template_key : str | None
113
+ template_key : TemplateKey | None
110
114
  Named template key bundled with the package.
111
- template_path : str | None
115
+ template_path : StrPath | None
112
116
  Explicit template file override.
113
117
 
114
118
  Returns
@@ -123,7 +127,11 @@ def _resolve_template(
123
127
  ValueError
124
128
  If the template key is unknown.
125
129
  """
126
- file_override = template_path or os.environ.get('TEMPLATE_NAME')
130
+ file_override = (
131
+ str(template_path)
132
+ if template_path is not None
133
+ else os.environ.get('TEMPLATE_NAME')
134
+ )
127
135
  if file_override:
128
136
  path = Path(file_override)
129
137
  if not path.exists():
@@ -137,14 +145,14 @@ def _resolve_template(
137
145
  )
138
146
  return env, path.name
139
147
 
140
- key = (template_key or 'ddl').strip()
148
+ key: TemplateKey = template_key or 'ddl'
141
149
  if key not in TEMPLATES:
142
150
  choices = ', '.join(sorted(TEMPLATES))
143
151
  raise ValueError(
144
152
  f'Unknown template key "{key}". Choose from: {choices}',
145
153
  )
146
154
 
147
- # Load template from package data
155
+ # Load template from package data.
148
156
  template_filename = TEMPLATES[key]
149
157
  template_source = _load_template_text(template_filename)
150
158
 
@@ -161,19 +169,19 @@ def _resolve_template(
161
169
 
162
170
 
163
171
  def load_table_spec(
164
- path: Path | str,
165
- ) -> dict[str, Any]:
172
+ path: StrPath,
173
+ ) -> StrAnyMap:
166
174
  """
167
175
  Load a table specification from disk.
168
176
 
169
177
  Parameters
170
178
  ----------
171
- path : Path | str
179
+ path : StrPath
172
180
  Path to the JSON or YAML specification file.
173
181
 
174
182
  Returns
175
183
  -------
176
- dict[str, Any]
184
+ StrAnyMap
177
185
  Parsed table specification mapping.
178
186
 
179
187
  Raises
@@ -210,9 +218,9 @@ def load_table_spec(
210
218
 
211
219
 
212
220
  def render_table_sql(
213
- spec: Mapping[str, Any],
221
+ spec: StrAnyMap,
214
222
  *,
215
- template: str | None = 'ddl',
223
+ template: TemplateKey | None = 'ddl',
216
224
  template_path: str | None = None,
217
225
  ) -> str:
218
226
  """
@@ -220,9 +228,9 @@ def render_table_sql(
220
228
 
221
229
  Parameters
222
230
  ----------
223
- spec : Mapping[str, Any]
231
+ spec : StrAnyMap
224
232
  Table specification mapping.
225
- template : str | None, optional
233
+ template : TemplateKey | None, optional
226
234
  Template key to use (default: 'ddl').
227
235
  template_path : str | None, optional
228
236
  Path to a custom template file (overrides ``template``).
@@ -241,9 +249,9 @@ def render_table_sql(
241
249
 
242
250
 
243
251
  def render_tables(
244
- specs: Iterable[Mapping[str, Any]],
252
+ specs: Iterable[StrAnyMap],
245
253
  *,
246
- template: str | None = 'ddl',
254
+ template: TemplateKey | None = 'ddl',
247
255
  template_path: str | None = None,
248
256
  ) -> list[str]:
249
257
  """
@@ -251,9 +259,9 @@ def render_tables(
251
259
 
252
260
  Parameters
253
261
  ----------
254
- specs : Iterable[Mapping[str, Any]]
262
+ specs : Iterable[StrAnyMap]
255
263
  Table specification mappings.
256
- template : str | None, optional
264
+ template : TemplateKey | None, optional
257
265
  Template key to use (default: 'ddl').
258
266
  template_path : str | None, optional
259
267
  Path to a custom template file (overrides ``template``).
@@ -271,21 +279,21 @@ def render_tables(
271
279
 
272
280
 
273
281
  def render_tables_to_string(
274
- spec_paths: Iterable[Path | str],
282
+ spec_paths: Iterable[StrPath],
275
283
  *,
276
- template: str | None = 'ddl',
277
- template_path: Path | str | None = None,
284
+ template: TemplateKey | None = 'ddl',
285
+ template_path: StrPath | None = None,
278
286
  ) -> str:
279
287
  """
280
288
  Render one or more specs and concatenate the SQL payloads.
281
289
 
282
290
  Parameters
283
291
  ----------
284
- spec_paths : Iterable[Path | str]
292
+ spec_paths : Iterable[StrPath]
285
293
  Paths to table specification files.
286
- template : str | None, optional
294
+ template : TemplateKey | None, optional
287
295
  Template key bundled with ETLPlus. Defaults to ``'ddl'``.
288
- template_path : Path | str | None, optional
296
+ template_path : StrPath | None, optional
289
297
  Custom Jinja template to override the bundled templates.
290
298
 
291
299
  Returns
@@ -10,12 +10,15 @@ import os
10
10
  from collections.abc import Mapping
11
11
  from pathlib import Path
12
12
  from typing import Any
13
+ from typing import Final
13
14
 
14
15
  from sqlalchemy import create_engine
15
16
  from sqlalchemy.engine import Engine
16
17
  from sqlalchemy.orm import sessionmaker
17
18
 
18
19
  from ..file import File
20
+ from ..types import StrAnyMap
21
+ from ..types import StrPath
19
22
 
20
23
  # SECTION: EXPORTS ========================================================== #
21
24
 
@@ -33,7 +36,7 @@ __all__ = [
33
36
  # SECTION: INTERNAL CONSTANTS =============================================== #
34
37
 
35
38
 
36
- DATABASE_URL: str = (
39
+ DATABASE_URL: Final[str] = (
37
40
  os.getenv('DATABASE_URL')
38
41
  or os.getenv('DATABASE_DSN')
39
42
  or 'sqlite+pysqlite:///:memory:'
@@ -43,13 +46,15 @@ DATABASE_URL: str = (
43
46
  # SECTION: INTERNAL FUNCTIONS =============================================== #
44
47
 
45
48
 
46
- def _resolve_url_from_mapping(cfg: Mapping[str, Any]) -> str | None:
49
+ def _resolve_url_from_mapping(
50
+ cfg: StrAnyMap,
51
+ ) -> str | None:
47
52
  """
48
53
  Return a URL/DSN from a mapping if present.
49
54
 
50
55
  Parameters
51
56
  ----------
52
- cfg : Mapping[str, Any]
57
+ cfg : StrAnyMap
53
58
  Configuration mapping potentially containing connection fields.
54
59
 
55
60
  Returns
@@ -74,7 +79,7 @@ def _resolve_url_from_mapping(cfg: Mapping[str, Any]) -> str | None:
74
79
 
75
80
 
76
81
  def load_database_url_from_config(
77
- path: str | Path,
82
+ path: StrPath,
78
83
  *,
79
84
  name: str | None = None,
80
85
  ) -> str:
@@ -88,7 +93,7 @@ def load_database_url_from_config(
88
93
 
89
94
  Parameters
90
95
  ----------
91
- path : str | Path
96
+ path : StrPath
92
97
  Location of the configuration file.
93
98
  name : str | None, optional
94
99
  Named database entry under the ``databases`` map (default:
etlplus/database/orm.py CHANGED
@@ -13,9 +13,8 @@ Usage
13
13
  from __future__ import annotations
14
14
 
15
15
  import re
16
- from collections.abc import Callable
17
- from pathlib import Path
18
16
  from typing import Any
17
+ from typing import Final
19
18
 
20
19
  from sqlalchemy import Boolean
21
20
  from sqlalchemy import CheckConstraint
@@ -41,11 +40,15 @@ from sqlalchemy.orm import DeclarativeBase
41
40
  from sqlalchemy.orm import mapped_column
42
41
  from sqlalchemy.types import TypeEngine
43
42
 
43
+ from ..types import StrPath
44
44
  from .schema import ForeignKeySpec
45
45
  from .schema import TableSpec
46
46
  from .schema import load_table_specs
47
+ from .types import ModelRegistry
48
+ from .types import TypeFactory
49
+
50
+ # SECTION: EXPORTS ========================================================== #
47
51
 
48
- # SECTION: INTERNAL CONSTANTS =============================================== #
49
52
 
50
53
  __all__ = [
51
54
  # Classes
@@ -57,7 +60,9 @@ __all__ = [
57
60
  ]
58
61
 
59
62
 
60
- _TYPE_MAPPING: dict[str, Callable[[list[int]], TypeEngine]] = {
63
+ # SECTION: INTERNAL CONSTANTS =============================================== #
64
+
65
+ _TYPE_MAPPING: Final[dict[str, TypeFactory]] = {
61
66
  'int': lambda _: Integer(),
62
67
  'integer': lambda _: Integer(),
63
68
  'bigint': lambda _: Integer(),
@@ -102,6 +107,8 @@ _TYPE_MAPPING: dict[str, Callable[[list[int]], TypeEngine]] = {
102
107
  class Base(DeclarativeBase):
103
108
  """Base class for all ORM models."""
104
109
 
110
+ __abstract__ = True
111
+
105
112
 
106
113
  # SECTION: INTERNAL FUNCTIONS =============================================== #
107
114
 
@@ -191,7 +198,7 @@ def build_models(
191
198
  specs: list[TableSpec],
192
199
  *,
193
200
  base: type[DeclarativeBase] = Base,
194
- ) -> dict[str, type[DeclarativeBase]]:
201
+ ) -> ModelRegistry:
195
202
  """
196
203
  Build SQLAlchemy ORM models from table specifications.
197
204
  Parameters
@@ -202,10 +209,10 @@ def build_models(
202
209
  Base class for the ORM models (default: :class:`Base`).
203
210
  Returns
204
211
  -------
205
- dict[str, type[DeclarativeBase]]
212
+ ModelRegistry
206
213
  Registry mapping fully qualified table names to ORM model classes.
207
214
  """
208
- registry: dict[str, type[DeclarativeBase]] = {}
215
+ registry: ModelRegistry = {}
209
216
 
210
217
  for spec in specs:
211
218
  table_args: list[object] = []
@@ -302,23 +309,23 @@ def build_models(
302
309
 
303
310
 
304
311
  def load_and_build_models(
305
- path: str | Path,
312
+ path: StrPath,
306
313
  *,
307
314
  base: type[DeclarativeBase] = Base,
308
- ) -> dict[str, type[DeclarativeBase]]:
315
+ ) -> ModelRegistry:
309
316
  """
310
317
  Load table specifications from a file and build SQLAlchemy models.
311
318
 
312
319
  Parameters
313
320
  ----------
314
- path : str | Path
321
+ path : StrPath
315
322
  Path to the YAML file containing table specifications.
316
323
  base : type[DeclarativeBase], optional
317
324
  Base class for the ORM models (default: :class:`Base`).
318
325
 
319
326
  Returns
320
327
  -------
321
- dict[str, type[DeclarativeBase]]
328
+ ModelRegistry
322
329
  Registry mapping fully qualified table names to ORM model classes.
323
330
  """
324
331
  return build_models(load_table_specs(path), base=base)
@@ -16,6 +16,7 @@ from pydantic import ConfigDict
16
16
  from pydantic import Field
17
17
 
18
18
  from ..file import File
19
+ from ..types import StrPath
19
20
 
20
21
  # SECTION: EXPORTS ========================================================== #
21
22
 
@@ -244,14 +245,14 @@ class TableSpec(BaseModel):
244
245
 
245
246
 
246
247
  def load_table_specs(
247
- path: str | Path,
248
+ path: StrPath,
248
249
  ) -> list[TableSpec]:
249
250
  """
250
251
  Load table specifications from a YAML file.
251
252
 
252
253
  Parameters
253
254
  ----------
254
- path : str | Path
255
+ path : StrPath
255
256
  Path to the YAML file containing table specifications.
256
257
 
257
258
  Returns
@@ -0,0 +1,33 @@
1
+ """
2
+ :mod:`etlplus.database.types` module.
3
+
4
+ Shared type aliases leveraged across :mod:`etlplus.database` modules.
5
+ """
6
+
7
+ from __future__ import annotations
8
+
9
+ from collections.abc import Callable
10
+
11
+ from sqlalchemy.orm import DeclarativeBase
12
+ from sqlalchemy.types import TypeEngine
13
+
14
+ # SECTION: EXPORTS ========================================================== #
15
+
16
+
17
+ __all__ = [
18
+ # Type Aliases
19
+ 'ModelRegistry',
20
+ 'TypeFactory',
21
+ ]
22
+
23
+
24
+ # SECTION: TYPE ALIASES ===================================================== #
25
+
26
+
27
+ # pylint: disable=invalid-name
28
+
29
+ # Registry mapping fully qualified table names to declarative classes.
30
+ type ModelRegistry = dict[str, type[DeclarativeBase]]
31
+
32
+ # Callable producing a SQLAlchemy TypeEngine from parsed parameters.
33
+ type TypeFactory = Callable[[list[int]], TypeEngine]
etlplus/types.py CHANGED
@@ -225,3 +225,8 @@ type Sleeper = Callable[[float], None]
225
225
 
226
226
  # Numeric timeout in seconds or ``None`` for no timeout.
227
227
  type Timeout = float | None
228
+
229
+ # -- Templates -- #
230
+
231
+ # Allowed template keys for bundled DDL rendering.
232
+ type TemplateKey = Literal['ddl', 'view']
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: etlplus
3
- Version: 0.7.1
3
+ Version: 0.8.0
4
4
  Summary: A Swiss Army knife for simple ETL operations
5
5
  Home-page: https://github.com/Dagitali/ETLPlus
6
6
  Author: ETLPlus Team
@@ -366,8 +366,6 @@ etlplus check --config examples/configs/pipeline.yml --summary
366
366
 
367
367
  # Run a job
368
368
  etlplus run --config examples/configs/pipeline.yml --job file_to_file_customers
369
-
370
- # Deprecated shim (will be removed): etlplus pipeline
371
369
  ```
372
370
 
373
371
  ### Complete ETL Pipeline Example
@@ -10,7 +10,7 @@ etlplus/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
10
10
  etlplus/run.py,sha256=X4kp5FQlIWVf1_d9oSrchKau7BFDCE1Zkscvu7WPaWw,12340
11
11
  etlplus/run_helpers.py,sha256=bj6MkaeFxjl3CeKG1HoXKx5DwAlXNERVW-GX-z1P_qQ,24373
12
12
  etlplus/transform.py,sha256=uAUVDDHYCgx7GpVez9IK3OAZM-CnCuMa9iox3vwGGJA,25296
13
- etlplus/types.py,sha256=SJiZ7wJiSnV4CEvF-9E5nSFLBo4DT9OqHQqj1GSHkv8,6042
13
+ etlplus/types.py,sha256=1hsDlnF6r76zAwaUYay-i6pCM-Y0IU5nP7Crj8PLCQ4,6157
14
14
  etlplus/utils.py,sha256=_fn8b-SAdxiw28VX-Ugr8sZUPZI9mEkWKAGExlgxhJA,13993
15
15
  etlplus/validate.py,sha256=7rJoEI_SIILdPpoBqqh2UJqg9oeReDz34mYSlc3t7Qg,12989
16
16
  etlplus/api/README.md,sha256=UkK5PiZWXbbnMNP0MaPa56S88PjSqOwhMNCyswOhvKc,7329
@@ -31,9 +31,9 @@ etlplus/api/rate_limiting/__init__.py,sha256=ZySB1dZettEDnWvI1EHf_TZ9L08M_kKsNR-
31
31
  etlplus/api/rate_limiting/config.py,sha256=2b4wIynblN-1EyMqI4aXa71SljzSjXYh5N1Nngr3jOg,9406
32
32
  etlplus/api/rate_limiting/rate_limiter.py,sha256=Uxozqd_Ej5Lsj-M-mLT2WexChgWh7x35_YP10yqYPQA,7159
33
33
  etlplus/cli/__init__.py,sha256=J97-Rv931IL1_b4AXnB7Fbbd7HKnHBpx18NQfC_kE6c,299
34
- etlplus/cli/app.py,sha256=SYPO-NDwXgymJrACw39jZ_NJrSKAs0O8anuWR5o42WM,35893
35
- etlplus/cli/handlers.py,sha256=nFMvqHQhJ8kJZPisDCiUHeOhjlqAO6hJvRjXiJTcU74,18951
36
- etlplus/cli/main.py,sha256=ijYOy72SEsxrTEBan5yADW8CZyr0yddVF8HeMgFw6Zg,16576
34
+ etlplus/cli/app.py,sha256=kQuMmY-RqadRGWS5yDpkKl5bWdOpqbR0jqsXCORLsMA,34532
35
+ etlplus/cli/handlers.py,sha256=5Blk5LSqTVSwTPPGEcbOw2NwNTTbFFOTxlpUdy5r2bA,17928
36
+ etlplus/cli/main.py,sha256=1U2WS-yIxTEr6ZJJkQFtisCxOcZ3cdnjIxUTewapN5M,15878
37
37
  etlplus/config/__init__.py,sha256=VZWzOg7d2YR9NT6UwKTv44yf2FRUMjTHynkm1Dl5Qzo,1486
38
38
  etlplus/config/connector.py,sha256=0-TIwevHbKRHVmucvyGpPd-3tB1dKHB-dj0yJ6kq5eY,9809
39
39
  etlplus/config/jobs.py,sha256=hmzRCqt0OvCEZZR4ONKrd3lvSv0OmayjLc4yOBk3ug8,7399
@@ -41,19 +41,20 @@ etlplus/config/pipeline.py,sha256=Va4MQY6KEyKqHGMKPmh09ZcGpx95br-iNUjpkqtzVbw,95
41
41
  etlplus/config/profile.py,sha256=Ss2zedQGjkaGSpvBLTD4SZaWViMJ7TJPLB8Q2_BTpPg,1898
42
42
  etlplus/config/types.py,sha256=a0epJ3z16HQ5bY3Ctf8s_cQPa3f0HHcwdOcjCP2xoG4,4954
43
43
  etlplus/config/utils.py,sha256=4SUHMkt5bKBhMhiJm-DrnmE2Q4TfOgdNCKz8PJDS27o,3443
44
- etlplus/database/__init__.py,sha256=0gWnMlQiVHS6SVUxIT9zklQUHU36y-2RF_gN1cx7icg,1018
45
- etlplus/database/ddl.py,sha256=lIar9KIOoBRslp_P0DnpoMDXzkjt64J5-iVV7CeSV_M,7747
46
- etlplus/database/engine.py,sha256=54f-XtNKIuogJhsLV9cX_xPoBwcl_HNJTL5HqMCi8kw,3986
47
- etlplus/database/orm.py,sha256=StjeguokM70oNKq7mNXLyc4_mYUZR-EKW3oGRlsd8QE,9962
48
- etlplus/database/schema.py,sha256=BmRP2wwX2xex1phLm0tnHrP6A2AQgguA-hSLnK0xwwc,7003
44
+ etlplus/database/__init__.py,sha256=AKJsDl2RHuRGPS-eXgNJeh4aSncJP5Y0yLApBF6i7i8,1052
45
+ etlplus/database/ddl.py,sha256=z9KvHi1MPhPBLHxMDdqJgLTp3A2-lcz0gqhZ7HIE6kU,7916
46
+ etlplus/database/engine.py,sha256=7rr7YndA8LwyWJL8k1YhQbqxxmW4gWEUQjp0NwQcYtc,4061
47
+ etlplus/database/orm.py,sha256=gCSqH-CjQz6tV9133-VqgiwokK5ylun0BwXaIWfImAo,10008
48
+ etlplus/database/schema.py,sha256=HNTgglI8qvQLInr7gq--2lLmLKHzAZTL2MJUOIw9DlY,7025
49
+ etlplus/database/types.py,sha256=_pkQyC14TzAlgyeIqZG4F5LWYknZbHw3TW68Auk7Ya0,795
49
50
  etlplus/templates/__init__.py,sha256=tsniN7XJYs3NwYxJ6c2HD5upHP3CDkLx-bQCMt97UOM,106
50
51
  etlplus/templates/ddl.sql.j2,sha256=s8fMWvcb4eaJVXkifuib1aQPljtZ8buuyB_uA-ZdU3Q,4734
51
52
  etlplus/templates/view.sql.j2,sha256=Iy8DHfhq5yyvrUKDxqp_aHIEXY4Tm6j4wT7YDEFWAhk,2180
52
53
  etlplus/validation/__init__.py,sha256=Pe5Xg1_EA4uiNZGYu5WTF3j7odjmyxnAJ8rcioaplSQ,1254
53
54
  etlplus/validation/utils.py,sha256=Mtqg449VIke0ziy_wd2r6yrwJzQkA1iulZC87FzXMjo,10201
54
- etlplus-0.7.1.dist-info/licenses/LICENSE,sha256=MuNO63i6kWmgnV2pbP2SLqP54mk1BGmu7CmbtxMmT-U,1069
55
- etlplus-0.7.1.dist-info/METADATA,sha256=Y2MYm3-8rGosgvY29er_Pt_j9qxgBVndnRXK3k0xUBM,19383
56
- etlplus-0.7.1.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
57
- etlplus-0.7.1.dist-info/entry_points.txt,sha256=6w-2-jzuPa55spzK34h-UKh2JTEShh38adFRONNP9QE,45
58
- etlplus-0.7.1.dist-info/top_level.txt,sha256=aWWF-udn_sLGuHTM6W6MLh99ArS9ROkUWO8Mi8y1_2U,8
59
- etlplus-0.7.1.dist-info/RECORD,,
55
+ etlplus-0.8.0.dist-info/licenses/LICENSE,sha256=MuNO63i6kWmgnV2pbP2SLqP54mk1BGmu7CmbtxMmT-U,1069
56
+ etlplus-0.8.0.dist-info/METADATA,sha256=VjENPm-4JBGKuJ_NIjRLjce135eB7_ZTOFY6ZmAdS30,19328
57
+ etlplus-0.8.0.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
58
+ etlplus-0.8.0.dist-info/entry_points.txt,sha256=6w-2-jzuPa55spzK34h-UKh2JTEShh38adFRONNP9QE,45
59
+ etlplus-0.8.0.dist-info/top_level.txt,sha256=aWWF-udn_sLGuHTM6W6MLh99ArS9ROkUWO8Mi8y1_2U,8
60
+ etlplus-0.8.0.dist-info/RECORD,,