> ## Documentation Index
> Fetch the complete documentation index at: https://clickhouse.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

> 원격 ClickHouse 서버의 데이터베이스 테이블에 실시간으로 액세스하고 `SELECT` 및 `INSERT` 쿼리를 해당 서버로 전달합니다.

# Remote

`Remote` 및 `RemoteSecure` 데이터베이스 엔진은 네이티브 TCP 프로토콜을 통해 원격 ClickHouse 서버에 있는 데이터베이스의 테이블에 실시간으로 액세스할 수 있게 합니다. 이는 [`MySQL`](/docs/ko/reference/engines/database-engines/mysql) 및 [`PostgreSQL`](/docs/ko/reference/engines/database-engines/postgresql) 데이터베이스 엔진의 ClickHouse 간 대응 기능입니다.

테이블 목록과 구조는 필요할 때 원격 서버에서 가져오므로(내부적으로 `SHOW TABLES` 및 `DESCRIBE TABLE` 사용) 데이터베이스는 항상 원격 서버의 현재 상태를 반영합니다. 각 테이블은 제공된 주소로 구성된 임시 클러스터를 기반으로 하는 [`Distributed`](/docs/ko/reference/engines/table-engines/special/distributed) 스토리지로 노출되며, 이 스토리지는 `SELECT` 및 `INSERT` 쿼리를 원격 서버로 전달합니다.

여러 ClickHouse 클러스터를 연동하거나, 더 큰 ClickHouse 클러스터를 `clickhouse-local` 또는 더 작은 클러스터에 연결할 때 유용합니다.

<div id="creating-a-database">
  ## 데이터베이스 생성
</div>

<Tabs>
  <Tab title="Remote" id="remote">
    포트를 생략하면 `Remote`는 일반 TCP 포트(기본값: `tcp_port`, `9000`)를 통해 연결합니다.

    ```sql theme={null}
    CREATE DATABASE remote_db
    ENGINE = Remote('addresses_expr', 'database'[, 'user'[, 'password']]);
    ```
  </Tab>

  <Tab title="RemoteSecure" id="remote-secure">
    포트를 생략하면 `RemoteSecure`는 보안 TCP 포트(기본값: `tcp_port_secure`, `9440`)를 사용해 보안 TLS 연결을 통해 연결합니다.

    ```sql theme={null}
    CREATE DATABASE remote_db
    ENGINE = RemoteSecure('addresses_expr', 'database'[, 'user'[, 'password']]);
    ```
  </Tab>
</Tabs>

**엔진 매개변수**

* `addresses_expr` — 원격 서버 주소 또는 여러 주소를 생성하는 표현식이며, 형식은 `host` 또는 `host:port`입니다. 주소 표현식은 [`remote`](/docs/ko/reference/functions/table-functions/remote) 테이블 함수와 동일한 글로빙 패턴을 지원합니다(예: 여러 세그먼트와 레플리카로 확장되는 `{a,b,c}`, `{N..M}`, `{a|b}`). 포트를 생략하면 `Remote`는 일반 TCP 포트(기본값: `tcp_port`, `9000`)를 사용하고, `RemoteSecure`는 보안 TCP 포트(기본값: `tcp_port_secure`, `9440`)를 사용합니다.
* `database` — 원격 서버의 데이터베이스 이름입니다.
* `user` — 원격 사용자 이름입니다. 선택 사항이며 기본값은 `default`입니다.
* `password` — 원격 사용자 비밀번호입니다. 선택 사항이며 기본값은 비어 있습니다.

주소와 자격 증명은 데이터베이스 정의에 저장되므로 `SHOW CREATE DATABASE`에서는 비밀번호가 숨겨집니다. `remote` 테이블 함수와 마찬가지로 현재 서버를 가리키는 주소는 로컬 세그먼트로 처리됩니다. 즉, `SELECT`와 `INSERT`는 현재 사용자로 직접 실행되므로 해당 사용자는 기본 데이터베이스와 해당 테이블에 대한 권한이 있어야 합니다. 저장된 자격 증명은 실제 원격 서버에만 사용됩니다. 세그먼트의 로컬 레플리카에 데이터베이스나 테이블이 없으면 조회는 [`Distributed`](/docs/ko/reference/engines/table-engines/special/distributed) 테이블처럼 해당 세그먼트의 원격 레플리카로 폴백합니다. 이 경우 `SHOW CREATE TABLE`은 구성된 주소 대신 실제 폴백 주소(각 세그먼트에서 로컬 레플리카를 제외한 주소)를 출력하므로, 출력된 `Remote(...)` 테이블 정의는 실제로 쿼리를 처리하는 객체를 재구성합니다.

주소 표현식이 여러 세그먼트를 나타내는 경우 각 프록시 테이블은 모든 세그먼트에서 읽지만, 메타데이터(테이블 목록 및 구조)는 [`remote`](/docs/ko/reference/functions/table-functions/remote) 테이블 함수와 마찬가지로 임의의 세그먼트(로컬 세그먼트 우선)에서 가져옵니다. 따라서 목록을 조회할 때 세그먼트당 쿼리 하나가 아니라 단일 쿼리만 실행됩니다. 따라서 클러스터의 세그먼트는 동일한 테이블 집합을 제공해야 합니다. 일부 세그먼트에만 존재하는 테이블은 프록시를 통해 제공되며, 해당 테이블이 없는 세그먼트에서는 쿼리가 실패합니다. 다중 세그먼트 데이터베이스의 테이블에 `INSERT`하면 각 행은 임의의 세그먼트로 전송됩니다(프록시 `Distributed` 테이블에는 암시적 `rand()` 세그먼트 분할 키가 있습니다). 쿼리의 세그먼트를 고정하려면 [`insert_shard_id`](/docs/ko/reference/settings/session-settings/insert#insert_shard_id)를 설정하십시오. 암시적 키는 삽입된 행만 분산합니다. 읽기 시에는 테이블이 세그먼트 분할 키가 없는 `Distributed` 테이블처럼 동작합니다(특히 [`optimize_skip_unused_shards`](/docs/ko/reference/settings/session-settings/optimize-skip#optimize_skip_unused_shards) 및 [`force_optimize_skip_unused_shards`](/docs/ko/reference/settings/session-settings/force-optimize#force_optimize_skip_unused_shards)는 이를 세그먼트 프루닝 키로 처리하지 않습니다). `SHOW CREATE TABLE`은 출력되는 `Remote(...)` 테이블 정의에 이 키를 포함하므로, 이를 기반으로 다시 생성한 테이블도 다중 세그먼트 `INSERT` 쿼리를 허용합니다.

이름이 지정된 컬렉션도 지원됩니다:

```sql theme={null}
CREATE DATABASE remote_db
ENGINE = Remote(my_named_collection, database = 'default');
```

<div id="notes">
  ## 참고 사항
</div>

* 이 엔진은 원격 서버를 읽어 오는 뷰입니다. `Remote` 데이터베이스에 대한 `CREATE TABLE`, `DROP TABLE`, `ALTER` 및 이와 유사한 DDL 문은 지원되지 않습니다. 스키마는 원격 서버에서 직접 관리하십시오.
* 구성된 원격 사용자의 접근 권한은 원격 서버에서 적용되며, 로컬에서는 데이터베이스 및 해당 테이블에 대한 일반적인 권한이 적용됩니다.
* 사용자가 볼 권한이 없는 로컬 세그먼트의 테이블은 권한 없음이 아니라 누락된 것으로 보고됩니다. 따라서 사용자는 권한이 없는 로컬 데이터베이스의 테이블 이름을 알아내기 위해 `Remote` 데이터베이스를 사용할 수 없습니다. 이는 목록 조회(`SHOW TABLES`, `EXISTS TABLE`)와 확인(`DESCRIBE TABLE`, `SHOW CREATE TABLE`, `SELECT`) 모두에 적용되며, 이러한 테이블은 해당 세그먼트의 원격 레플리카를 통해서도 제공되지 않습니다. 위에서 설명한 폴백은 로컬 레플리카에 실제로 테이블이 없는 경우에만 수행됩니다.
* 세그먼트의 로컬 레플리카에 존재하는 데이터베이스의 테이블을 나열하면 해당 세그먼트의 원격 레플리카에만 존재하는 테이블도 포함됩니다. 따라서 `SHOW TABLES` 및 `system.tables`는 해당 레플리카로 폴백하는 `EXISTS TABLE`, `DESCRIBE TABLE`, `SELECT`와 일관되게 동작합니다. 원격 레플리카 중 어느 것도 응답하지 않으면 로컬 레플리카의 목록은 이미 사용 가능한 레플리카의 응답이므로 있는 그대로 반환됩니다.
* 원격 서버를 사용할 수 없는 경우 해당 서버의 테이블 목록(`SHOW TABLES`, `system.tables`)은 빈 테이블 목록 대신 연결 오류를 보고합니다. 이는 동일한 데이터베이스에 대한 `EXISTS TABLE` 및 `SELECT`와 동일합니다. 모든 데이터베이스를 대상으로 하는 `system.tables`의 `SELECT`도 이러한 데이터베이스에 연결할 수 없는 동안 실패합니다.
* `Remote` 데이터베이스는 동일한 서버의 다른 `Remote` 데이터베이스를 가리킬 수 있습니다. 이러한 체인에서 테이블을 나열하거나 설명하는 데는 중간 데이터베이스에 대한 권한이 필요하지 않습니다. 중간 데이터베이스는 자체 데이터나 메타데이터를 보유하지 않으며, 각 홉에서 프록시하는 객체에 대한 호출자의 권한을 이미 확인하기 때문입니다. 반면 데이터를 읽고 쓰려면 체인의 모든 홉에 대해 `SELECT` / `INSERT` 권한이 필요합니다. 쿼리가 다른 `Distributed` 테이블을 대상으로 하는 `Distributed` 테이블과 정확히 마찬가지로 중간 데이터베이스의 테이블에 대해 실제로 실행되기 때문입니다. 위에서 설명한 가시성 규칙은 체인에서도 유지됩니다. 중간 데이터베이스가 호출자에게 숨기는 테이블은 외부 데이터베이스의 원격 레플리카를 통해서도 제공되지 않습니다. 로컬 레플리카의 중간 데이터베이스가 자체 대상에 연결할 수 없는 경우 외부 세그먼트의 로컬 레플리카는 전혀 응답할 수 없습니다. 이는 레플리카 자체가 다운된 경우와 정확히 같으며, 외부 데이터베이스는 세그먼트의 원격 레플리카로 폴백됩니다.

<div id="example">
  ## 예시
</div>

원격 서버의 `system` 데이터베이스를 참조하는 `Remote` 데이터베이스를 생성하고 해당 데이터베이스에서 읽습니다:

```sql theme={null}
CREATE DATABASE remote_system
ENGINE = Remote('127.0.0.1:9000', 'system', 'default', '');
```

```sql theme={null}
SHOW TABLES FROM remote_system LIKE 'one';
```

```text theme={null}
┌─name─┐
│ one  │
└──────┘
```

```sql theme={null}
SELECT * FROM remote_system.one;
```

```text theme={null}
┌─dummy─┐
│     0 │
└───────┘
```
