@@ -94,8 +94,68 @@ def github_pr_affected_files(pr_url: str) -> set[str]:
9494 return {x .filename for x in gh_pr .get_files ()}
9595
9696
97+ def is_operator_bundle_dir (
98+ operator_name : str ,
99+ bundle_version : str ,
100+ head_repo : OperatorRepo ,
101+ base_repo : OperatorRepo ,
102+ ) -> tuple [bool , bool ]:
103+ """
104+ Check if provided operator and bundle exist in either the head or base repo
105+
106+ Returns a tuple of two booleans, the first indicating if the operator exists
107+ and the second indicating if the bundle exists.
108+
109+ Args:
110+ operator_name (str): Operator name given by the directory name
111+ bundle_version (str): A bundle version given by the directory name
112+ head_repo (OperatorRepo): Git repository with the head state
113+ base_repo (OperatorRepo): Git repository with the base state
114+
115+ Returns:
116+ tuple[bool, bool]: A tuple of two booleans indicating if the operator
117+ and bundle exist in either the head or base repo
118+ """
119+ # Check if the operator and bundle exist in either the head or base repo
120+ is_operator = False
121+ is_bundle = False
122+ for repo in [head_repo , base_repo ]:
123+ if repo .has (operator_name ):
124+ is_operator = True
125+ if repo .operator (operator_name ).has (bundle_version ):
126+ is_bundle = True
127+ return is_operator , is_bundle
128+
129+
130+ def is_catalog_operator_dir (
131+ catalog_name : str ,
132+ catalog_operator : str ,
133+ head_repo : OperatorRepo ,
134+ base_repo : OperatorRepo ,
135+ ) -> bool :
136+ """
137+ Check if provided catalog and operator exist in either the head or base repo
138+
139+ Args:
140+ catalog_name (str): A catalog name given by the directory name
141+ catalog_operator (str): A catalog operator given by the directory name
142+ head_repo (OperatorRepo): Git repository with the head state
143+ base_repo (OperatorRepo): Git repository with the base state
144+
145+ Returns:
146+ bool: A boolean indicating if the catalog and operator exist in either
147+ the head or base repo
148+ """
149+ # Check if the catalog and operator exist in either the head or base repo
150+ for repo in [head_repo , base_repo ]:
151+ if repo .has_catalog (catalog_name ):
152+ if repo .catalog (catalog_name ).has (catalog_operator ):
153+ return True
154+ return False
155+
156+
97157def _find_directory_owner (
98- path : str ,
158+ path : str , head_repo : OperatorRepo , base_repo : OperatorRepo
99159) -> tuple [Optional [str ], Optional [str ], Optional [str ], Optional [str ]]:
100160 """
101161 Given a relative file name within an operator repo, return a tuple
@@ -106,6 +166,8 @@ def _find_directory_owner(
106166 If the file is outside an operator or catalog directory, all returns will be None.
107167 Args:
108168 path: Path to the file
169+ head_repo: OperatorRepo object representing the head state of the repo
170+ base_repo: OperatorRepo object representing the base state of the repo
109171 Returns:
110172 (operator_name, bundle_version, catalog_name, catalog_operator)
111173 Operator/bundle, Catalog/operator the files belongs to
@@ -115,29 +177,35 @@ def _find_directory_owner(
115177 filename_parts = pathlib .Path (path ).parts
116178 if len (filename_parts ) >= 3 and filename_parts [0 ] == "operators" :
117179 # inside an operator directory
118- _ , detected_operator_name , detected_bundle_version , * rest = filename_parts
119- if len (rest ) < 1 :
120- # inside an operator but not in a bundle (i.e.: the ci.yaml file)
121- return detected_operator_name , None , None , None
122- return detected_operator_name , detected_bundle_version , None , None
180+ is_operator , is_bundle = is_operator_bundle_dir (
181+ filename_parts [1 ], filename_parts [2 ], head_repo , base_repo
182+ )
183+ if is_operator and is_bundle :
184+ return filename_parts [1 ], filename_parts [2 ], None , None
185+ if is_operator :
186+ # path is inside an operator but outside a bundle
187+ # (i.e.: ci.yaml, catalog-templates, Makefile)
188+ return filename_parts [1 ], None , None , None
123189 if len (filename_parts ) >= 3 and filename_parts [0 ] == "catalogs" :
124- # inside a catalog directory
125- _ , detected_catalog_name , catalog_operator , * rest = filename_parts
126- if len ( rest ) >= 1 :
127- return None , None , detected_catalog_name , catalog_operator
190+ if is_catalog_operator_dir (
191+ filename_parts [ 1 ], filename_parts [ 2 ], head_repo , base_repo
192+ ) :
193+ return None , None , filename_parts [ 1 ], filename_parts [ 2 ]
128194 # path is outside an operator or catalog directory
129195 return None , None , None , None
130196
131197
132198def _affected_bundles_and_operators_from_files (
133- affected_files : set [str ],
199+ affected_files : set [str ], head_repo : OperatorRepo , base_repo : OperatorRepo
134200) -> tuple [dict [str , set [Optional [str ]]], dict [str , set [Optional [str ]]], set [str ]]:
135201 """
136202 Group a given set of file names depending on the operator, bundle,
137203 catalog and operator catalog they belong to
138204
139205 Args:
140206 affected_files: set of files names to parse
207+ head_repo: OperatorRepo object representing the head state of the repo
208+ base_repo: OperatorRepo object representing the base state of the repo
141209
142210 Returns:
143211 A tuple containing:
@@ -159,7 +227,7 @@ def _affected_bundles_and_operators_from_files(
159227 bundle_version ,
160228 catalog_name ,
161229 catalog_operator ,
162- ) = _find_directory_owner (filename )
230+ ) = _find_directory_owner (filename , head_repo , base_repo )
163231 if operator_name is None and catalog_name is None :
164232 extra_files .add (filename )
165233 elif operator_name is not None :
@@ -396,7 +464,7 @@ def detect_changes(
396464 all_affected_bundles ,
397465 all_affected_catalog_operators ,
398466 non_operator_files ,
399- ) = _affected_bundles_and_operators_from_files (pr_files )
467+ ) = _affected_bundles_and_operators_from_files (pr_files , head_repo , base_repo )
400468
401469 operators = detect_changed_operators (head_repo , base_repo , all_affected_bundles )
402470 bundles = detect_changed_operator_bundles (
0 commit comments