MindsDB 25.4.5.0__py3-none-any.whl → 25.5.4.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of MindsDB might be problematic. Click here for more details.
- mindsdb/__about__.py +1 -1
- mindsdb/__main__.py +215 -185
- mindsdb/api/a2a/__init__.py +0 -0
- mindsdb/api/a2a/__main__.py +114 -0
- mindsdb/api/a2a/a2a_client.py +439 -0
- mindsdb/api/a2a/agent.py +308 -0
- mindsdb/api/a2a/common/__init__.py +0 -0
- mindsdb/api/a2a/common/client/__init__.py +4 -0
- mindsdb/api/a2a/common/client/card_resolver.py +21 -0
- mindsdb/api/a2a/common/client/client.py +86 -0
- mindsdb/api/a2a/common/server/__init__.py +4 -0
- mindsdb/api/a2a/common/server/server.py +164 -0
- mindsdb/api/a2a/common/server/task_manager.py +287 -0
- mindsdb/api/a2a/common/server/utils.py +28 -0
- mindsdb/api/a2a/common/types.py +365 -0
- mindsdb/api/a2a/constants.py +9 -0
- mindsdb/api/a2a/run_a2a.py +129 -0
- mindsdb/api/a2a/task_manager.py +594 -0
- mindsdb/api/executor/command_executor.py +49 -28
- mindsdb/api/executor/datahub/classes/response.py +5 -2
- mindsdb/api/executor/datahub/datanodes/information_schema_datanode.py +8 -0
- mindsdb/api/executor/datahub/datanodes/integration_datanode.py +39 -72
- mindsdb/api/executor/datahub/datanodes/system_tables.py +10 -13
- mindsdb/api/executor/planner/query_planner.py +14 -2
- mindsdb/api/executor/sql_query/result_set.py +185 -52
- mindsdb/api/executor/sql_query/sql_query.py +1 -1
- mindsdb/api/executor/sql_query/steps/apply_predictor_step.py +11 -13
- mindsdb/api/executor/sql_query/steps/fetch_dataframe.py +8 -10
- mindsdb/api/executor/sql_query/steps/fetch_dataframe_partition.py +5 -44
- mindsdb/api/executor/sql_query/steps/insert_step.py +24 -15
- mindsdb/api/executor/sql_query/steps/join_step.py +1 -1
- mindsdb/api/executor/sql_query/steps/project_step.py +1 -1
- mindsdb/api/executor/sql_query/steps/sql_steps.py +1 -1
- mindsdb/api/executor/sql_query/steps/subselect_step.py +4 -8
- mindsdb/api/executor/sql_query/steps/union_step.py +1 -3
- mindsdb/api/http/initialize.py +118 -85
- mindsdb/api/http/namespaces/analysis.py +17 -4
- mindsdb/api/http/namespaces/file.py +8 -2
- mindsdb/api/http/namespaces/sql.py +13 -27
- mindsdb/api/http/namespaces/tree.py +1 -1
- mindsdb/api/http/start.py +7 -2
- mindsdb/api/mcp/start.py +42 -5
- mindsdb/api/mysql/mysql_proxy/data_types/mysql_packet.py +0 -1
- mindsdb/api/mysql/mysql_proxy/data_types/mysql_packets/binary_resultset_row_package.py +52 -19
- mindsdb/api/mysql/mysql_proxy/executor/mysql_executor.py +8 -10
- mindsdb/api/mysql/mysql_proxy/libs/constants/mysql.py +54 -38
- mindsdb/api/mysql/mysql_proxy/mysql_proxy.py +86 -123
- mindsdb/api/mysql/mysql_proxy/utilities/dump.py +351 -0
- mindsdb/api/mysql/mysql_proxy/utilities/exceptions.py +0 -4
- mindsdb/api/postgres/postgres_proxy/executor/executor.py +1 -1
- mindsdb/api/postgres/postgres_proxy/postgres_packets/postgres_message_formats.py +2 -2
- mindsdb/api/postgres/postgres_proxy/postgres_proxy.py +5 -6
- mindsdb/integrations/handlers/altibase_handler/altibase_handler.py +26 -27
- mindsdb/integrations/handlers/altibase_handler/connection_args.py +13 -13
- mindsdb/integrations/handlers/altibase_handler/tests/test_altibase_handler.py +8 -8
- mindsdb/integrations/handlers/altibase_handler/tests/test_altibase_handler_dsn.py +13 -13
- mindsdb/integrations/handlers/anthropic_handler/__init__.py +2 -2
- mindsdb/integrations/handlers/anthropic_handler/anthropic_handler.py +1 -3
- mindsdb/integrations/handlers/aurora_handler/aurora_handler.py +1 -0
- mindsdb/integrations/handlers/autosklearn_handler/autosklearn_handler.py +1 -1
- mindsdb/integrations/handlers/autosklearn_handler/config.py +0 -1
- mindsdb/integrations/handlers/bigquery_handler/bigquery_handler.py +1 -1
- mindsdb/integrations/handlers/bigquery_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/bigquery_handler/tests/test_bigquery_handler.py +1 -1
- mindsdb/integrations/handlers/binance_handler/binance_handler.py +1 -0
- mindsdb/integrations/handlers/binance_handler/binance_tables.py +3 -4
- mindsdb/integrations/handlers/byom_handler/__init__.py +0 -1
- mindsdb/integrations/handlers/chromadb_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/ckan_handler/ckan_handler.py +3 -0
- mindsdb/integrations/handlers/clickhouse_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/cloud_spanner_handler/tests/test_cloud_spanner_handler.py +0 -2
- mindsdb/integrations/handlers/cloud_sql_handler/cloud_sql_handler.py +0 -1
- mindsdb/integrations/handlers/cohere_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/cohere_handler/cohere_handler.py +11 -13
- mindsdb/integrations/handlers/confluence_handler/confluence_tables.py +6 -0
- mindsdb/integrations/handlers/databend_handler/connection_args.py +1 -1
- mindsdb/integrations/handlers/databend_handler/databend_handler.py +4 -4
- mindsdb/integrations/handlers/databend_handler/tests/__init__.py +0 -1
- mindsdb/integrations/handlers/databend_handler/tests/test_databend_handler.py +1 -1
- mindsdb/integrations/handlers/derby_handler/connection_args.py +1 -1
- mindsdb/integrations/handlers/derby_handler/derby_handler.py +14 -22
- mindsdb/integrations/handlers/derby_handler/tests/test_derby_handler.py +6 -6
- mindsdb/integrations/handlers/discord_handler/discord_handler.py +5 -5
- mindsdb/integrations/handlers/discord_handler/discord_tables.py +3 -3
- mindsdb/integrations/handlers/discord_handler/tests/test_discord.py +5 -3
- mindsdb/integrations/handlers/dockerhub_handler/dockerhub.py +3 -3
- mindsdb/integrations/handlers/dockerhub_handler/dockerhub_handler.py +2 -2
- mindsdb/integrations/handlers/dockerhub_handler/dockerhub_tables.py +57 -54
- mindsdb/integrations/handlers/dremio_handler/__init__.py +2 -2
- mindsdb/integrations/handlers/druid_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/druid_handler/druid_handler.py +2 -2
- mindsdb/integrations/handlers/edgelessdb_handler/tests/test_edgelessdb_handler.py +9 -9
- mindsdb/integrations/handlers/email_handler/email_client.py +1 -1
- mindsdb/integrations/handlers/email_handler/email_ingestor.py +1 -1
- mindsdb/integrations/handlers/email_handler/email_tables.py +0 -1
- mindsdb/integrations/handlers/email_handler/settings.py +0 -1
- mindsdb/integrations/handlers/eventstoredb_handler/eventstoredb_handler.py +2 -1
- mindsdb/integrations/handlers/firebird_handler/firebird_handler.py +1 -1
- mindsdb/integrations/handlers/flaml_handler/flaml_handler.py +9 -9
- mindsdb/integrations/handlers/frappe_handler/frappe_client.py +5 -5
- mindsdb/integrations/handlers/frappe_handler/frappe_handler.py +6 -5
- mindsdb/integrations/handlers/frappe_handler/frappe_tables.py +2 -2
- mindsdb/integrations/handlers/github_handler/connection_args.py +2 -2
- mindsdb/integrations/handlers/github_handler/github_handler.py +1 -8
- mindsdb/integrations/handlers/github_handler/github_tables.py +13 -24
- mindsdb/integrations/handlers/gitlab_handler/gitlab_handler.py +2 -1
- mindsdb/integrations/handlers/gitlab_handler/gitlab_tables.py +1 -4
- mindsdb/integrations/handlers/gmail_handler/gmail_handler.py +6 -13
- mindsdb/integrations/handlers/gmail_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/google_analytics_handler/requirements.txt +2 -1
- mindsdb/integrations/handlers/google_books_handler/google_books_handler.py +2 -1
- mindsdb/integrations/handlers/google_books_handler/google_books_tables.py +0 -3
- mindsdb/integrations/handlers/google_books_handler/requirements.txt +1 -1
- mindsdb/integrations/handlers/google_calendar_handler/google_calendar_handler.py +4 -4
- mindsdb/integrations/handlers/google_calendar_handler/google_calendar_tables.py +2 -6
- mindsdb/integrations/handlers/google_calendar_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/google_content_shopping_handler/google_content_shopping_handler.py +3 -2
- mindsdb/integrations/handlers/google_content_shopping_handler/google_content_shopping_tables.py +0 -3
- mindsdb/integrations/handlers/google_content_shopping_handler/requirements.txt +1 -1
- mindsdb/integrations/handlers/google_fit_handler/google_fit_handler.py +10 -12
- mindsdb/integrations/handlers/google_fit_handler/google_fit_tables.py +11 -13
- mindsdb/integrations/handlers/google_fit_handler/requirements.txt +2 -0
- mindsdb/integrations/handlers/google_search_handler/google_search_handler.py +2 -1
- mindsdb/integrations/handlers/google_search_handler/google_search_tables.py +0 -3
- mindsdb/integrations/handlers/google_search_handler/requirements.txt +1 -1
- mindsdb/integrations/handlers/groq_handler/__init__.py +3 -3
- mindsdb/integrations/handlers/hackernews_handler/hn_handler.py +5 -7
- mindsdb/integrations/handlers/hackernews_handler/hn_table.py +6 -7
- mindsdb/integrations/handlers/hive_handler/tests/test_hive_handler.py +1 -1
- mindsdb/integrations/handlers/hsqldb_handler/connection_args.py +6 -6
- mindsdb/integrations/handlers/hsqldb_handler/hsqldb_handler.py +4 -3
- mindsdb/integrations/handlers/huggingface_api_handler/exceptions.py +1 -1
- mindsdb/integrations/handlers/huggingface_api_handler/huggingface_api_handler.py +1 -8
- mindsdb/integrations/handlers/huggingface_handler/huggingface_handler.py +6 -6
- mindsdb/integrations/handlers/huggingface_handler/requirements.txt +1 -1
- mindsdb/integrations/handlers/huggingface_handler/requirements_cpu.txt +1 -1
- mindsdb/integrations/handlers/ignite_handler/ignite_handler.py +2 -1
- mindsdb/integrations/handlers/impala_handler/impala_handler.py +9 -12
- mindsdb/integrations/handlers/impala_handler/tests/test_impala_handler.py +11 -11
- mindsdb/integrations/handlers/influxdb_handler/influxdb_handler.py +10 -13
- mindsdb/integrations/handlers/influxdb_handler/influxdb_tables.py +20 -20
- mindsdb/integrations/handlers/informix_handler/__about__.py +8 -8
- mindsdb/integrations/handlers/informix_handler/__init__.py +12 -5
- mindsdb/integrations/handlers/informix_handler/informix_handler.py +99 -133
- mindsdb/integrations/handlers/informix_handler/tests/test_informix_handler.py +13 -11
- mindsdb/integrations/handlers/ingres_handler/__about__.py +0 -1
- mindsdb/integrations/handlers/ingres_handler/ingres_handler.py +1 -0
- mindsdb/integrations/handlers/jira_handler/jira_handler.archived.py +75 -0
- mindsdb/integrations/handlers/jira_handler/jira_handler.py +113 -38
- mindsdb/integrations/handlers/jira_handler/jira_tables.py +229 -0
- mindsdb/integrations/handlers/jira_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/kinetica_handler/__init__.py +0 -1
- mindsdb/integrations/handlers/langchain_handler/langchain_handler.py +4 -4
- mindsdb/integrations/handlers/langchain_handler/tools.py +9 -10
- mindsdb/integrations/handlers/leonardoai_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/lightfm_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/lightwood_handler/functions.py +2 -2
- mindsdb/integrations/handlers/lightwood_handler/lightwood_handler.py +0 -3
- mindsdb/integrations/handlers/lightwood_handler/requirements.txt +4 -4
- mindsdb/integrations/handlers/lightwood_handler/tests/test_lightwood_handler.py +11 -11
- mindsdb/integrations/handlers/lindorm_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/llama_index_handler/llama_index_handler.py +4 -4
- mindsdb/integrations/handlers/llama_index_handler/settings.py +10 -9
- mindsdb/integrations/handlers/materialize_handler/tests/test_materialize_handler.py +8 -10
- mindsdb/integrations/handlers/matrixone_handler/matrixone_handler.py +4 -4
- mindsdb/integrations/handlers/matrixone_handler/tests/test_matrixone_handler.py +8 -9
- mindsdb/integrations/handlers/maxdb_handler/connection_args.py +25 -25
- mindsdb/integrations/handlers/maxdb_handler/maxdb_handler.py +1 -0
- mindsdb/integrations/handlers/mediawiki_handler/mediawiki_handler.py +3 -2
- mindsdb/integrations/handlers/mediawiki_handler/mediawiki_tables.py +1 -1
- mindsdb/integrations/handlers/mendeley_handler/__about__.py +1 -1
- mindsdb/integrations/handlers/mendeley_handler/__init__.py +2 -2
- mindsdb/integrations/handlers/mendeley_handler/mendeley_handler.py +48 -56
- mindsdb/integrations/handlers/mendeley_handler/mendeley_tables.py +24 -29
- mindsdb/integrations/handlers/mendeley_handler/tests/test_mendeley_handler.py +19 -17
- mindsdb/integrations/handlers/merlion_handler/merlion_handler.py +5 -4
- mindsdb/integrations/handlers/minds_endpoint_handler/__init__.py +3 -3
- mindsdb/integrations/handlers/mlflow_handler/mlflow_handler.py +58 -36
- mindsdb/integrations/handlers/monetdb_handler/__about__.py +8 -8
- mindsdb/integrations/handlers/monetdb_handler/__init__.py +15 -5
- mindsdb/integrations/handlers/monetdb_handler/connection_args.py +17 -18
- mindsdb/integrations/handlers/monetdb_handler/monetdb_handler.py +40 -57
- mindsdb/integrations/handlers/monetdb_handler/tests/test_monetdb_handler.py +7 -8
- mindsdb/integrations/handlers/monetdb_handler/utils/monet_get_id.py +13 -14
- mindsdb/integrations/handlers/monkeylearn_handler/__about__.py +1 -1
- mindsdb/integrations/handlers/monkeylearn_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/monkeylearn_handler/monkeylearn_handler.py +2 -5
- mindsdb/integrations/handlers/ms_one_drive_handler/ms_graph_api_one_drive_client.py +1 -0
- mindsdb/integrations/handlers/ms_one_drive_handler/ms_one_drive_handler.py +1 -1
- mindsdb/integrations/handlers/ms_one_drive_handler/requirements.txt +2 -0
- mindsdb/integrations/handlers/ms_teams_handler/ms_graph_api_teams_client.py +23 -23
- mindsdb/integrations/handlers/ms_teams_handler/ms_teams_handler.py +3 -3
- mindsdb/integrations/handlers/ms_teams_handler/ms_teams_tables.py +10 -5
- mindsdb/integrations/handlers/ms_teams_handler/requirements.txt +3 -1
- mindsdb/integrations/handlers/mssql_handler/mssql_handler.py +73 -8
- mindsdb/integrations/handlers/mysql_handler/__about__.py +8 -8
- mindsdb/integrations/handlers/mysql_handler/__init__.py +15 -5
- mindsdb/integrations/handlers/mysql_handler/connection_args.py +43 -47
- mindsdb/integrations/handlers/mysql_handler/mysql_handler.py +101 -34
- mindsdb/integrations/handlers/mysql_handler/settings.py +15 -13
- mindsdb/integrations/handlers/neuralforecast_handler/neuralforecast_handler.py +1 -1
- mindsdb/integrations/handlers/newsapi_handler/newsapi_handler.py +1 -1
- mindsdb/integrations/handlers/newsapi_handler/tests/test_newsapi_handler.py +4 -4
- mindsdb/integrations/handlers/nuo_jdbc_handler/connection_args.py +2 -2
- mindsdb/integrations/handlers/nuo_jdbc_handler/nuo_jdbc_handler.py +28 -36
- mindsdb/integrations/handlers/nuo_jdbc_handler/tests/test_nuo_handler.py +5 -5
- mindsdb/integrations/handlers/oceanbase_handler/oceanbase_handler.py +0 -1
- mindsdb/integrations/handlers/oceanbase_handler/tests/test_oceanbase_handler.py +8 -10
- mindsdb/integrations/handlers/ollama_handler/ollama_handler.py +3 -3
- mindsdb/integrations/handlers/openai_handler/openai_handler.py +5 -4
- mindsdb/integrations/handlers/opengauss_handler/tests/test_opengauss_handler.py +1 -2
- mindsdb/integrations/handlers/openstreetmap_handler/__init__.py +7 -7
- mindsdb/integrations/handlers/oracle_handler/connection_args.py +6 -0
- mindsdb/integrations/handlers/oracle_handler/oracle_handler.py +77 -11
- mindsdb/integrations/handlers/orioledb_handler/tests/test_orioledb_handler.py +8 -10
- mindsdb/integrations/handlers/palm_handler/__about__.py +1 -1
- mindsdb/integrations/handlers/palm_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/palm_handler/palm_handler.py +1 -3
- mindsdb/integrations/handlers/paypal_handler/paypal_handler.py +2 -2
- mindsdb/integrations/handlers/paypal_handler/paypal_tables.py +15 -14
- mindsdb/integrations/handlers/pgvector_handler/pgvector_handler.py +53 -10
- mindsdb/integrations/handlers/phoenix_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/phoenix_handler/phoenix_handler.py +1 -0
- mindsdb/integrations/handlers/pinot_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/pinot_handler/pinot_handler.py +3 -2
- mindsdb/integrations/handlers/plaid_handler/plaid_handler.py +13 -13
- mindsdb/integrations/handlers/plaid_handler/plaid_tables.py +10 -12
- mindsdb/integrations/handlers/plaid_handler/utils.py +4 -6
- mindsdb/integrations/handlers/planetscale_handler/planetscale_handler.py +1 -4
- mindsdb/integrations/handlers/portkey_handler/__init__.py +2 -2
- mindsdb/integrations/handlers/postgres_handler/postgres_handler.py +105 -24
- mindsdb/integrations/handlers/postgres_handler/tests/test_postgres_handler.py +11 -6
- mindsdb/integrations/handlers/questdb_handler/questdb_handler.py +1 -2
- mindsdb/integrations/handlers/questdb_handler/tests/test_questdb_handler.py +2 -3
- mindsdb/integrations/handlers/quickbooks_handler/quickbooks_handler.py +6 -8
- mindsdb/integrations/handlers/quickbooks_handler/quickbooks_table.py +10 -10
- mindsdb/integrations/handlers/rag_handler/ingest.py +2 -2
- mindsdb/integrations/handlers/rag_handler/rag_handler.py +1 -1
- mindsdb/integrations/handlers/rag_handler/settings.py +1 -1
- mindsdb/integrations/handlers/reddit_handler/reddit_handler.py +2 -7
- mindsdb/integrations/handlers/reddit_handler/reddit_tables.py +2 -3
- mindsdb/integrations/handlers/replicate_handler/replicate_handler.py +6 -6
- mindsdb/integrations/handlers/rocket_chat_handler/rocket_chat_handler.py +1 -2
- mindsdb/integrations/handlers/rocket_chat_handler/rocket_chat_tables.py +0 -3
- mindsdb/integrations/handlers/rockset_handler/connection_args.py +14 -14
- mindsdb/integrations/handlers/rockset_handler/tests/test_rockset_handler.py +1 -0
- mindsdb/integrations/handlers/scylla_handler/scylla_handler.py +6 -5
- mindsdb/integrations/handlers/sendinblue_handler/sendinblue_handler.py +2 -1
- mindsdb/integrations/handlers/sendinblue_handler/sendinblue_tables.py +16 -16
- mindsdb/integrations/handlers/sentence_transformers_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/sheets_handler/connection_args.py +1 -1
- mindsdb/integrations/handlers/shopify_handler/shopify_handler.py +7 -6
- mindsdb/integrations/handlers/shopify_handler/shopify_tables.py +38 -41
- mindsdb/integrations/handlers/singlestore_handler/__about__.py +1 -1
- mindsdb/integrations/handlers/singlestore_handler/__init__.py +0 -1
- mindsdb/integrations/handlers/singlestore_handler/singlestore_handler.py +1 -0
- mindsdb/integrations/handlers/singlestore_handler/tests/test_singlestore_handler.py +3 -3
- mindsdb/integrations/handlers/slack_handler/__init__.py +3 -3
- mindsdb/integrations/handlers/snowflake_handler/requirements.txt +1 -1
- mindsdb/integrations/handlers/snowflake_handler/snowflake_handler.py +100 -6
- mindsdb/integrations/handlers/solr_handler/connection_args.py +7 -7
- mindsdb/integrations/handlers/solr_handler/solr_handler.py +2 -1
- mindsdb/integrations/handlers/solr_handler/tests/test_solr_handler.py +2 -1
- mindsdb/integrations/handlers/sqlany_handler/sqlany_handler.py +3 -2
- mindsdb/integrations/handlers/sqlite_handler/sqlite_handler.py +1 -0
- mindsdb/integrations/handlers/sqreamdb_handler/connection_args.py +1 -1
- mindsdb/integrations/handlers/sqreamdb_handler/sqreamdb_handler.py +15 -20
- mindsdb/integrations/handlers/sqreamdb_handler/tests/test_sqreamdb_handler.py +4 -4
- mindsdb/integrations/handlers/stabilityai_handler/__init__.py +1 -1
- mindsdb/integrations/handlers/starrocks_handler/starrocks_handler.py +0 -1
- mindsdb/integrations/handlers/starrocks_handler/tests/test_starrocks_handler.py +8 -10
- mindsdb/integrations/handlers/statsforecast_handler/statsforecast_handler.py +2 -2
- mindsdb/integrations/handlers/strava_handler/strava_handler.py +4 -8
- mindsdb/integrations/handlers/strava_handler/strava_tables.py +22 -30
- mindsdb/integrations/handlers/stripe_handler/stripe_handler.py +3 -2
- mindsdb/integrations/handlers/stripe_handler/stripe_tables.py +11 -27
- mindsdb/integrations/handlers/supabase_handler/tests/test_supabase_handler.py +1 -1
- mindsdb/integrations/handlers/surrealdb_handler/surrealdb_handler.py +4 -4
- mindsdb/integrations/handlers/tdengine_handler/tdengine_handler.py +25 -27
- mindsdb/integrations/handlers/tdengine_handler/tests/test_tdengine_handler.py +8 -8
- mindsdb/integrations/handlers/tidb_handler/tests/test_tidb_handler.py +1 -2
- mindsdb/integrations/handlers/timegpt_handler/timegpt_handler.py +5 -5
- mindsdb/integrations/handlers/tpot_handler/tpot_handler.py +21 -26
- mindsdb/integrations/handlers/trino_handler/trino_handler.py +14 -14
- mindsdb/integrations/handlers/twitter_handler/twitter_handler.py +2 -4
- mindsdb/integrations/handlers/unify_handler/tests/test_unify_handler.py +7 -8
- mindsdb/integrations/handlers/unify_handler/unify_handler.py +9 -9
- mindsdb/integrations/handlers/vertex_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/vertex_handler/vertex_client.py +1 -1
- mindsdb/integrations/handlers/vertica_handler/tests/test_vertica_handler.py +11 -11
- mindsdb/integrations/handlers/vertica_handler/vertica_handler.py +11 -14
- mindsdb/integrations/handlers/vitess_handler/tests/test_vitess_handler.py +9 -11
- mindsdb/integrations/handlers/vitess_handler/vitess_handler.py +0 -1
- mindsdb/integrations/handlers/web_handler/web_handler.py +1 -0
- mindsdb/integrations/handlers/whatsapp_handler/__init__.py +3 -3
- mindsdb/integrations/handlers/writer_handler/evaluate.py +1 -1
- mindsdb/integrations/handlers/writer_handler/settings.py +0 -1
- mindsdb/integrations/handlers/writer_handler/writer_handler.py +1 -0
- mindsdb/integrations/handlers/youtube_handler/requirements.txt +1 -0
- mindsdb/integrations/handlers/youtube_handler/youtube_handler.py +5 -5
- mindsdb/integrations/handlers/youtube_handler/youtube_tables.py +26 -27
- mindsdb/integrations/handlers/yugabyte_handler/tests/test_yugabyte_handler.py +3 -3
- mindsdb/integrations/handlers/yugabyte_handler/yugabyte_handler.py +0 -6
- mindsdb/integrations/libs/response.py +67 -52
- mindsdb/integrations/libs/vectordatabase_handler.py +6 -0
- mindsdb/integrations/utilities/files/file_reader.py +5 -2
- mindsdb/integrations/utilities/handler_utils.py +15 -3
- mindsdb/integrations/utilities/handlers/api_utilities/__init__.py +0 -1
- mindsdb/integrations/utilities/handlers/auth_utilities/__init__.py +0 -2
- mindsdb/integrations/utilities/utils.py +3 -3
- mindsdb/interfaces/agents/agents_controller.py +164 -1
- mindsdb/interfaces/agents/constants.py +29 -2
- mindsdb/interfaces/agents/langchain_agent.py +18 -8
- mindsdb/interfaces/agents/mindsdb_database_agent.py +101 -2
- mindsdb/interfaces/database/projects.py +1 -7
- mindsdb/interfaces/functions/controller.py +11 -14
- mindsdb/interfaces/functions/to_markdown.py +9 -124
- mindsdb/interfaces/knowledge_base/controller.py +47 -19
- mindsdb/interfaces/knowledge_base/preprocessing/document_preprocessor.py +41 -15
- mindsdb/interfaces/knowledge_base/preprocessing/json_chunker.py +434 -0
- mindsdb/interfaces/knowledge_base/preprocessing/models.py +54 -0
- mindsdb/interfaces/knowledge_base/utils.py +10 -15
- mindsdb/interfaces/model/model_controller.py +0 -2
- mindsdb/interfaces/query_context/context_controller.py +66 -10
- mindsdb/interfaces/skills/custom/text2sql/mindsdb_kb_tools.py +190 -0
- mindsdb/interfaces/skills/custom/text2sql/mindsdb_sql_toolkit.py +92 -0
- mindsdb/interfaces/skills/skill_tool.py +202 -57
- mindsdb/interfaces/skills/sql_agent.py +238 -28
- mindsdb/interfaces/storage/fs.py +1 -0
- mindsdb/interfaces/variables/__init__.py +0 -0
- mindsdb/interfaces/variables/variables_controller.py +97 -0
- mindsdb/migrations/env.py +5 -7
- mindsdb/migrations/migrate.py +47 -9
- mindsdb/migrations/versions/2025-05-21_9f150e4f9a05_checkpoint_1.py +360 -0
- mindsdb/utilities/config.py +333 -220
- mindsdb/utilities/context.py +1 -1
- mindsdb/utilities/functions.py +0 -36
- mindsdb/utilities/langfuse.py +19 -10
- mindsdb/utilities/otel/__init__.py +9 -193
- mindsdb/utilities/otel/metric_handlers/__init__.py +5 -1
- mindsdb/utilities/otel/prepare.py +198 -0
- mindsdb/utilities/sql.py +83 -0
- mindsdb/utilities/starters.py +13 -0
- {mindsdb-25.4.5.0.dist-info → mindsdb-25.5.4.0.dist-info}/METADATA +351 -338
- {mindsdb-25.4.5.0.dist-info → mindsdb-25.5.4.0.dist-info}/RECORD +348 -322
- {mindsdb-25.4.5.0.dist-info → mindsdb-25.5.4.0.dist-info}/WHEEL +1 -1
- mindsdb/api/mysql/mysql_proxy/classes/sql_statement_parser.py +0 -151
- mindsdb/integrations/handlers/monkeylearn_handler/requirements.txt +0 -1
- {mindsdb-25.4.5.0.dist-info → mindsdb-25.5.4.0.dist-info}/licenses/LICENSE +0 -0
- {mindsdb-25.4.5.0.dist-info → mindsdb-25.5.4.0.dist-info}/top_level.txt +0 -0
|
@@ -18,4 +18,4 @@ icon_path = "icon.svg"
|
|
|
18
18
|
permanent = False
|
|
19
19
|
execution_method = "subprocess_keep"
|
|
20
20
|
|
|
21
|
-
__all__ = ["Handler", "version", "name", "type", "title", "description", "import_error", "icon_path"]
|
|
21
|
+
__all__ = ["Handler", "version", "name", "type", "title", "description", "import_error", "icon_path"]
|
|
@@ -13,6 +13,7 @@ from mindsdb.integrations.libs.api_handler_exceptions import InvalidNativeQuery,
|
|
|
13
13
|
|
|
14
14
|
logger = log.getLogger(__name__)
|
|
15
15
|
|
|
16
|
+
|
|
16
17
|
class ShopifyHandler(APIHandler):
|
|
17
18
|
"""
|
|
18
19
|
The Shopify handler implementation.
|
|
@@ -30,7 +31,7 @@ class ShopifyHandler(APIHandler):
|
|
|
30
31
|
super().__init__(name)
|
|
31
32
|
|
|
32
33
|
if kwargs.get("connection_data") is None:
|
|
33
|
-
raise MissingConnectionParams(
|
|
34
|
+
raise MissingConnectionParams("Incomplete parameters passed to Shopify Handler")
|
|
34
35
|
|
|
35
36
|
connection_data = kwargs.get("connection_data", {})
|
|
36
37
|
self.connection_data = connection_data
|
|
@@ -78,7 +79,7 @@ class ShopifyHandler(APIHandler):
|
|
|
78
79
|
return self.connection
|
|
79
80
|
|
|
80
81
|
if self.kwargs.get("connection_data") is None:
|
|
81
|
-
raise MissingConnectionParams(
|
|
82
|
+
raise MissingConnectionParams("Incomplete parameters passed to Shopify Handler")
|
|
82
83
|
|
|
83
84
|
api_session = shopify.Session(self.connection_data['shop_url'], '2021-10', self.connection_data['access_token'])
|
|
84
85
|
|
|
@@ -106,8 +107,8 @@ class ShopifyHandler(APIHandler):
|
|
|
106
107
|
shopify.Shop.current()
|
|
107
108
|
response.success = True
|
|
108
109
|
except Exception as e:
|
|
109
|
-
logger.error(
|
|
110
|
-
raise ConnectionFailed(
|
|
110
|
+
logger.error('Error connecting to Shopify!')
|
|
111
|
+
raise ConnectionFailed("Conenction to Shopify failed.")
|
|
111
112
|
response.error_message = str(e)
|
|
112
113
|
|
|
113
114
|
if self.yotpo_app_key is not None and self.yotpo_access_token is not None:
|
|
@@ -138,6 +139,6 @@ class ShopifyHandler(APIHandler):
|
|
|
138
139
|
"""
|
|
139
140
|
try:
|
|
140
141
|
ast = parse_sql(query)
|
|
141
|
-
except Exception
|
|
142
|
+
except Exception:
|
|
142
143
|
raise InvalidNativeQuery(f"The query {query} is invalid.")
|
|
143
|
-
return self.query(ast)
|
|
144
|
+
return self.query(ast)
|
|
@@ -57,7 +57,7 @@ class ProductsTable(APITable):
|
|
|
57
57
|
products_df = select_statement_executor.execute_query()
|
|
58
58
|
|
|
59
59
|
return products_df
|
|
60
|
-
|
|
60
|
+
|
|
61
61
|
def insert(self, query: ast.Insert) -> None:
|
|
62
62
|
"""Inserts data into the Shopify "POST /products" API endpoint.
|
|
63
63
|
|
|
@@ -78,12 +78,12 @@ class ProductsTable(APITable):
|
|
|
78
78
|
insert_statement_parser = INSERTQueryParser(
|
|
79
79
|
query,
|
|
80
80
|
supported_columns=['title', 'body_html', 'vendor', 'product_type', 'tags', 'status'],
|
|
81
|
-
mandatory_columns=['title'
|
|
81
|
+
mandatory_columns=['title'],
|
|
82
82
|
all_mandatory=False
|
|
83
83
|
)
|
|
84
84
|
product_data = insert_statement_parser.parse_query()
|
|
85
85
|
self.create_products(product_data)
|
|
86
|
-
|
|
86
|
+
|
|
87
87
|
def delete(self, query: ast.Delete) -> None:
|
|
88
88
|
"""
|
|
89
89
|
Deletes data from the Shopify "DELETE /products" API endpoint.
|
|
@@ -407,7 +407,7 @@ class OrdersTable(APITable):
|
|
|
407
407
|
----------
|
|
408
408
|
query : ast.Insert
|
|
409
409
|
Given SQL INSERT query
|
|
410
|
-
|
|
410
|
+
|
|
411
411
|
Returns
|
|
412
412
|
-------
|
|
413
413
|
None
|
|
@@ -420,26 +420,26 @@ class OrdersTable(APITable):
|
|
|
420
420
|
insert_statement_parser = INSERTQueryParser(
|
|
421
421
|
query,
|
|
422
422
|
supported_columns=['address1_ba', 'address2_ba', 'city_ba', 'company_ba', 'country_ba',
|
|
423
|
-
'country_code_ba', 'first_name_ba', 'last_name_ba', 'latitude_ba',
|
|
424
|
-
'longitude_ba', 'name_ba', 'phone_ba', 'province_ba', 'province_code_ba',
|
|
425
|
-
'zip_ba',
|
|
423
|
+
'country_code_ba', 'first_name_ba', 'last_name_ba', 'latitude_ba',
|
|
424
|
+
'longitude_ba', 'name_ba', 'phone_ba', 'province_ba', 'province_code_ba',
|
|
425
|
+
'zip_ba',
|
|
426
426
|
'address1_sa', 'address2_sa', 'city_sa', 'company_sa',
|
|
427
|
-
'country_sa', 'country_code_sa', 'first_name_sa', 'last_name_sa',
|
|
428
|
-
'latitude_sa', 'longitude_sa', 'name_sa', 'phone_sa', 'province_sa',
|
|
429
|
-
'province_code_sa', 'zip_sa',
|
|
427
|
+
'country_sa', 'country_code_sa', 'first_name_sa', 'last_name_sa',
|
|
428
|
+
'latitude_sa', 'longitude_sa', 'name_sa', 'phone_sa', 'province_sa',
|
|
429
|
+
'province_code_sa', 'zip_sa',
|
|
430
430
|
'amount_dc', 'code_dc', 'type_dc',
|
|
431
|
-
'gift_card_li', 'grams_li',
|
|
432
|
-
'vendor_li', 'fulfillment_status_li', 'sku_li', 'variant_title_li',
|
|
431
|
+
'gift_card_li', 'grams_li', 'price_li', 'quantity_li', 'title_li',
|
|
432
|
+
'vendor_li', 'fulfillment_status_li', 'sku_li', 'variant_title_li',
|
|
433
433
|
'name_li', 'value_li',
|
|
434
434
|
'price_tl', 'rate_tl', 'title_tl', 'channel_liable_tl',
|
|
435
435
|
'name_na', 'value_na',
|
|
436
|
-
'code_sl', 'price_sl', 'discounted_price_sl', 'source_sl',
|
|
437
|
-
'title_sl',
|
|
438
|
-
'carrier_identifier_sl', 'requested_fulfillment_service_id_sl',
|
|
436
|
+
'code_sl', 'price_sl', 'discounted_price_sl', 'source_sl',
|
|
437
|
+
'title_sl',
|
|
438
|
+
'carrier_identifier_sl', 'requested_fulfillment_service_id_sl',
|
|
439
439
|
'is_removed_sl',
|
|
440
|
-
'buyer_accepts_marketing', 'currency', 'email', 'financial_status',
|
|
441
|
-
'fulfillment_status', 'note', 'phone', 'po_number', 'processed_at',
|
|
442
|
-
'referring_site', 'source_name', 'source_identifier', 'source_url',
|
|
440
|
+
'buyer_accepts_marketing', 'currency', 'email', 'financial_status',
|
|
441
|
+
'fulfillment_status', 'note', 'phone', 'po_number', 'processed_at',
|
|
442
|
+
'referring_site', 'source_name', 'source_identifier', 'source_url',
|
|
443
443
|
'tags', 'taxes_included', 'test', 'total_tax', 'total_weight'],
|
|
444
444
|
mandatory_columns=['price_li', 'title_li'],
|
|
445
445
|
all_mandatory=False
|
|
@@ -447,7 +447,6 @@ class OrdersTable(APITable):
|
|
|
447
447
|
order_data = insert_statement_parser.parse_query()
|
|
448
448
|
self.create_orders(order_data)
|
|
449
449
|
|
|
450
|
-
|
|
451
450
|
def update(self, query: ast.Update) -> None:
|
|
452
451
|
"""Updates data in the Shopify "PUT /orders" API endpoint.
|
|
453
452
|
|
|
@@ -525,15 +524,15 @@ class OrdersTable(APITable):
|
|
|
525
524
|
shopify.ShopifyResource.activate_session(api_session)
|
|
526
525
|
# separate columns by API object
|
|
527
526
|
line_items_columns = {'gift_card_li', 'grams_li', 'price_li', 'quantity_li', 'title_li',
|
|
528
|
-
|
|
527
|
+
'vendor_li', 'fulfillment_status_li', 'sku_li', 'variant_title_li'}
|
|
529
528
|
billing_address_columns = {'address1_ba', 'address2_ba', 'city_ba', 'company_ba',
|
|
530
|
-
'country_ba', 'country_code_ba', 'first_name_ba', 'last_name_ba',
|
|
529
|
+
'country_ba', 'country_code_ba', 'first_name_ba', 'last_name_ba',
|
|
531
530
|
'latitude_ba', 'longitude_ba', 'name_ba', 'phone_ba',
|
|
532
531
|
'province_ba', 'province_code_ba', 'zip_ba'}
|
|
533
532
|
shipping_address_columns = {'address1_sa', 'address2_sa', 'city_sa', 'company_sa',
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
533
|
+
'country_sa', 'country_code_sa', 'first_name_sa', 'last_name_sa',
|
|
534
|
+
'latitude_sa', 'longitude_sa', 'name_sa', 'phone_sa',
|
|
535
|
+
'province_sa', 'province_code_sa', 'zip_sa'}
|
|
537
536
|
discount_codes_columns = {'amount_dc', 'code_dc', 'type_dc'}
|
|
538
537
|
tax_lines_columns = {'price_tl', 'rate_tl', 'title_tl', 'channel_liable_tl'}
|
|
539
538
|
note_attributes_columns = {'name_na', 'value_na'}
|
|
@@ -541,15 +540,15 @@ class OrdersTable(APITable):
|
|
|
541
540
|
'source_sl', 'title_sl', 'carrier_identifier_sl',
|
|
542
541
|
'requested_fulfillment_service_id_sl', 'is_removed_sl'}
|
|
543
542
|
line_items_properties_columns = {'name_li', 'value_li'}
|
|
544
|
-
all_columns = (line_items_columns | billing_address_columns | shipping_address_columns
|
|
545
|
-
discount_codes_columns | tax_lines_columns | note_attributes_columns
|
|
546
|
-
shipping_lines_columns | line_items_properties_columns)
|
|
543
|
+
all_columns = (line_items_columns | billing_address_columns | shipping_address_columns
|
|
544
|
+
| discount_codes_columns | tax_lines_columns | note_attributes_columns
|
|
545
|
+
| shipping_lines_columns | line_items_properties_columns)
|
|
547
546
|
modified_order_data = []
|
|
548
547
|
|
|
549
548
|
for order in order_data:
|
|
550
549
|
# separate values by object
|
|
551
550
|
order_data_trimmed = {key: val for key, val in order.items()
|
|
552
|
-
|
|
551
|
+
if key not in all_columns}
|
|
553
552
|
line_items_data = OrdersTable._extract_data_helper(order, line_items_columns)
|
|
554
553
|
billing_address_data = OrdersTable._extract_data_helper(order, billing_address_columns)
|
|
555
554
|
shipping_address_data = OrdersTable._extract_data_helper(order, shipping_address_columns)
|
|
@@ -604,6 +603,7 @@ class OrdersTable(APITable):
|
|
|
604
603
|
orders = shopify.Order.find(**kwargs)
|
|
605
604
|
return [order.to_dict() for order in orders]
|
|
606
605
|
|
|
606
|
+
|
|
607
607
|
class InventoryLevelTable(APITable):
|
|
608
608
|
"""The Shopify Inventory Table implementation"""
|
|
609
609
|
|
|
@@ -687,6 +687,7 @@ class InventoryLevelTable(APITable):
|
|
|
687
687
|
inventories = shopify.InventoryLevel.find(**kwargs)
|
|
688
688
|
return [inventory.to_dict() for inventory in inventories]
|
|
689
689
|
|
|
690
|
+
|
|
690
691
|
class LocationTable(APITable):
|
|
691
692
|
"""The Shopify Location Table implementation"""
|
|
692
693
|
|
|
@@ -738,6 +739,7 @@ class LocationTable(APITable):
|
|
|
738
739
|
locations = shopify.Location.find(**kwargs)
|
|
739
740
|
return [location.to_dict() for location in locations]
|
|
740
741
|
|
|
742
|
+
|
|
741
743
|
class CustomerReviews(APITable):
|
|
742
744
|
"""The Shopify Customer Reviews Table implementation"""
|
|
743
745
|
|
|
@@ -794,6 +796,7 @@ class CustomerReviews(APITable):
|
|
|
794
796
|
json_response = requests.get(url, headers=headers).json()
|
|
795
797
|
return [review for review in json_response['reviews']] if 'reviews' in json_response else []
|
|
796
798
|
|
|
799
|
+
|
|
797
800
|
class CarrierServiceTable(APITable):
|
|
798
801
|
"""The Shopify carrier service Table implementation. Example carrier services like usps, dhl etc."""
|
|
799
802
|
|
|
@@ -831,11 +834,11 @@ class CarrierServiceTable(APITable):
|
|
|
831
834
|
where_conditions,
|
|
832
835
|
order_by_conditions
|
|
833
836
|
)
|
|
834
|
-
|
|
837
|
+
|
|
835
838
|
carrier_service_df = select_statement_executor.execute_query()
|
|
836
839
|
|
|
837
840
|
return carrier_service_df
|
|
838
|
-
|
|
841
|
+
|
|
839
842
|
def insert(self, query: ast.Insert) -> None:
|
|
840
843
|
"""Inserts data into the Shopify "POST /carrier_services" API endpoint.
|
|
841
844
|
|
|
@@ -895,7 +898,6 @@ class CarrierServiceTable(APITable):
|
|
|
895
898
|
carrier_service_ids = carrier_services_df['id'].tolist()
|
|
896
899
|
self.delete_carrier_services(carrier_service_ids)
|
|
897
900
|
|
|
898
|
-
|
|
899
901
|
def update(self, query: ast.Update) -> None:
|
|
900
902
|
"""Updates data from the Shopify "PUT /carrier_services" API endpoint.
|
|
901
903
|
|
|
@@ -925,8 +927,6 @@ class CarrierServiceTable(APITable):
|
|
|
925
927
|
carrier_service_ids = carrier_services_df['id'].tolist()
|
|
926
928
|
self.update_carrier_service(carrier_service_ids, values_to_update)
|
|
927
929
|
|
|
928
|
-
|
|
929
|
-
|
|
930
930
|
def get_columns(self) -> List[Text]:
|
|
931
931
|
return ["id", "name", "active", "service_discovery", "carrier_service_type", "admin_graphql_api_id"]
|
|
932
932
|
|
|
@@ -935,7 +935,7 @@ class CarrierServiceTable(APITable):
|
|
|
935
935
|
shopify.ShopifyResource.activate_session(api_session)
|
|
936
936
|
services = shopify.CarrierService.find()
|
|
937
937
|
return [service.to_dict() for service in services]
|
|
938
|
-
|
|
938
|
+
|
|
939
939
|
def create_carrier_service(self, carrier_service_data: List[Dict[Text, Any]]) -> None:
|
|
940
940
|
api_session = self.handler.connect()
|
|
941
941
|
shopify.ShopifyResource.activate_session(api_session)
|
|
@@ -968,7 +968,6 @@ class CarrierServiceTable(APITable):
|
|
|
968
968
|
logger.info(f'Carrier Service {carrier_service_id} updated')
|
|
969
969
|
|
|
970
970
|
|
|
971
|
-
|
|
972
971
|
class ShippingZoneTable(APITable):
|
|
973
972
|
"""The Shopify shipping zone Table implementation"""
|
|
974
973
|
|
|
@@ -1000,7 +999,6 @@ class ShippingZoneTable(APITable):
|
|
|
1000
999
|
|
|
1001
1000
|
shipping_zone_df = pd.json_normalize(self.get_shipping_zone(), record_path="countries", meta=["id", "name"], record_prefix="countries_")
|
|
1002
1001
|
|
|
1003
|
-
|
|
1004
1002
|
select_statement_executor = SELECTQueryExecutor(
|
|
1005
1003
|
shipping_zone_df,
|
|
1006
1004
|
selected_columns,
|
|
@@ -1008,7 +1006,7 @@ class ShippingZoneTable(APITable):
|
|
|
1008
1006
|
order_by_conditions,
|
|
1009
1007
|
result_limit
|
|
1010
1008
|
)
|
|
1011
|
-
|
|
1009
|
+
|
|
1012
1010
|
shipping_zone_df = select_statement_executor.execute_query()
|
|
1013
1011
|
|
|
1014
1012
|
return shipping_zone_df
|
|
@@ -1029,12 +1027,13 @@ class ShippingZoneTable(APITable):
|
|
|
1029
1027
|
zones = shopify.ShippingZone.find()
|
|
1030
1028
|
return [self.clean_response(zone.to_dict()) for zone in zones]
|
|
1031
1029
|
|
|
1030
|
+
|
|
1032
1031
|
class SalesChannelTable(APITable):
|
|
1033
1032
|
"""The Shopify Sales Channel Table implementation"""
|
|
1034
1033
|
|
|
1035
1034
|
def select(self, query: ast.Select) -> pd.DataFrame:
|
|
1036
1035
|
"""Pulls data from the Shopify "GET /publication API endpoint, as Channel API endpoint is deprecated
|
|
1037
|
-
|
|
1036
|
+
|
|
1038
1037
|
|
|
1039
1038
|
Parameters
|
|
1040
1039
|
----------
|
|
@@ -1071,13 +1070,11 @@ class SalesChannelTable(APITable):
|
|
|
1071
1070
|
sales_channel_df = select_statement_executor.execute_query()
|
|
1072
1071
|
return sales_channel_df
|
|
1073
1072
|
|
|
1074
|
-
|
|
1075
1073
|
def get_columns(self) -> List[Text]:
|
|
1076
1074
|
return pd.json_normalize(self.get_sales_channel(limit=1)).columns.tolist()
|
|
1077
|
-
|
|
1078
1075
|
|
|
1079
1076
|
def get_sales_channel(self, **kwargs) -> List[Dict]:
|
|
1080
1077
|
api_session = self.handler.connect()
|
|
1081
1078
|
shopify.ShopifyResource.activate_session(api_session)
|
|
1082
1079
|
sales_channels = shopify.Publication.find(**kwargs)
|
|
1083
|
-
return
|
|
1080
|
+
return [sales_channel.to_dict() for sales_channel in sales_channels]
|
|
@@ -27,10 +27,10 @@ class MySQLHandlerTest(unittest.TestCase):
|
|
|
27
27
|
def test_2_get_tables(self):
|
|
28
28
|
tbls = self.handler.get_tables()
|
|
29
29
|
assert tbls['type'] is not RESPONSE_TYPE.ERROR
|
|
30
|
-
|
|
30
|
+
|
|
31
31
|
def test_5_drop_table(self):
|
|
32
32
|
res = self.handler.native_query("DROP TABLE IF EXISTS test_mdb")
|
|
33
|
-
assert res['type'] is not RESPONSE_TYPE.ERROR
|
|
33
|
+
assert res['type'] is not RESPONSE_TYPE.ERROR
|
|
34
34
|
|
|
35
35
|
def test_4_create_table(self):
|
|
36
36
|
res = self.handler.native_query("CREATE TABLE IF NOT EXISTS test_mdb (test_col INT)")
|
|
@@ -39,4 +39,4 @@ class MySQLHandlerTest(unittest.TestCase):
|
|
|
39
39
|
def test_7_select_query(self):
|
|
40
40
|
query = "SELECT * FROM test_mdb WHERE 'id'='a'"
|
|
41
41
|
result = self.handler.native_query(query)
|
|
42
|
-
assert result['type'] is RESPONSE_TYPE.TABLE
|
|
42
|
+
assert result['type'] is RESPONSE_TYPE.TABLE
|
|
@@ -9,7 +9,7 @@ try:
|
|
|
9
9
|
import_error = None
|
|
10
10
|
except Exception as e:
|
|
11
11
|
Handler = None
|
|
12
|
-
import_error = e
|
|
12
|
+
import_error = e
|
|
13
13
|
|
|
14
14
|
title = 'Slack'
|
|
15
15
|
name = 'slack'
|
|
@@ -21,8 +21,8 @@ __all__ = [
|
|
|
21
21
|
'version',
|
|
22
22
|
'name',
|
|
23
23
|
'type',
|
|
24
|
-
'title',
|
|
24
|
+
'title',
|
|
25
25
|
'description',
|
|
26
26
|
'import_error',
|
|
27
27
|
'icon_path'
|
|
28
|
-
]
|
|
28
|
+
]
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
snowflake-connector-python[pandas]==3.
|
|
1
|
+
snowflake-connector-python[pandas]==3.15.0
|
|
2
2
|
snowflake-sqlalchemy==1.7.0
|
|
@@ -1,14 +1,16 @@
|
|
|
1
1
|
import psutil
|
|
2
2
|
import pandas
|
|
3
3
|
from pandas import DataFrame
|
|
4
|
+
from pandas.api import types as pd_types
|
|
4
5
|
from snowflake.sqlalchemy import snowdialect
|
|
5
6
|
from snowflake import connector
|
|
6
7
|
from snowflake.connector.errors import NotSupportedError
|
|
8
|
+
from snowflake.connector.cursor import SnowflakeCursor, ResultMetadata
|
|
7
9
|
|
|
8
|
-
from mindsdb.utilities import log
|
|
9
10
|
from mindsdb_sql_parser.ast.base import ASTNode
|
|
10
11
|
from mindsdb_sql_parser.ast import Select, Identifier
|
|
11
12
|
|
|
13
|
+
from mindsdb.utilities import log
|
|
12
14
|
from mindsdb.integrations.libs.base import DatabaseHandler
|
|
13
15
|
from mindsdb.utilities.render.sqlalchemy_render import SqlalchemyRender
|
|
14
16
|
from mindsdb.integrations.libs.response import (
|
|
@@ -61,10 +63,105 @@ def _map_type(internal_type_name: str) -> MYSQL_DATA_TYPE:
|
|
|
61
63
|
if internal_type_name in db_types_list:
|
|
62
64
|
return mysql_data_type
|
|
63
65
|
|
|
64
|
-
logger.
|
|
66
|
+
logger.debug(f"Snowflake handler type mapping: unknown type: {internal_type_name}, use VARCHAR as fallback.")
|
|
65
67
|
return MYSQL_DATA_TYPE.VARCHAR
|
|
66
68
|
|
|
67
69
|
|
|
70
|
+
def _make_table_response(result: DataFrame, cursor: SnowflakeCursor) -> Response:
|
|
71
|
+
"""Build response from result and cursor.
|
|
72
|
+
NOTE: Snowflake return only 'general' type in description, so look on result's
|
|
73
|
+
DF types and use types from description only if DF type is 'object'
|
|
74
|
+
|
|
75
|
+
Args:
|
|
76
|
+
result (DataFrame): result of the query.
|
|
77
|
+
cursor (SnowflakeCursor): cursor object.
|
|
78
|
+
|
|
79
|
+
Returns:
|
|
80
|
+
Response: response object.
|
|
81
|
+
"""
|
|
82
|
+
description: list[ResultMetadata] = cursor.description
|
|
83
|
+
mysql_types: list[MYSQL_DATA_TYPE] = []
|
|
84
|
+
for column in description:
|
|
85
|
+
column_dtype = result[column.name].dtype
|
|
86
|
+
description_column_type = connector.constants.FIELD_ID_TO_NAME.get(column.type_code)
|
|
87
|
+
if pd_types.is_integer_dtype(column_dtype):
|
|
88
|
+
column_dtype_name = column_dtype.name
|
|
89
|
+
if column_dtype_name in ('int8', 'Int8'):
|
|
90
|
+
mysql_types.append(MYSQL_DATA_TYPE.TINYINT)
|
|
91
|
+
elif column_dtype in ('int16', 'Int16'):
|
|
92
|
+
mysql_types.append(MYSQL_DATA_TYPE.SMALLINT)
|
|
93
|
+
elif column_dtype in ('int32', 'Int32'):
|
|
94
|
+
mysql_types.append(MYSQL_DATA_TYPE.MEDIUMINT)
|
|
95
|
+
elif column_dtype in ('int64', 'Int64'):
|
|
96
|
+
mysql_types.append(MYSQL_DATA_TYPE.BIGINT)
|
|
97
|
+
else:
|
|
98
|
+
mysql_types.append(MYSQL_DATA_TYPE.INT)
|
|
99
|
+
continue
|
|
100
|
+
if pd_types.is_float_dtype(column_dtype):
|
|
101
|
+
column_dtype_name = column_dtype.name
|
|
102
|
+
if column_dtype_name in ('float16', 'Float16'): # Float16 does not exists so far
|
|
103
|
+
mysql_types.append(MYSQL_DATA_TYPE.FLOAT)
|
|
104
|
+
elif column_dtype_name in ('float32', 'Float32'):
|
|
105
|
+
mysql_types.append(MYSQL_DATA_TYPE.FLOAT)
|
|
106
|
+
elif column_dtype_name in ('float64', 'Float64'):
|
|
107
|
+
mysql_types.append(MYSQL_DATA_TYPE.DOUBLE)
|
|
108
|
+
else:
|
|
109
|
+
mysql_types.append(MYSQL_DATA_TYPE.FLOAT)
|
|
110
|
+
continue
|
|
111
|
+
if pd_types.is_bool_dtype(column_dtype):
|
|
112
|
+
mysql_types.append(MYSQL_DATA_TYPE.BOOLEAN)
|
|
113
|
+
continue
|
|
114
|
+
if pd_types.is_datetime64_any_dtype(column_dtype):
|
|
115
|
+
mysql_types.append(MYSQL_DATA_TYPE.DATETIME)
|
|
116
|
+
series = result[column.name]
|
|
117
|
+
# snowflake use pytz.timezone
|
|
118
|
+
if series.dt.tz is not None and getattr(series.dt.tz, 'zone', 'UTC') != 'UTC':
|
|
119
|
+
series = series.dt.tz_convert('UTC')
|
|
120
|
+
result[column.name] = series.dt.tz_localize(None)
|
|
121
|
+
continue
|
|
122
|
+
|
|
123
|
+
if pd_types.is_object_dtype(column_dtype):
|
|
124
|
+
if description_column_type == 'TEXT':
|
|
125
|
+
# we can also check column.internal_size, if == 16777216 then it is TEXT, else VARCHAR(internal_size)
|
|
126
|
+
mysql_types.append(MYSQL_DATA_TYPE.TEXT)
|
|
127
|
+
continue
|
|
128
|
+
elif description_column_type == 'BINARY':
|
|
129
|
+
# if column.internal_size == 8388608 then BINARY, else VARBINARY(internal_size)
|
|
130
|
+
mysql_types.append(MYSQL_DATA_TYPE.BINARY)
|
|
131
|
+
continue
|
|
132
|
+
elif description_column_type == 'DATE':
|
|
133
|
+
mysql_types.append(MYSQL_DATA_TYPE.DATE)
|
|
134
|
+
continue
|
|
135
|
+
elif description_column_type == 'TIME':
|
|
136
|
+
mysql_types.append(MYSQL_DATA_TYPE.TIME)
|
|
137
|
+
continue
|
|
138
|
+
|
|
139
|
+
if description_column_type == 'FIXED':
|
|
140
|
+
if column.scale == 0:
|
|
141
|
+
mysql_types.append(MYSQL_DATA_TYPE.INT)
|
|
142
|
+
else:
|
|
143
|
+
# It is NUMBER, DECIMAL or NUMERIC with scale > 0
|
|
144
|
+
mysql_types.append(MYSQL_DATA_TYPE.FLOAT)
|
|
145
|
+
continue
|
|
146
|
+
elif description_column_type == 'REAL':
|
|
147
|
+
mysql_types.append(MYSQL_DATA_TYPE.FLOAT)
|
|
148
|
+
continue
|
|
149
|
+
|
|
150
|
+
mysql_types.append(MYSQL_DATA_TYPE.TEXT)
|
|
151
|
+
|
|
152
|
+
df = DataFrame(
|
|
153
|
+
result,
|
|
154
|
+
columns=[column.name for column in description],
|
|
155
|
+
)
|
|
156
|
+
|
|
157
|
+
return Response(
|
|
158
|
+
RESPONSE_TYPE.TABLE,
|
|
159
|
+
data_frame=df,
|
|
160
|
+
affected_rows=None,
|
|
161
|
+
mysql_types=mysql_types
|
|
162
|
+
)
|
|
163
|
+
|
|
164
|
+
|
|
68
165
|
class SnowflakeHandler(DatabaseHandler):
|
|
69
166
|
"""
|
|
70
167
|
This handler handles connection and execution of the Snowflake statements.
|
|
@@ -214,10 +311,7 @@ class SnowflakeHandler(DatabaseHandler):
|
|
|
214
311
|
raise MemoryError('Not enought memory')
|
|
215
312
|
# endregion
|
|
216
313
|
if len(batches) > 0:
|
|
217
|
-
response =
|
|
218
|
-
RESPONSE_TYPE.TABLE,
|
|
219
|
-
pandas.concat(batches, ignore_index=True)
|
|
220
|
-
)
|
|
314
|
+
response = _make_table_response(result=pandas.concat(batches, ignore_index=True), cursor=cur)
|
|
221
315
|
else:
|
|
222
316
|
response = Response(
|
|
223
317
|
RESPONSE_TYPE.TABLE,
|
|
@@ -36,11 +36,11 @@ connection_args = OrderedDict(
|
|
|
36
36
|
)
|
|
37
37
|
|
|
38
38
|
connection_args_example = OrderedDict(
|
|
39
|
-
username
|
|
40
|
-
password
|
|
41
|
-
host
|
|
42
|
-
port
|
|
43
|
-
server_path
|
|
44
|
-
collection
|
|
45
|
-
use_ssl
|
|
39
|
+
username="demo_user",
|
|
40
|
+
password="demo_password",
|
|
41
|
+
host="127.0.0.1",
|
|
42
|
+
port=8981,
|
|
43
|
+
server_path="solr",
|
|
44
|
+
collection="gettingstarted",
|
|
45
|
+
use_ssl=False,
|
|
46
46
|
)
|
|
@@ -17,6 +17,7 @@ from mindsdb.integrations.libs.response import (
|
|
|
17
17
|
|
|
18
18
|
logger = log.getLogger(__name__)
|
|
19
19
|
|
|
20
|
+
|
|
20
21
|
class SolrHandler(DatabaseHandler):
|
|
21
22
|
"""
|
|
22
23
|
This handler handles connection and execution of the Solr SQL statements.
|
|
@@ -131,7 +132,7 @@ class SolrHandler(DatabaseHandler):
|
|
|
131
132
|
RESPONSE_TYPE.TABLE,
|
|
132
133
|
pd.DataFrame(
|
|
133
134
|
result,
|
|
134
|
-
columns
|
|
135
|
+
columns=columns
|
|
135
136
|
)
|
|
136
137
|
)
|
|
137
138
|
else:
|
|
@@ -18,6 +18,7 @@ from mindsdb.integrations.libs.response import (
|
|
|
18
18
|
|
|
19
19
|
logger = log.getLogger(__name__)
|
|
20
20
|
|
|
21
|
+
|
|
21
22
|
class SQLAnyHandler(DatabaseHandler):
|
|
22
23
|
"""
|
|
23
24
|
This handler handles connection and execution of the SAP SQL Anywhere statements.
|
|
@@ -61,7 +62,7 @@ class SQLAnyHandler(DatabaseHandler):
|
|
|
61
62
|
self.encryption = "SIMPLE"
|
|
62
63
|
else:
|
|
63
64
|
self.encryption = "NONE"
|
|
64
|
-
|
|
65
|
+
|
|
65
66
|
connection = sqlanydb.connect(
|
|
66
67
|
host=self.host,
|
|
67
68
|
userid=self.userid,
|
|
@@ -160,7 +161,7 @@ class SQLAnyHandler(DatabaseHandler):
|
|
|
160
161
|
List all tables in SAP SQL Anywhere in the current schema
|
|
161
162
|
"""
|
|
162
163
|
|
|
163
|
-
return self.native_query(
|
|
164
|
+
return self.native_query("""
|
|
164
165
|
SELECT USER_NAME(ob.UID) AS SCHEMA_NAME
|
|
165
166
|
, st.TABLE_NAME
|
|
166
167
|
, st.TABLE_TYPE
|