relationalai 0.12.13__py3-none-any.whl → 0.13.0.dev0__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.
- relationalai/__init__.py +1 -209
- relationalai/config/__init__.py +56 -0
- relationalai/config/config.py +289 -0
- relationalai/config/config_fields.py +86 -0
- relationalai/config/connections/__init__.py +46 -0
- relationalai/config/connections/base.py +23 -0
- relationalai/config/connections/duckdb.py +29 -0
- relationalai/config/connections/snowflake.py +243 -0
- relationalai/config/external/__init__.py +17 -0
- relationalai/config/external/dbt_converter.py +101 -0
- relationalai/config/external/dbt_models.py +93 -0
- relationalai/config/external/snowflake_converter.py +41 -0
- relationalai/config/external/snowflake_models.py +85 -0
- relationalai/config/external/utils.py +19 -0
- relationalai/semantics/__init__.py +146 -22
- relationalai/semantics/backends/lqp/annotations.py +11 -0
- relationalai/semantics/backends/sql/sql_compiler.py +327 -0
- relationalai/semantics/frontend/base.py +1707 -0
- relationalai/semantics/frontend/core.py +179 -0
- relationalai/semantics/frontend/front_compiler.py +1313 -0
- relationalai/semantics/frontend/pprint.py +408 -0
- relationalai/semantics/metamodel/__init__.py +6 -40
- relationalai/semantics/metamodel/builtins.py +205 -769
- relationalai/semantics/metamodel/metamodel.py +437 -0
- relationalai/semantics/metamodel/metamodel_analyzer.py +519 -0
- relationalai/semantics/metamodel/pprint.py +412 -0
- relationalai/semantics/metamodel/rewriter.py +266 -0
- relationalai/semantics/metamodel/typer.py +1378 -0
- relationalai/semantics/std/__init__.py +60 -40
- relationalai/semantics/std/aggregates.py +149 -0
- relationalai/semantics/std/common.py +44 -0
- relationalai/semantics/std/constraints.py +37 -43
- relationalai/semantics/std/datetime.py +246 -135
- relationalai/semantics/std/decimals.py +45 -52
- relationalai/semantics/std/floats.py +13 -5
- relationalai/semantics/std/integers.py +26 -11
- relationalai/semantics/std/math.py +183 -112
- relationalai/semantics/std/numbers.py +86 -0
- relationalai/semantics/std/re.py +80 -62
- relationalai/semantics/std/strings.py +117 -60
- relationalai/shims/executor.py +147 -0
- relationalai/shims/helpers.py +126 -0
- relationalai/shims/hoister.py +221 -0
- relationalai/shims/mm2v0.py +1290 -0
- relationalai/tools/cli/__init__.py +6 -0
- relationalai/tools/cli/cli.py +90 -0
- relationalai/tools/cli/components/__init__.py +5 -0
- relationalai/tools/cli/components/progress_reader.py +1524 -0
- relationalai/tools/cli/components/utils.py +58 -0
- relationalai/tools/cli/config_template.py +45 -0
- relationalai/tools/cli/dev.py +19 -0
- relationalai/tools/debugger.py +289 -183
- relationalai/tools/typer_debugger.py +93 -0
- relationalai/util/dataclasses.py +43 -0
- relationalai/util/docutils.py +40 -0
- relationalai/util/error.py +199 -0
- relationalai/util/format.py +48 -106
- relationalai/util/naming.py +145 -0
- relationalai/util/python.py +35 -0
- relationalai/util/runtime.py +156 -0
- relationalai/util/schema.py +197 -0
- relationalai/util/source.py +185 -0
- relationalai/util/structures.py +163 -0
- relationalai/util/tracing.py +261 -0
- relationalai-0.13.0.dev0.dist-info/METADATA +46 -0
- relationalai-0.13.0.dev0.dist-info/RECORD +488 -0
- relationalai-0.13.0.dev0.dist-info/WHEEL +5 -0
- relationalai-0.13.0.dev0.dist-info/entry_points.txt +3 -0
- relationalai-0.13.0.dev0.dist-info/top_level.txt +2 -0
- v0/relationalai/__init__.py +216 -0
- v0/relationalai/clients/azure.py +477 -0
- v0/relationalai/clients/client.py +912 -0
- v0/relationalai/clients/config.py +673 -0
- v0/relationalai/clients/direct_access_client.py +118 -0
- v0/relationalai/clients/hash_util.py +31 -0
- v0/relationalai/clients/local.py +571 -0
- v0/relationalai/clients/profile_polling.py +73 -0
- v0/relationalai/clients/result_helpers.py +420 -0
- v0/relationalai/clients/snowflake.py +3869 -0
- v0/relationalai/clients/types.py +113 -0
- v0/relationalai/clients/use_index_poller.py +980 -0
- v0/relationalai/clients/util.py +356 -0
- v0/relationalai/debugging.py +389 -0
- v0/relationalai/dsl.py +1749 -0
- v0/relationalai/early_access/builder/__init__.py +30 -0
- v0/relationalai/early_access/builder/builder/__init__.py +35 -0
- v0/relationalai/early_access/builder/snowflake/__init__.py +12 -0
- v0/relationalai/early_access/builder/std/__init__.py +25 -0
- v0/relationalai/early_access/builder/std/decimals/__init__.py +12 -0
- v0/relationalai/early_access/builder/std/integers/__init__.py +12 -0
- v0/relationalai/early_access/builder/std/math/__init__.py +12 -0
- v0/relationalai/early_access/builder/std/strings/__init__.py +14 -0
- v0/relationalai/early_access/devtools/__init__.py +12 -0
- v0/relationalai/early_access/devtools/benchmark_lqp/__init__.py +12 -0
- v0/relationalai/early_access/devtools/extract_lqp/__init__.py +12 -0
- v0/relationalai/early_access/dsl/adapters/orm/adapter_qb.py +427 -0
- v0/relationalai/early_access/dsl/adapters/orm/parser.py +636 -0
- v0/relationalai/early_access/dsl/adapters/owl/adapter.py +176 -0
- v0/relationalai/early_access/dsl/adapters/owl/parser.py +160 -0
- v0/relationalai/early_access/dsl/bindings/common.py +402 -0
- v0/relationalai/early_access/dsl/bindings/csv.py +170 -0
- v0/relationalai/early_access/dsl/bindings/legacy/binding_models.py +143 -0
- v0/relationalai/early_access/dsl/bindings/snowflake.py +64 -0
- v0/relationalai/early_access/dsl/codegen/binder.py +411 -0
- v0/relationalai/early_access/dsl/codegen/common.py +79 -0
- v0/relationalai/early_access/dsl/codegen/helpers.py +23 -0
- v0/relationalai/early_access/dsl/codegen/relations.py +700 -0
- v0/relationalai/early_access/dsl/codegen/weaver.py +417 -0
- v0/relationalai/early_access/dsl/core/builders/__init__.py +47 -0
- v0/relationalai/early_access/dsl/core/builders/logic.py +19 -0
- v0/relationalai/early_access/dsl/core/builders/scalar_constraint.py +11 -0
- v0/relationalai/early_access/dsl/core/constraints/predicate/atomic.py +455 -0
- v0/relationalai/early_access/dsl/core/constraints/predicate/universal.py +73 -0
- v0/relationalai/early_access/dsl/core/constraints/scalar.py +310 -0
- v0/relationalai/early_access/dsl/core/context.py +13 -0
- v0/relationalai/early_access/dsl/core/cset.py +132 -0
- v0/relationalai/early_access/dsl/core/exprs/__init__.py +116 -0
- v0/relationalai/early_access/dsl/core/exprs/relational.py +18 -0
- v0/relationalai/early_access/dsl/core/exprs/scalar.py +412 -0
- v0/relationalai/early_access/dsl/core/instances.py +44 -0
- v0/relationalai/early_access/dsl/core/logic/__init__.py +193 -0
- v0/relationalai/early_access/dsl/core/logic/aggregation.py +98 -0
- v0/relationalai/early_access/dsl/core/logic/exists.py +223 -0
- v0/relationalai/early_access/dsl/core/logic/helper.py +163 -0
- v0/relationalai/early_access/dsl/core/namespaces.py +32 -0
- v0/relationalai/early_access/dsl/core/relations.py +276 -0
- v0/relationalai/early_access/dsl/core/rules.py +112 -0
- v0/relationalai/early_access/dsl/core/std/__init__.py +45 -0
- v0/relationalai/early_access/dsl/core/temporal/recall.py +6 -0
- v0/relationalai/early_access/dsl/core/types/__init__.py +270 -0
- v0/relationalai/early_access/dsl/core/types/concepts.py +128 -0
- v0/relationalai/early_access/dsl/core/types/constrained/__init__.py +267 -0
- v0/relationalai/early_access/dsl/core/types/constrained/nominal.py +143 -0
- v0/relationalai/early_access/dsl/core/types/constrained/subtype.py +124 -0
- v0/relationalai/early_access/dsl/core/types/standard.py +92 -0
- v0/relationalai/early_access/dsl/core/types/unconstrained.py +50 -0
- v0/relationalai/early_access/dsl/core/types/variables.py +203 -0
- v0/relationalai/early_access/dsl/ir/compiler.py +318 -0
- v0/relationalai/early_access/dsl/ir/executor.py +260 -0
- v0/relationalai/early_access/dsl/ontologies/constraints.py +88 -0
- v0/relationalai/early_access/dsl/ontologies/export.py +30 -0
- v0/relationalai/early_access/dsl/ontologies/models.py +453 -0
- v0/relationalai/early_access/dsl/ontologies/python_printer.py +303 -0
- v0/relationalai/early_access/dsl/ontologies/readings.py +60 -0
- v0/relationalai/early_access/dsl/ontologies/relationships.py +322 -0
- v0/relationalai/early_access/dsl/ontologies/roles.py +87 -0
- v0/relationalai/early_access/dsl/ontologies/subtyping.py +55 -0
- v0/relationalai/early_access/dsl/orm/constraints.py +438 -0
- v0/relationalai/early_access/dsl/orm/measures/dimensions.py +200 -0
- v0/relationalai/early_access/dsl/orm/measures/initializer.py +16 -0
- v0/relationalai/early_access/dsl/orm/measures/measure_rules.py +275 -0
- v0/relationalai/early_access/dsl/orm/measures/measures.py +299 -0
- v0/relationalai/early_access/dsl/orm/measures/role_exprs.py +268 -0
- v0/relationalai/early_access/dsl/orm/models.py +256 -0
- v0/relationalai/early_access/dsl/orm/object_oriented_printer.py +344 -0
- v0/relationalai/early_access/dsl/orm/printer.py +469 -0
- v0/relationalai/early_access/dsl/orm/reasoners.py +480 -0
- v0/relationalai/early_access/dsl/orm/relations.py +19 -0
- v0/relationalai/early_access/dsl/orm/relationships.py +251 -0
- v0/relationalai/early_access/dsl/orm/types.py +42 -0
- v0/relationalai/early_access/dsl/orm/utils.py +79 -0
- v0/relationalai/early_access/dsl/orm/verb.py +204 -0
- v0/relationalai/early_access/dsl/physical_metadata/tables.py +133 -0
- v0/relationalai/early_access/dsl/relations.py +170 -0
- v0/relationalai/early_access/dsl/rulesets.py +69 -0
- v0/relationalai/early_access/dsl/schemas/__init__.py +450 -0
- v0/relationalai/early_access/dsl/schemas/builder.py +48 -0
- v0/relationalai/early_access/dsl/schemas/comp_names.py +51 -0
- v0/relationalai/early_access/dsl/schemas/components.py +203 -0
- v0/relationalai/early_access/dsl/schemas/contexts.py +156 -0
- v0/relationalai/early_access/dsl/schemas/exprs.py +89 -0
- v0/relationalai/early_access/dsl/schemas/fragments.py +464 -0
- v0/relationalai/early_access/dsl/serialization.py +79 -0
- v0/relationalai/early_access/dsl/serialize/exporter.py +163 -0
- v0/relationalai/early_access/dsl/snow/api.py +104 -0
- v0/relationalai/early_access/dsl/snow/common.py +76 -0
- v0/relationalai/early_access/dsl/state_mgmt/__init__.py +129 -0
- v0/relationalai/early_access/dsl/state_mgmt/state_charts.py +125 -0
- v0/relationalai/early_access/dsl/state_mgmt/transitions.py +130 -0
- v0/relationalai/early_access/dsl/types/__init__.py +40 -0
- v0/relationalai/early_access/dsl/types/concepts.py +12 -0
- v0/relationalai/early_access/dsl/types/entities.py +135 -0
- v0/relationalai/early_access/dsl/types/values.py +17 -0
- v0/relationalai/early_access/dsl/utils.py +102 -0
- v0/relationalai/early_access/graphs/__init__.py +13 -0
- v0/relationalai/early_access/lqp/__init__.py +12 -0
- v0/relationalai/early_access/lqp/compiler/__init__.py +12 -0
- v0/relationalai/early_access/lqp/constructors/__init__.py +18 -0
- v0/relationalai/early_access/lqp/executor/__init__.py +12 -0
- v0/relationalai/early_access/lqp/ir/__init__.py +12 -0
- v0/relationalai/early_access/lqp/passes/__init__.py +12 -0
- v0/relationalai/early_access/lqp/pragmas/__init__.py +12 -0
- v0/relationalai/early_access/lqp/primitives/__init__.py +12 -0
- v0/relationalai/early_access/lqp/types/__init__.py +12 -0
- v0/relationalai/early_access/lqp/utils/__init__.py +12 -0
- v0/relationalai/early_access/lqp/validators/__init__.py +12 -0
- v0/relationalai/early_access/metamodel/__init__.py +58 -0
- v0/relationalai/early_access/metamodel/builtins/__init__.py +12 -0
- v0/relationalai/early_access/metamodel/compiler/__init__.py +12 -0
- v0/relationalai/early_access/metamodel/dependency/__init__.py +12 -0
- v0/relationalai/early_access/metamodel/factory/__init__.py +17 -0
- v0/relationalai/early_access/metamodel/helpers/__init__.py +12 -0
- v0/relationalai/early_access/metamodel/ir/__init__.py +14 -0
- v0/relationalai/early_access/metamodel/rewrite/__init__.py +7 -0
- v0/relationalai/early_access/metamodel/typer/__init__.py +3 -0
- v0/relationalai/early_access/metamodel/typer/typer/__init__.py +12 -0
- v0/relationalai/early_access/metamodel/types/__init__.py +15 -0
- v0/relationalai/early_access/metamodel/util/__init__.py +15 -0
- v0/relationalai/early_access/metamodel/visitor/__init__.py +12 -0
- v0/relationalai/early_access/rel/__init__.py +12 -0
- v0/relationalai/early_access/rel/executor/__init__.py +12 -0
- v0/relationalai/early_access/rel/rel_utils/__init__.py +12 -0
- v0/relationalai/early_access/rel/rewrite/__init__.py +7 -0
- v0/relationalai/early_access/solvers/__init__.py +19 -0
- v0/relationalai/early_access/sql/__init__.py +11 -0
- v0/relationalai/early_access/sql/executor/__init__.py +3 -0
- v0/relationalai/early_access/sql/rewrite/__init__.py +3 -0
- v0/relationalai/early_access/tests/logging/__init__.py +12 -0
- v0/relationalai/early_access/tests/test_snapshot_base/__init__.py +12 -0
- v0/relationalai/early_access/tests/utils/__init__.py +12 -0
- v0/relationalai/environments/__init__.py +35 -0
- v0/relationalai/environments/base.py +381 -0
- v0/relationalai/environments/colab.py +14 -0
- v0/relationalai/environments/generic.py +71 -0
- v0/relationalai/environments/ipython.py +68 -0
- v0/relationalai/environments/jupyter.py +9 -0
- v0/relationalai/environments/snowbook.py +169 -0
- v0/relationalai/errors.py +2455 -0
- v0/relationalai/experimental/SF.py +38 -0
- v0/relationalai/experimental/inspect.py +47 -0
- v0/relationalai/experimental/pathfinder/__init__.py +158 -0
- v0/relationalai/experimental/pathfinder/api.py +160 -0
- v0/relationalai/experimental/pathfinder/automaton.py +584 -0
- v0/relationalai/experimental/pathfinder/bridge.py +226 -0
- v0/relationalai/experimental/pathfinder/compiler.py +416 -0
- v0/relationalai/experimental/pathfinder/datalog.py +214 -0
- v0/relationalai/experimental/pathfinder/diagnostics.py +56 -0
- v0/relationalai/experimental/pathfinder/filter.py +236 -0
- v0/relationalai/experimental/pathfinder/glushkov.py +439 -0
- v0/relationalai/experimental/pathfinder/options.py +265 -0
- v0/relationalai/experimental/pathfinder/rpq.py +344 -0
- v0/relationalai/experimental/pathfinder/transition.py +200 -0
- v0/relationalai/experimental/pathfinder/utils.py +26 -0
- v0/relationalai/experimental/paths/api.py +143 -0
- v0/relationalai/experimental/paths/benchmarks/grid_graph.py +37 -0
- v0/relationalai/experimental/paths/examples/basic_example.py +40 -0
- v0/relationalai/experimental/paths/examples/minimal_engine_warmup.py +3 -0
- v0/relationalai/experimental/paths/examples/movie_example.py +77 -0
- v0/relationalai/experimental/paths/examples/paths_benchmark.py +115 -0
- v0/relationalai/experimental/paths/examples/paths_example.py +116 -0
- v0/relationalai/experimental/paths/examples/pattern_to_automaton.py +28 -0
- v0/relationalai/experimental/paths/find_paths_via_automaton.py +85 -0
- v0/relationalai/experimental/paths/graph.py +185 -0
- v0/relationalai/experimental/paths/path_algorithms/find_paths.py +280 -0
- v0/relationalai/experimental/paths/path_algorithms/one_sided_ball_repetition.py +26 -0
- v0/relationalai/experimental/paths/path_algorithms/one_sided_ball_upto.py +111 -0
- v0/relationalai/experimental/paths/path_algorithms/single.py +59 -0
- v0/relationalai/experimental/paths/path_algorithms/two_sided_balls_repetition.py +39 -0
- v0/relationalai/experimental/paths/path_algorithms/two_sided_balls_upto.py +103 -0
- v0/relationalai/experimental/paths/path_algorithms/usp-old.py +130 -0
- v0/relationalai/experimental/paths/path_algorithms/usp-tuple.py +183 -0
- v0/relationalai/experimental/paths/path_algorithms/usp.py +150 -0
- v0/relationalai/experimental/paths/product_graph.py +93 -0
- v0/relationalai/experimental/paths/rpq/automaton.py +584 -0
- v0/relationalai/experimental/paths/rpq/diagnostics.py +56 -0
- v0/relationalai/experimental/paths/rpq/rpq.py +378 -0
- v0/relationalai/experimental/paths/tests/tests_limit_sp_max_length.py +90 -0
- v0/relationalai/experimental/paths/tests/tests_limit_sp_multiple.py +119 -0
- v0/relationalai/experimental/paths/tests/tests_limit_sp_single.py +104 -0
- v0/relationalai/experimental/paths/tests/tests_limit_walks_multiple.py +113 -0
- v0/relationalai/experimental/paths/tests/tests_limit_walks_single.py +149 -0
- v0/relationalai/experimental/paths/tests/tests_one_sided_ball_repetition_multiple.py +70 -0
- v0/relationalai/experimental/paths/tests/tests_one_sided_ball_repetition_single.py +64 -0
- v0/relationalai/experimental/paths/tests/tests_one_sided_ball_upto_multiple.py +115 -0
- v0/relationalai/experimental/paths/tests/tests_one_sided_ball_upto_single.py +75 -0
- v0/relationalai/experimental/paths/tests/tests_single_paths.py +152 -0
- v0/relationalai/experimental/paths/tests/tests_single_walks.py +208 -0
- v0/relationalai/experimental/paths/tests/tests_single_walks_undirected.py +297 -0
- v0/relationalai/experimental/paths/tests/tests_two_sided_balls_repetition_multiple.py +107 -0
- v0/relationalai/experimental/paths/tests/tests_two_sided_balls_repetition_single.py +76 -0
- v0/relationalai/experimental/paths/tests/tests_two_sided_balls_upto_multiple.py +76 -0
- v0/relationalai/experimental/paths/tests/tests_two_sided_balls_upto_single.py +110 -0
- v0/relationalai/experimental/paths/tests/tests_usp_nsp_multiple.py +229 -0
- v0/relationalai/experimental/paths/tests/tests_usp_nsp_single.py +108 -0
- v0/relationalai/experimental/paths/tree_agg.py +168 -0
- v0/relationalai/experimental/paths/utilities/iterators.py +27 -0
- v0/relationalai/experimental/paths/utilities/prefix_sum.py +91 -0
- v0/relationalai/experimental/solvers.py +1087 -0
- v0/relationalai/loaders/__init__.py +0 -0
- v0/relationalai/loaders/csv.py +195 -0
- v0/relationalai/loaders/loader.py +177 -0
- v0/relationalai/loaders/types.py +23 -0
- v0/relationalai/rel_emitter.py +373 -0
- v0/relationalai/rel_utils.py +185 -0
- v0/relationalai/semantics/__init__.py +29 -0
- v0/relationalai/semantics/devtools/benchmark_lqp.py +536 -0
- v0/relationalai/semantics/devtools/compilation_manager.py +294 -0
- v0/relationalai/semantics/devtools/extract_lqp.py +110 -0
- v0/relationalai/semantics/internal/internal.py +3785 -0
- v0/relationalai/semantics/internal/snowflake.py +324 -0
- v0/relationalai/semantics/lqp/builtins.py +16 -0
- v0/relationalai/semantics/lqp/compiler.py +22 -0
- v0/relationalai/semantics/lqp/constructors.py +68 -0
- v0/relationalai/semantics/lqp/executor.py +469 -0
- v0/relationalai/semantics/lqp/intrinsics.py +24 -0
- v0/relationalai/semantics/lqp/model2lqp.py +839 -0
- v0/relationalai/semantics/lqp/passes.py +680 -0
- v0/relationalai/semantics/lqp/primitives.py +252 -0
- v0/relationalai/semantics/lqp/result_helpers.py +202 -0
- v0/relationalai/semantics/lqp/rewrite/annotate_constraints.py +57 -0
- v0/relationalai/semantics/lqp/rewrite/cdc.py +216 -0
- v0/relationalai/semantics/lqp/rewrite/extract_common.py +338 -0
- v0/relationalai/semantics/lqp/rewrite/extract_keys.py +449 -0
- v0/relationalai/semantics/lqp/rewrite/function_annotations.py +114 -0
- v0/relationalai/semantics/lqp/rewrite/functional_dependencies.py +314 -0
- v0/relationalai/semantics/lqp/rewrite/quantify_vars.py +296 -0
- v0/relationalai/semantics/lqp/rewrite/splinter.py +76 -0
- v0/relationalai/semantics/lqp/types.py +101 -0
- v0/relationalai/semantics/lqp/utils.py +160 -0
- v0/relationalai/semantics/lqp/validators.py +57 -0
- v0/relationalai/semantics/metamodel/__init__.py +40 -0
- v0/relationalai/semantics/metamodel/builtins.py +774 -0
- v0/relationalai/semantics/metamodel/compiler.py +133 -0
- v0/relationalai/semantics/metamodel/dependency.py +862 -0
- v0/relationalai/semantics/metamodel/executor.py +61 -0
- v0/relationalai/semantics/metamodel/factory.py +287 -0
- v0/relationalai/semantics/metamodel/helpers.py +361 -0
- v0/relationalai/semantics/metamodel/rewrite/discharge_constraints.py +39 -0
- v0/relationalai/semantics/metamodel/rewrite/dnf_union_splitter.py +210 -0
- v0/relationalai/semantics/metamodel/rewrite/extract_nested_logicals.py +78 -0
- v0/relationalai/semantics/metamodel/rewrite/flatten.py +549 -0
- v0/relationalai/semantics/metamodel/rewrite/format_outputs.py +165 -0
- v0/relationalai/semantics/metamodel/typer/checker.py +353 -0
- v0/relationalai/semantics/metamodel/typer/typer.py +1395 -0
- v0/relationalai/semantics/reasoners/__init__.py +10 -0
- v0/relationalai/semantics/reasoners/graph/__init__.py +37 -0
- v0/relationalai/semantics/reasoners/graph/core.py +9020 -0
- v0/relationalai/semantics/reasoners/optimization/__init__.py +68 -0
- v0/relationalai/semantics/reasoners/optimization/common.py +88 -0
- v0/relationalai/semantics/reasoners/optimization/solvers_dev.py +568 -0
- v0/relationalai/semantics/reasoners/optimization/solvers_pb.py +1163 -0
- v0/relationalai/semantics/rel/builtins.py +40 -0
- v0/relationalai/semantics/rel/compiler.py +989 -0
- v0/relationalai/semantics/rel/executor.py +359 -0
- v0/relationalai/semantics/rel/rel.py +482 -0
- v0/relationalai/semantics/rel/rel_utils.py +276 -0
- v0/relationalai/semantics/snowflake/__init__.py +3 -0
- v0/relationalai/semantics/sql/compiler.py +2503 -0
- v0/relationalai/semantics/sql/executor/duck_db.py +52 -0
- v0/relationalai/semantics/sql/executor/result_helpers.py +64 -0
- v0/relationalai/semantics/sql/executor/snowflake.py +145 -0
- v0/relationalai/semantics/sql/rewrite/denormalize.py +222 -0
- v0/relationalai/semantics/sql/rewrite/double_negation.py +49 -0
- v0/relationalai/semantics/sql/rewrite/recursive_union.py +127 -0
- v0/relationalai/semantics/sql/rewrite/sort_output_query.py +246 -0
- v0/relationalai/semantics/sql/sql.py +504 -0
- v0/relationalai/semantics/std/__init__.py +54 -0
- v0/relationalai/semantics/std/constraints.py +43 -0
- v0/relationalai/semantics/std/datetime.py +363 -0
- v0/relationalai/semantics/std/decimals.py +62 -0
- v0/relationalai/semantics/std/floats.py +7 -0
- v0/relationalai/semantics/std/integers.py +22 -0
- v0/relationalai/semantics/std/math.py +141 -0
- v0/relationalai/semantics/std/pragmas.py +11 -0
- v0/relationalai/semantics/std/re.py +83 -0
- v0/relationalai/semantics/std/std.py +14 -0
- v0/relationalai/semantics/std/strings.py +63 -0
- v0/relationalai/semantics/tests/__init__.py +0 -0
- v0/relationalai/semantics/tests/test_snapshot_abstract.py +143 -0
- v0/relationalai/semantics/tests/test_snapshot_base.py +9 -0
- v0/relationalai/semantics/tests/utils.py +46 -0
- v0/relationalai/std/__init__.py +70 -0
- v0/relationalai/tools/__init__.py +0 -0
- v0/relationalai/tools/cli.py +1940 -0
- v0/relationalai/tools/cli_controls.py +1826 -0
- v0/relationalai/tools/cli_helpers.py +390 -0
- v0/relationalai/tools/debugger.py +183 -0
- v0/relationalai/tools/debugger_client.py +109 -0
- v0/relationalai/tools/debugger_server.py +302 -0
- v0/relationalai/tools/dev.py +685 -0
- v0/relationalai/tools/qb_debugger.py +425 -0
- v0/relationalai/util/clean_up_databases.py +95 -0
- v0/relationalai/util/format.py +123 -0
- v0/relationalai/util/list_databases.py +9 -0
- v0/relationalai/util/otel_configuration.py +25 -0
- v0/relationalai/util/otel_handler.py +484 -0
- v0/relationalai/util/snowflake_handler.py +88 -0
- v0/relationalai/util/span_format_test.py +43 -0
- v0/relationalai/util/span_tracker.py +207 -0
- v0/relationalai/util/spans_file_handler.py +72 -0
- v0/relationalai/util/tracing_handler.py +34 -0
- frontend/debugger/dist/.gitignore +0 -2
- frontend/debugger/dist/assets/favicon-Dy0ZgA6N.png +0 -0
- frontend/debugger/dist/assets/index-Cssla-O7.js +0 -208
- frontend/debugger/dist/assets/index-DlHsYx1V.css +0 -9
- frontend/debugger/dist/index.html +0 -17
- relationalai/clients/azure.py +0 -477
- relationalai/clients/client.py +0 -912
- relationalai/clients/config.py +0 -673
- relationalai/clients/direct_access_client.py +0 -118
- relationalai/clients/export_procedure.py.jinja +0 -249
- relationalai/clients/hash_util.py +0 -31
- relationalai/clients/local.py +0 -571
- relationalai/clients/profile_polling.py +0 -73
- relationalai/clients/result_helpers.py +0 -420
- relationalai/clients/snowflake.py +0 -3869
- relationalai/clients/types.py +0 -113
- relationalai/clients/use_index_poller.py +0 -980
- relationalai/clients/util.py +0 -356
- relationalai/debugging.py +0 -389
- relationalai/dsl.py +0 -1749
- relationalai/early_access/builder/__init__.py +0 -30
- relationalai/early_access/builder/builder/__init__.py +0 -35
- relationalai/early_access/builder/snowflake/__init__.py +0 -12
- relationalai/early_access/builder/std/__init__.py +0 -25
- relationalai/early_access/builder/std/decimals/__init__.py +0 -12
- relationalai/early_access/builder/std/integers/__init__.py +0 -12
- relationalai/early_access/builder/std/math/__init__.py +0 -12
- relationalai/early_access/builder/std/strings/__init__.py +0 -14
- relationalai/early_access/devtools/__init__.py +0 -12
- relationalai/early_access/devtools/benchmark_lqp/__init__.py +0 -12
- relationalai/early_access/devtools/extract_lqp/__init__.py +0 -12
- relationalai/early_access/dsl/adapters/orm/adapter_qb.py +0 -427
- relationalai/early_access/dsl/adapters/orm/parser.py +0 -636
- relationalai/early_access/dsl/adapters/owl/adapter.py +0 -176
- relationalai/early_access/dsl/adapters/owl/parser.py +0 -160
- relationalai/early_access/dsl/bindings/common.py +0 -402
- relationalai/early_access/dsl/bindings/csv.py +0 -170
- relationalai/early_access/dsl/bindings/legacy/binding_models.py +0 -143
- relationalai/early_access/dsl/bindings/snowflake.py +0 -64
- relationalai/early_access/dsl/codegen/binder.py +0 -411
- relationalai/early_access/dsl/codegen/common.py +0 -79
- relationalai/early_access/dsl/codegen/helpers.py +0 -23
- relationalai/early_access/dsl/codegen/relations.py +0 -700
- relationalai/early_access/dsl/codegen/weaver.py +0 -417
- relationalai/early_access/dsl/core/builders/__init__.py +0 -47
- relationalai/early_access/dsl/core/builders/logic.py +0 -19
- relationalai/early_access/dsl/core/builders/scalar_constraint.py +0 -11
- relationalai/early_access/dsl/core/constraints/predicate/atomic.py +0 -455
- relationalai/early_access/dsl/core/constraints/predicate/universal.py +0 -73
- relationalai/early_access/dsl/core/constraints/scalar.py +0 -310
- relationalai/early_access/dsl/core/context.py +0 -13
- relationalai/early_access/dsl/core/cset.py +0 -132
- relationalai/early_access/dsl/core/exprs/__init__.py +0 -116
- relationalai/early_access/dsl/core/exprs/relational.py +0 -18
- relationalai/early_access/dsl/core/exprs/scalar.py +0 -412
- relationalai/early_access/dsl/core/instances.py +0 -44
- relationalai/early_access/dsl/core/logic/__init__.py +0 -193
- relationalai/early_access/dsl/core/logic/aggregation.py +0 -98
- relationalai/early_access/dsl/core/logic/exists.py +0 -223
- relationalai/early_access/dsl/core/logic/helper.py +0 -163
- relationalai/early_access/dsl/core/namespaces.py +0 -32
- relationalai/early_access/dsl/core/relations.py +0 -276
- relationalai/early_access/dsl/core/rules.py +0 -112
- relationalai/early_access/dsl/core/std/__init__.py +0 -45
- relationalai/early_access/dsl/core/temporal/recall.py +0 -6
- relationalai/early_access/dsl/core/types/__init__.py +0 -270
- relationalai/early_access/dsl/core/types/concepts.py +0 -128
- relationalai/early_access/dsl/core/types/constrained/__init__.py +0 -267
- relationalai/early_access/dsl/core/types/constrained/nominal.py +0 -143
- relationalai/early_access/dsl/core/types/constrained/subtype.py +0 -124
- relationalai/early_access/dsl/core/types/standard.py +0 -92
- relationalai/early_access/dsl/core/types/unconstrained.py +0 -50
- relationalai/early_access/dsl/core/types/variables.py +0 -203
- relationalai/early_access/dsl/ir/compiler.py +0 -318
- relationalai/early_access/dsl/ir/executor.py +0 -260
- relationalai/early_access/dsl/ontologies/constraints.py +0 -88
- relationalai/early_access/dsl/ontologies/export.py +0 -30
- relationalai/early_access/dsl/ontologies/models.py +0 -453
- relationalai/early_access/dsl/ontologies/python_printer.py +0 -303
- relationalai/early_access/dsl/ontologies/readings.py +0 -60
- relationalai/early_access/dsl/ontologies/relationships.py +0 -322
- relationalai/early_access/dsl/ontologies/roles.py +0 -87
- relationalai/early_access/dsl/ontologies/subtyping.py +0 -55
- relationalai/early_access/dsl/orm/constraints.py +0 -438
- relationalai/early_access/dsl/orm/measures/dimensions.py +0 -200
- relationalai/early_access/dsl/orm/measures/initializer.py +0 -16
- relationalai/early_access/dsl/orm/measures/measure_rules.py +0 -275
- relationalai/early_access/dsl/orm/measures/measures.py +0 -299
- relationalai/early_access/dsl/orm/measures/role_exprs.py +0 -268
- relationalai/early_access/dsl/orm/models.py +0 -256
- relationalai/early_access/dsl/orm/object_oriented_printer.py +0 -344
- relationalai/early_access/dsl/orm/printer.py +0 -469
- relationalai/early_access/dsl/orm/reasoners.py +0 -480
- relationalai/early_access/dsl/orm/relations.py +0 -19
- relationalai/early_access/dsl/orm/relationships.py +0 -251
- relationalai/early_access/dsl/orm/types.py +0 -42
- relationalai/early_access/dsl/orm/utils.py +0 -79
- relationalai/early_access/dsl/orm/verb.py +0 -204
- relationalai/early_access/dsl/physical_metadata/tables.py +0 -133
- relationalai/early_access/dsl/relations.py +0 -170
- relationalai/early_access/dsl/rulesets.py +0 -69
- relationalai/early_access/dsl/schemas/__init__.py +0 -450
- relationalai/early_access/dsl/schemas/builder.py +0 -48
- relationalai/early_access/dsl/schemas/comp_names.py +0 -51
- relationalai/early_access/dsl/schemas/components.py +0 -203
- relationalai/early_access/dsl/schemas/contexts.py +0 -156
- relationalai/early_access/dsl/schemas/exprs.py +0 -89
- relationalai/early_access/dsl/schemas/fragments.py +0 -464
- relationalai/early_access/dsl/serialization.py +0 -79
- relationalai/early_access/dsl/serialize/exporter.py +0 -163
- relationalai/early_access/dsl/snow/api.py +0 -104
- relationalai/early_access/dsl/snow/common.py +0 -76
- relationalai/early_access/dsl/state_mgmt/__init__.py +0 -129
- relationalai/early_access/dsl/state_mgmt/state_charts.py +0 -125
- relationalai/early_access/dsl/state_mgmt/transitions.py +0 -130
- relationalai/early_access/dsl/types/__init__.py +0 -40
- relationalai/early_access/dsl/types/concepts.py +0 -12
- relationalai/early_access/dsl/types/entities.py +0 -135
- relationalai/early_access/dsl/types/values.py +0 -17
- relationalai/early_access/dsl/utils.py +0 -102
- relationalai/early_access/graphs/__init__.py +0 -13
- relationalai/early_access/lqp/__init__.py +0 -12
- relationalai/early_access/lqp/compiler/__init__.py +0 -12
- relationalai/early_access/lqp/constructors/__init__.py +0 -18
- relationalai/early_access/lqp/executor/__init__.py +0 -12
- relationalai/early_access/lqp/ir/__init__.py +0 -12
- relationalai/early_access/lqp/passes/__init__.py +0 -12
- relationalai/early_access/lqp/pragmas/__init__.py +0 -12
- relationalai/early_access/lqp/primitives/__init__.py +0 -12
- relationalai/early_access/lqp/types/__init__.py +0 -12
- relationalai/early_access/lqp/utils/__init__.py +0 -12
- relationalai/early_access/lqp/validators/__init__.py +0 -12
- relationalai/early_access/metamodel/__init__.py +0 -58
- relationalai/early_access/metamodel/builtins/__init__.py +0 -12
- relationalai/early_access/metamodel/compiler/__init__.py +0 -12
- relationalai/early_access/metamodel/dependency/__init__.py +0 -12
- relationalai/early_access/metamodel/factory/__init__.py +0 -17
- relationalai/early_access/metamodel/helpers/__init__.py +0 -12
- relationalai/early_access/metamodel/ir/__init__.py +0 -14
- relationalai/early_access/metamodel/rewrite/__init__.py +0 -7
- relationalai/early_access/metamodel/typer/__init__.py +0 -3
- relationalai/early_access/metamodel/typer/typer/__init__.py +0 -12
- relationalai/early_access/metamodel/types/__init__.py +0 -15
- relationalai/early_access/metamodel/util/__init__.py +0 -15
- relationalai/early_access/metamodel/visitor/__init__.py +0 -12
- relationalai/early_access/rel/__init__.py +0 -12
- relationalai/early_access/rel/executor/__init__.py +0 -12
- relationalai/early_access/rel/rel_utils/__init__.py +0 -12
- relationalai/early_access/rel/rewrite/__init__.py +0 -7
- relationalai/early_access/solvers/__init__.py +0 -19
- relationalai/early_access/sql/__init__.py +0 -11
- relationalai/early_access/sql/executor/__init__.py +0 -3
- relationalai/early_access/sql/rewrite/__init__.py +0 -3
- relationalai/early_access/tests/logging/__init__.py +0 -12
- relationalai/early_access/tests/test_snapshot_base/__init__.py +0 -12
- relationalai/early_access/tests/utils/__init__.py +0 -12
- relationalai/environments/__init__.py +0 -35
- relationalai/environments/base.py +0 -381
- relationalai/environments/colab.py +0 -14
- relationalai/environments/generic.py +0 -71
- relationalai/environments/ipython.py +0 -68
- relationalai/environments/jupyter.py +0 -9
- relationalai/environments/snowbook.py +0 -169
- relationalai/errors.py +0 -2455
- relationalai/experimental/SF.py +0 -38
- relationalai/experimental/inspect.py +0 -47
- relationalai/experimental/pathfinder/__init__.py +0 -158
- relationalai/experimental/pathfinder/api.py +0 -160
- relationalai/experimental/pathfinder/automaton.py +0 -584
- relationalai/experimental/pathfinder/bridge.py +0 -226
- relationalai/experimental/pathfinder/compiler.py +0 -416
- relationalai/experimental/pathfinder/datalog.py +0 -214
- relationalai/experimental/pathfinder/diagnostics.py +0 -56
- relationalai/experimental/pathfinder/filter.py +0 -236
- relationalai/experimental/pathfinder/glushkov.py +0 -439
- relationalai/experimental/pathfinder/options.py +0 -265
- relationalai/experimental/pathfinder/pathfinder-v0.7.0.rel +0 -1951
- relationalai/experimental/pathfinder/rpq.py +0 -344
- relationalai/experimental/pathfinder/transition.py +0 -200
- relationalai/experimental/pathfinder/utils.py +0 -26
- relationalai/experimental/paths/README.md +0 -107
- relationalai/experimental/paths/api.py +0 -143
- relationalai/experimental/paths/benchmarks/grid_graph.py +0 -37
- relationalai/experimental/paths/code_organization.md +0 -2
- relationalai/experimental/paths/examples/Movies.ipynb +0 -16328
- relationalai/experimental/paths/examples/basic_example.py +0 -40
- relationalai/experimental/paths/examples/minimal_engine_warmup.py +0 -3
- relationalai/experimental/paths/examples/movie_example.py +0 -77
- relationalai/experimental/paths/examples/movies_data/actedin.csv +0 -193
- relationalai/experimental/paths/examples/movies_data/directed.csv +0 -45
- relationalai/experimental/paths/examples/movies_data/follows.csv +0 -7
- relationalai/experimental/paths/examples/movies_data/movies.csv +0 -39
- relationalai/experimental/paths/examples/movies_data/person.csv +0 -134
- relationalai/experimental/paths/examples/movies_data/produced.csv +0 -16
- relationalai/experimental/paths/examples/movies_data/ratings.csv +0 -10
- relationalai/experimental/paths/examples/movies_data/wrote.csv +0 -11
- relationalai/experimental/paths/examples/paths_benchmark.py +0 -115
- relationalai/experimental/paths/examples/paths_example.py +0 -116
- relationalai/experimental/paths/examples/pattern_to_automaton.py +0 -28
- relationalai/experimental/paths/find_paths_via_automaton.py +0 -85
- relationalai/experimental/paths/graph.py +0 -185
- relationalai/experimental/paths/path_algorithms/find_paths.py +0 -280
- relationalai/experimental/paths/path_algorithms/one_sided_ball_repetition.py +0 -26
- relationalai/experimental/paths/path_algorithms/one_sided_ball_upto.py +0 -111
- relationalai/experimental/paths/path_algorithms/single.py +0 -59
- relationalai/experimental/paths/path_algorithms/two_sided_balls_repetition.py +0 -39
- relationalai/experimental/paths/path_algorithms/two_sided_balls_upto.py +0 -103
- relationalai/experimental/paths/path_algorithms/usp-old.py +0 -130
- relationalai/experimental/paths/path_algorithms/usp-tuple.py +0 -183
- relationalai/experimental/paths/path_algorithms/usp.py +0 -150
- relationalai/experimental/paths/product_graph.py +0 -93
- relationalai/experimental/paths/rpq/automaton.py +0 -584
- relationalai/experimental/paths/rpq/diagnostics.py +0 -56
- relationalai/experimental/paths/rpq/rpq.py +0 -378
- relationalai/experimental/paths/tests/tests_limit_sp_max_length.py +0 -90
- relationalai/experimental/paths/tests/tests_limit_sp_multiple.py +0 -119
- relationalai/experimental/paths/tests/tests_limit_sp_single.py +0 -104
- relationalai/experimental/paths/tests/tests_limit_walks_multiple.py +0 -113
- relationalai/experimental/paths/tests/tests_limit_walks_single.py +0 -149
- relationalai/experimental/paths/tests/tests_one_sided_ball_repetition_multiple.py +0 -70
- relationalai/experimental/paths/tests/tests_one_sided_ball_repetition_single.py +0 -64
- relationalai/experimental/paths/tests/tests_one_sided_ball_upto_multiple.py +0 -115
- relationalai/experimental/paths/tests/tests_one_sided_ball_upto_single.py +0 -75
- relationalai/experimental/paths/tests/tests_single_paths.py +0 -152
- relationalai/experimental/paths/tests/tests_single_walks.py +0 -208
- relationalai/experimental/paths/tests/tests_single_walks_undirected.py +0 -297
- relationalai/experimental/paths/tests/tests_two_sided_balls_repetition_multiple.py +0 -107
- relationalai/experimental/paths/tests/tests_two_sided_balls_repetition_single.py +0 -76
- relationalai/experimental/paths/tests/tests_two_sided_balls_upto_multiple.py +0 -76
- relationalai/experimental/paths/tests/tests_two_sided_balls_upto_single.py +0 -110
- relationalai/experimental/paths/tests/tests_usp_nsp_multiple.py +0 -229
- relationalai/experimental/paths/tests/tests_usp_nsp_single.py +0 -108
- relationalai/experimental/paths/tree_agg.py +0 -168
- relationalai/experimental/paths/utilities/iterators.py +0 -27
- relationalai/experimental/paths/utilities/prefix_sum.py +0 -91
- relationalai/experimental/solvers.py +0 -1087
- relationalai/loaders/csv.py +0 -195
- relationalai/loaders/loader.py +0 -177
- relationalai/loaders/types.py +0 -23
- relationalai/rel_emitter.py +0 -373
- relationalai/rel_utils.py +0 -185
- relationalai/semantics/designs/query_builder/identify_by.md +0 -106
- relationalai/semantics/devtools/benchmark_lqp.py +0 -536
- relationalai/semantics/devtools/compilation_manager.py +0 -294
- relationalai/semantics/devtools/extract_lqp.py +0 -110
- relationalai/semantics/internal/internal.py +0 -3785
- relationalai/semantics/internal/snowflake.py +0 -324
- relationalai/semantics/lqp/README.md +0 -34
- relationalai/semantics/lqp/builtins.py +0 -16
- relationalai/semantics/lqp/compiler.py +0 -22
- relationalai/semantics/lqp/constructors.py +0 -68
- relationalai/semantics/lqp/executor.py +0 -469
- relationalai/semantics/lqp/intrinsics.py +0 -24
- relationalai/semantics/lqp/model2lqp.py +0 -839
- relationalai/semantics/lqp/passes.py +0 -680
- relationalai/semantics/lqp/primitives.py +0 -252
- relationalai/semantics/lqp/result_helpers.py +0 -202
- relationalai/semantics/lqp/rewrite/annotate_constraints.py +0 -57
- relationalai/semantics/lqp/rewrite/cdc.py +0 -216
- relationalai/semantics/lqp/rewrite/extract_common.py +0 -338
- relationalai/semantics/lqp/rewrite/extract_keys.py +0 -449
- relationalai/semantics/lqp/rewrite/function_annotations.py +0 -114
- relationalai/semantics/lqp/rewrite/functional_dependencies.py +0 -314
- relationalai/semantics/lqp/rewrite/quantify_vars.py +0 -296
- relationalai/semantics/lqp/rewrite/splinter.py +0 -76
- relationalai/semantics/lqp/types.py +0 -101
- relationalai/semantics/lqp/utils.py +0 -160
- relationalai/semantics/lqp/validators.py +0 -57
- relationalai/semantics/metamodel/compiler.py +0 -133
- relationalai/semantics/metamodel/dependency.py +0 -862
- relationalai/semantics/metamodel/executor.py +0 -61
- relationalai/semantics/metamodel/factory.py +0 -287
- relationalai/semantics/metamodel/helpers.py +0 -361
- relationalai/semantics/metamodel/rewrite/discharge_constraints.py +0 -39
- relationalai/semantics/metamodel/rewrite/dnf_union_splitter.py +0 -210
- relationalai/semantics/metamodel/rewrite/extract_nested_logicals.py +0 -78
- relationalai/semantics/metamodel/rewrite/flatten.py +0 -549
- relationalai/semantics/metamodel/rewrite/format_outputs.py +0 -165
- relationalai/semantics/metamodel/typer/checker.py +0 -353
- relationalai/semantics/metamodel/typer/typer.py +0 -1395
- relationalai/semantics/reasoners/__init__.py +0 -10
- relationalai/semantics/reasoners/graph/README.md +0 -620
- relationalai/semantics/reasoners/graph/__init__.py +0 -37
- relationalai/semantics/reasoners/graph/core.py +0 -9020
- relationalai/semantics/reasoners/graph/design/beyond_demand_transform.md +0 -797
- relationalai/semantics/reasoners/graph/tests/README.md +0 -21
- relationalai/semantics/reasoners/optimization/__init__.py +0 -68
- relationalai/semantics/reasoners/optimization/common.py +0 -88
- relationalai/semantics/reasoners/optimization/solvers_dev.py +0 -568
- relationalai/semantics/reasoners/optimization/solvers_pb.py +0 -1163
- relationalai/semantics/rel/builtins.py +0 -40
- relationalai/semantics/rel/compiler.py +0 -989
- relationalai/semantics/rel/executor.py +0 -359
- relationalai/semantics/rel/rel.py +0 -482
- relationalai/semantics/rel/rel_utils.py +0 -276
- relationalai/semantics/snowflake/__init__.py +0 -3
- relationalai/semantics/sql/compiler.py +0 -2503
- relationalai/semantics/sql/executor/duck_db.py +0 -52
- relationalai/semantics/sql/executor/result_helpers.py +0 -64
- relationalai/semantics/sql/executor/snowflake.py +0 -145
- relationalai/semantics/sql/rewrite/denormalize.py +0 -222
- relationalai/semantics/sql/rewrite/double_negation.py +0 -49
- relationalai/semantics/sql/rewrite/recursive_union.py +0 -127
- relationalai/semantics/sql/rewrite/sort_output_query.py +0 -246
- relationalai/semantics/sql/sql.py +0 -504
- relationalai/semantics/std/pragmas.py +0 -11
- relationalai/semantics/std/std.py +0 -14
- relationalai/semantics/tests/test_snapshot_abstract.py +0 -143
- relationalai/semantics/tests/test_snapshot_base.py +0 -9
- relationalai/semantics/tests/utils.py +0 -46
- relationalai/std/__init__.py +0 -70
- relationalai/tools/cli.py +0 -1940
- relationalai/tools/cli_controls.py +0 -1826
- relationalai/tools/cli_helpers.py +0 -390
- relationalai/tools/debugger_client.py +0 -109
- relationalai/tools/debugger_server.py +0 -302
- relationalai/tools/dev.py +0 -685
- relationalai/tools/notes +0 -7
- relationalai/tools/qb_debugger.py +0 -425
- relationalai/util/clean_up_databases.py +0 -95
- relationalai/util/list_databases.py +0 -9
- relationalai/util/otel_configuration.py +0 -25
- relationalai/util/otel_handler.py +0 -484
- relationalai/util/snowflake_handler.py +0 -88
- relationalai/util/span_format_test.py +0 -43
- relationalai/util/span_tracker.py +0 -207
- relationalai/util/spans_file_handler.py +0 -72
- relationalai/util/tracing_handler.py +0 -34
- relationalai-0.12.13.dist-info/METADATA +0 -74
- relationalai-0.12.13.dist-info/RECORD +0 -449
- relationalai-0.12.13.dist-info/WHEEL +0 -4
- relationalai-0.12.13.dist-info/entry_points.txt +0 -3
- relationalai-0.12.13.dist-info/licenses/LICENSE +0 -202
- relationalai_test_util/__init__.py +0 -4
- relationalai_test_util/fixtures.py +0 -228
- relationalai_test_util/snapshot.py +0 -252
- relationalai_test_util/traceback.py +0 -118
- /relationalai/{analysis → semantics/frontend}/__init__.py +0 -0
- /relationalai/{auth/__init__.py → semantics/metamodel/metamodel_compiler.py} +0 -0
- /relationalai/{early_access → shims}/__init__.py +0 -0
- {relationalai/early_access/dsl/adapters → v0/relationalai/analysis}/__init__.py +0 -0
- {relationalai → v0/relationalai}/analysis/mechanistic.py +0 -0
- {relationalai → v0/relationalai}/analysis/whynot.py +0 -0
- {relationalai/early_access/dsl/adapters/orm → v0/relationalai/auth}/__init__.py +0 -0
- {relationalai → v0/relationalai}/auth/jwt_generator.py +0 -0
- {relationalai → v0/relationalai}/auth/oauth_callback_server.py +0 -0
- {relationalai → v0/relationalai}/auth/token_handler.py +0 -0
- {relationalai → v0/relationalai}/auth/util.py +0 -0
- {relationalai → v0/relationalai}/clients/__init__.py +0 -0
- {relationalai → v0/relationalai}/clients/cache_store.py +0 -0
- {relationalai → v0/relationalai}/compiler.py +0 -0
- {relationalai → v0/relationalai}/dependencies.py +0 -0
- {relationalai → v0/relationalai}/docutils.py +0 -0
- {relationalai/early_access/dsl/adapters/owl → v0/relationalai/early_access}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/__init__.py +0 -0
- {relationalai/early_access/dsl/bindings → v0/relationalai/early_access/dsl/adapters}/__init__.py +0 -0
- {relationalai/early_access/dsl/bindings/legacy → v0/relationalai/early_access/dsl/adapters/orm}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/adapters/orm/model.py +0 -0
- {relationalai/early_access/dsl/codegen → v0/relationalai/early_access/dsl/adapters/owl}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/adapters/owl/model.py +0 -0
- {relationalai/early_access/dsl/core/temporal → v0/relationalai/early_access/dsl/bindings}/__init__.py +0 -0
- {relationalai/early_access/dsl/ir → v0/relationalai/early_access/dsl/bindings/legacy}/__init__.py +0 -0
- {relationalai/early_access/dsl/ontologies → v0/relationalai/early_access/dsl/codegen}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/constants.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/core/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/core/constraints/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/core/constraints/predicate/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/core/stack.py +0 -0
- {relationalai/early_access/dsl/orm → v0/relationalai/early_access/dsl/core/temporal}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/core/utils.py +0 -0
- {relationalai/early_access/dsl/orm/measures → v0/relationalai/early_access/dsl/ir}/__init__.py +0 -0
- {relationalai/early_access/dsl/physical_metadata → v0/relationalai/early_access/dsl/ontologies}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/ontologies/raw_source.py +0 -0
- {relationalai/early_access/dsl/serialize → v0/relationalai/early_access/dsl/orm}/__init__.py +0 -0
- {relationalai/early_access/dsl/snow → v0/relationalai/early_access/dsl/orm/measures}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/orm/reasoner_errors.py +0 -0
- {relationalai/loaders → v0/relationalai/early_access/dsl/physical_metadata}/__init__.py +0 -0
- {relationalai/semantics/tests → v0/relationalai/early_access/dsl/serialize}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/serialize/binding_model.py +0 -0
- {relationalai → v0/relationalai}/early_access/dsl/serialize/model.py +0 -0
- {relationalai/tools → v0/relationalai/early_access/dsl/snow}/__init__.py +0 -0
- {relationalai → v0/relationalai}/early_access/tests/__init__.py +0 -0
- {relationalai → v0/relationalai}/environments/ci.py +0 -0
- {relationalai → v0/relationalai}/environments/hex.py +0 -0
- {relationalai → v0/relationalai}/environments/terminal.py +0 -0
- {relationalai → v0/relationalai}/experimental/__init__.py +0 -0
- {relationalai → v0/relationalai}/experimental/graphs.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/__init__.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/benchmarks/__init__.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/path_algorithms/__init__.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/rpq/__init__.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/rpq/filter.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/rpq/glushkov.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/rpq/transition.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/utilities/__init__.py +0 -0
- {relationalai → v0/relationalai}/experimental/paths/utilities/utilities.py +0 -0
- {relationalai → v0/relationalai}/metagen.py +0 -0
- {relationalai → v0/relationalai}/metamodel.py +0 -0
- {relationalai → v0/relationalai}/rel.py +0 -0
- {relationalai → v0/relationalai}/semantics/devtools/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/internal/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/internal/annotations.py +0 -0
- {relationalai → v0/relationalai}/semantics/lqp/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/lqp/ir.py +0 -0
- {relationalai → v0/relationalai}/semantics/lqp/pragmas.py +0 -0
- {relationalai → v0/relationalai}/semantics/lqp/rewrite/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/dataflow.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/ir.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/rewrite/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/typer/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/types.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/util.py +0 -0
- {relationalai → v0/relationalai}/semantics/metamodel/visitor.py +0 -0
- {relationalai → v0/relationalai}/semantics/reasoners/experimental/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/rel/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/sql/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/sql/executor/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/sql/rewrite/__init__.py +0 -0
- {relationalai → v0/relationalai}/semantics/tests/logging.py +0 -0
- {relationalai → v0/relationalai}/std/aggregates.py +0 -0
- {relationalai → v0/relationalai}/std/dates.py +0 -0
- {relationalai → v0/relationalai}/std/graphs.py +0 -0
- {relationalai → v0/relationalai}/std/inspect.py +0 -0
- {relationalai → v0/relationalai}/std/math.py +0 -0
- {relationalai → v0/relationalai}/std/re.py +0 -0
- {relationalai → v0/relationalai}/std/strings.py +0 -0
- {relationalai → v0/relationalai}/tools/cleanup_snapshots.py +0 -0
- {relationalai → v0/relationalai}/tools/constants.py +0 -0
- {relationalai → v0/relationalai}/tools/query_utils.py +0 -0
- {relationalai → v0/relationalai}/tools/snapshot_viewer.py +0 -0
- {relationalai → v0/relationalai}/util/__init__.py +0 -0
- {relationalai → v0/relationalai}/util/constants.py +0 -0
- {relationalai → v0/relationalai}/util/graph.py +0 -0
- {relationalai → v0/relationalai}/util/timeout.py +0 -0
|
@@ -0,0 +1,361 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Helpers to analyze the metamodel IR.
|
|
3
|
+
"""
|
|
4
|
+
from __future__ import annotations
|
|
5
|
+
|
|
6
|
+
import re
|
|
7
|
+
from dataclasses import fields
|
|
8
|
+
from typing import cast, Tuple, Iterable, Optional, TypeVar
|
|
9
|
+
from v0.relationalai.semantics.metamodel import ir, visitor, builtins, types, factory as f
|
|
10
|
+
from v0.relationalai.semantics.metamodel.util import NameCache, OrderedSet, FrozenOrderedSet, flatten_tuple, ordered_set
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
#--------------------------------------------------
|
|
15
|
+
# Name helpers
|
|
16
|
+
#--------------------------------------------------
|
|
17
|
+
|
|
18
|
+
def sanitize(name:str) -> str:
|
|
19
|
+
""" Cleanup the name to make it more palatable to names. """
|
|
20
|
+
x = re.sub(r"[ ,\.\(\)\|]", "_", name)
|
|
21
|
+
return x[0:-1] if x[-1] == "_" else x
|
|
22
|
+
|
|
23
|
+
#--------------------------------------------------
|
|
24
|
+
# Checks
|
|
25
|
+
#--------------------------------------------------
|
|
26
|
+
|
|
27
|
+
def is_concept_lookup(node: ir.Lookup|ir.Relation):
|
|
28
|
+
""" Whether this task is a concept lookup. """
|
|
29
|
+
if isinstance(node, ir.Lookup) and is_concept_lookup(node.relation):
|
|
30
|
+
return True
|
|
31
|
+
return builtins.concept_relation_annotation in node.annotations
|
|
32
|
+
|
|
33
|
+
def is_external(relation: ir.Relation):
|
|
34
|
+
""" Whether this relation is external, by being marked with the external annotation. """
|
|
35
|
+
return builtins.external_annotation in relation.annotations
|
|
36
|
+
|
|
37
|
+
def is_from_cast(node: ir.Lookup|ir.Relation):
|
|
38
|
+
""" Whether this relation is from cast, by being marked with the from_cast_annotation annotation. """
|
|
39
|
+
if isinstance(node, ir.Lookup) and is_from_cast(node.relation):
|
|
40
|
+
return True
|
|
41
|
+
return builtins.from_cast_annotation in node.annotations
|
|
42
|
+
|
|
43
|
+
def is_aggregate_input(var: ir.Var, agg: ir.Aggregate):
|
|
44
|
+
""" Whether this var is an input to this aggregation. """
|
|
45
|
+
return (var in agg.args and agg.aggregation.fields[agg.args.index(var)].input)
|
|
46
|
+
|
|
47
|
+
def is_effective_logical(n: ir.Task):
|
|
48
|
+
""" Whether this task is a Logical and contains an Update child, recursively. """
|
|
49
|
+
return isinstance(n, ir.Logical) and len(visitor.collect_by_type(ir.Update, n)) > 0
|
|
50
|
+
|
|
51
|
+
def is_nullable_logical(n: ir.Task):
|
|
52
|
+
""" Whether this task is a Logical that contains a hoisted variable with a None default. """
|
|
53
|
+
return isinstance(n, ir.Logical) and any(isinstance(v, ir.Default) and v.value is None for v in n.hoisted)
|
|
54
|
+
|
|
55
|
+
def relation_is_subtype(r1: ir.Relation, r2: ir.Relation):
|
|
56
|
+
if r1 is r2:
|
|
57
|
+
return True
|
|
58
|
+
if len(r1.fields) != len(r2.fields):
|
|
59
|
+
return False
|
|
60
|
+
return all(types.is_subtype(f1.type, f2.type) for f1, f2 in zip(r1.fields, r2.fields))
|
|
61
|
+
|
|
62
|
+
def relation_is_proper_subtype(r1: ir.Relation, r2: ir.Relation):
|
|
63
|
+
if r1 is r2:
|
|
64
|
+
return False
|
|
65
|
+
if relation_is_subtype(r1, r2):
|
|
66
|
+
return any(types.is_proper_subtype(f1.type, f2.type) for f1, f2 in zip(r1.fields, r2.fields))
|
|
67
|
+
else:
|
|
68
|
+
return False
|
|
69
|
+
|
|
70
|
+
def relation_name_prefix(relation: ir.Relation):
|
|
71
|
+
prefix = ""
|
|
72
|
+
if len(relation.fields) > 0 and not is_concept_lookup(relation):
|
|
73
|
+
main_type = relation.fields[0].type
|
|
74
|
+
if (isinstance(main_type, ir.ScalarType) and
|
|
75
|
+
main_type not in types.builtin_types and
|
|
76
|
+
not relation.name.startswith(main_type.name) and
|
|
77
|
+
not relation.name.startswith("_")):
|
|
78
|
+
prefix = f"{main_type.name.lower()}_"
|
|
79
|
+
return prefix
|
|
80
|
+
|
|
81
|
+
def get_outputs(lookup: ir.Lookup):
|
|
82
|
+
"""
|
|
83
|
+
Return an array with the arguments of this lookup that are referring to output fields
|
|
84
|
+
on the relation being looked up.
|
|
85
|
+
"""
|
|
86
|
+
if builtins.is_eq(lookup.relation):
|
|
87
|
+
# special case eq because it can be input or output
|
|
88
|
+
x, y = lookup.args[0], lookup.args[1]
|
|
89
|
+
if isinstance(x, ir.Var) and not isinstance(y, ir.Var):
|
|
90
|
+
return [x]
|
|
91
|
+
elif not isinstance(x, ir.Var) and isinstance(y, ir.Var):
|
|
92
|
+
return [y]
|
|
93
|
+
# both are inputs
|
|
94
|
+
return []
|
|
95
|
+
else:
|
|
96
|
+
outputs = []
|
|
97
|
+
# register variables depending on the input flag of the relation bound to the lookup
|
|
98
|
+
for idx, fld in enumerate(lookup.relation.fields):
|
|
99
|
+
arg = lookup.args[idx]
|
|
100
|
+
if isinstance(arg, Iterable):
|
|
101
|
+
# deal with ListType fields that pack arguments in a tuple
|
|
102
|
+
for element in arg:
|
|
103
|
+
if isinstance(element, ir.Var) and not fld.input:
|
|
104
|
+
outputs.append(element)
|
|
105
|
+
else:
|
|
106
|
+
if isinstance(arg, ir.Var) and not fld.input:
|
|
107
|
+
outputs.append(arg)
|
|
108
|
+
return outputs
|
|
109
|
+
|
|
110
|
+
def get_agg_outputs(lookup: ir.Aggregate):
|
|
111
|
+
"""
|
|
112
|
+
Return an array with the arguments of this aggregate that are referring to output fields
|
|
113
|
+
on the relation being looked up.
|
|
114
|
+
"""
|
|
115
|
+
outputs = []
|
|
116
|
+
# register variables depending on the input flag of the relation bound to the lookup
|
|
117
|
+
for idx, fld in enumerate(lookup.aggregation.fields):
|
|
118
|
+
arg = lookup.args[idx]
|
|
119
|
+
if isinstance(arg, Iterable):
|
|
120
|
+
# deal with ListType fields that pack arguments in a tuple
|
|
121
|
+
for element in arg:
|
|
122
|
+
if isinstance(element, ir.Var) and not fld.input:
|
|
123
|
+
outputs.append(element)
|
|
124
|
+
else:
|
|
125
|
+
if isinstance(arg, ir.Var) and not fld.input:
|
|
126
|
+
outputs.append(arg)
|
|
127
|
+
return outputs
|
|
128
|
+
|
|
129
|
+
#--------------------------------------------------
|
|
130
|
+
# Filters
|
|
131
|
+
#--------------------------------------------------
|
|
132
|
+
|
|
133
|
+
def aggregate_outputs(agg: ir.Aggregate) -> list[ir.Var]:
|
|
134
|
+
""" Get the list of vars bound to the outputs of this aggregation. """
|
|
135
|
+
return list(filter(lambda arg: isinstance(arg, ir.Var) and not is_aggregate_input(arg, agg), agg.args)) # type: ignore
|
|
136
|
+
|
|
137
|
+
def aggregate_inputs(agg: ir.Aggregate) -> list[ir.Var]:
|
|
138
|
+
""" Get the list of vars bound to the args that are inputs of this aggregation. """
|
|
139
|
+
return list(filter(lambda arg: isinstance(arg, ir.Var) and is_aggregate_input(arg, agg), agg.args)) # type: ignore
|
|
140
|
+
|
|
141
|
+
def effective_logicals(tasks: OrderedSet[ir.Task]) -> OrderedSet[ir.Logical]:
|
|
142
|
+
""" Filter tasks to return only the Logical tasks that are effective. """
|
|
143
|
+
return OrderedSet.from_iterable(filter(lambda t: is_effective_logical(t), tasks))
|
|
144
|
+
|
|
145
|
+
def nullable_logicals(tasks: OrderedSet[ir.Task]) -> OrderedSet[ir.Logical]:
|
|
146
|
+
""" Filter tasks to return only the Logical tasks that are nullable. """
|
|
147
|
+
return OrderedSet.from_iterable(filter(lambda t: is_nullable_logical(t), tasks))
|
|
148
|
+
|
|
149
|
+
def hoisted_vars(hoisted: Iterable[ir.VarOrDefault]) -> list[ir.Var]:
|
|
150
|
+
""" Extract the vars from defaults in the hoisted list, returning just Vars. """
|
|
151
|
+
return [hoisted_var(v) for v in hoisted]
|
|
152
|
+
|
|
153
|
+
def hoisted_var(hoisted: ir.VarOrDefault) -> ir.Var:
|
|
154
|
+
""" Extract the var from VarOrDefault, returning just Var. """
|
|
155
|
+
return hoisted.var if isinstance(hoisted, ir.Default) else hoisted
|
|
156
|
+
|
|
157
|
+
def vars(args: Tuple[ir.Value, ...]) -> list[ir.Var]:
|
|
158
|
+
""" Filter this list of values, keeping only Vars. """
|
|
159
|
+
return cast(list[ir.Var], list(filter(lambda v: isinstance(v, ir.Var), flatten_tuple(args, ir.Value))))
|
|
160
|
+
|
|
161
|
+
def output_vars(aliases: FrozenOrderedSet[Tuple[str, ir.Value]]) -> list[ir.Var]:
|
|
162
|
+
return [alias[1] for alias in aliases if isinstance(alias[1], ir.Var)]
|
|
163
|
+
|
|
164
|
+
def output_values(aliases: FrozenOrderedSet[Tuple[str, ir.Value]]) -> list[ir.Value]:
|
|
165
|
+
return [alias[1] for alias in aliases]
|
|
166
|
+
|
|
167
|
+
def output_alias_names(aliases: FrozenOrderedSet[Tuple[str, ir.Value]]) -> list[str]:
|
|
168
|
+
return [alias[0] for alias in aliases]
|
|
169
|
+
|
|
170
|
+
#--------------------------------------------------
|
|
171
|
+
# Visitors/Collectors
|
|
172
|
+
#--------------------------------------------------
|
|
173
|
+
|
|
174
|
+
def collect_vars(*nodes: ir.Node) -> OrderedSet[ir.Var]:
|
|
175
|
+
""" Collect all Vars starting at this node. """
|
|
176
|
+
return cast(OrderedSet[ir.Var],
|
|
177
|
+
visitor.collect_by_type(ir.Var, *nodes)
|
|
178
|
+
)
|
|
179
|
+
|
|
180
|
+
def collect_quantified_vars(*nodes: ir.Node) -> OrderedSet[ir.Var]:
|
|
181
|
+
""" Collect all Vars that are children of Exists and ForAll. """
|
|
182
|
+
return cast(OrderedSet[ir.Var],
|
|
183
|
+
visitor.collect(
|
|
184
|
+
lambda n, parent: isinstance(n, ir.Var) and isinstance(parent, (ir.Exists, ir.ForAll)),
|
|
185
|
+
*nodes)
|
|
186
|
+
)
|
|
187
|
+
|
|
188
|
+
def collect_aggregate_vars(*nodes: ir.Node) -> OrderedSet[ir.Var]:
|
|
189
|
+
""" Collect vars that are declared by aggregates in Rel (projection + over). """
|
|
190
|
+
return cast(OrderedSet[ir.Var],
|
|
191
|
+
# TODO - when dealing with multiple aggregations we will need to consider groupbys
|
|
192
|
+
visitor.collect(
|
|
193
|
+
lambda n, parent:
|
|
194
|
+
# parent of var is an aggregate and either
|
|
195
|
+
isinstance(parent, ir.Aggregate) and isinstance(n, ir.Var) and (
|
|
196
|
+
# var is in the projection
|
|
197
|
+
n in parent.projection or
|
|
198
|
+
# var is an input to the aggregation's relation
|
|
199
|
+
is_aggregate_input(n, parent)
|
|
200
|
+
),
|
|
201
|
+
*nodes)
|
|
202
|
+
)
|
|
203
|
+
|
|
204
|
+
def collect_rank_vars(*nodes: ir.Node) -> OrderedSet[ir.Var]:
|
|
205
|
+
""" Collect vars that are declared by ranks in Rel (projection + over). """
|
|
206
|
+
return cast(OrderedSet[ir.Var],
|
|
207
|
+
# TODO - when dealing with multiple aggregations we will need to consider groupbys
|
|
208
|
+
visitor.collect(
|
|
209
|
+
lambda n, parent:
|
|
210
|
+
# parent of var is an aggregate and either
|
|
211
|
+
isinstance(parent, ir.Rank) and isinstance(n, ir.Var) and (
|
|
212
|
+
# var is in the projection
|
|
213
|
+
n in parent.projection or
|
|
214
|
+
n in parent.args
|
|
215
|
+
),
|
|
216
|
+
*nodes)
|
|
217
|
+
)
|
|
218
|
+
|
|
219
|
+
def collect_implicit_vars(*nodes: ir.Node) -> OrderedSet[ir.Var]:
|
|
220
|
+
""" Collect vars except the quantified and aggregate vars. """
|
|
221
|
+
if not nodes:
|
|
222
|
+
return ordered_set()
|
|
223
|
+
return collect_vars(*nodes) - collect_quantified_vars(*nodes) - collect_aggregate_vars(*nodes) - collect_rank_vars(*nodes)
|
|
224
|
+
|
|
225
|
+
#--------------------------------------------------
|
|
226
|
+
# Useful node categories
|
|
227
|
+
#--------------------------------------------------
|
|
228
|
+
|
|
229
|
+
BINDERS = (ir.Lookup, ir.Construct, ir.Aggregate, ir.Exists, ir.Data, ir.Not)
|
|
230
|
+
COMPOSITES = (ir.Logical, ir.Sequence, ir.Union, ir.Match, ir.Until, ir.Wait)
|
|
231
|
+
EFFECTS = (ir.Update, ir.Output)
|
|
232
|
+
|
|
233
|
+
#--------------------------------------------------
|
|
234
|
+
# Helper classes
|
|
235
|
+
#--------------------------------------------------
|
|
236
|
+
|
|
237
|
+
class RewriteContext():
|
|
238
|
+
"""
|
|
239
|
+
Container of information collected during a rewrite pass.
|
|
240
|
+
"""
|
|
241
|
+
def __init__(self):
|
|
242
|
+
# the logicals that will be at the top level at the end of the rewrite
|
|
243
|
+
self.top_level: list[ir.Logical] = []
|
|
244
|
+
# new relations created during the pass
|
|
245
|
+
self.relations: list[ir.Relation] = []
|
|
246
|
+
|
|
247
|
+
|
|
248
|
+
#--------------------------------------------------
|
|
249
|
+
# Rewrite helpers
|
|
250
|
+
#--------------------------------------------------
|
|
251
|
+
|
|
252
|
+
def extract(task: ir.Task, body: OrderedSet[ir.Task], exposed_vars: list[ir.Var], ctx: RewriteContext, name: str) -> ir.Relation:
|
|
253
|
+
"""
|
|
254
|
+
Extract into this Analysiscontext a new top level Logical that contains this body plus a
|
|
255
|
+
derive task into a new temporary relation, which is also registered with the ctx.
|
|
256
|
+
The exposed_vars determine the arguments of this temporary relation. The prefix
|
|
257
|
+
can be used to customize the name of the relation, which defaults to the task kind.
|
|
258
|
+
|
|
259
|
+
Return the temporary relation created for the extraction.
|
|
260
|
+
"""
|
|
261
|
+
connection = create_connection_relation(task, exposed_vars, ctx, name)
|
|
262
|
+
|
|
263
|
+
# add derivation to the extracted body
|
|
264
|
+
body.add(f.derive(connection, exposed_vars))
|
|
265
|
+
|
|
266
|
+
# extract the body
|
|
267
|
+
ctx.top_level.append(clone_task(ir.Logical(task.engine, tuple(), tuple(body))))
|
|
268
|
+
|
|
269
|
+
return connection
|
|
270
|
+
|
|
271
|
+
def create_connection_relation(task: ir.Task, exposed_vars: list[ir.Var], ctx: RewriteContext, name: str) -> ir.Relation:
|
|
272
|
+
"""
|
|
273
|
+
Create a new relation with a name based off this task, with fields that represent
|
|
274
|
+
the types and names of these exposed vars, and register in the context.
|
|
275
|
+
"""
|
|
276
|
+
connection = f.relation(name, [f.field(v.name, v.type) for v in exposed_vars])
|
|
277
|
+
ctx.relations.append(connection)
|
|
278
|
+
|
|
279
|
+
return connection
|
|
280
|
+
|
|
281
|
+
|
|
282
|
+
def create_task_name(name_cache: NameCache, task: ir.Task, prefix: Optional[str]=None) -> str:
|
|
283
|
+
""" Helper to generate consistent names for tasks extracted from a logical. """
|
|
284
|
+
prefix = prefix if prefix else f"_{task.kind}"
|
|
285
|
+
return name_cache.get_name(task.id, prefix)
|
|
286
|
+
|
|
287
|
+
|
|
288
|
+
CLONABLE = (ir.Var, ir.Default, ir.Task)
|
|
289
|
+
T = TypeVar('T', bound=ir.Task)
|
|
290
|
+
def clone_task(task: T) -> T:
|
|
291
|
+
"""
|
|
292
|
+
Create a new task that is a clone of this task. This operation clones only sub-tasks
|
|
293
|
+
and variables, and preserves variable references.
|
|
294
|
+
|
|
295
|
+
This is useful when we are rewriting the metamodel and want to copy parts of a task to
|
|
296
|
+
some other place. It is important to clone to avoid having the same object present
|
|
297
|
+
multiple times in the metamodel.
|
|
298
|
+
"""
|
|
299
|
+
|
|
300
|
+
# map from original object id to the rewritten object
|
|
301
|
+
cache = {}
|
|
302
|
+
def from_cache(original):
|
|
303
|
+
""" Lookup this object from the cache above, dealing with collections and with
|
|
304
|
+
objects that were not rewritten. """
|
|
305
|
+
if isinstance(original, tuple):
|
|
306
|
+
return tuple([from_cache(c) for c in original])
|
|
307
|
+
elif isinstance(original, FrozenOrderedSet):
|
|
308
|
+
return ordered_set(*[from_cache(c) for c in original])
|
|
309
|
+
elif isinstance(original, CLONABLE):
|
|
310
|
+
return cache.get(original.id, original)
|
|
311
|
+
else:
|
|
312
|
+
return original
|
|
313
|
+
|
|
314
|
+
# the last node that was processed and rewritten
|
|
315
|
+
prev_node = None
|
|
316
|
+
stack: list[ir.Node] = [task]
|
|
317
|
+
def to_stack(original):
|
|
318
|
+
""" Add this original node to the stack if it is clonable and was never processed;
|
|
319
|
+
return True iff the node was added to the stack. """
|
|
320
|
+
if isinstance(original, CLONABLE) and original.id not in cache:
|
|
321
|
+
stack.append(original)
|
|
322
|
+
return True
|
|
323
|
+
return False
|
|
324
|
+
|
|
325
|
+
while stack:
|
|
326
|
+
# peek the current node and get the initializable fields (i.e. ignore Node id)
|
|
327
|
+
curr = stack[-1]
|
|
328
|
+
curr_fields = list(filter(lambda f: f.init, fields(curr)))
|
|
329
|
+
stacked_children = False
|
|
330
|
+
|
|
331
|
+
# go over the fields adding to the stack the ones that we need to rewrite
|
|
332
|
+
for field in curr_fields:
|
|
333
|
+
field_value = getattr(curr, field.name)
|
|
334
|
+
if isinstance(field_value, (tuple, FrozenOrderedSet)):
|
|
335
|
+
# node field is a collection (tuple or set)
|
|
336
|
+
for s in field_value:
|
|
337
|
+
if isinstance(s, tuple):
|
|
338
|
+
# the value within the collection is a tuple (can happen for lookup args)
|
|
339
|
+
for c in s:
|
|
340
|
+
stacked_children = to_stack(c) or stacked_children
|
|
341
|
+
else:
|
|
342
|
+
# the value within the collection is a scalar
|
|
343
|
+
stacked_children = to_stack(s) or stacked_children
|
|
344
|
+
else:
|
|
345
|
+
# node field is a scalar
|
|
346
|
+
stacked_children = to_stack(field_value) or stacked_children
|
|
347
|
+
|
|
348
|
+
# if no childrean were stacked, we rewrote all fields of curr, so we can pop it and rewrite it
|
|
349
|
+
if not stacked_children:
|
|
350
|
+
stack.pop()
|
|
351
|
+
if curr.id not in cache:
|
|
352
|
+
children = []
|
|
353
|
+
for f in curr_fields:
|
|
354
|
+
children.append(from_cache(getattr(curr, f.name)))
|
|
355
|
+
# create a new prev_node with the cloned children
|
|
356
|
+
prev_node = curr.__class__(*children)
|
|
357
|
+
cache[curr.id] = prev_node
|
|
358
|
+
|
|
359
|
+
# the last node we processed is the rewritten original node
|
|
360
|
+
assert(isinstance(prev_node, type(task)))
|
|
361
|
+
return prev_node
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
from dataclasses import dataclass
|
|
4
|
+
from v0.relationalai.semantics.metamodel import ir, compiler as c, visitor as v, builtins
|
|
5
|
+
from v0.relationalai.semantics.metamodel.util import rewrite_list
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
class DischargeConstraints(c.Pass):
|
|
9
|
+
"""
|
|
10
|
+
Since we should not generate code for `unique`, `exclusive`, `anyof` builtins all Require Check nodes marked with
|
|
11
|
+
`discharge` annotation when at least one of the builtins is presented in a check.
|
|
12
|
+
All Require/Check ir nodes marked with `discharge` annotation will be removed from the IR model in Flatten pass.
|
|
13
|
+
"""
|
|
14
|
+
|
|
15
|
+
def rewrite(self, model: ir.Model, options: dict = {}) -> ir.Model:
|
|
16
|
+
return DischargeConstraintsVisitor().walk(model)
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
@dataclass
|
|
20
|
+
class DischargeConstraintsVisitor(v.Rewriter):
|
|
21
|
+
"""
|
|
22
|
+
Visitor marks all nodes which should be removed from IR model with `discharge` annotation.
|
|
23
|
+
"""
|
|
24
|
+
|
|
25
|
+
def handle_require(self, node: ir.Require, parent: ir.Node):
|
|
26
|
+
checks = rewrite_list(ir.Check, lambda n: self.walk(n, node), node.checks)
|
|
27
|
+
# discharge require if all the checks are discharged
|
|
28
|
+
if all(builtins.discharged_annotation in check.annotations for check in checks):
|
|
29
|
+
return node.reconstruct(node.engine, node.domain, checks, node.annotations | [builtins.discharged_annotation])
|
|
30
|
+
return node.reconstruct(node.engine, node.domain, checks, node.annotations)
|
|
31
|
+
|
|
32
|
+
def handle_check(self, node: ir.Check, parent: ir.Node):
|
|
33
|
+
check = self.walk(node.check, node)
|
|
34
|
+
assert isinstance(check, ir.Logical)
|
|
35
|
+
discharged_names = [builtins.unique.name, builtins.exclusive.name, builtins.anyof.name]
|
|
36
|
+
for item in check.body:
|
|
37
|
+
if isinstance(item, ir.Lookup) and item.relation.name in discharged_names:
|
|
38
|
+
return node.reconstruct(check, node.error, node.annotations | [builtins.discharged_annotation])
|
|
39
|
+
return node.reconstruct(check, node.error, node.annotations)
|
|
@@ -0,0 +1,210 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
from v0.relationalai.semantics.metamodel import ir
|
|
4
|
+
from v0.relationalai.semantics.metamodel.compiler import Pass
|
|
5
|
+
from v0.relationalai.semantics.metamodel.visitor import Visitor, Rewriter
|
|
6
|
+
from v0.relationalai.semantics.metamodel.util import OrderedSet
|
|
7
|
+
from v0.relationalai.semantics.metamodel import helpers, factory as f
|
|
8
|
+
from typing import Optional, Any
|
|
9
|
+
|
|
10
|
+
"""
|
|
11
|
+
Handle DNF decomposition of unions
|
|
12
|
+
|
|
13
|
+
E.g., we go from
|
|
14
|
+
|
|
15
|
+
Logical
|
|
16
|
+
Logical
|
|
17
|
+
Union
|
|
18
|
+
Logical
|
|
19
|
+
Foo(foo::Foo)
|
|
20
|
+
a(foo::Foo, a::Int128)
|
|
21
|
+
a::Int128 < 100::Int128
|
|
22
|
+
Union
|
|
23
|
+
Logical
|
|
24
|
+
b(foo::Foo, b::Int128)
|
|
25
|
+
b::Int128 < 100::Int128
|
|
26
|
+
Logical
|
|
27
|
+
c(foo::Foo, c::Int128)
|
|
28
|
+
c::Int128 > 0::Int128
|
|
29
|
+
Logical
|
|
30
|
+
Foo(foo::Foo)
|
|
31
|
+
id(foo::Foo, id::Int128)
|
|
32
|
+
id::Int128 < 100::Int128
|
|
33
|
+
Logical
|
|
34
|
+
Foo(foo::Foo)
|
|
35
|
+
x(foo::Foo, x::Int128)
|
|
36
|
+
x::Int128 < 100::Int128
|
|
37
|
+
Union
|
|
38
|
+
Logical
|
|
39
|
+
y(foo::Foo, y::Int128)
|
|
40
|
+
y::Int128 < 100::Int128
|
|
41
|
+
Logical
|
|
42
|
+
z(foo::Foo, z::Int128)
|
|
43
|
+
z::Int128 > 0::Int128
|
|
44
|
+
...
|
|
45
|
+
-> output(...)
|
|
46
|
+
|
|
47
|
+
to
|
|
48
|
+
|
|
49
|
+
Logical
|
|
50
|
+
Logical
|
|
51
|
+
Logical
|
|
52
|
+
Foo(foo::Foo)
|
|
53
|
+
a(foo::Foo, a::Int128)
|
|
54
|
+
a::Int128 < 100::Int128
|
|
55
|
+
Logical
|
|
56
|
+
b(foo::Foo, b::Int128)
|
|
57
|
+
b::Int128 < 100::Int128
|
|
58
|
+
...
|
|
59
|
+
-> output(...)
|
|
60
|
+
Logical
|
|
61
|
+
Logical
|
|
62
|
+
Foo(foo::Foo)
|
|
63
|
+
a(foo::Foo, a::Int128)
|
|
64
|
+
a::Int128 < 100::Int128
|
|
65
|
+
Logical
|
|
66
|
+
c(foo::Foo, c::Int128)
|
|
67
|
+
c::Int128 > 0::Int128
|
|
68
|
+
...
|
|
69
|
+
-> output(...)
|
|
70
|
+
Logical
|
|
71
|
+
Logical
|
|
72
|
+
Foo(foo::Foo)
|
|
73
|
+
id(foo::Foo, id::Int128)
|
|
74
|
+
id::Int128 < 100::Int128
|
|
75
|
+
...
|
|
76
|
+
-> output(...)
|
|
77
|
+
Logical
|
|
78
|
+
Logical
|
|
79
|
+
Foo(foo::Foo)
|
|
80
|
+
x(foo::Foo, x::Int128)
|
|
81
|
+
x::Int128 < 100::Int128
|
|
82
|
+
Logical
|
|
83
|
+
y(foo::Foo, y::Int128)
|
|
84
|
+
y::Int128 < 100::Int128
|
|
85
|
+
...
|
|
86
|
+
-> output(...)
|
|
87
|
+
Logical
|
|
88
|
+
Logical
|
|
89
|
+
Foo(foo::Foo)
|
|
90
|
+
x(foo::Foo, x::Int128)
|
|
91
|
+
x::Int128 < 100::Int128
|
|
92
|
+
Logical
|
|
93
|
+
z(foo::Foo, z::Int128)
|
|
94
|
+
z::Int128 > 0::Int128
|
|
95
|
+
...
|
|
96
|
+
-> output(...)
|
|
97
|
+
"""
|
|
98
|
+
class DNFUnionSplitter(Pass):
|
|
99
|
+
def rewrite(self, model: ir.Model, options:dict={}) -> ir.Model:
|
|
100
|
+
visitor = DNFExtractor()
|
|
101
|
+
model.accept(visitor)
|
|
102
|
+
return DNFRewriter(visitor).walk(model) if visitor.replaced_by else model
|
|
103
|
+
|
|
104
|
+
class DNFExtractor(Visitor):
|
|
105
|
+
def __init__(self):
|
|
106
|
+
# The logical that contains the output.
|
|
107
|
+
# The assumption for the IR at this point is that there is only one output.
|
|
108
|
+
self.output_logical: Optional[ir.Logical] = None
|
|
109
|
+
self.active_negations: list[ir.Not] = []
|
|
110
|
+
# Nodes that have to split into multiple similar nodes, depending on the changes
|
|
111
|
+
# of sub-nodes.
|
|
112
|
+
self.should_split: OrderedSet[ir.Node] = OrderedSet()
|
|
113
|
+
# Track that a node has to be replaced by other nodes.
|
|
114
|
+
# If node X should be replaced by nodes Y and Z, then the parent should be replicated
|
|
115
|
+
# one time replacing X with Y and one time replacing X with Z.
|
|
116
|
+
self.replaced_by: dict[ir.Node, list[ir.Task]] = {}
|
|
117
|
+
|
|
118
|
+
def enter(self, node: ir.Node, parent: Optional[ir.Node]=None) -> Visitor:
|
|
119
|
+
if isinstance(node, ir.Logical):
|
|
120
|
+
if any(isinstance(x, ir.Output) for x in node.body):
|
|
121
|
+
assert not self.output_logical, "multiple outputs"
|
|
122
|
+
self.output_logical = node
|
|
123
|
+
|
|
124
|
+
elif isinstance(node, ir.Not):
|
|
125
|
+
self.active_negations.append(node)
|
|
126
|
+
|
|
127
|
+
return self
|
|
128
|
+
|
|
129
|
+
def leave(self, node: ir.Node, parent: Optional[ir.Node]=None) -> ir.Node:
|
|
130
|
+
if isinstance(node, ir.Logical) and node in self.should_split:
|
|
131
|
+
# The given logical, will be replaced by multiple logicals, each with a different
|
|
132
|
+
# group of tasks. We need to generate all the possible groups.
|
|
133
|
+
# A list of logical bodies (lists).
|
|
134
|
+
replacement_bodies: list[list[ir.Task]] = [[]]
|
|
135
|
+
for task in node.body:
|
|
136
|
+
if task in self.replaced_by:
|
|
137
|
+
new_replacement_bodies: list[list[ir.Task]] = []
|
|
138
|
+
replacement_tasks = self.replaced_by[task]
|
|
139
|
+
for body in replacement_bodies:
|
|
140
|
+
for new_task in replacement_tasks:
|
|
141
|
+
# copy to mutate
|
|
142
|
+
new_body = list(body)
|
|
143
|
+
new_body.append(new_task.clone())
|
|
144
|
+
new_replacement_bodies.append(new_body)
|
|
145
|
+
replacement_bodies = new_replacement_bodies
|
|
146
|
+
|
|
147
|
+
else:
|
|
148
|
+
for new_body in replacement_bodies:
|
|
149
|
+
new_body.append(task.clone())
|
|
150
|
+
|
|
151
|
+
replacement_tasks: list[ir.Task] = []
|
|
152
|
+
for body in replacement_bodies:
|
|
153
|
+
new_task = f.logical(body, node.hoisted)
|
|
154
|
+
replacement_tasks.append(new_task)
|
|
155
|
+
self.replaced_by[node] = replacement_tasks
|
|
156
|
+
|
|
157
|
+
if node != self.output_logical:
|
|
158
|
+
self.should_split.add(parent)
|
|
159
|
+
elif node == self.output_logical:
|
|
160
|
+
assert parent and isinstance(parent, ir.Logical)
|
|
161
|
+
new_parent = f.logical(tuple(replacement_tasks), node.hoisted)
|
|
162
|
+
self.replaced_by[parent] = [new_parent]
|
|
163
|
+
|
|
164
|
+
elif isinstance(node, ir.Not) and self.active_negations[-1] == node:
|
|
165
|
+
self.active_negations.pop()
|
|
166
|
+
|
|
167
|
+
elif (isinstance(node, ir.Union) and
|
|
168
|
+
self.output_logical and
|
|
169
|
+
len(self.active_negations) % 2 == 0 and
|
|
170
|
+
len(node.tasks) > 1):
|
|
171
|
+
# We split the union when there is a branch with vars "X,Y" and another with "X,Z"
|
|
172
|
+
# If some branches have vars "X, Y, Z" and others have "X, Y" or "Y, Z" we don't split
|
|
173
|
+
should_split = False
|
|
174
|
+
all_vars = helpers.collect_vars(node.tasks[0])
|
|
175
|
+
for t in node.tasks[1:]:
|
|
176
|
+
vars = helpers.collect_vars(t)
|
|
177
|
+
curr_intersection = vars.get_set().intersection(all_vars.get_set())
|
|
178
|
+
should_split |= not (curr_intersection == vars.get_set() or curr_intersection == all_vars.get_set())
|
|
179
|
+
if should_split:
|
|
180
|
+
replacements:list[ir.Task] = []
|
|
181
|
+
for t in node.tasks:
|
|
182
|
+
# If some branch should already be replaced, we flatten all the replacements here.
|
|
183
|
+
if t in self.replaced_by:
|
|
184
|
+
replacements.extend(self.replaced_by[t])
|
|
185
|
+
else:
|
|
186
|
+
replacements.append(t)
|
|
187
|
+
self.replaced_by[node] = replacements
|
|
188
|
+
self.should_split.add(parent)
|
|
189
|
+
break
|
|
190
|
+
all_vars.update(vars)
|
|
191
|
+
|
|
192
|
+
if isinstance(node, ir.Logical) and node == self.output_logical:
|
|
193
|
+
self.output_logical = None
|
|
194
|
+
|
|
195
|
+
return node
|
|
196
|
+
|
|
197
|
+
class DNFRewriter(Rewriter):
|
|
198
|
+
def __init__(self, visitor: DNFExtractor):
|
|
199
|
+
super().__init__()
|
|
200
|
+
self.visitor = visitor
|
|
201
|
+
self.outer_parent_logical: Optional[ir.Logical] = None
|
|
202
|
+
|
|
203
|
+
def handle_logical(self, node: ir.Logical, parent: ir.Node, ctx:Optional[Any]=None) -> ir.Logical:
|
|
204
|
+
if node in self.visitor.replaced_by:
|
|
205
|
+
new_tasks = self.visitor.replaced_by[node]
|
|
206
|
+
assert len(new_tasks) == 1
|
|
207
|
+
new_task = new_tasks[0]
|
|
208
|
+
assert isinstance(new_task, ir.Logical)
|
|
209
|
+
return new_task
|
|
210
|
+
return node
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
from v0.relationalai.semantics.metamodel import ir, factory as f, helpers
|
|
4
|
+
from v0.relationalai.semantics.metamodel.visitor import Rewriter, collect_by_type
|
|
5
|
+
from v0.relationalai.semantics.metamodel.compiler import Pass
|
|
6
|
+
from v0.relationalai.semantics.metamodel.util import OrderedSet, ordered_set, NameCache
|
|
7
|
+
from v0.relationalai.semantics.metamodel import dependency
|
|
8
|
+
|
|
9
|
+
class ExtractNestedLogicals(Pass):
|
|
10
|
+
|
|
11
|
+
def __init__(self):
|
|
12
|
+
super().__init__()
|
|
13
|
+
|
|
14
|
+
#--------------------------------------------------
|
|
15
|
+
# Public API
|
|
16
|
+
#--------------------------------------------------
|
|
17
|
+
def rewrite(self, model: ir.Model, options:dict={}) -> ir.Model:
|
|
18
|
+
# process the root node
|
|
19
|
+
extractor = LogicalExtractor(model)
|
|
20
|
+
root = extractor.walk(model.root, model)
|
|
21
|
+
|
|
22
|
+
# no extractions, just return the original model
|
|
23
|
+
if not extractor.ctx.top_level:
|
|
24
|
+
return model
|
|
25
|
+
|
|
26
|
+
# create a new model with the extracted top level + the new root
|
|
27
|
+
body = extractor.ctx.top_level + [root]
|
|
28
|
+
return ir.Model(
|
|
29
|
+
model.engines,
|
|
30
|
+
OrderedSet.from_iterable(model.relations).update(extractor.ctx.relations).frozen(),
|
|
31
|
+
model.types,
|
|
32
|
+
ir.Logical(model.root.engine, tuple(), tuple(body))
|
|
33
|
+
)
|
|
34
|
+
|
|
35
|
+
class LogicalExtractor(Rewriter):
|
|
36
|
+
def __init__(self, model):
|
|
37
|
+
super().__init__()
|
|
38
|
+
self.ctx = helpers.RewriteContext()
|
|
39
|
+
self.info = dependency.analyze(model.root)
|
|
40
|
+
self.name_cache = NameCache()
|
|
41
|
+
|
|
42
|
+
def handle_logical(self, node: ir.Logical, parent: ir.Node):
|
|
43
|
+
# rewrite the children
|
|
44
|
+
logical = super().handle_logical(node, parent)
|
|
45
|
+
|
|
46
|
+
# logicals that hoist vars and all vars do not have a default value will be
|
|
47
|
+
# extracted, except for logicals that require special treatment of the exposed
|
|
48
|
+
# variables (which is currently done by flatten), such as when the parent is a Match
|
|
49
|
+
# or a Union, of if the logical has a Rank.
|
|
50
|
+
if not (
|
|
51
|
+
logical.hoisted and
|
|
52
|
+
not isinstance(parent, (ir.Match, ir.Union)) and
|
|
53
|
+
all(isinstance(v, ir.Var) for v in logical.hoisted) and
|
|
54
|
+
not any(isinstance(c, ir.Rank) for c in logical.body)
|
|
55
|
+
):
|
|
56
|
+
return logical
|
|
57
|
+
|
|
58
|
+
# compute the vars to be exposed by the extracted logical; those are keys (what
|
|
59
|
+
# makes the values unique) + the values (the hoisted variables)
|
|
60
|
+
exposed_vars = ordered_set()
|
|
61
|
+
|
|
62
|
+
# if there are aggregations, make sure we don't expose the projected and input vars,
|
|
63
|
+
# but expose groupbys
|
|
64
|
+
for agg in collect_by_type(ir.Aggregate, logical):
|
|
65
|
+
exposed_vars.difference_update(agg.projection)
|
|
66
|
+
exposed_vars.difference_update(helpers.aggregate_inputs(agg))
|
|
67
|
+
exposed_vars.update(agg.group)
|
|
68
|
+
|
|
69
|
+
# add the values (hoisted)
|
|
70
|
+
exposed_vars.update(helpers.hoisted_vars(logical.hoisted))
|
|
71
|
+
|
|
72
|
+
body = ordered_set()
|
|
73
|
+
body.update(self.info.task_dependencies(node)) # notice info is based on the original node
|
|
74
|
+
body.update(logical.body)
|
|
75
|
+
|
|
76
|
+
name = helpers.create_task_name(self.name_cache, logical, "_nested_logical")
|
|
77
|
+
connection = helpers.extract(logical, body, exposed_vars.get_list(), self.ctx, name)
|
|
78
|
+
return f.lookup(connection, exposed_vars.get_list())
|