Files
crewAI/docs/edge/ko/tools/database-data/nl2sqltool.mdx
Rip&Tear 338662201f docs: document NL2SQL read-only enforcement and its limits
The page claimed read-only mode blocked "multi-statement queries containing
semicolons" and said nothing about CTEs, EXPLAIN ANALYZE, or the fact that a
SELECT can still reach the database server's filesystem. Both gaps matter now
that those routes are enforced.

- Replace the semicolon sentence with a table of every indirect write route
  blocked in read-only mode: multi-statement, writable CTEs (including
  AS MATERIALIZED), a write after a CTE, EXPLAIN ANALYZE, INTO OUTFILE,
  server-filesystem functions, and unparseable WITH statements.
- Explain that analysis masks literals and comments, so `SELECT 'DROP TABLE
  users'` is allowed while `EXPLAIN /*x*/ ANALYZE DELETE ...` is blocked, and
  that a semicolon inside a literal no longer splits statements.
- Document the new SET TRANSACTION READ ONLY backstop and which backends
  fall back without it.
- Add a warning that these checks are defence in depth and a least-privileged
  read-only database role is the only complete control.

Every example in the new table was verified against the implementation.
Applied to en/ar/ko/pt-BR under docs/edge; the ko and pt-BR pages carry the
warning inline as they have no Hardening Recommendations section.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-31 08:47:04 +08:00

165 lines
8.2 KiB
Plaintext

---
title: NL2SQL 도구
description: NL2SQLTool은 자연어를 SQL 쿼리로 변환하도록 설계되었습니다.
icon: language
mode: "wide"
---
## 개요
이 도구는 자연어를 SQL 쿼리로 변환하는 데 사용됩니다. 에이전트에 전달되면 쿼리를 생성하고 이를 사용하여 데이터베이스와 상호작용합니다.
이를 통해 에이전트가 데이터베이스에 접근하여 목표에 따라 정보를 가져오고, 해당 정보를 사용해 응답, 보고서 또는 기타 출력물을 생성하는 다양한 워크플로우가 가능해집니다. 또한 에이전트가 자신의 목표에 맞춰 데이터베이스를 업데이트할 수 있는 기능도 제공합니다.
**주의**: 도구는 기본적으로 읽기 전용(SELECT/SHOW/DESCRIBE/EXPLAIN만 허용)으로 동작합니다. 쓰기 작업을 수행하려면 `allow_dml=True` 매개변수 또는 `CREWAI_NL2SQL_ALLOW_DML=true` 환경 변수가 필요합니다. 쓰기 접근이 활성화된 경우, 가능하면 권한이 제한된 데이터베이스 사용자나 읽기 복제본을 사용하십시오.
## 읽기 전용 모드 및 DML 구성
`NL2SQLTool`은 기본적으로 **읽기 전용 모드**로 동작합니다. 추가 구성 없이 허용되는 구문 유형은 다음과 같습니다:
- `SELECT`
- `SHOW`
- `DESCRIBE`
- `EXPLAIN`
DML을 명시적으로 활성화하지 않으면 쓰기 작업(`INSERT`, `UPDATE`, `DELETE`, `DROP`, `CREATE`, `ALTER`, `TRUNCATE` 등)을 실행하려고 할 때 오류가 발생합니다.
읽기 전용 모드는 우회 경로를 통한 쓰기도 차단합니다:
| 읽기 전용 모드에서 차단됨 | 예시 |
| --- | --- |
| 다중 구문 쿼리 | `SELECT 1; DROP TABLE users` |
| 쓰기 CTE(`MATERIALIZED` 표기 포함) | `WITH d AS MATERIALIZED (DELETE FROM users RETURNING *) SELECT * FROM d` |
| CTE 뒤에 오는 쓰기 작업 | `WITH d AS (SELECT 1) DELETE FROM users` |
| 인자를 실제로 실행하는 `EXPLAIN ANALYZE` | `EXPLAIN ANALYZE DELETE FROM users` |
| 데이터베이스 서버 파일시스템에 대한 쓰기 | `SELECT * FROM users INTO OUTFILE '/var/www/shell.php'` |
| 서버 파일시스템에 접근하거나 새 연결을 여는 함수 | `SELECT pg_read_file('/etc/passwd')`, `dblink_exec(...)` |
| 읽기 전용임을 확인할 수 없는 `WITH` 구문 | `WITH d AS DELETE FROM users` |
구문은 문자열 리터럴과 주석을 가린 상태에서 분석됩니다. 따라서 리터럴 안에 숨은 키워드는 명령으로 오인되지 않고(`SELECT 'DROP TABLE users'`는 허용), 키워드 사이에 삽입된 주석이 명령을 숨기지도 못합니다(`EXPLAIN /*x*/ ANALYZE DELETE ...`는 차단). 문자열 리터럴 안의 세미콜론은 구문 구분자로 세지 않으므로 `SELECT ';'`는 유효한 단일 구문입니다.
읽기 전용 모드에서는 트랜잭션에 `SET TRANSACTION READ ONLY`도 적용하므로, PostgreSQL과 MySQL은 구문 표기 방식과 무관하게 데이터베이스 차원에서 쓰기를 거부합니다. 해당 구문을 지원하지 않는 백엔드(SQLite, SQL Server, Snowflake)는 디버그 로그를 남기고 구문 검증에만 의존합니다. 파싱이 아니라 읽기 전용 역할에 의존해야 하는 이유가 하나 더 있는 셈입니다.
<Warning>
내장된 읽기 전용 검사는 완전한 경계가 아니라 심층 방어 수단입니다. 이 검사는 구문 텍스트를 검사하며 SQL은 데이터베이스마다 다릅니다. `SELECT`로 시작하는 구문도 데이터베이스 서버의 파일시스템에 접근하거나(`SELECT ... INTO OUTFILE`, `pg_read_file()`) 부수 효과가 있는 함수를 호출할 수 있습니다. 알려진 경로는 명시적으로 차단하지만, 완전한 통제 수단은 `db_uri`에 부여하는 권한뿐입니다. **최소 권한의 읽기 전용 데이터베이스 역할을 사용하십시오.**
</Warning>
### 쓰기 작업 활성화
DML(데이터 조작 언어)을 활성화하는 방법은 두 가지입니다:
**옵션 1 — 생성자 매개변수:**
```python
from crewai_tools import NL2SQLTool
nl2sql = NL2SQLTool(
db_uri="postgresql://example@localhost:5432/test_db",
allow_dml=True,
)
```
**옵션 2 — 환경 변수:**
```bash
CREWAI_NL2SQL_ALLOW_DML=true
```
```python
from crewai_tools import NL2SQLTool
# 환경 변수를 통해 DML 활성화
nl2sql = NL2SQLTool(db_uri="postgresql://example@localhost:5432/test_db")
```
### 사용 예시
**읽기 전용(기본값) — 분석 및 보고 워크로드에 안전:**
```python
from crewai_tools import NL2SQLTool
# SELECT/SHOW/DESCRIBE/EXPLAIN만 허용
nl2sql = NL2SQLTool(db_uri="postgresql://example@localhost:5432/test_db")
```
**DML 활성화 — 쓰기 워크로드에 필요:**
```python
from crewai_tools import NL2SQLTool
# INSERT, UPDATE, DELETE, DROP 등이 허용됨
nl2sql = NL2SQLTool(
db_uri="postgresql://example@localhost:5432/test_db",
allow_dml=True,
)
```
<Warning>
DML을 활성화하면 에이전트가 데이터를 수정하거나 삭제할 수 있습니다. 사용 사례에서 명시적으로 쓰기 접근이 필요한 경우에만 활성화하고, 데이터베이스 자격 증명이 최소 필요 권한으로 제한되어 있는지 확인하십시오.
</Warning>
## 요구 사항
- SqlAlchemy
- 모든 DB 호환 라이브러리(예: psycopg2, mysql-connector-python)
## 설치
crewai_tools 패키지 설치
```shell
pip install 'crewai[tools]'
```
## 사용법
NL2SQLTool을 사용하려면 데이터베이스 URI를 도구에 전달해야 합니다. URI는 `dialect+driver://username:password@host:port/database` 형식이어야 합니다.
```python Code
from crewai_tools import NL2SQLTool
# psycopg2 was installed to run this example with PostgreSQL
nl2sql = NL2SQLTool(db_uri="postgresql://example@localhost:5432/test_db")
@agent
def researcher(self) -> Agent:
return Agent(
config=self.agents_config["researcher"],
allow_delegation=False,
tools=[nl2sql]
)
```
## 예시
주요 작업 목표는 다음과 같았습니다:
"각 도시에 대해 월별 평균, 최대, 최소 매출을 조회하되, 사용자 수가 1명 초과인 도시만 포함하세요. 또한 각 도시의 사용자 수를 세고, 평균 월 매출을 기준으로 내림차순 정렬하십시오."
그래서 에이전트는 DB에서 정보를 얻으려고 시도했고, 처음 시도는 잘못되었으므로 에이전트가 다시 시도하여 올바른 정보를 얻은 후 다음 에이전트로 전달합니다.
![alt text](https://github.com/crewAIInc/crewAI-tools/blob/main/crewai_tools/tools/nl2sql/images/image-2.png?raw=true)
![alt text](https://github.com/crewAIInc/crewAI-tools/raw/main/crewai_tools/tools/nl2sql/images/image-3.png)
두 번째 작업 목표는 다음과 같았습니다:
"데이터를 검토하고 상세한 보고서를 작성한 다음, 제공된 데이터를 기반으로 필드를 갖는 테이블을 데이터베이스에 생성하세요. 각 도시에 대해 월별 평균, 최대, 최소 매출 정보를 포함하되, 사용자 수가 1명 초과인 도시만 포함시키세요. 또한 각 도시의 사용자 수를 세고, 평균 월 매출을 기준으로 내림차순 정렬하십시오."
이제 상황이 흥미로워집니다. 에이전트는 테이블을 생성할 SQL 쿼리뿐만 아니라 데이터를 테이블에 삽입하는 쿼리도 생성합니다. 그리고 마지막에는 데이터베이스에 있던 것과 정확히 일치하는 최종 보고서도 반환합니다.
![alt text](https://github.com/crewAIInc/crewAI-tools/raw/main/crewai_tools/tools/nl2sql/images/image-4.png)
![alt text](https://github.com/crewAIInc/crewAI-tools/raw/main/crewai_tools/tools/nl2sql/images/image-5.png)
![alt text](https://github.com/crewAIInc/crewAI-tools/raw/main/crewai_tools/tools/nl2sql/images/image-9.png)
![alt text](https://github.com/crewAIInc/crewAI-tools/raw/main/crewai_tools/tools/nl2sql/images/image-7.png)
이것은 NL2SQLTool이 데이터베이스와 상호작용하고, 데이터베이스의 데이터를 기반으로 보고서를 생성하는 데 어떻게 사용될 수 있는지에 대한 간단한 예시입니다.
이 도구는 에이전트의 논리와 데이터베이스와 상호작용하는 방식에 대해 무한한 가능성을 제공합니다.
```md
DB -> Agent -> ... -> Agent -> DB
```