경험의 모든 이벤트와 사용자의 요청을 수동으로 모니터링하는 대신, 웹훅을 설정하여 타사 메시징 도구나 HTTP 요청을 수신할 수 있는 사용자 지정 끝점에서 실시간 알림을 받을 수 있습니다.이렇게 하면 알림 관리 워크플로를 자동화하여 수동으로 처리되는 알림의 노력을 줄일 수 있습니다.
웹훅 워크플로
웹훅은 Roblox 및 타사 메시징 도구와 같은 두 개의 다른 응용 프로그램이나 서비스 간에 실시간 알림이나 데이터를 전송합니다.전통적인 API와 달리 클라이언트 응용 프로그램을 설정하여 서버에 요청을 보내고 데이터를 받아야 하는 것과는 달리, 웹훅은 이벤트가 발생하는 즉시 클라이언트 끝점에 데이터를 보냅니다.Roblox와 팀 간 공동 작업을 위해 사용하는 타사 응용 프로그램 간의 워크플로를 자동화하는 데 유용하며, 실시간 데이터 공유 및 처리를 허용하기 때문입니다.
웹훅을 설정한 후 대상 이벤트가 발생할 때마다 Roblox는 제공한 웹훅 URL로 요청을 보냅니다.그런 다음 웹훅 URL은 웹훅 페이로드에 포함된 데이터에 따라 받는 응용 프로그램이나 사용자 지정 끝점으로 요청을 리디렉션하여 작업을 수행합니다.이에는 GDPR에 대한 데이터 지우기, 사용자에게 확인 전송 또는 다른 이벤트 트리거가 포함될 수 있습니다.
지원되는 트리거
Roblox는 현재 알림에 대한 다음 이벤트 트리거를 지원합니다:
- 구독 취소됨 - 사용자가 구독을 취소할 때, 구독과 구독자, 취소 이유가 포함된 메시지가 전송됩니다.
- 구독 구매됨 - 사용자가 구독을 구매하면 구독과 구독자가 포함된 메시지가 전송됩니다.
- 구독 환불 - 사용자가 구독에 대한 환불을 받을 때 구독과 구독자가 포함된 메시지가 전송됩니다.
- 구독 갱신됨 - 사용자가 구독을 갱신하면 구독과 구독자가 포함된 메시지가 전송됩니다.
- 구독 재구독 - 사용자가 구독에 재구독할 때 구독과 구독자가 포함된 메시지가 전송됩니다.
- "잊혀질 권리" 일반 데이터 보호 규정( GDPR )에서 데이터 삭제 요청.
구독 이벤트와 필드에 대한 자세한 정보는 클라우드 API 구독 참조 문서를 참조하십시오.
크리에이터 대시보드에서 웹훅 구성
웹훅을 통해 알림을 받으려면 알림을 트리거하기 위해 특정 이벤트에 구독하는 웹훅을 구성해야 합니다.그룹 소유 경험의 경우, 그룹 소유자만 웹훅 알림을 구성하고 받을 수 있습니다.
웹훅을 설정하려면:
- 크리에이터 대시보드의 웹훅 섹션으로 이동합니다.
- 클릭하십시오 웹훅 추가 버튼.
- 클릭하십시오 변경 사항 저장 버튼.
웹훅 URL 설정
다음 요건을 충족하면 웹훅 URL로 사용자 지정 HTTP 서비스 끝점을 설정할 수 있습니다: You can set up a custom HTTP service endpoint as your webhook URL, provided it fulfills the following requirements:
- 요청을 처리하기 위해 공개적으로 액세스해야 합니다.
- POST 요청을 처리할 수 있습니다.
- 5초 이내에 2XX 응답으로 요청에 응답할 수 있습니다.
- HTTPS 요청을 처리할 수 있습니다.
끝점이 POST 요청을 받을 때, 다음을 수행할 수 있어야 합니다:
- 포스트 메시지의 본문에서 알림에 필요한 세부 정보를 추출합니다.
- 알림의 일반적인 세부 정보와 알림의 이벤트 유형과 관련된 특정 세부 정보로 POST 메시지의 본문을 읽습니다.Read the body of the POST message with the generic details on the notification and specific details related to the event type on the notification.
처리할 POST 요청의 스키마에 대한 자세한 정보는 Payload 스키마에 참조하십시오.
배달 실패 재시도 정책
끝점 불가용 등의 오류로 인해 웹훅 알림이 지정된 URL에 도달하지 못하면 Roblox는 고정된 창 크기를 사용하여 5번 구성된 URL로 메시지를 보내는 것을 다시 시도합니다.알림이 5번의 시도 후에도 전달되지 않으면 Roblox는 알림 전송을 중지하고 URL이 더 이상 유효하지 않다고 가정합니다.이 상황에서는 연결할 수 있고 알림을 받을 수 있는 새 URL로 웹훅 구성을 업데이트해야 합니다.웹훅 URL이 알림을 성공적으로 받을 수 있는지 문제를 해결하고 확인하려면 웹훅 테스트를 참조하십시오.
제3자 요구 사항
타사 도구는 일반적으로 웹훅 URL을 설정할 때 따라야 하는 웹훅 요구 사항을 가지고 있습니다.대상 도구의 지원 또는 문서화 사이트에서 "webhook" 키워드를 검색하여 이러한 요구 사항을 찾을 수 있습니다.지원되는 세 가지 타사 도구에 대해서는 팔로잉참조하십시오:
테스트 웹훅
구성한 웹훅이 크리에이터 대시보드에서 알림을 성공적으로 수신할 수 있는지 테스트할 수 있습니다.
- 웹훅 구성 페이지로 이동합니다.
- 구성된 웹훅 목록에서 테스트하려는 웹훅을 선택합니다.
- 대상 웹훅 옆에 있는 연필 아이콘을 클릭하십시오.
- 클릭하십시오 테스트 응답 버튼.
시스템은 다음 예시 스키마와 같이 알림을 트리거하는 사용자의 사용자 ID를 포함하는 알림 입력전송합니다.
샘플 알림 스키마
Body: {
"NotificationId": "string",
"EventType": "SampleNotification",
"EventTime": "2023-12-30T16:24:24.2118874Z", // 유형: ISO 8601 타임스탬프
"EventPayload": {
"UserId": 1 // 유형: 길게
}
}
웹훅을 타사 서비스와 통합하는 경우 타사 URL을 사용하여 서비스가 웹훅에서 알림을 성공적으로 수신할 수 있는지 테스트할 수 있습니다.웹훅을 구성할 때 비밀을 제공하면 또한 roblox-signature 로직을 테스트할 수 있는 roblox-signature 을 생성합니다.
웹훅 보안 확인
서버에 페이로드를 받도록 구성하면 끝점에 전송된 페이로드를 수신하기 시작합니다.웹훅을 구성할 때 비밀을 설정하면 Roblox는 데이터 보안을 보호하기 위해 모든 웹훅 알림과 함께 roblox-signature를 보냅니다.이런 방식으로 알림이 Roblox에서 온 것을 확인하고 서버가 Roblox에서 출발하는 요청만 받도록 제한할 수 있습니다.서명은 사용자 지정 끝점의 페이로드 헤더와 타사 서버의 피터에 있습니다.
Signature Format with Secret for Custom Endpoints
"roblox-signature": "t=<timestamp>,v1=<signature>"
웹훅에 비밀이 없는 경우 받은 서명에는 알림이 전송된 시점의 타임스탬프 값만 포함됩니다.
Signature Format without Secret for Custom Endpoints
"roblox-signature": "t=<timestamp>"
서명을 확인하려면:
타임스탬프 및 서명 값 추출.비밀이 있는 웹훅의 모든 서명은 접두사 다음에 이 두 값과 동일한 형식의 CSV 문자열을 공유합니다. All signatures for webhooks with secrets share the same format as a CSV string with these two values following by the prefixes:
- t : 알림이 전송될 때의 타임스탬프 값.
- v1 : 크리에이터 대시보드 구성에서 제공하는 비밀을 사용하여 생성된 서명 값.이 경우 구분 기호를 사용하여 문자열을 구분하는 함수를 사용하여 이 두 값을 추출할 수 있습니다.
다음을 결합하여 roblox-signature의 기본 문자열 다시 만들기:
- 문자열로 된 타임스탬프.
- 기간 문자 . .
- 요청 본문의 JSON 문자열.
구성 중에 정의한 비밀과 2단계에서 생성한 메시지를 메시지로 사용하여 SHA256 해시 함수를 사용하여 해시 기반 메시지 인증 코드(HMAC)를 계산합니다.Compute a Hash-based message authentication code (HMAC) with the SHA256 hash function using the secret you defined during the configuration as the key and the base string you generated through step 2 as the message.결과를 Base64 형식으로 변환하여 예상 서명을 얻습니다.
추출된 서명 값을 예상 서명과 비교합니다. 서명을 올바르게 생성했으면 값이 동일해야 합니다.
(옵션) 재생 공격을 방지하려면, 공격자가 데이터를 가로채고 다시 전송하여 승인되지 않은 액세스를 얻거나 악의적인 작업을 수행하는 사이버 공격의 한 유형으로, 추출된 타임스탬프 값과 현재 타임스탬프를 비교하고 적절한 시간 제한 내에 있는지 확인하는 것이 도움이 됩니다.예를 들어, 10분 창은 일반적으로 적절한 시간 제한입니다.
페이로드 스키마
웹훅의 대상 이벤트가 트리거되면 페이로드에 대한 이벤트 정보를 포함하여 웹훅 URL에 요청이 전송됩니다.요청의 모든 페이로드는 고정 및 변수 필드로 구성된 동일한 스키마를 공유합니다.이렇게 하면 페이로드에 전송된 데이터가 구조화되고 일관되어 받는 응용 프로그램이 데이터를 처리하고 사용하기 더 쉽습니다.
고정된 페이로드 스키마 필드 는 다음 필드를 사용하여 모든 웹훅 요청에서 일관성을 유지하는 데 도움이 될 수 있습니다:
NotificationId , string : 각 전송된 알림에 대한 고유 식별자. 동일한 NotificationId 가 두 번 받으면 중복으로 간주됩니다.
EventType , string : 문자열은 알림이 트리거된 이벤트 유형을 나타냅니다.
EventTime , timestamp : 이벤트가 트리거된 시점을 나타내는 대략적인 타임스탬프. 변수 페이로드 스키마 필드 는 웹훅이 다양한 유형의 이벤트를 수용할 수 있도록 유연성을 제공하며 포함:
EventPayload , object : 웹훅을 트리거한 특정 정보를 포함합니다. EventType``EventPayload 스키마의 구조는 이벤트 유형에 따라 다릅니다.
다음 예제에서는 삭제 요청 이벤트의 페이로드 스키마를 보여줍니다.
삭제 요청에 대한 예제 스키마
Body:{
"NotificationId": "string",
"EventType": "RightToErasureRequest",
"EventTime": "2023-12-30T16:24:24.2118874Z",
"EventPayload": {
"UserId": 1, // 유형: 길게
"GameIds": [ // 유형: 길이의 배열
1234, 2345
]
}
}
알림 처리
사용자 ID와 같은 사용자의 개인 식별 정보(PII)를 저장하는 경우, GDPR의 삭제 요구 준수 요구 사항을 충족하기 위해 이 정보를 삭제해야 합니다.데이터 상점PII를 저장하는 경우 웹훅 알림을 처리하고 데이터 삭제를 자동화하기 위한 봇을 만들 수 있습니다.자동 삭제 요청 실행 자동화에서 Guilded 또는 Discord에서 데이터 저장소용 오픈 클라우드 API를 사용하여 PII 데이터를 자동화 솔루션으로 삭제하는 방법에 대한 예제를 참조하십시오.이 예제는 구독 이벤트와 같은 다른 알림을 처리하기 위해 조정될 수 있습니다.
타사 도구 대신 사용자 지정 끝점을 웹훅 서버로 사용하면 웹훅 페이로드에서 삭제할 데이터 주체를 추출하고 자체 자동화 솔루션을 구축할 수 있습니다.다음 코드 샘플은 요청이 Roblox에서 온 것인지 확인하여 재생 공격을 방지하는 예시 솔루션을 제공하고 재생 공격을 방지하기 위해 요청을 추가합니다.
Extracting PII from Payload
const crypto = require('crypto')
const express = require('express');
let app = express();
app.use(express.json());
app.use(express.urlencoded({ extended: true }));
// This is a sample only code
app.all('/*', function (req, res) {
console.log('-------- New Request Seen -------');
// 1. Extract the timestamp and signature
const shared_secret = '<Your secret>' // This can be set as an environment variable
const hmac = crypto.createHmac('sha256', shared_secret)
const roblox_signature_header = req.headers['roblox-signature'].split(',')
// 'roblox-signature' is present in all requests:
// Timestamp(t) is present in all requests, however signature value(v1) is not set unless a secret is shared during the webhook configuration.
// Fetch header component at Index 0 -> 't=' and Index 1 -> 'v1='
const timestamp = roblox_signature_header.find(e => e.startsWith('t=')).substring(2);
const extracted_signature = roblox_signature_header.find(e => e.startsWith('v1='));
// 2. Prevent Replay attack: 300 seconds window
const request_timestamp_ms = timestamp * 1000;
const window_time_ms = 300 * 1000
const oldest_timestamp_allowed = Date.now() - window_time_ms;
if (request_timestamp_ms < oldest_timestamp_allowed) {
res.status(403).send('Expired Request')
}
// 3. Validate Signature
if (extracted_signature !== undefined) {
const signature_v1 = extracted_signature.substring(3);
const message = `${timestamp}.${JSON.stringify(req.body)}`
const base64_signature = hmac.update(message).digest('base64')
if (signature_v1 !== base64_signature) {
res.status(401).send('Unauthorized Request')
}
}
// 4. Your logic to handle payload
const payloadBody = req.body
const eventType = payloadBody['EventType']
if (eventType === 'RightToErasureRequest'){
const userId = payloadBody['EventPayload']['UserId']
const gameIds = payloadBody['EventPayload']['GameIds']
const gameIdString = gameIds.toString()
console.log(`The payload: UserId=${userId} and GameIds=${gameIdString}`)
// If you store PII in data stores, use the UserId and GameIds to make a data store call to delete the information.
}
// 5. Return Response
res.json({ message: 'Processed the message Successfully' });
})
app.listen(8080, function () {
console.log('This is a Sample application')
})