---
title: 채널 조건 - 스마트 알림 필터링
sidebarTitle: 조건
description: "조건식으로 Echobell 알림을 필터링하세요: 연산자, 시간 기반 규칙, 그리고 알림 피로를 줄이는 모범 사례를 안내합니다."
---

# 채널 조건

채널 조건은 알림을 언제 보낼지 결정하는 강력한 표현식입니다. 채널에 조건을 설정하면 변수나 HTTP 헤더의 내용을 기준으로 알림을 필터링할 수 있어, 구독자는 관련 있는 알림만 받게 됩니다. 이는 알림 피로를 줄이고 알림 시스템의 신호 대 잡음 비율을 높게 유지하는 데 필수적입니다.

조건은 알림의 문지기라고 생각하면 됩니다. 들어오는 트리거 데이터를 평가해 특정 기준을 충족할 때만 알림을 통과시킵니다.

## 조건 이해하기

조건은 `true` 또는 `false`로 평가되는 표현식입니다. 채널이 트리거되면 다음과 같이 동작합니다.

- 조건이 **설정되지 않은** 경우(비어 있는 경우) 모든 구독자에게 알림이 전송됩니다.
- 조건이 **설정된** 경우 표현식이 `true`로 평가될 때만 알림이 전송됩니다.

## 조건 작성하기

조건은 템플릿에서 사용하는 `{{}}` 래퍼 없이 표현식으로 작성합니다. 예를 들면 다음과 같습니다.

```
status == "active"
```

이 조건은 `status` 변수가 "active"일 때만 알림이 전송되도록 허용합니다.

## 일반적인 사용 사례

다음은 조건을 활용하는 실용적인 예시입니다.

### 기본 변수 확인

```
amount > 100
```

"amount" 변수가 100보다 클 때만 알림을 보냅니다.

```
message != ""
```

"message" 변수가 비어 있지 않을 때만 알림을 보냅니다.

```
isUrgent == true
```

"isUrgent" 변수가 true일 때만 알림을 보냅니다.

### HTTP 헤더 확인

특수 변수 `header`를 사용해 HTTP 헤더에 접근할 수 있습니다.

```
header["x-webhook-source"] == "grafana"
```

사용자 지정 소스 헤더가 "grafana"와 정확히 일치할 때만 알림을 보냅니다.

```
header["content-type"] == "application/json"
```

콘텐츠 유형이 JSON일 때만 알림을 보냅니다.

```
header["x-priority"] == "high"
```

사용자 지정 우선순위 헤더가 "high"로 설정된 경우에만 알림을 보냅니다.

<Callout type="info">헤더의 모든 키는 소문자입니다.</Callout>

### 복합 조건

논리 연산자를 사용해 여러 조건을 결합할 수 있습니다.

```
(temperature > 30 || pressure > 100) && status == "monitoring"
```

온도가 30을 넘거나 압력이 100을 넘으면서 상태가 "monitoring"일 때만 알림을 보냅니다.

```
environment == "production" && (errorLevel == "critical" || errorLevel == "high")
```

프로덕션 환경에서 critical 또는 high 수준의 오류가 발생한 경우에만 알림을 보냅니다.

## 지원되는 연산자

조건식에서는 다음 연산자를 사용할 수 있습니다.

| 연산자                    | 설명                     | 예시                                        |
| ------------------------- | ------------------------ | ------------------------------------------- |
| `==`                      | 같음                     | `status == "active"`                        |
| `!=`                      | 같지 않음                | `status != "inactive"`                      |
| `!`                       | 논리 NOT                 | `!isCompleted`                              |
| `<`                       | 미만                     | `count < 10`                                |
| `>`                       | 초과                     | `price > 99.99`                             |
| `<=`                      | 이하                     | `battery <= 20`                             |
| `>=`                      | 이상                     | `confidence >= 0.95`                        |
| `&&`                      | 논리 AND                 | `isAdmin && isActive`                       |
| <code>&#124;&#124;</code> | 논리 OR                  | <code>isError &#124;&#124; isWarning</code> |

## 조건 변수

Webhook으로 채널이 트리거되면 다음 값에 접근할 수 있습니다.

1. URL의 **쿼리 파라미터**
2. POST 요청의 **JSON 본문**
3. `header` 객체를 통한 **HTTP 헤더**

이메일 트리거의 경우 다음 값에 접근할 수 있습니다.

- `from`: 이메일 발신자 주소
- `to`: 수신자 주소
- `subject`: 이메일 제목
- `text`: 일반 텍스트 본문 내용
- `html`: HTML 본문 내용

### 시스템 시간 변수(UTC)

이 읽기 전용 변수들은 조건과 템플릿 양쪽에서 항상 사용할 수 있습니다. 모든 값은 UTC 기준으로 계산됩니다.

다음 값들은 플랫한 형태로 직접 주입되므로 이름만으로 사용할 수 있습니다.

- `year`: 네 자리 연도(숫자)
- `month`: 월 번호 `1–12`
- `dayOfMonth`: 일 `1–31`
- `dayOfWeek`: 요일 `0–6`(일요일 = 0)
- `hour`: 시 `0–23`
- `minute`: 분 `0–59`
- `second`: 초 `0–59`
- `date`: `YYYY-MM-DD` 형식 문자열
- `time`: `HH:mm:ss` 형식 문자열
- `iso`: 현재 시각의 ISO‑8601 문자열(예: `2025-05-06T12:34:56.789Z`)

다음 값들은 `sys.` 네임스페이스에서**만** 사용할 수 있으며, 플랫한 이름으로는 주입되지 않습니다.

- `sys.timezone`: 상수 문자열 `"UTC"`
- `sys.now`: 현재 시각의 ISO‑8601 문자열(`iso`와 같은 값)
- `sys.epochMs`: Unix epoch 이후 경과한 밀리초(숫자)
- `sys.epochSeconds`: Unix epoch 이후 경과한 초(숫자)
- `sys.monthName`: 월 이름 `January–December`
- `sys.dayOfWeekName`: 요일 이름 `Sunday–Saturday`

`sys.` 네임스페이스는 모든 플랫 값도 그대로 제공합니다(예: `sys.year`, `sys.hour`).

예시:

```
// Weekdays during 09:00–17:00 UTC
hour >= 9 && hour < 17 && dayOfWeek >= 1 && dayOfWeek <= 5

// Weekends only
dayOfWeek == 0 || dayOfWeek == 6

// First day of month at top of hour
dayOfMonth == 1 && minute == 0
```

## 모범 사례

### 단순하게 시작하기
기본 조건부터 시작해 필요에 따라 복잡도를 높이세요.

**1단계:** 단일 조건으로 시작합니다
```
temperature > 30
```

**2단계:** 논리 연산자를 추가합니다
```
temperature > 30 && location == "server-room"
```

**3단계:** 중첩된 논리를 추가합니다
```
(temperature > 30 || humidity > 80) && location == "server-room" && status == "monitoring"
```

### 철저하게 테스트하기
다양한 입력값으로 조건을 테스트해 예상대로 동작하는지 확인하세요.

1. **정상적인 값으로 테스트** - 예상되는 상황에서 조건이 동작하는지 확인합니다
2. **경계값 테스트** - 임계값과 정확히 같을 때는 어떻게 되나요?
3. **변수가 없는 경우 테스트** - 데이터가 없을 때 조건은 어떻게 처리되나요?
4. **예상치 못한 타입 테스트** - 숫자가 문자열로 전달되면 어떻게 되나요?
5. **테스트용 Webhook 사용** - 여러 데이터 조합으로 테스트 트리거를 보내 보세요

### 조건 문서화하기
복잡한 조건을 설명하려면 채널의 메모 필드에 주석을 추가하세요.

```
Channel Note:
Condition: (cpu > 80 && memory > 90) || diskSpace < 10

This condition triggers alerts when:
- Both CPU is above 80% AND memory is above 90%
- OR when disk space drops below 10GB
```

이렇게 하면 팀원들이 표현식을 일일이 해석하지 않고도 알림 로직을 이해할 수 있습니다.

### 경계 상황 고려하기
변수 누락이나 예상치 못한 값에 대비하세요.

- **변수 누락**: 정의되지 않은 변수는 빈 값 또는 false로 평가되므로, 로직이 이를 처리할 수 있어야 합니다
- **숫자 비교**: `<`, `>`, `<=`, `>=`는 **양쪽** 피연산자를 모두 `Number()`로 변환하므로 사전순이 아니라 숫자로 비교합니다. `"100" > "20"`은 사전순이 아니라 100 > 20이므로 `true`입니다.
- **숫자가 아닌 값**: `<`, `>`, `<=`, `>=` 비교에서 어느 한쪽이라도 숫자가 아니면 `Number()`가 `NaN`을 만들어 비교 결과는 항상 `false`가 됩니다.
- **동등 비교와 대소 비교**: `==`와 `!=`는 느슨한 동등 비교를 사용하지만(그래서 `count == "5"`는 숫자 5와 일치합니다), 대소 비교 연산자는 항상 숫자로 비교합니다.
- **대소문자 구분**: `status == "Active"`는 `status == "active"`와 다릅니다

### 알림 폭주 방지하기
일시적인 문제로 알림이 연달아 쏟아지지 않도록 조건을 활용하세요.

```
errorCount > 5    # Not just errorCount > 0
cpuUsage > 90     # Not cpuUsage > 50
failureRate > 0.1 # Not just hasFailures
```

적절한 임계값과 함께 사용하면 중요한 이벤트를 놓치지 않으면서 잡음을 줄일 수 있습니다.

### 업무 시간 필터링 활용하기
심각도와 시간 기반 조건을 결합하세요.

```
severity == "critical" || (severity == "high" && hour >= 9 && hour < 17)
```

이렇게 하면 critical 알림은 24시간 내내 전송되고, 우선순위가 높은 알림은 업무 시간에만 전송됩니다.

### 헤더 검사 활용하기
스팸이나 허가되지 않은 트리거를 막으려면 Webhook 출처를 검증하세요.

```
header["x-webhook-source"] == "grafana" || header["x-webhook-source"] == "prometheus"
```

요청 출처를 확인함으로써 보안 계층을 하나 더 추가할 수 있습니다.

## 실제 활용 예시

### 서버 모니터링 - 단계적 알림
```
# Only alert when CPU is consistently high, not transient spikes
cpu > 80 && duration >= 300
```

### 이커머스 - 고액 주문
```
# Only notify for orders above $500 or fraud-flagged orders
orderAmount > 500 || isFraudSuspected == true
```

### 개발 - 치명적인 빌드 실패
```
# Alert only for main branch failures or failed deployments
(branch == "main" || branch == "master") && status == "failed"
```

### IoT - 환경 모니터링
```
# Temperature extremes outside acceptable range
temperature < 15 || temperature > 28
```

### 보안 - 로그인 실패 시도
```
# Multiple failed logins from same IP in short time
failedAttempts >= 3 && timeSinceFirst < 300
```

### CI/CD - 배포 추적
```
# Only notify on production deploys or staging failures
(environment == "production") || (environment == "staging" && status == "failed")
```

### 트레이딩 - 가격 알림
```
# Significant price movements beyond threshold
(priceChange > 5 || priceChange < -5) && volume > 1000000
```

### 고객 지원 - SLA 위반
```
# Tickets approaching or exceeding SLA
ticketAge > slaThreshold || priority == "urgent"
```

## 자주 쓰는 조건 패턴

### 임계값 기반 알림
```
value > threshold
percentage >= 90
count < minimumRequired
```

### 상태 기반 필터링
```
status == "error" || status == "critical"
state != "healthy"
isActive == true
```

### 시간대 기반 필터링
```
# Business hours only (9 AM - 5 PM UTC, Monday-Friday)
hour >= 9 && hour < 17 && dayOfWeek >= 1 && dayOfWeek <= 5

# After hours only
hour < 9 || hour >= 17 || dayOfWeek == 0 || dayOfWeek == 6

# Weekend maintenance windows
(dayOfWeek == 0 || dayOfWeek == 6) && hour >= 2 && hour < 6
```

### 다중 요소 조건
```
# Combine multiple criteria
severity == "high" && environment == "production" && region == "us-east-1"

# Either critical OR production with high severity
severity == "critical" || (severity == "high" && environment == "production")
```

### 문자열 매칭
```
# Exact match (there is no "contains" operator)
status == "error"
errorType == "database"

# String comparison
environment == "production"
username != "test-user"
```

## 조건과 템플릿 함께 사용하기

조건과 [템플릿](/docs/template)은 함께 작동해 스마트하고 상황에 맞는 알림을 만들어 줍니다.

**조건**(어떤 트리거가 알림을 보낼지 필터링):
```
temperature > 30 || humidity > 80
```

**템플릿**(알림 내용의 형식 지정):
```
Title: {{location}} Environment Alert
Body: Temp: {{temperature}}°C, Humidity: {{humidity}}%
```

이렇게 역할을 분리하면 다음과 같은 이점이 있습니다.
1. 조건으로 원치 않는 알림을 **필터링**합니다
2. 템플릿으로 중요한 알림의 **형식을 지정**합니다
3. 심각도에 따라 알림 내용을 **조정**합니다

[템플릿 문법과 기능](/docs/template)에 대해 더 알아보세요.

## 조건 디버깅하기

조건이 예상대로 동작하지 않는다면 다음을 확인하세요.

1. **조건을 단순화하세요** - 한 번에 하나의 비교만 테스트합니다
2. **변수 이름을 확인하세요** - 정확히 일치하는지 확인합니다(대소문자를 구분합니다)
3. **데이터 타입을 확인하세요** - 테스트용 Webhook으로 변수 타입을 확인합니다
4. **불리언 로직을 테스트하세요** - 복잡한 조건을 작은 단위로 나눕니다
5. **연산자 우선순위를 검토하세요** - 괄호를 사용해 의도를 명확히 합니다
6. **오타를 확인하세요** - `header["Content-Type"]`이 아니라 `header["content-type"]`입니다

## 관련 문서

- **[템플릿 가이드](/docs/template)** - 변수로 알림 내용의 형식을 지정합니다
- **[Webhook 연동](/docs/webhook)** - HTTP 요청으로 변수를 전달합니다
- **[이메일 트리거](/docs/email-trigger)** - 이메일 트리거에서 제공되는 변수
- **[시작하기](/docs)** - 첫 조건부 채널을 설정합니다

## 다음 단계

이제 조건을 이해했다면 다음을 살펴보세요.

- **[스마트 모니터링 알림 만들기](/docs/developer/grafana)** - 인프라 알림 필터링
- **[CI/CD 알림 설정하기](/docs/developer/github)** - 중요한 빌드 이벤트에만 알림 보내기
- **[시간 기반 알림 구성하기](/blog/time-window-notifications-using-utc-conditions)** - 업무 시간 필터링
- **[모든 기능 살펴보기](/docs/features)** - Echobell로 할 수 있는 일 알아보기

---

조건을 효과적으로 활용하면 알림 잡음을 줄이고 구독자가 자신에게 관련 있고 실제로 조치할 수 있는 알림만 받도록 할 수 있습니다. 간단한 조건부터 시작해 필요에 맞춰 점차 정교한 필터링 로직으로 발전시켜 보세요.
