omnata-plugin-runtime 0.11.0a313__py3-none-any.whl → 0.11.1__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.
- omnata_plugin_runtime/json_schema.py +83 -24
- {omnata_plugin_runtime-0.11.0a313.dist-info → omnata_plugin_runtime-0.11.1.dist-info}/METADATA +3 -2
- {omnata_plugin_runtime-0.11.0a313.dist-info → omnata_plugin_runtime-0.11.1.dist-info}/RECORD +5 -5
- {omnata_plugin_runtime-0.11.0a313.dist-info → omnata_plugin_runtime-0.11.1.dist-info}/WHEEL +1 -1
- {omnata_plugin_runtime-0.11.0a313.dist-info → omnata_plugin_runtime-0.11.1.dist-info/licenses}/LICENSE +0 -0
@@ -470,10 +470,20 @@ class SnowflakeViewPart(BaseModel):
|
|
470
470
|
c.name_with_comment(binding_list) for c in self.columns
|
471
471
|
]
|
472
472
|
|
473
|
-
def cte_text(self,original_name: bool = False,
|
473
|
+
def cte_text(self,original_name: bool = False,
|
474
|
+
include_only_columns:Optional[List[str]] = None,
|
475
|
+
include_extra_columns:Optional[List[str]] = None
|
476
|
+
) -> str:
|
474
477
|
"""
|
475
478
|
Returns the CTE text for this view part.
|
476
479
|
"""
|
480
|
+
if include_extra_columns is not None:
|
481
|
+
# includes direct columns plus any extra specified
|
482
|
+
return f""" "{self.stream_name}" as (
|
483
|
+
select {', '.join([c.definition(original_name=original_name,remove_stream_prefix=self.stream_name) for c in self.columns
|
484
|
+
if c.original_name in include_extra_columns or not c.is_join_column])}
|
485
|
+
from {self.raw_table_location.get_fully_qualified_name()}
|
486
|
+
) """
|
477
487
|
if include_only_columns is None:
|
478
488
|
return f""" "{self.stream_name}" as (
|
479
489
|
select {', '.join([c.definition(original_name=original_name,remove_stream_prefix=self.stream_name) for c in self.direct_columns()])}
|
@@ -504,6 +514,29 @@ class SnowflakeViewParts(BaseModel):
|
|
504
514
|
..., description="The other streams that are joined to the main stream"
|
505
515
|
)
|
506
516
|
|
517
|
+
def column_indirectly_references_other_streams(
|
518
|
+
self,
|
519
|
+
all_view_parts:List[SnowflakeViewPart],
|
520
|
+
stream_name:str,column_name:str) -> bool:
|
521
|
+
|
522
|
+
for part in all_view_parts:
|
523
|
+
if part.stream_name == stream_name:
|
524
|
+
for col in part.columns:
|
525
|
+
if col.original_name == column_name:
|
526
|
+
if col.referenced_columns:
|
527
|
+
for ref_stream, ref_cols in col.referenced_columns.items():
|
528
|
+
if ref_stream != stream_name:
|
529
|
+
return True
|
530
|
+
else:
|
531
|
+
# we have to call this recursively in case the referenced column also references other streams
|
532
|
+
result = any(
|
533
|
+
self.column_indirectly_references_other_streams(
|
534
|
+
all_view_parts, ref_stream, ref_col
|
535
|
+
) for ref_col in ref_cols
|
536
|
+
)
|
537
|
+
return result
|
538
|
+
return False
|
539
|
+
|
507
540
|
def view_body(self):
|
508
541
|
"""
|
509
542
|
Creates a view definition from the parts.
|
@@ -519,31 +552,44 @@ class SnowflakeViewParts(BaseModel):
|
|
519
552
|
|
520
553
|
# first, we need to collapse all referenced columns into a single map
|
521
554
|
all_referenced_columns:Dict[str,List[str]] = {}
|
555
|
+
|
556
|
+
# if a column references other columns, but there are no dependencies outside of its own stream, we can include those columns in the initial CTE for that stream
|
557
|
+
# because they can be calculated directly without needing joins
|
558
|
+
columns_only_referencing_own_stream:Dict[str,List[str]] = {}
|
559
|
+
|
522
560
|
for part in [self.main_part] + self.joined_parts:
|
523
|
-
# if the main part references any columns in this part in its joins, we need to include those columns
|
561
|
+
# if the main part references any columns in this part in its joins, we need to include those columns because they are used in the join condition
|
524
562
|
aliases_for_stream = [j.join_stream_alias for j in self.main_part.joins
|
525
563
|
if j.join_stream_name == part.stream_name]
|
526
564
|
columns_used_in_joins = [
|
527
565
|
j.left_column for j in self.main_part.joins if j.left_alias in aliases_for_stream
|
528
566
|
]
|
529
|
-
|
530
|
-
|
531
|
-
all_referenced_columns[part.stream_name] += columns_used_in_joins
|
567
|
+
all_referenced_columns.setdefault(part.stream_name, []).extend(columns_used_in_joins)
|
568
|
+
# now, for each column in the part, if it references columns in other streams, we need to include those columns
|
532
569
|
for column in part.columns:
|
533
570
|
if column.referenced_columns:
|
534
571
|
for stream_name, referenced_columns in column.referenced_columns.items():
|
535
|
-
|
536
|
-
|
537
|
-
all_referenced_columns[
|
572
|
+
aliases_for_referenced_stream = [j.join_stream_name for j in self.main_part.joins
|
573
|
+
if j.join_stream_alias == stream_name]
|
574
|
+
all_referenced_columns.setdefault(stream_name, []).extend(referenced_columns)
|
575
|
+
# the stream name could be an alias, so we need to check if it's one of the aliases for this part
|
576
|
+
for stream_name_for_alias in aliases_for_referenced_stream:
|
577
|
+
all_referenced_columns.setdefault(stream_name_for_alias, []).extend(referenced_columns)
|
578
|
+
# populate columns_only_referencing_own_stream by following the chain of references until we reach a column that references another stream or has no references
|
579
|
+
if self.column_indirectly_references_other_streams(
|
580
|
+
[self.main_part] + self.joined_parts, part.stream_name, column.original_name
|
581
|
+
) == False:
|
582
|
+
columns_only_referencing_own_stream.setdefault(part.stream_name, []).append(column.original_name)
|
583
|
+
else:
|
584
|
+
# if the column has no references, it can be included in the initial CTE for its own stream
|
585
|
+
columns_only_referencing_own_stream.setdefault(part.stream_name, []).append(column.original_name)
|
586
|
+
# if this part has joins to other streams, we need to include the join columns
|
538
587
|
for join in part.joins:
|
539
|
-
|
540
|
-
|
541
|
-
all_referenced_columns[
|
542
|
-
all_referenced_columns[part.stream_name].append(join.left_column)
|
543
|
-
|
544
|
-
|
588
|
+
all_referenced_columns.setdefault(join.join_stream_name, []).append(join.join_stream_column)
|
589
|
+
all_referenced_columns.setdefault(join.join_stream_alias, []).append(join.join_stream_column)
|
590
|
+
all_referenced_columns.setdefault(part.stream_name, []).append(join.left_column)
|
545
591
|
ctes = [
|
546
|
-
self.main_part.cte_text(original_name=True)
|
592
|
+
self.main_part.cte_text(original_name=True,include_extra_columns=columns_only_referencing_own_stream.get(self.main_part.stream_name))
|
547
593
|
] + [
|
548
594
|
part.cte_text(original_name=True,include_only_columns=all_referenced_columns.get(part.stream_name))
|
549
595
|
for part in joined_parts_deduped
|
@@ -553,9 +599,9 @@ class SnowflakeViewParts(BaseModel):
|
|
553
599
|
final_cte = f""" OMNATA_FINAL_CTE as (
|
554
600
|
select {', '.join(
|
555
601
|
[
|
556
|
-
f'"{self.main_part.stream_name}"."{c.original_name}"' for c in self.main_part.
|
602
|
+
f'"{self.main_part.stream_name}"."{c.original_name}"' for c in self.main_part.columns if not c.is_join_column or c.original_name in columns_only_referencing_own_stream.get(self.main_part.stream_name,[])
|
557
603
|
]+[
|
558
|
-
c.definition(original_name=True) for c in self.main_part.
|
604
|
+
c.definition(original_name=True) for c in self.main_part.columns if c.is_join_column and c.original_name not in columns_only_referencing_own_stream.get(self.main_part.stream_name,[])
|
559
605
|
])}
|
560
606
|
from "{self.main_part.stream_name}" """
|
561
607
|
if len(self.main_part.joins) > 0:
|
@@ -761,6 +807,25 @@ class SnowflakeViewParts(BaseModel):
|
|
761
807
|
|
762
808
|
return cls(main_part=main_stream_view_part, joined_parts=joined_parts)
|
763
809
|
|
810
|
+
|
811
|
+
# Helper function to find a view part by stream name
|
812
|
+
def find_part(view_part: SnowflakeViewPart, joined_parts: List[SnowflakeViewPart], stream_name: str) -> Optional[SnowflakeViewPart]:
|
813
|
+
if stream_name == view_part.stream_name:
|
814
|
+
return view_part
|
815
|
+
for part in joined_parts:
|
816
|
+
if part.stream_name == stream_name:
|
817
|
+
return part
|
818
|
+
for join in view_part.joins:
|
819
|
+
if join.join_stream_alias == stream_name:
|
820
|
+
# this is the join, we need to find the actual stream
|
821
|
+
for part in joined_parts:
|
822
|
+
if part.stream_name == join.join_stream_name:
|
823
|
+
return part
|
824
|
+
logger.warning(
|
825
|
+
f"Join alias {stream_name} maps to stream {join.join_stream_name}, but that stream is not in the joined parts"
|
826
|
+
)
|
827
|
+
return None
|
828
|
+
|
764
829
|
def prune(view_part: SnowflakeViewPart, joined_parts: List[SnowflakeViewPart]) -> bool:
|
765
830
|
"""
|
766
831
|
Prunes columns from view parts that reference fields that don't exist in the referenced streams.
|
@@ -773,12 +838,6 @@ def prune(view_part: SnowflakeViewPart, joined_parts: List[SnowflakeViewPart]) -
|
|
773
838
|
Raises ValueError if a cyclic dependency is detected.
|
774
839
|
"""
|
775
840
|
columns_removed = False
|
776
|
-
|
777
|
-
# Helper function to find a view part by stream name
|
778
|
-
def find_part(stream_name: str) -> Optional[SnowflakeViewPart]:
|
779
|
-
if stream_name == view_part.stream_name:
|
780
|
-
return view_part
|
781
|
-
return next((p for p in joined_parts if p.stream_name == stream_name), None)
|
782
841
|
|
783
842
|
# Helper function to check if a column should be kept or removed
|
784
843
|
def should_keep_column(column: SnowflakeViewColumn, part: SnowflakeViewPart) -> bool:
|
@@ -793,7 +852,7 @@ def prune(view_part: SnowflakeViewPart, joined_parts: List[SnowflakeViewPart]) -
|
|
793
852
|
# Check each referenced stream and its fields
|
794
853
|
for ref_stream_name, ref_fields in column.referenced_columns.items():
|
795
854
|
# Find the referenced part
|
796
|
-
ref_part = find_part(ref_stream_name)
|
855
|
+
ref_part = find_part(view_part, joined_parts,ref_stream_name)
|
797
856
|
|
798
857
|
# If referenced stream doesn't exist, remove the column
|
799
858
|
if ref_part is None:
|
{omnata_plugin_runtime-0.11.0a313.dist-info → omnata_plugin_runtime-0.11.1.dist-info}/METADATA
RENAMED
@@ -1,7 +1,8 @@
|
|
1
|
-
Metadata-Version: 2.
|
1
|
+
Metadata-Version: 2.4
|
2
2
|
Name: omnata-plugin-runtime
|
3
|
-
Version: 0.11.
|
3
|
+
Version: 0.11.1
|
4
4
|
Summary: Classes and common runtime components for building and running Omnata Plugins
|
5
|
+
License-File: LICENSE
|
5
6
|
Author: James Weakley
|
6
7
|
Author-email: james.weakley@omnata.com
|
7
8
|
Requires-Python: >=3.8,<=3.11
|
{omnata_plugin_runtime-0.11.0a313.dist-info → omnata_plugin_runtime-0.11.1.dist-info}/RECORD
RENAMED
@@ -2,12 +2,12 @@ omnata_plugin_runtime/__init__.py,sha256=MS9d1whnfT_B3-ThqZ7l63QeC_8OEKTuaYV5wTw
|
|
2
2
|
omnata_plugin_runtime/api.py,sha256=5gbjbnFy72Xjf0E3kbG23G0V2J3CorvD5kpBn_BkdlI,8084
|
3
3
|
omnata_plugin_runtime/configuration.py,sha256=SffokJfgvy6V3kUsoEjXcK3GdNgHo6U3mgBEs0qBv4I,46972
|
4
4
|
omnata_plugin_runtime/forms.py,sha256=Lrbr3otsFDrvHWJw7v-slsW4PvEHJ6BG1Yl8oaJfiDo,20529
|
5
|
-
omnata_plugin_runtime/json_schema.py,sha256=
|
5
|
+
omnata_plugin_runtime/json_schema.py,sha256=_3oLravvrbIM8dy-bOZSON22Di1FvNnDAsiehwfoH-E,54125
|
6
6
|
omnata_plugin_runtime/logging.py,sha256=WBuZt8lF9E5oFWM4KYQbE8dDJ_HctJ1pN3BHwU6rcd0,4461
|
7
7
|
omnata_plugin_runtime/omnata_plugin.py,sha256=PV1BzsqI2yi3pd6DBSRc1s1QJ_My-b6pewrB7ad4sms,140256
|
8
8
|
omnata_plugin_runtime/plugin_entrypoints.py,sha256=_1pDLov3iQorGmfcae8Sw2bVjxw1vYeowBaKKNzRclQ,32629
|
9
9
|
omnata_plugin_runtime/rate_limiting.py,sha256=qpr5esU4Ks8hMzuMpSR3gLFdor2ZUXYWCjmsQH_K6lQ,25882
|
10
|
-
omnata_plugin_runtime-0.11.
|
11
|
-
omnata_plugin_runtime-0.11.
|
12
|
-
omnata_plugin_runtime-0.11.
|
13
|
-
omnata_plugin_runtime-0.11.
|
10
|
+
omnata_plugin_runtime-0.11.1.dist-info/METADATA,sha256=d040ESGm3ElaDUf4pdLsIsXE21J5h2xuwDHwbpnbrNg,2229
|
11
|
+
omnata_plugin_runtime-0.11.1.dist-info/WHEEL,sha256=zp0Cn7JsFoX2ATtOhtaFYIiE2rmFAD4OcMhtUki8W3U,88
|
12
|
+
omnata_plugin_runtime-0.11.1.dist-info/licenses/LICENSE,sha256=rGaMQG3R3F5-JGDp_-rlMKpDIkg5n0SI4kctTk8eZSI,56
|
13
|
+
omnata_plugin_runtime-0.11.1.dist-info/RECORD,,
|
File without changes
|