From fc3ac6ced1a104c29c58386fe4055fb390bec980 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rados=C5=82aw=20Wa=C5=9Bko?= Date: Tue, 13 Aug 2024 17:20:55 +0200 Subject: [PATCH] Various fixes to visualizations (#10745) - Closes #10716 by un-marking the `Snowflake_Connection` as `private`. - Does the same to `SQLServer_Connection`. - Makes sure that `Snowflake_Connection` has correct visualization and enables links for it. - Adds a fallback in `to_default_visualization_data` and in Table's `prepare_visualization` so that if `to_js_object` of a given type is malformed, we still get some kind of visualization + debug info about the underlying error. --- .../visualizations/TableVisualization.vue | 3 +++ .../src/Internal/SQLServer_Connection.enso | 2 -- .../{Internal => }/Snowflake_Connection.enso | 8 ++++-- .../0.0.0-dev/src/Snowflake_Details.enso | 2 +- .../Visualization/0.0.0-dev/src/Helpers.enso | 4 ++- .../0.0.0-dev/src/Table/Visualization.enso | 26 ++++++++++++------- .../job/ProgramExecutionSupport.scala | 2 +- .../RuntimeVisualizationsTest.scala | 2 +- 8 files changed, 32 insertions(+), 17 deletions(-) rename distribution/lib/Standard/Snowflake/0.0.0-dev/src/{Internal => }/Snowflake_Connection.enso (98%) diff --git a/app/gui2/src/components/visualizations/TableVisualization.vue b/app/gui2/src/components/visualizations/TableVisualization.vue index 34618e78285..46ac45af551 100644 --- a/app/gui2/src/components/visualizations/TableVisualization.vue +++ b/app/gui2/src/components/visualizations/TableVisualization.vue @@ -106,6 +106,8 @@ const SQLITE_CONNECTIONS_NODE_TYPE = 'Standard.Database.Internal.SQLite.SQLite_Connection.SQLite_Connection' const POSTGRES_CONNECTIONS_NODE_TYPE = 'Standard.Database.Internal.Postgres.Postgres_Connection.Postgres_Connection' +const SNOWFLAKE_CONNECTIONS_NODE_TYPE = + 'Standard.Snowflake.Snowflake_Connection.Snowflake_Connection' const rowLimit = ref(0) const page = ref(0) @@ -165,6 +167,7 @@ const newNodeSelectorValues = computed(() => { break case SQLITE_CONNECTIONS_NODE_TYPE: case POSTGRES_CONNECTIONS_NODE_TYPE: + case SNOWFLAKE_CONNECTIONS_NODE_TYPE: tooltipValue = 'table' headerName = 'Tables' break diff --git a/distribution/lib/Standard/Microsoft/0.0.0-dev/src/Internal/SQLServer_Connection.enso b/distribution/lib/Standard/Microsoft/0.0.0-dev/src/Internal/SQLServer_Connection.enso index c1ff786833f..f3699e5ccb2 100644 --- a/distribution/lib/Standard/Microsoft/0.0.0-dev/src/Internal/SQLServer_Connection.enso +++ b/distribution/lib/Standard/Microsoft/0.0.0-dev/src/Internal/SQLServer_Connection.enso @@ -1,5 +1,3 @@ -private - from Standard.Base import all import Standard.Base.Metadata.Display from Standard.Base.Metadata.Choice import Option diff --git a/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Internal/Snowflake_Connection.enso b/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Connection.enso similarity index 98% rename from distribution/lib/Standard/Snowflake/0.0.0-dev/src/Internal/Snowflake_Connection.enso rename to distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Connection.enso index 8f3f4248552..cb1a29135a1 100644 --- a/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Internal/Snowflake_Connection.enso +++ b/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Connection.enso @@ -1,5 +1,3 @@ -private - from Standard.Base import all import Standard.Base.Metadata.Display from Standard.Base.Metadata.Choice import Option @@ -314,3 +312,9 @@ type Snowflake_Connection on the 'subclasses'. base_connection : Connection base_connection self = self.connection + + ## PRIVATE + Converts this value to a JSON serializable object. + to_js_object : JS_Object + to_js_object self = + JS_Object.from_pairs [["type", "Snowflake_Connection"], ["links", self.tables.at "Name" . to_vector]] diff --git a/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Details.enso b/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Details.enso index 560fc05f254..4b55d5338dd 100644 --- a/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Details.enso +++ b/distribution/lib/Standard/Snowflake/0.0.0-dev/src/Snowflake_Details.enso @@ -5,7 +5,7 @@ import Standard.Base.Errors.Illegal_State.Illegal_State import Standard.Database.Connection.Connection_Options.Connection_Options import Standard.Database.Connection.Credentials.Credentials -import project.Internal.Snowflake_Connection.Snowflake_Connection +import project.Snowflake_Connection.Snowflake_Connection polyglot java import net.snowflake.client.jdbc.SnowflakeDriver diff --git a/distribution/lib/Standard/Visualization/0.0.0-dev/src/Helpers.enso b/distribution/lib/Standard/Visualization/0.0.0-dev/src/Helpers.enso index 01380c3cae7..68b29f2a4ea 100644 --- a/distribution/lib/Standard/Visualization/0.0.0-dev/src/Helpers.enso +++ b/distribution/lib/Standard/Visualization/0.0.0-dev/src/Helpers.enso @@ -34,7 +34,9 @@ JS_Object.default_visualization self = Id.json 2.to_default_visualization_data Any.to_default_visualization_data : Text -Any.to_default_visualization_data self = self.to_json +Any.to_default_visualization_data self = + Panic.recover Any self.to_json . catch Any err-> + (JS_Object.from_pairs [["value", self.to_display_text], ["_to_js_object_error_", err.to_display_text]]).to_json ## PRIVATE diff --git a/distribution/lib/Standard/Visualization/0.0.0-dev/src/Table/Visualization.enso b/distribution/lib/Standard/Visualization/0.0.0-dev/src/Table/Visualization.enso index faa6126e2f9..98732fc8de6 100644 --- a/distribution/lib/Standard/Visualization/0.0.0-dev/src/Table/Visualization.enso +++ b/distribution/lib/Standard/Visualization/0.0.0-dev/src/Table/Visualization.enso @@ -187,15 +187,23 @@ make_json_for_table dataframe all_rows_count include_index_col = Create JSON serialization of values. make_json_for_other : Any -> JS_Object make_json_for_other x = - js_value = x.to_js_object - value = if js_value.is_a JS_Object . not then js_value else - pairs = [['_display_text_', x.to_display_text]] + js_value.field_names.map f-> [f, make_json_for_value (js_value.get f)] - JS_Object.from_pairs pairs - link_fields = if js_value.is_a JS_Object . not then [] else - if js_value.contains_key 'links' then [["links", js_value.get 'links']] else [] - additional_fields = if js_value.is_a JS_Object . not then [] else - if js_value.contains_key 'get_child_node' then [["get_child_node", js_value.get 'get_child_node']] else [] - JS_Object.from_pairs <| [["json", value]] + additional_fields + link_fields + js_value = Panic.recover Any x.to_js_object + supports_js_object = js_value.is_error.not + case supports_js_object of + True -> + value = if js_value.is_a JS_Object . not then js_value else + pairs = [['_display_text_', x.to_display_text]] + js_value.field_names.map f-> [f, make_json_for_value (js_value.get f)] + JS_Object.from_pairs pairs + link_fields = if js_value.is_a JS_Object . not then [] else + if js_value.contains_key 'links' then [["links", js_value.get 'links']] else [] + additional_fields = if js_value.is_a JS_Object . not then [] else + if js_value.contains_key 'get_child_node' then [["get_child_node", js_value.get 'get_child_node']] else [] + JS_Object.from_pairs <| [["json", value]] + additional_fields + link_fields + + # Fallback for objects that fail to be serialized through `to_js_object`. + False -> + json = JS_Object.from_pairs [["_display_text_", x.to_display_text], ["_to_js_object_error_", js_value.catch.to_display_text]] + JS_Object.from_pairs [["json", json]] ## PRIVATE Create JSON serialization of values for the table. diff --git a/engine/runtime-instrument-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala b/engine/runtime-instrument-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala index 17d4c65c696..779b6d80024 100644 --- a/engine/runtime-instrument-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala +++ b/engine/runtime-instrument-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala @@ -623,7 +623,7 @@ object ProgramExecutionSupport { .getOrElse(expressionValue.getClass) ctx.executionService.getLogger.log( Level.WARNING, - "Execution of visualization [{0}] on value [{1}] of [{2}] failed. {3} | {4}", + "Execution of visualization [{0}] on value [{1}] of [{2}] failed. {3} | {4} | {5}", Array[Object]( visualizationId, expressionId, diff --git a/engine/runtime-integration-tests/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala b/engine/runtime-integration-tests/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala index 4ab935b80a7..85d02a6bb92 100644 --- a/engine/runtime-integration-tests/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala +++ b/engine/runtime-integration-tests/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala @@ -2806,7 +2806,7 @@ class RuntimeVisualizationsTest extends AnyFlatSpec with Matchers { data } val stringified = new String(data) - stringified shouldEqual "\"Function\"" + stringified should include("""{"value":"Function"""") } it should "attach text visualization with arguments" in withContext() {