Android 앱에서 검색 기능을 만들다 보면 결과가 있을 때의 화면은 비교적 쉽게 구성됩니다. 리스트를 보여주고, 항목을 누르면 상세 화면으로 이동하면 되죠. 막상 구현해보면 더 자주 헷갈리는 부분은 검색 결과가 없을 때입니다.
검색 결과가 없는 상태를 모두 같은 문구로 처리하면 사용자는 무엇을 해야 하는지 알기 어렵습니다. 검색어를 바꿔야 하는 상황인지, 네트워크 문제인지, 현재 지역에서 제공하지 않는 데이터인지 구분되지 않기 때문입니다.
특히 공공데이터나 지역 기반 앱에서는 빈 결과가 단순히 데이터 없음만 의미하지 않을 수 있습니다. API 응답이 일시적으로 비어 있을 수도 있고, 선택한 지역이 아직 지원되지 않을 수도 있습니다. 그래서 empty state는 빈 화면이 아니라 다음 행동을 안내하는 화면으로 보는 편이 좋습니다.
이 글에서는 공공데이터나 지역 기반 Android 앱을 기준으로 empty state를 설계하는 방법을 정리해보겠습니다. 실제 사용자 검색어, 위치 정보, 내부 API 주소는 예시에서 제외하고, 화면 상태와 안내 문구를 나누는 기준에 집중해보겠습니다.
empty state는 빈 화면이 아니라 다음 행동 안내입니다
empty state는 단순히 데이터가 없다는 사실을 보여주는 화면이 아닙니다. 사용자가 다음에 무엇을 하면 되는지 알려주는 안내 영역에 가깝습니다. 특히 검색 화면에서는 빈 결과가 정상 흐름일 수도 있고 오류일 수도 있습니다.
- 검색어와 맞는 데이터가 없을 수 있다.
- 서버나 네트워크 문제로 데이터를 불러오지 못했을 수 있다.
- 선택한 지역이 아직 지원되지 않을 수 있다.
- 검색어가 너무 구체적이거나 다른 이름으로 등록되어 있을 수 있다.
그래서 empty state를 설계할 때는 메시지 하나로 끝내기보다 상태별 원인과 버튼을 함께 고민하는 편이 좋습니다. 사용자에게 단순히 비어 있음을 보여주는 것이 아니라, 다음에 어떤 행동을 하면 되는지 알려주는 것이 핵심입니다.
검색 결과 없음과 오류를 먼저 구분하기
가장 먼저 나눠야 하는 것은 결과 없음과 오류입니다. 둘 다 화면에는 리스트가 비어 보이지만 사용자에게 필요한 행동은 다릅니다.
| 상태 | 원인 | 메시지 방향 | 버튼 예시 |
|---|---|---|---|
| 검색 결과 없음 | 검색어와 일치하는 데이터가 없음 | 다른 단어로 검색하도록 안내 | 검색어 지우기 |
| 네트워크 오류 | 인터넷 연결 또는 서버 응답 실패 | 잠시 후 다시 시도하도록 안내 | 다시 시도 |
| 미지원 지역 | 선택한 지역 데이터가 없음 | 지원 지역을 다시 선택하도록 안내 | 지역 변경 |
| 초기 상태 | 아직 검색 전 | 검색 가능한 예시를 안내 | 추천 검색어 선택 |
리스트가 비었는지만 확인해서 같은 empty view를 보여주면 구현은 단순해집니다. 다만 운영 관점에서는 상태를 나눠두는 편이 문제를 찾기도 쉽고, 사용자 안내도 훨씬 자연스럽습니다.
검색어 보정은 과하지 않게 사용하기
검색 결과가 없을 때 추천 검색어나 검색어 보정을 넣으면 사용자가 다시 시도하기 편합니다. 다만 공공데이터 앱에서는 임의로 너무 많은 추측을 넣는 것도 조심해야 합니다. 실제 데이터에 없는 품목이나 장소를 있는 것처럼 보이게 만들 수 있기 때문입니다.
- 띄어쓰기 제거 정도의 단순 보정은 비교적 안전하다.
- 초성 검색이나 유사어 검색은 결과 출처를 분명히 해야 한다.
- 인기 검색어는 실제 사용자 로그를 그대로 공개하지 않는다.
- 추천 검색어는 개인을 식별할 수 없는 일반 키워드로 구성한다.
예를 들어 대형폐기물 앱이라면 의자, 책상, 매트리스 같은 일반적인 품목명을 추천할 수 있습니다. 반대로 사용자의 실제 검색어 로그를 그대로 노출하는 방식은 피해야 합니다. 검색어 보정은 사용자를 돕는 기능이지, 없는 데이터를 있는 것처럼 보이게 만드는 기능이 되어서는 안 됩니다.
Android 화면 상태 예시
검색 화면을 만들 때는 UI 상태를 먼저 나눠두면 empty state 처리가 단순해집니다. 아래 코드는 실제 프로젝트 코드가 아니라 구조 설명을 위한 예시입니다.
sealed interface SearchUiState {
data object Initial : SearchUiState
data object Loading : SearchUiState
data class Success(val items: List<SearchItem>) : SearchUiState
data class Empty(val keyword: String) : SearchUiState
data class UnsupportedRegion(val regionName: String) : SearchUiState
data class NetworkError(val canRetry: Boolean = true) : SearchUiState
}
data class SearchItem(
val title: String,
val subtitle: String
)
이렇게 나누면 화면에서는 상태별로 다른 문구와 버튼을 보여줄 수 있습니다. Empty에서는 검색어를 지우거나 다른 키워드를 안내하고, NetworkError에서는 다시 시도 버튼을 보여주는 식입니다.
코드를 나눠보다 보면 상태 이름이 곧 화면 문구의 기준이 됩니다. 초기 상태, 검색 결과 없음, 미지원 지역, 네트워크 오류를 구분해두면 화면에서 무엇을 보여줘야 하는지도 더 명확해집니다.
문구는 짧고 구체적으로 작성하기
empty state 문구는 길게 설명하기보다 사용자가 이해할 수 있는 한두 문장으로 작성하는 편이 좋습니다. 특히 모바일 화면에서는 안내 문구가 길어질수록 버튼이나 검색창이 아래로 밀릴 수 있습니다.
| 상황 | 피하면 좋은 문구 | 개선 문구 예시 |
|---|---|---|
| 검색 결과 없음 | 데이터가 없습니다. | 검색 결과가 없습니다. 다른 품목명으로 다시 검색해보세요. |
| 네트워크 오류 | 오류가 발생했습니다. | 정보를 불러오지 못했습니다. 연결 상태를 확인한 뒤 다시 시도해주세요. |
| 미지원 지역 | 지원하지 않습니다. | 현재 선택한 지역의 정보는 아직 제공되지 않습니다. 다른 지역을 선택해보세요. |
| 검색 전 | 검색하세요. | 품목명이나 키워드를 입력해 정보를 찾아볼 수 있습니다. |
문구를 작성할 때 중요한 것은 사용자를 탓하지 않는 것입니다. 잘못 입력했습니다 같은 표현보다 다른 단어로 검색해보세요처럼 다음 행동을 알려주는 문장이 더 자연스럽습니다.
재시도 버튼은 오류 상태에만 두기
재시도 버튼은 모든 empty state에 넣기보다 네트워크 오류나 서버 응답 실패처럼 다시 요청할 가치가 있는 상태에 두는 편이 좋습니다. 검색 결과 없음 상태에서 다시 시도 버튼만 보여주면 같은 요청을 반복하게 될 가능성이 큽니다.
- 검색 결과 없음 상태에서는 검색어 지우기, 추천 검색어, 이전 화면 이동을 제공한다.
- 네트워크 오류 상태에서는 다시 시도, 연결 상태 확인 안내를 제공한다.
- 미지원 지역 상태에서는 지역 변경, 제공 지역 안내를 제공한다.
- 검색 전 초기 상태에서는 예시 검색어, 최근 검색어를 제공한다.
이 기준을 정해두면 디자이너나 기획자와 화면을 맞출 때도 대화가 쉬워집니다. 단순히 빈 화면이라고 부르는 대신 상태 이름을 기준으로 이야기할 수 있기 때문입니다.
공공데이터 앱에서 추가로 조심할 점
공공데이터를 사용하는 앱은 빈 결과가 실제로 데이터가 없는 것인지, API 응답이 일시적으로 비어 있는 것인지, 지역별 제공 범위가 다른 것인지 확인해야 합니다. 이 부분을 구분하지 않으면 사용자에게 잘못된 안내를 줄 수 있습니다.
- API 응답이 비어 있을 때와 요청 실패를 구분한다.
- 지역별 제공 범위를 화면 문구에 반영한다.
- 사용자 검색어와 위치 정보를 로그나 예시로 공개하지 않는다.
- 정확성이 필요한 행정 정보는 최신 안내 확인 문구를 남긴다.
- 내부 API 주소, 인증 키, 관리자 URL은 공개 글에 포함하지 않는다.
실제로 정리해보면 empty state는 작은 UI 요소가 아니라 서비스 신뢰도와 연결됩니다. 사용자가 원하는 정보를 찾지 못했을 때 앱이 어떤 안내를 해주느냐에 따라 앱이 친절하게 느껴질 수도 있고, 고장 난 것처럼 느껴질 수도 있습니다.
테스트 기준
empty state는 정상 검색 결과만 확인해서는 부족합니다. 검색 결과 없음, 네트워크 오류, 미지원 지역, 초기 상태를 각각 따로 확인해야 화면 문구와 버튼이 자연스럽게 맞습니다.
- 검색 결과 없음과 네트워크 오류를 같은 화면으로 처리하지 않는지 확인한다.
- 빈 결과 문구에 다음 행동을 포함했는지 확인한다.
- 추천 검색어에 실제 사용자 검색 로그를 그대로 노출하지 않는지 확인한다.
- 미지원 지역과 데이터 없음 상태를 구분하는지 확인한다.
- 정책이나 행정 절차가 바뀔 수 있는 정보에는 최신 확인 문구를 두었는지 확인한다.
자주 하는 실수
1. 리스트가 비어 있으면 모두 같은 empty view를 보여주는 경우가 있습니다. 검색 결과 없음과 네트워크 오류는 사용자에게 필요한 행동이 다르므로 상태를 나누는 편이 좋습니다.
2. 검색 결과 없음 상태에 다시 시도 버튼만 넣는 경우도 있습니다. 같은 검색어로 다시 요청해도 결과가 바뀌지 않을 수 있으므로 검색어 지우기나 추천 검색어가 더 자연스러울 수 있습니다.
3. 사용자 검색 로그를 추천 검색어처럼 보여주는 경우가 있습니다. 검색 로그에는 개인을 식별할 수 있는 정보가 섞일 수 있으므로 그대로 노출하면 안 됩니다.
4. 미지원 지역과 데이터 없음 상태를 구분하지 않는 경우도 있습니다. 현재 지역에서 제공하지 않는 것인지, 검색어와 맞는 결과만 없는 것인지 문구가 달라져야 합니다.
마무리
Android 검색 화면에서 empty state는 단순히 리스트가 비었을 때 보여주는 빈 화면이 아닙니다. 사용자가 다음에 어떤 행동을 해야 하는지 알려주는 중요한 안내 흐름입니다.
검색 결과 없음, 네트워크 오류, 미지원 지역, 초기 상태를 구분해두면 화면 문구와 버튼도 자연스럽게 달라집니다. 작은 차이처럼 보일 수 있지만, 공공데이터나 지역 기반 앱에서는 사용자의 오해를 줄이고 앱의 신뢰도를 높이는 데 도움이 됩니다.
참고 자료
- Android Developers, Guide to app architecture
- Android Developers, UI state production
- Material Design, Empty states
- 각 공공데이터 제공 기관의 API 응답 및 오류 안내 문서
'개발 노트 > 기타' 카테고리의 다른 글
| [Android] 앱에서 스플래시 화면의 역할을 최소화하는 방법 (0) | 2026.05.22 |
|---|---|
| [Android/공공데이터앱] 외부 검색 API와 내부 관리자 API를 함께 사용할 때의 경계 (0) | 2026.05.22 |
| [Android/공공데이터앱] 대형폐기물 정보 앱 개발노트 (0) | 2026.05.22 |
| [UI/반응형] 앱 화면 최적화를 위한 문서와 테스트 체크리스트 작성 방법 (0) | 2026.05.21 |
| [UI Test] GitHub Actions UI 테스트 실패 로그를 읽고 원인을 좁히는 순서 (0) | 2026.05.21 |