Skip to content

Add suporte a MySQL e postgree - #15

Merged
Petroncini merged 6 commits into
gruporaia:devfrom
antoniocaarvalh:feature/postgres-mysql-support
Sep 29, 2026
Merged

Petroncini merged 6 commits into
gruporaia:devfrom
antoniocaarvalh:feature/postgres-mysql-support

Conversation

@antoniocaarvalh

Copy link
Copy Markdown
Collaborator

Adicionei suporte a PostgreSQL e MySQL. Criei a introspecção de schema pros dois bancos (via information_schema, sem precisar de Java/SchemaCrawler) e os executores de query (psycopg2 e pymysql), com a mesma validação de segurança de antes (só SELECT/WITH). O prompt do LLM agora sabe qual banco é o alvo, em vez de sempre assumir SQLite (Isso estava me dando problema). Testei tudo local com Postgres 17 e MySQL 8.4, incluindo uma query de exemplo do BIRD que vcfs passaram, e rodei a suíte de testes inteira para ver se quebrava algo do SQLite, e deu tudo certinho. Fiz um docx detalhando mais o processo

Petroncini and others added 5 commits June 20, 2026 11:15
…the single source of project dependencies"

This reverts commit a289a2f.
Adds native schema introspection (information_schema, no Java/SchemaCrawler
required) and query execution (psycopg2/pymysql) for PostgreSQL and MySQL,
routed via a new db_dialeto/db_config state field. The code-gen prompt now
tells the LLM which dialect it's targeting instead of always assuming
SQLite. SQLite behavior is unchanged (dialect defaults to sqlite when not
specified).
Adds an optional db_url field (e.g. postgresql://user:pass@host:port/db)
that, when set, drives schema introspection and query execution through
SQLAlchemy instead of the manual db_dialeto/db_config path added earlier.
The dialect is read from engine.dialect.name, so the caller only needs to
provide one connection string instead of six separate flags/params.

This is purely additive: when db_url is not set, behavior is unchanged
(same db_dialeto/db_config/db_path path as before).

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot review overview

🟡 Changes recommended

Critical credential and query-safety issues remain, along with incorrect remote routing, dialect handling, and timeout/error behavior.

Review effort: Lite
Findings: 4 High severity · 6 Medium severity

Open (10)
What changed in this PR

Adds PostgreSQL and MySQL support with schema introspection, query execution, dialect-aware prompts, CLI configuration, and SQLAlchemy URL support.

Changes:

  • Adds database connection state and CLI options.
  • Implements PostgreSQL/MySQL introspection and executors.
  • Adds dialect-specific prompts and dependencies.
File Summary
text_to_insight/​state.py Adds database dialect and connection fields.
text_to_insight/​runtime.py Propagates database configuration.
text_to_insight/​nodes/​schema.py Adds remote schema introspection.
text_to_insight/​nodes/​sandbox.py Routes execution by database target.
text_to_insight/​nodes/​code_agent/​code_sql.py Adds PostgreSQL, MySQL, and URL execution.
text_to_insight/​nodes/​code_agent/​code_agent.py Adds dialect-aware prompt guidance.
text_to_insight/​InsightEngine.py Exposes database configuration.
text_to_insight/​cli.py Adds database connection arguments.
pyproject.toml Adds database dependencies.

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread text_to_insight/cli.py Outdated
Comment on lines +88 to +90
"--db-password",
default=None,
help="Senha do banco remoto.",
with conn.cursor() as cur:
cur.execute("SET SESSION TRANSACTION READ ONLY")
cur.execute(f"SET SESSION max_execution_time = {int(timeout_segundos * 1000)}")
cur.execute(sql)
Comment on lines +53 to +59
"args": lambda _db, cfg: [
"--server=mysql",
f"--host={cfg['host']}",
f"--port={cfg.get('port', 3306)}",
f"--database={cfg['database']}",
f"--user={cfg['user']}",
f"--password={cfg['password']}",
"db_path": db_path,
"db_dialeto": db_dialeto,
"db_url": db_url,
"db_config": db_config,
Comment on lines +49 to +51
dialeto = (estado.get("db_dialeto") or "sqlite").strip().lower()
nome = _NOME_DIALETO.get(dialeto, _NOME_DIALETO["sqlite"])
nota = _NOTA_DIALETO.get(dialeto, _NOTA_DIALETO["sqlite"])
Comment on lines +311 to +315
def executar_sql_via_url(
db_url: str,
sql: str,
limite_preview: int = 5,
timeout_segundos: float = 15.0,
Comment thread text_to_insight/nodes/schema.py Outdated
Comment on lines +589 to +592
# sqlite / duckdb / fallback padrão
conn = sqlite3.connect(f"file:{caminho_db}?mode=ro", uri=True)
with conn:
return _formatar_schema_sqlite(conn)
Comment thread text_to_insight/nodes/schema.py Outdated
Comment on lines +807 to +815
db_url = estado.get("db_url", "").strip()
if db_url:
from sqlalchemy import create_engine

engine = create_engine(db_url)
try:
contexto = _formatar_schema_sqlalchemy(engine)
finally:
engine.dispose()
Comment on lines +816 to +821
return {
"contexto_schema": contexto,
"erro_execucao": "",
"status": "schema_obtido",
"tem_descricao": False,
}
Comment thread text_to_insight/runtime.py Outdated
Comment on lines +49 to +51
db_dialeto: str = "sqlite",
db_config: dict[str, Any] | None = None,
db_url: str = "",
@Petroncini
Petroncini changed the base branch from main to dev September 28, 2026 17:48
- CLI --db-password now reads from DB_PASSWORD env var by default (avoids
  leaking secrets into shell history/process args)
- validar_sql_segura blocks MySQL INTO OUTFILE/DUMPFILE and LOAD_FILE(),
  plus Postgres pg_read_file/pg_ls_dir/lo_import/lo_export and SQLite
  load_extension() -- these start with SELECT and previously slipped past
  the read-only check
- state now redacts db_config/db_url passwords before returning results to
  callers (_redigir_credenciais), instead of leaking them in plain text
- code-gen prompt now also resolves dialect from db_url when db_dialeto is
  unset, instead of always defaulting to SQLite syntax
- executar_sql_via_url now applies the same timeout/read-only session
  settings the dialect-specific executors already had
- schema fallback for an unsupported dialect (e.g. duckdb) now raises a
  clear error instead of silently trying to open it with the sqlite3 driver
- schema introspection failures (native fallback and db_url path) now
  return a structured exec_erro instead of an uncaught exception
- db_url schema path now applies FK inference the same way the db_config
  path already did
- db_dialeto now defaults to "" instead of "sqlite" through runtime/
  InsightEngine/cli, so extension-based detection (.duckdb etc) isn't
  short-circuited for callers who don't set it explicitly
@antoniocaarvalh
antoniocaarvalh force-pushed the feature/postgres-mysql-support branch from fce2c88 to ec68b4c Compare September 28, 2026 20:09
@Petroncini
Petroncini merged commit 29904b0 into gruporaia:dev Sep 29, 2026
8 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants