@@ -1115,6 +1115,146 @@ def test_bigquery_graph_missing_spanner_deps(monkeypatch):
11151115 display_mock .assert_not_called ()
11161116
11171117
1118+ @pytest .mark .skipif (
1119+ graph_visualization is None or bigquery_storage is None ,
1120+ reason = "Requires `spanner-graph-notebook` and `google-cloud-bigquery-storage`" ,
1121+ )
1122+ def test_add_graph_widget_with_schema (monkeypatch ):
1123+ """Test _add_graph_widget with a valid graph query that retrieves a schema."""
1124+ mock_display = mock .patch ("IPython.display.display" , autospec = True )
1125+ mock_gen_html = mock .patch (
1126+ "spanner_graphs.graph_visualization.generate_visualization_html" ,
1127+ return_value = "<html>generated_html</html>" ,
1128+ )
1129+
1130+ bq_client = mock .create_autospec (bigquery .Client , instance = True )
1131+ query_result = pandas .DataFrame ([{"id" : 1 }], columns = ["result" ])
1132+ query_text = "GRAPH my_dataset.my_graph"
1133+
1134+ query_job = mock .create_autospec (bigquery .job .QueryJob , instance = True )
1135+ query_job .configuration .destination .project = "p"
1136+ query_job .configuration .destination .dataset_id = "d"
1137+ query_job .configuration .destination .table_id = "t"
1138+
1139+ args = mock .Mock ()
1140+ args .bigquery_api_endpoint = "e"
1141+ args .project = "p"
1142+ args .location = "l"
1143+
1144+ # Mock INFORMATION_SCHEMA query for schema retrieval
1145+ schema_json = '{"propertyGraphReference": {"propertyGraphId": "my_graph"}}'
1146+ mock_schema_df = pandas .DataFrame (
1147+ [[schema_json ]], columns = ["PROPERTY_GRAPH_METADATA_JSON" ]
1148+ )
1149+ bq_client .query .return_value .to_dataframe .return_value = mock_schema_df
1150+
1151+ with mock_display as display_mock , mock_gen_html as gen_html_mock :
1152+ magics ._add_graph_widget (bq_client , query_result , query_text , query_job , args )
1153+
1154+ # Verify schema was retrieved and converted
1155+ assert bq_client .query .called
1156+ call_args = bq_client .query .call_args [0 ][0 ]
1157+ assert "INFORMATION_SCHEMA.PROPERTY_GRAPHS" in call_args
1158+ assert 'PROPERTY_GRAPH_NAME = "my_graph"' in call_args
1159+
1160+ # Verify generate_visualization_html was called with the converted schema
1161+ assert gen_html_mock .called
1162+ params_str = gen_html_mock .call_args [1 ]["params" ]
1163+ params = json .loads (params_str .replace ('\\ "' , '"' ).replace ("\\ \\ " , "\\ " ))
1164+ assert "schema" in params
1165+ schema_obj = json .loads (params ["schema" ])
1166+ assert schema_obj ["name" ] == "my_graph"
1167+
1168+ # Verify display was called
1169+ assert display_mock .called
1170+
1171+
1172+ @pytest .mark .skipif (
1173+ graph_visualization is None or bigquery_storage is None ,
1174+ reason = "Requires `spanner-graph-notebook` and `google-cloud-bigquery-storage`" ,
1175+ )
1176+ def test_add_graph_widget_no_graph_name (monkeypatch ):
1177+ """Test _add_graph_widget with a query that is not a GRAPH query."""
1178+ mock_display = mock .patch ("IPython.display.display" , autospec = True )
1179+ mock_gen_html = mock .patch (
1180+ "spanner_graphs.graph_visualization.generate_visualization_html" ,
1181+ return_value = "<html>generated_html</html>" ,
1182+ )
1183+
1184+ bq_client = mock .create_autospec (bigquery .Client , instance = True )
1185+ query_result = pandas .DataFrame ([{"id" : 1 }], columns = ["result" ])
1186+ query_text = "SELECT * FROM my_dataset.my_table"
1187+
1188+ query_job = mock .create_autospec (bigquery .job .QueryJob , instance = True )
1189+ query_job .configuration .destination .project = "p"
1190+ query_job .configuration .destination .dataset_id = "d"
1191+ query_job .configuration .destination .table_id = "t"
1192+
1193+ args = mock .Mock ()
1194+ args .bigquery_api_endpoint = "e"
1195+ args .project = "p"
1196+ args .location = "l"
1197+
1198+ with mock_display as display_mock , mock_gen_html as gen_html_mock :
1199+ magics ._add_graph_widget (bq_client , query_result , query_text , query_job , args )
1200+
1201+ # Verify schema retrieval was NOT attempted since graph name couldn't be parsed
1202+ assert not bq_client .query .called
1203+
1204+ # Verify generate_visualization_html was called without a schema
1205+ assert gen_html_mock .called
1206+ params_str = gen_html_mock .call_args [1 ]["params" ]
1207+ params = json .loads (params_str .replace ('\\ "' , '"' ).replace ("\\ \\ " , "\\ " ))
1208+ assert "schema" not in params
1209+
1210+ assert display_mock .called
1211+
1212+
1213+ @pytest .mark .skipif (
1214+ graph_visualization is None or bigquery_storage is None ,
1215+ reason = "Requires `spanner-graph-notebook` and `google-cloud-bigquery-storage`" ,
1216+ )
1217+ def test_add_graph_widget_schema_not_found (monkeypatch ):
1218+ """Test _add_graph_widget when the graph schema is not found in INFORMATION_SCHEMA."""
1219+ mock_display = mock .patch ("IPython.display.display" , autospec = True )
1220+ mock_gen_html = mock .patch (
1221+ "spanner_graphs.graph_visualization.generate_visualization_html" ,
1222+ return_value = "<html>generated_html</html>" ,
1223+ )
1224+
1225+ bq_client = mock .create_autospec (bigquery .Client , instance = True )
1226+ query_result = pandas .DataFrame ([{"id" : 1 }], columns = ["result" ])
1227+ query_text = "GRAPH my_dataset.my_graph"
1228+
1229+ query_job = mock .create_autospec (bigquery .job .QueryJob , instance = True )
1230+ query_job .configuration .destination .project = "p"
1231+ query_job .configuration .destination .dataset_id = "d"
1232+ query_job .configuration .destination .table_id = "t"
1233+
1234+ args = mock .Mock ()
1235+ args .bigquery_api_endpoint = "e"
1236+ args .project = "p"
1237+ args .location = "l"
1238+
1239+ # Mock INFORMATION_SCHEMA query returning empty results
1240+ mock_schema_df = pandas .DataFrame ([], columns = ["PROPERTY_GRAPH_METADATA_JSON" ])
1241+ bq_client .query .return_value .to_dataframe .return_value = mock_schema_df
1242+
1243+ with mock_display as display_mock , mock_gen_html as gen_html_mock :
1244+ magics ._add_graph_widget (bq_client , query_result , query_text , query_job , args )
1245+
1246+ # Verify schema retrieval was attempted
1247+ assert bq_client .query .called
1248+
1249+ # Verify generate_visualization_html was called without a schema
1250+ assert gen_html_mock .called
1251+ params_str = gen_html_mock .call_args [1 ]["params" ]
1252+ params = json .loads (params_str .replace ('\\ "' , '"' ).replace ("\\ \\ " , "\\ " ))
1253+ assert "schema" not in params
1254+
1255+ assert display_mock .called
1256+
1257+
11181258def test_bigquery_magic_default_connection_user_agent ():
11191259 globalipapp .start_ipython ()
11201260 ip = globalipapp .get_ipython ()
0 commit comments