@@ -2228,6 +2228,85 @@ def test_create_routine(self):
22282228 assert len (rows ) == 1
22292229 assert rows [0 ].max_value == 100.0
22302230
2231+ def test_create_tvf_routine (self ):
2232+ from google .cloud .bigquery import Routine , RoutineArgument , RoutineType
2233+
2234+ StandardSqlDataType = bigquery_v2 .types .StandardSqlDataType
2235+ StandardSqlField = bigquery_v2 .types .StandardSqlField
2236+ StandardSqlTableType = bigquery_v2 .types .StandardSqlTableType
2237+
2238+ INT64 = StandardSqlDataType .TypeKind .INT64
2239+ STRING = StandardSqlDataType .TypeKind .STRING
2240+
2241+ client = Config .CLIENT
2242+
2243+ dataset = self .temp_dataset (_make_dataset_id ("create_tvf_routine" ))
2244+ routine_ref = dataset .routine ("test_tvf_routine" )
2245+
2246+ routine_body = """
2247+ SELECT int_col, str_col
2248+ FROM (
2249+ UNNEST([1, 2, 3]) int_col
2250+ JOIN
2251+ (SELECT str_col FROM UNNEST(["one", "two", "three"]) str_col)
2252+ ON TRUE
2253+ )
2254+ WHERE int_col > threshold
2255+ """
2256+
2257+ return_table_type = StandardSqlTableType (
2258+ columns = [
2259+ StandardSqlField (
2260+ name = "int_col" , type = StandardSqlDataType (type_kind = INT64 ),
2261+ ),
2262+ StandardSqlField (
2263+ name = "str_col" , type = StandardSqlDataType (type_kind = STRING ),
2264+ ),
2265+ ]
2266+ )
2267+
2268+ routine_args = [
2269+ RoutineArgument (
2270+ name = "threshold" , data_type = StandardSqlDataType (type_kind = INT64 ),
2271+ )
2272+ ]
2273+
2274+ routine_def = Routine (
2275+ routine_ref ,
2276+ type_ = RoutineType .TABLE_VALUED_FUNCTION ,
2277+ arguments = routine_args ,
2278+ return_table_type = return_table_type ,
2279+ body = routine_body ,
2280+ )
2281+
2282+ # Create TVF routine.
2283+ client .delete_routine (routine_ref , not_found_ok = True )
2284+ routine = client .create_routine (routine_def )
2285+
2286+ assert routine .body == routine_body
2287+ assert routine .return_table_type == return_table_type
2288+ assert routine .arguments == routine_args
2289+
2290+ # Execute the routine to see if it's working as expected.
2291+ query_job = client .query (
2292+ f"""
2293+ SELECT int_col, str_col
2294+ FROM `{ routine .reference } `(1)
2295+ ORDER BY int_col, str_col ASC
2296+ """
2297+ )
2298+
2299+ result_rows = [tuple (row ) for row in query_job .result ()]
2300+ expected = [
2301+ (2 , "one" ),
2302+ (2 , "three" ),
2303+ (2 , "two" ),
2304+ (3 , "one" ),
2305+ (3 , "three" ),
2306+ (3 , "two" ),
2307+ ]
2308+ assert result_rows == expected
2309+
22312310 def test_create_table_rows_fetch_nested_schema (self ):
22322311 table_name = "test_table"
22332312 dataset = self .temp_dataset (_make_dataset_id ("create_table_nested_schema" ))
0 commit comments