4545from dbt .adapters .bigquery import BigQueryColumn , BigQueryConnectionManager
4646from dbt .adapters .bigquery .column import get_nested_column_data_types
4747from dbt .adapters .bigquery .connections import BigQueryAdapterResponse
48- from dbt .adapters .bigquery .dataset import add_access_entry_to_dataset , is_access_entry_in_dataset
48+ from dbt .adapters .bigquery .dataset import add_access_entry_to_dataset , is_access_entry_in_dataset , delete_access_entry_to_dataset
4949from dbt .adapters .bigquery .python_submissions import (
5050 ClusterDataprocHelper ,
5151 ServerlessDataProcHelper ,
@@ -817,10 +817,46 @@ def describe_relation(
817817 return parser .from_bq_table (bq_table )
818818 return None
819819
820+
821+
822+ @available .parse_none
823+ def grant_access_to (self , entity , entity_type , role , grant_target_dict ,full_refresh = False ):
824+ """
825+ Given an entity, grants access to a dataset.
826+ """
827+ conn : BigQueryConnectionManager = self .connections .get_thread_connection ()
828+ client = conn .handle
829+ GrantTarget .validate (grant_target_dict )
830+ grant_target = GrantTarget .from_dict (grant_target_dict )
831+ if entity_type == "view" :
832+ entity = self .get_table_ref_from_relation (entity ).to_api_repr ()
833+ with _dataset_lock :
834+ dataset_ref = self .connections .dataset_ref (grant_target .project , grant_target .dataset )
835+ dataset = client .get_dataset (dataset_ref )
836+ access_entry = AccessEntry (role , entity_type , entity )
837+ # only perform update if access entry in dataset but if full_refresh remove it first
838+ if is_access_entry_in_dataset (dataset , access_entry ):
839+ if not full_refresh :
840+ logger .warning (f"Access entry { access_entry } " f"already exists in dataset" )
841+ return
842+ else :
843+ dataset = delete_access_entry_to_dataset (dataset ,access_entry )
844+ dataset = client .update_dataset (
845+ dataset ,
846+ ["access_entries" ],
847+ ) # Make an API request.
848+ full_dataset_id = f"{ dataset .project } .{ dataset .dataset_id } "
849+ print (f"Revoked dataset access for '{ access_entry .entity_id } ' to ' dataset '{ full_dataset_id } .'" )
850+ dataset = add_access_entry_to_dataset (dataset , access_entry )
851+ dataset = client .update_dataset (dataset , ["access_entries" ])
852+ full_dataset_id = f"{ dataset .project } .{ dataset .dataset_id } "
853+ print (f"allowed dataset access for '{ access_entry .entity_id } ' to ' dataset '{ full_dataset_id } .'" )
854+
855+
820856 @available .parse_none
821- def grant_access_to (self , entity , entity_type , role , grant_target_dict ):
857+ def remove_grant_access_to (self , entity , entity_type , role , grant_target_dict ):
822858 """
823- Given an entity, grants it access to a dataset.
859+ Given an entity, grants access to a dataset.
824860 """
825861 conn : BigQueryConnectionManager = self .connections .get_thread_connection ()
826862 client = conn .handle
@@ -832,12 +868,18 @@ def grant_access_to(self, entity, entity_type, role, grant_target_dict):
832868 dataset_ref = self .connections .dataset_ref (grant_target .project , grant_target .dataset )
833869 dataset = client .get_dataset (dataset_ref )
834870 access_entry = AccessEntry (role , entity_type , entity )
835- # only perform update if access entry not in dataset
871+ # only perform removing if access entry in dataset
836872 if is_access_entry_in_dataset (dataset , access_entry ):
837- logger .warning (f"Access entry { access_entry } " f"already exists in dataset" )
873+ dataset = delete_access_entry_to_dataset (dataset ,access_entry )
874+ dataset = client .update_dataset (
875+ dataset ,
876+ ["access_entries" ],
877+ ) # Make an API request.
878+
879+ full_dataset_id = f"{ dataset .project } .{ dataset .dataset_id } "
880+ print (f"Revoked dataset access for '{ access_entry .entity_id } ' to ' dataset '{ full_dataset_id } .'" )
838881 else :
839- dataset = add_access_entry_to_dataset (dataset , access_entry )
840- client .update_dataset (dataset , ["access_entries" ])
882+ logger .warning (f"Access entry { access_entry } not in the dataset { full_dataset_id } no need to remove it" )
841883
842884 @available .parse_none
843885 def get_dataset_location (self , relation ):
0 commit comments