데이터 규칙
이 장에서는 AE 백엔드의 데이터 구조, 데이터 타입, 데이터 제한을 자세히 소개합니다. 이 장을 통해 규칙에 맞는 데이터를 구성하는 방법과 데이터 전송 문제를 해결하는 방법을 알 수 있습니다.
LogBus 또는 RESTful API로 데이터를 업로드하는 경우 이 장의 데이터 규칙에 따라 데이터 형식을 처리해야 합니다.
1. 데이터 구조
AE 백엔드는 규칙에 맞는 JSON 데이터를 받습니다. SDK로 연동하는 경우 데이터는 JSON 데이터로 변환되어 전송됩니다. LogBus 또는 POST 방식으로 데이터를 업로드하는 경우 데이터는 규칙에 맞는 JSON 데이터여야 합니다.
JSON 데이터는 행 단위입니다. 즉 한 행에 JSON 데이터가 하나씩 있으며, 물리적으로는 데이터 한 건에 해당하고, 데이터의 의미로는 유저의 행동 1회 또는 유저 속성 설정 1회에 해당합니다.
데이터 형식과 요구 사항은 다음과 같습니다(읽기 편하도록 데이터를 정렬했으며, 실제 환경에서는 줄을 바꾸지 마십시오):
- 다음은 이벤트 데이터의 예시입니다:
{
"#account_id": "ABCDEFG-123-abc",
"#distinct_id": "F53A58ED-E5DA-4F18-B082-7E1228746E88",
"#type": "track",
"#ip": "192.168.171.111",
"#uuid": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
"#time": "2017-12-18 14:37:28.527",
"#event_name": "test",
"properties": {
"argString": "abc",
"argNum": 123,
"argBool": true
}
}
- 다음은 유저 속성 설정의 예시입니다:
{
"#account_id": "ABCDEFG-123-abc",
"#distinct_id": "F53A58ED-E5DA-4F18-B082-7E1228746E88",
"#type": "user_set",
"#uuid": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
"#time": "2017-12-18 14:37:28.527",
"properties": {
"userArgString": "abc",
"userArgNum": 123,
"userArgBool": true
}
}
"#type"의 값은 "user_setOnce", "user_add", "user_unset", "user_append", "user_del"로 바꿀 수 있습니다
구조와 기능 측면에서 JSON 데이터 한 건은 두 부분으로 나눌 수 있습니다:
properties와 같은 계층에 있는 다른 필드는 해당 데이터의 기본 정보를 구성하며, 다음 항목만 포함합니다:
- 트리거한 유저를 나타내는 계정 ID
#account_id와 게스트 ID#distinct_id - 트리거 시간을 나타내는
#time(초 또는 밀리초 단위까지 지정 가능) - 데이터 타입(이벤트인지 유저 속성 설정인지)을 나타내는
#type - 이벤트 이름을 나타내는
#event_name(이벤트 데이터에만 포함) - 유저 IP를 나타내는
#ip - 데이터 고유성을 나타내는
#uuid
위 항목을 제외하고 "#"으로 시작하는 나머지 속성은 모두 properties 내부에 넣어야 합니다
properties 내부는 해당 데이터의 내용, 즉 이벤트의 속성 또는 설정할 유저 속성이며, 백엔드에서 분석할 때 속성 또는 분석 대상으로 바로 사용됩니다.
구조적으로 이 두 부분은 메시지 헤더(Header)와 메시지 본문(Content)과 비슷합니다. 다음으로 두 부분의 각 필드가 가지는 의미를 자세히 소개합니다.
1.1 데이터 정보 부분
위의 이벤트 데이터 예시처럼 "properties"와 같은 계층에 있는 여러 필드가 해당 데이터의 정보 부분을 구성합니다.
이 필드들은 해당 데이터의 트리거 유저, 트리거 시간 등의 데이터 정보를 담고 있으며, 모든 필드가 "#"으로 시작한다는 특징이 있습니다. 이 절에서는 각 필드의 의미와 설정 방법을 정리합니다.
1.1.1 유저 정보(#account_id와 #distinct_id)
#account_id와 #distinct_id는 AE 백엔드가 유저를 식별하는 데 사용하는 두 필드입니다. #account_id는 유저가 로그인한 상태의 ID이고, #distinct_id는 유저가 로그인하지 않은 상태의 식별자입니다. AE 백엔드는 이 두 필드로 해당 행동을 트리거한 유저를 판단하며, #account_id를 우선으로 판단합니다. 구체적인 규칙은 유저 식별 규칙 장을 참고하십시오.
#account_id와 #distinct_id 중 적어도 하나는 전달해야 합니다. 모든 이벤트가 유저가 로그인한 상태에서 트리거된다면 #account_id만 전달해도 되지만, 로그인하지 않은 상태(가입 전 포함)에서 트리거되는 이벤트가 있다면 두 필드를 모두 입력하는 것을 권장합니다.
1.1.2 데이터 타입 정보(#type과 #event_name)
#type은 해당 데이터의 타입, 즉 유저의 행동 기록인지 유저 속성을 수정하는 작업인지를 결정하며, 모든 데이터에 #type 필드를 설정해야 합니다. #type의 값은 두 종류로 나뉩니다. track은 해당 데이터가 유저 행동 기록임을 나타내고, user_로 시작하는 값은 유저 속성에 대한 작업을 나타냅니다. 구체적인 의미는 다음과 같습니다:
- track: 이벤트 테이블에 이벤트 하나를 전달합니다. 이벤트 업로드는 모두 track입니다
- user_set: 유저 테이블에 대한 작업으로, 하나 이상의 유저 속성을 덮어씁니다. 해당 속성에 이미 값이 있으면 이전 값을 덮어씁니다
- user_setOnce: 유저 테이블에 대한 작업으로, 하나 이상의 유저 속성을 초기화합니다. 해당 속성에 이미 값이 있으면 이번 작업은 무시됩니다
- user_add: 유저 테이블에 대한 작업으로, 하나 이상의 숫자형 유저 속성을 누적 계산합니다
- user_unset: 유저 테이블에 대한 작업으로, 해당 유저의 하나 이상의 유저 속성 값을 비웁니다
- user_del: 유저 테이블에 대한 작업으로, 해당 유저를 삭제합니다
- user_append: 유저 테이블에 대한 작업으로, 유저의 리스트 타입 속성 값에 요소를 추가합니다
- user_uniq_append: 유저 테이블에 대한 작업으로, 유저의 리스트 타입 속성 값에 요소를 추가하고 리스트 전체의 중복을 한 번 제거합니다(중복을 제거해도 기존 요소의 순서는 그대로 유지됩니다)
#type의 값이 track인 경우, 즉 해당 데이터가 행동 기록인 경우 이벤트 이름 #event_name을 반드시 설정해야 합니다. 이벤트 이름은 영문자로 시작해야 하며 영문 소문자, 숫자, 밑줄 "_"만 포함할 수 있고, 최대 길이는 50자입니다. 설정할 때 공백이 포함되지 않도록 주의하십시오. 해당 데이터가 유저 속성을 수정하는 작업이라면 #event_name 필드는 필요하지 않습니다.
유저 속성은 유저에게 마일스톤과 같은 의미를 가지는 속성이므로 짧은 시간 안에 자주 수정하는 것은 권장하지 않습니다. 자주 변경해야 하는 속성은 이벤트에 이벤트 속성으로 넣는 것을 권장합니다
1.1.3 트리거 시간(#time)
#time은 이벤트가 발생한 시간으로 반드시 설정해야 하며, 형식은 밀리초("yyyy-MM-dd HH:mm:ss.SSS") 또는 초("yyyy-MM-dd HH:mm:ss")까지 표시한 문자열이어야 합니다
User 테이블에 대한 작업 데이터에도 #time을 설정해야 하지만, 유저 속성에 대한 작업은 백엔드가 데이터를 받은 순서대로 수행됩니다.
예를 들어 유저가 과거 어느 날의 User 테이블 작업 데이터를 다시 전송하더라도 속성 덮어쓰기와 초기화 모두 평소대로 수행되며, #time 필드로 판단하지 않습니다
1.1.4 트리거 위치(#ip)
#ip는 디바이스의 IP 주소이며 선택 설정 항목입니다. AE는 IP 주소로 유저의 지리적 위치 정보를 계산합니다. "properties"에 #country, #province, #city 등의 지리적 위치 속성을 전달한 경우 전달한 값을 기준으로 합니다
1.1.5 데이터 고유 ID(#uuid)
#uuid는 데이터의 고유성을 나타내는 필드이며 선택 설정 항목입니다. 형식은 uuid 표준 형식이어야 합니다. AE는 데이터양에 따라 일정 시간 동안 수신 측에서 짧은 시간 안에 같은 #uuid를 가진 데이터(즉 중복 데이터)가 나타나는지 검증하고, 중복 데이터는 바로 폐기하며 저장하지 않습니다
참고로 #uuid를 통한 수신 측 검증은 최근 몇 시간 동안 수신된 데이터만 검증하며, 주로 네트워크 불안정으로 인한 단시간 데이터 중복을 해결합니다. 수신된 데이터를 전체 데이터와 대조하여 검증할 수는 없습니다. 데이터 중복 제거가 필요하면 ThinkingAI 담당자에게 문의하십시오.
1.2 데이터 본문 부분
데이터의 다른 한 부분은 properties 내부에 포함된 데이터입니다. properties는 JSON 객체이며, 내부 데이터는 키-값 쌍 형식으로 표현됩니다. 유저 행동 데이터인 경우 해당 행동의 속성과 지표(행동 테이블의 필드에 해당)를 나타내며, 이러한 속성과 지표는 분석할 때 바로 사용할 수 있습니다. 유저 속성에 대한 작업인 경우 설정할 속성 내용을 나타냅니다.
key 값은 해당 속성의 이름이며 타입은 문자열입니다. 커스텀 속성은 영문자로 시작해야 하며 영문 소문자, 숫자, 밑줄 "_"만 포함할 수 있고, 최대 길이는 50자입니다. 이 밖에 #으로 시작하는 AE 시스템 속성도 있으며, 자세한 내용은 시스템 속성 장에서 확인할 수 있습니다. 단, 대부분의 경우 커스텀 속성만 사용하고 #은 사용하지 않는 것을 권장합니다.
value 값은 해당 속성의 값이며 숫자, 텍스트, 시간, 불리언, 리스트, 객체, 객체 그룹일 수 있습니다. 데이터 타입별 표현 방식은 아래 표와 같습니다:
| AE 데이터 타입 | 값 예시 | 값 설명 | 데이터 타입 |
|---|---|---|---|
| 숫자 | 123,1.23 | 데이터 범위는 -9E15 ~ 9E15 | Number |
| 텍스트 | "ABC","상하이" | 문자의 기본 상한은 2KB | String |
시간 | "2019-01-01 00:00:00","2019-01-01 00:00:00.000" | "yyyy-MM-dd HH:mm:ss.SSS" 또는 "yyyy-MM-dd HH:mm:ss". 날짜를 나타내려면 "yyyy-MM-dd 00:00:00"을 사용할 수 있습니다 | String |
| 불리언 | true,false | - | Boolean |
| 리스트 | ["a","1","true"] | 리스트의 요소는 모두 문자열 타입으로 변환되며, 리스트에는 최대 500개의 요소를 넣을 수 있습니다 | Array(String) |
| 객체 | {"hero_name":"유비","hero_level":22,"hero_equipment": ["자웅쌍고검","적로"],"hero_if_support":false} | 객체 안의 각 하위 속성(Key)은 각자의 데이터 타입을 가지며, 값 설명은 위의 해당 타입 일반 속성을 참고하십시오 객체 안에는 최대 100개의 하위 속성을 넣을 수 있습니다 | Object |
| 객체 그룹 | [{"hero_name":"유비","hero_level":22,"hero_equipment": ["자웅쌍고검","적로"],"hero_if_support":false}, {"hero_name":"유비","hero_level":22,"hero_equipment": ["자웅쌍고검","적로"],"hero_if_support":false}] | 객체 그룹 안의 각 하위 속성(Key)은 각자의 데이터 타입을 가지며, 값 설명은 위의 해당 타입 일반 속성을 참고하십시오 객체 그룹 안에는 최대 500개의 객체를 넣을 수 있습니다 | Array(Object) |
모든 속성의 타입은 해당 속성 값을 처음 받았을 때의 타입으로 결정되며, 이후 데이터의 타입은 해당 속성의 타입과 일치해야 합니다. 타입이 맞지 않는 속성은 폐기되며(해당 데이터에서 타입이 맞는 나머지 속성은 유지됨), AE는 타입 호환 변환을 하지 않습니다.
2. 데이터 처리 규칙
AE 서버는 데이터를 받은 후 몇 가지 처리를 수행합니다. 이 절에서는 실제 사용 시나리오와 함께 AE 백엔드의 처리 규칙을 설명합니다:
2.1 새 이벤트 데이터 수신
새 이벤트 데이터를 받으면 AE 백엔드는 새 이벤트와 해당 속성의 연관 모델을 자동으로 생성합니다. 새 속성을 받은 경우 해당 속성을 처음 받았을 때의 속성 타입이 해당 속성의 타입으로 설정되며, 이후에는 속성 타입을 수정할 수 없습니다.
2.2 이벤트 속성 추가
기존 이벤트에 속성을 추가하려면 데이터를 업로드할 때 새 속성을 함께 전달하기만 하면 됩니다. AE 백엔드가 이벤트와 새 속성을 동적으로 연관시키므로 별도로 설정할 필요가 없습니다.
2.3 속성 불일치 처리
이벤트 데이터를 받았을 때 그중 어떤 속성의 타입이 백엔드에 이미 저장된 해당 속성의 타입과 일치하지 않으면 해당 속성의 값은 폐기됩니다(즉 값이 null이 됨).
2.4 이벤트 속성 사용 중단
이벤트의 특정 속성을 더 이상 사용하지 않으려면 AE 백엔드의 데이터 관리 모듈에서 해당 속성을 숨기기만 하면 되며, 이후 전송하는 데이터에서는 해당 속성을 전달하지 않아도 됩니다. AE 백엔드는 해당 속성의 데이터를 삭제하지 않으며 숨기기 작업은 되돌릴 수 있습니다. 속성을 숨긴 후에도 해당 속성을 전송하면 해당 속성의 값은 계속 유지됩니다.
2.5 여러 이벤트가 공유하는 속성
서로 다른 이벤트의 같은 이름 속성은 같은 속성으로 간주되며 타입도 같습니다. 따라서 타입 불일치로 속성 값이 폐기되지 않도록 같은 이름의 모든 속성의 타입을 일치시켜야 합니다.
2.6 유저 테이블 작업 로직
유저 테이블에서 유저의 데이터를 수정하는 데이터, 즉 전송 데이터에서 #type 필드가 user_set, user_setOnce, user_add, user_unset, user_append 또는 user_del인 데이터는 본질적으로 하나의 명령으로 볼 수 있습니다. 즉 해당 데이터가 가리키는 유저의 유저 테이블 데이터에 대해 작업을 수행하며, 작업 타입은 #type 필드로 결정되고 작업 내용은 properties의 속성으로 결정됩니다.
다음은 주요 유저 테이블 속성 작업의 구체적인 로직입니다:
2.6.1 유저 속성 덮어쓰기(user_set)
데이터의 유저 ID로 작업할 유저를 정한 다음, properties의 속성에 따라 모든 속성을 덮어씁니다. 어떤 속성이 존재하지 않으면 해당 속성을 새로 생성합니다.
2.6.2 유저 속성 초기화(user_setOnce)
데이터의 유저 ID로 작업할 유저를 정한 다음, properties의 속성에 따라 값이 할당되지 않은(비어 있는) 속성을 설정합니다. 해당 유저의 설정할 속성에 이미 값이 있으면 덮어쓰지 않으며, 어떤 속성이 존재하지 않으면 해당 속성을 새로 생성합니다.
2.6.3 유저 속성 누적(user_add)
데이터의 유저 ID로 작업할 유저를 정한 다음, properties의 속성에 따라 숫자형 속성을 누적합니다. 음수를 전달하면 원래 속성 값에서 전달한 값을 빼는 것과 같습니다. 해당 유저의 설정할 속성에 값이 할당되지 않은(비어 있는) 경우 기본값 0으로 설정한 후 누적하며, 해당 속성이 존재하지 않으면 해당 속성을 새로 생성합니다.
2.6.4 유저 속성 값 비우기(user_unset)
데이터의 유저 ID로 작업할 유저를 정한 다음, properties의 속성에 따라 해당하는 모든 속성을 비웁니다(즉 NULL로 설정). 어떤 속성이 존재하지 않으면 해당 속성을 새로 생성하지 않습니다.
2.6.5 리스트형 유저 속성에 요소 추가(user_append)
데이터의 유저 ID로 작업할 유저를 정한 다음, properties의 속성에 따라 리스트형 속성에 요소를 추가합니다
2.6.6 유저 삭제(user_del)
데이터의 유저 ID로 작업할 유저를 정하고 해당 유저를 유저 테이블에서 삭제합니다. 해당 유저의 이벤트 데이터는 삭제되지 않습니다.
2.6.7 중복 제거형 리스트 유저 속성에 요소 추가(user_uniq_append)
데이터의 유저 ID로 작업할 유저를 정한 다음, properties의 속성에 따라 리스트형 속성에 요소를 추가하고 리스트 전체의 중복을 한 번 제거합니다(중복을 제거해도 기존 요소의 순서는 그대로 유지됩니다)
3. 데이터 제한
- 이벤트 타입 및 속성 수 제한
성능을 고려하여 AE 백엔드는 기본적으로 프로젝트의 이벤트 타입과 속성 수를 제한합니다:
| 제한 | 이벤트 종류 상한 | 이벤트 속성 상한 | 유저 속성 상한 |
|---|---|---|---|
| 권장 상한 | 100 | 300 | 100 |
| 하드 상한 | 500 | 1000 | 500 |
관리자는 프로젝트 관리 페이지에서 각 프로젝트에서 이미 사용 중인 이벤트 타입 수와 속성 수를 조회할 수 있으며, ThinkingAI 담당자에게 문의하여 이벤트 종류 수와 속성 수의 상한 상향을 신청할 수 있습니다.
-
계정 ID(#account_id), 게스트 ID(#distinct_id) 길이 제한
- 3.1 버전 이전에 생성한 프로젝트: 64자. 128자로 늘리려면 ThinkingAI 담당자에게 문의하십시오
- 3.1 버전 및 이후에 생성한 프로젝트: 128자
-
이벤트, 속성 이름 제한
- 이벤트 이름:
String타입, 영문자로 시작하며 숫자, 영문 소문자, 밑줄 "_"을 포함할 수 있고, 최대 길이는 50자 - 속성 이름:
String타입, 영문자로 시작하며 숫자, 영문 소문자, 밑줄 "_"을 포함할 수 있고, 최대 길이는 50자. 시스템 속성만 # 기호로 시작할 수 있습니다.
- 이벤트 이름:
-
텍스트, 숫자, 리스트, 객체, 객체 그룹 타입 속성의 데이터 범위
- 텍스트: 문자열 상한은 2KB
- 숫자: 데이터 범위는 -9E15~9E15
- 리스트: 최대 500개의 요소 포함. 각 요소는 문자열 타입이며 상한은 255바이트
- 객체: 최대 100개의 하위 속성 포함
- 객체 그룹: 최대 500개의 객체 포함
-
데이터 수신 시간 제한
- 서버 측 데이터 수신 기간: 서버 시간 기준 3년 전부터 3일 후까지
- 클라이언트 측 데이터 수신 기간: 서버 시간 기준 10일 전부터 3일 후까지
4. 기타 규칙
- 문자 깨짐 문제를 방지하려면 데이터를 UTF-8로 인코딩하십시오
- AE 백엔드의 속성 이름은 소문자만 지원하며, 단어 구분자로 "_"를 사용하는 것을 권장합니다
- AE 백엔드는 기본적으로 최근 3년간의 데이터만 수신하며, 3년이 지난 데이터는 입력할 수 없습니다. 3년 이전의 데이터를 입력해야 하는 경우 ThinkingAI 담당자에게 문의하여 시간 제한을 완화할 수 있습니다
5. 자주 묻는 질문
이 절에서는 데이터가 데이터 규칙에 맞지 않아 자주 발생하는 문제를 정리했습니다. 데이터 전송 문제가 발생하면 먼저 이 절의 내용에 따라 원인을 확인하십시오
5.1 AE 백엔드에서 데이터를 수신하지 못함
SDK로 전송하는 경우:
- SDK가 정상적으로 통합되었는지 확인하십시오
- APPID와 전송 URL이 올바르게 설정되었는지, 전송 포트 번호와 전송 방식에 해당하는 접미사가 누락되지 않았는지 확인하십시오
LogBus 또는 POST 방식으로 전송하는 경우:
- APPID와 전송 URL이 올바르게 설정되었는지, 전송 포트 번호와 전송 방식에 해당하는 접미사가 누락되지 않았는지 확인하십시오
- 데이터가 JSON 형식으로 전송되는지 확인하고, 한 행에 JSON 데이터가 하나씩 있도록 하십시오
- 데이터 정보 부분의 key 값이 "#"으로 시작하는지, 필수 필드가 누락되지 않았는지 확인하십시오
- 데이터 정보 부분의 value 값의 타입과 형식(시간 형식)이 올바른지 확인하십시오
- "#event_name"의 value 값이 규칙에 맞는지, 한자나 공백 등의 문자가 포함되지 않았는지 확인하십시오
- "properties"라는 key 자체는 "#"으로 시작하지 않도록 하십시오("#properties"로 쓰지 마십시오)
- 또한 유저 속성 설정은 행동 기록을 생성하지 않으므로,
user_set등의 데이터만 업로드한 경우 백엔드의 행동 분석 모델(SQL IDE 제외)에서는 데이터를 바로 조회할 수 없습니다 - 업로드한 데이터의 시간에 유의하십시오. 너무 오래된(3년 초과) 데이터는 입력되지 않습니다. 업로드한 데이터가 과거 데이터라면 조회 기간이 업로드한 데이터의 시간을 포함하지 않았을 수 있으므로 조회 기간을 조정하십시오
5.2 데이터 누락, 일부 속성이 수신되지 않음
- 데이터 본문 부분의 속성 key 값이 규칙에 맞는지, 한자나 공백 등의 문자가 포함되지 않았는지 확인하십시오
- 데이터 본문 부분의 속성 중 "#"으로 시작하는 key 값이 시스템 속성에 속하는지 확인하십시오
- 누락된 속성의 업로드 시 타입이 백엔드에 있는 해당 속성의 타입과 일치하는지 확인하십시오. 백엔드의 메타데이터 관리에서 이미 수신된 속성의 타입을 확인할 수 있습니다
5.3 데이터를 잘못 전송하여 삭제하려는 경우
- 프라이빗 배포 서비스 유저는 데이터 삭제 도구로 직접 데이터를 삭제할 수 있습니다. 클라우드 서비스 유저는 ThinkingAI 담당자에게 문의하여 데이터를 삭제할 수 있습니다
- 데이터 변경이 큰 경우 새 프로젝트를 바로 생성하는 것을 권장하며, 정식으로 데이터를 전송하기 전에 테스트 프로젝트에서 충분한 데이터 테스트를 진행하는 것을 권장합니다

