Send Outcomes
curl --request POST \
--url https://{host}/v1/outcomes \
--header 'Authorization: <api-key>' \
--header 'Content-Type: application/json' \
--data '
{
"outcomes": [
{
"placement_id": "example-4390001",
"gall_id": "example_gallery",
"post_no": 31899120,
"tier": "main",
"placed_at": "2026-09-29T02:40:00+09:00",
"picked_by": {
"type": "operator"
},
"score_at_placement": 0.62,
"views_at_placement": 1875,
"up_at_placement": 40,
"down_at_placement": 3,
"comment_at_placement": 21,
"readings": [
{
"age_h": 1,
"observed_at": "2026-09-29T03:40:00+09:00",
"views": 9120,
"up": 66,
"down": 8,
"comment_cnt": 30
}
],
"hidden_at": null,
"deleted_at": null,
"deleted_by": null
}
]
}
'import requests
url = "https://{host}/v1/outcomes"
payload = { "outcomes": [
{
"placement_id": "example-4390001",
"gall_id": "example_gallery",
"post_no": 31899120,
"tier": "main",
"placed_at": "2026-09-29T02:40:00+09:00",
"picked_by": { "type": "operator" },
"score_at_placement": 0.62,
"views_at_placement": 1875,
"up_at_placement": 40,
"down_at_placement": 3,
"comment_at_placement": 21,
"readings": [
{
"age_h": 1,
"observed_at": "2026-09-29T03:40:00+09:00",
"views": 9120,
"up": 66,
"down": 8,
"comment_cnt": 30
}
],
"hidden_at": None,
"deleted_at": None,
"deleted_by": None
}
] }
headers = {
"Authorization": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
outcomes: [
{
placement_id: 'example-4390001',
gall_id: 'example_gallery',
post_no: 31899120,
tier: 'main',
placed_at: '2026-09-29T02:40:00+09:00',
picked_by: {type: 'operator'},
score_at_placement: 0.62,
views_at_placement: 1875,
up_at_placement: 40,
down_at_placement: 3,
comment_at_placement: 21,
readings: [
{
age_h: 1,
observed_at: '2026-09-29T03:40:00+09:00',
views: 9120,
up: 66,
down: 8,
comment_cnt: 30
}
],
hidden_at: null,
deleted_at: null,
deleted_by: null
}
]
})
};
fetch('https://{host}/v1/outcomes', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://{host}/v1/outcomes",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'outcomes' => [
[
'placement_id' => 'example-4390001',
'gall_id' => 'example_gallery',
'post_no' => 31899120,
'tier' => 'main',
'placed_at' => '2026-09-29T02:40:00+09:00',
'picked_by' => [
'type' => 'operator'
],
'score_at_placement' => 0.62,
'views_at_placement' => 1875,
'up_at_placement' => 40,
'down_at_placement' => 3,
'comment_at_placement' => 21,
'readings' => [
[
'age_h' => 1,
'observed_at' => '2026-09-29T03:40:00+09:00',
'views' => 9120,
'up' => 66,
'down' => 8,
'comment_cnt' => 30
]
],
'hidden_at' => null,
'deleted_at' => null,
'deleted_by' => null
]
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: <api-key>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://{host}/v1/outcomes"
payload := strings.NewReader("{\n \"outcomes\": [\n {\n \"placement_id\": \"example-4390001\",\n \"gall_id\": \"example_gallery\",\n \"post_no\": 31899120,\n \"tier\": \"main\",\n \"placed_at\": \"2026-09-29T02:40:00+09:00\",\n \"picked_by\": {\n \"type\": \"operator\"\n },\n \"score_at_placement\": 0.62,\n \"views_at_placement\": 1875,\n \"up_at_placement\": 40,\n \"down_at_placement\": 3,\n \"comment_at_placement\": 21,\n \"readings\": [\n {\n \"age_h\": 1,\n \"observed_at\": \"2026-09-29T03:40:00+09:00\",\n \"views\": 9120,\n \"up\": 66,\n \"down\": 8,\n \"comment_cnt\": 30\n }\n ],\n \"hidden_at\": null,\n \"deleted_at\": null,\n \"deleted_by\": null\n }\n ]\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "<api-key>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://{host}/v1/outcomes")
.header("Authorization", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"outcomes\": [\n {\n \"placement_id\": \"example-4390001\",\n \"gall_id\": \"example_gallery\",\n \"post_no\": 31899120,\n \"tier\": \"main\",\n \"placed_at\": \"2026-09-29T02:40:00+09:00\",\n \"picked_by\": {\n \"type\": \"operator\"\n },\n \"score_at_placement\": 0.62,\n \"views_at_placement\": 1875,\n \"up_at_placement\": 40,\n \"down_at_placement\": 3,\n \"comment_at_placement\": 21,\n \"readings\": [\n {\n \"age_h\": 1,\n \"observed_at\": \"2026-09-29T03:40:00+09:00\",\n \"views\": 9120,\n \"up\": 66,\n \"down\": 8,\n \"comment_cnt\": 30\n }\n ],\n \"hidden_at\": null,\n \"deleted_at\": null,\n \"deleted_by\": null\n }\n ]\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://{host}/v1/outcomes")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"outcomes\": [\n {\n \"placement_id\": \"example-4390001\",\n \"gall_id\": \"example_gallery\",\n \"post_no\": 31899120,\n \"tier\": \"main\",\n \"placed_at\": \"2026-09-29T02:40:00+09:00\",\n \"picked_by\": {\n \"type\": \"operator\"\n },\n \"score_at_placement\": 0.62,\n \"views_at_placement\": 1875,\n \"up_at_placement\": 40,\n \"down_at_placement\": 3,\n \"comment_at_placement\": 21,\n \"readings\": [\n {\n \"age_h\": 1,\n \"observed_at\": \"2026-09-29T03:40:00+09:00\",\n \"views\": 9120,\n \"up\": 66,\n \"down\": 8,\n \"comment_cnt\": 30\n }\n ],\n \"hidden_at\": null,\n \"deleted_at\": null,\n \"deleted_by\": null\n }\n ]\n}"
response = http.request(request)
puts response.read_body{
"received": 1,
"created": 1,
"updated": 0
}{
"error": {
"code": "bad_request",
"message": "2 fields failed validation",
"fields": [
{
"path": "candidates[0].created_at",
"problem": "timestamp must include an explicit offset"
},
{
"path": "engagement[3].views",
"problem": "must be a non-negative integer or null"
}
]
}
}{
"error": {
"code": "unauthorized",
"message": "API key missing or unknown"
}
}{
"error": {
"code": "too_large",
"message": "JSON body exceeds 16 MiB after decompression"
}
}{
"error": {
"code": "unprocessable",
"message": "cycle_time cannot be in the future",
"fields": [
{
"path": "cycle_time",
"problem": "must not be in the future"
}
]
}
}{
"error": {
"code": "server_error",
"message": "internal error"
}
}Weights and Outcomes
Operator Outcomes
Not in scope for trial — outcomes endpoint reference
POST
/
v1
/
outcomes
Send Outcomes
curl --request POST \
--url https://{host}/v1/outcomes \
--header 'Authorization: <api-key>' \
--header 'Content-Type: application/json' \
--data '
{
"outcomes": [
{
"placement_id": "example-4390001",
"gall_id": "example_gallery",
"post_no": 31899120,
"tier": "main",
"placed_at": "2026-09-29T02:40:00+09:00",
"picked_by": {
"type": "operator"
},
"score_at_placement": 0.62,
"views_at_placement": 1875,
"up_at_placement": 40,
"down_at_placement": 3,
"comment_at_placement": 21,
"readings": [
{
"age_h": 1,
"observed_at": "2026-09-29T03:40:00+09:00",
"views": 9120,
"up": 66,
"down": 8,
"comment_cnt": 30
}
],
"hidden_at": null,
"deleted_at": null,
"deleted_by": null
}
]
}
'import requests
url = "https://{host}/v1/outcomes"
payload = { "outcomes": [
{
"placement_id": "example-4390001",
"gall_id": "example_gallery",
"post_no": 31899120,
"tier": "main",
"placed_at": "2026-09-29T02:40:00+09:00",
"picked_by": { "type": "operator" },
"score_at_placement": 0.62,
"views_at_placement": 1875,
"up_at_placement": 40,
"down_at_placement": 3,
"comment_at_placement": 21,
"readings": [
{
"age_h": 1,
"observed_at": "2026-09-29T03:40:00+09:00",
"views": 9120,
"up": 66,
"down": 8,
"comment_cnt": 30
}
],
"hidden_at": None,
"deleted_at": None,
"deleted_by": None
}
] }
headers = {
"Authorization": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
outcomes: [
{
placement_id: 'example-4390001',
gall_id: 'example_gallery',
post_no: 31899120,
tier: 'main',
placed_at: '2026-09-29T02:40:00+09:00',
picked_by: {type: 'operator'},
score_at_placement: 0.62,
views_at_placement: 1875,
up_at_placement: 40,
down_at_placement: 3,
comment_at_placement: 21,
readings: [
{
age_h: 1,
observed_at: '2026-09-29T03:40:00+09:00',
views: 9120,
up: 66,
down: 8,
comment_cnt: 30
}
],
hidden_at: null,
deleted_at: null,
deleted_by: null
}
]
})
};
fetch('https://{host}/v1/outcomes', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://{host}/v1/outcomes",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'outcomes' => [
[
'placement_id' => 'example-4390001',
'gall_id' => 'example_gallery',
'post_no' => 31899120,
'tier' => 'main',
'placed_at' => '2026-09-29T02:40:00+09:00',
'picked_by' => [
'type' => 'operator'
],
'score_at_placement' => 0.62,
'views_at_placement' => 1875,
'up_at_placement' => 40,
'down_at_placement' => 3,
'comment_at_placement' => 21,
'readings' => [
[
'age_h' => 1,
'observed_at' => '2026-09-29T03:40:00+09:00',
'views' => 9120,
'up' => 66,
'down' => 8,
'comment_cnt' => 30
]
],
'hidden_at' => null,
'deleted_at' => null,
'deleted_by' => null
]
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: <api-key>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://{host}/v1/outcomes"
payload := strings.NewReader("{\n \"outcomes\": [\n {\n \"placement_id\": \"example-4390001\",\n \"gall_id\": \"example_gallery\",\n \"post_no\": 31899120,\n \"tier\": \"main\",\n \"placed_at\": \"2026-09-29T02:40:00+09:00\",\n \"picked_by\": {\n \"type\": \"operator\"\n },\n \"score_at_placement\": 0.62,\n \"views_at_placement\": 1875,\n \"up_at_placement\": 40,\n \"down_at_placement\": 3,\n \"comment_at_placement\": 21,\n \"readings\": [\n {\n \"age_h\": 1,\n \"observed_at\": \"2026-09-29T03:40:00+09:00\",\n \"views\": 9120,\n \"up\": 66,\n \"down\": 8,\n \"comment_cnt\": 30\n }\n ],\n \"hidden_at\": null,\n \"deleted_at\": null,\n \"deleted_by\": null\n }\n ]\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "<api-key>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://{host}/v1/outcomes")
.header("Authorization", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"outcomes\": [\n {\n \"placement_id\": \"example-4390001\",\n \"gall_id\": \"example_gallery\",\n \"post_no\": 31899120,\n \"tier\": \"main\",\n \"placed_at\": \"2026-09-29T02:40:00+09:00\",\n \"picked_by\": {\n \"type\": \"operator\"\n },\n \"score_at_placement\": 0.62,\n \"views_at_placement\": 1875,\n \"up_at_placement\": 40,\n \"down_at_placement\": 3,\n \"comment_at_placement\": 21,\n \"readings\": [\n {\n \"age_h\": 1,\n \"observed_at\": \"2026-09-29T03:40:00+09:00\",\n \"views\": 9120,\n \"up\": 66,\n \"down\": 8,\n \"comment_cnt\": 30\n }\n ],\n \"hidden_at\": null,\n \"deleted_at\": null,\n \"deleted_by\": null\n }\n ]\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://{host}/v1/outcomes")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"outcomes\": [\n {\n \"placement_id\": \"example-4390001\",\n \"gall_id\": \"example_gallery\",\n \"post_no\": 31899120,\n \"tier\": \"main\",\n \"placed_at\": \"2026-09-29T02:40:00+09:00\",\n \"picked_by\": {\n \"type\": \"operator\"\n },\n \"score_at_placement\": 0.62,\n \"views_at_placement\": 1875,\n \"up_at_placement\": 40,\n \"down_at_placement\": 3,\n \"comment_at_placement\": 21,\n \"readings\": [\n {\n \"age_h\": 1,\n \"observed_at\": \"2026-09-29T03:40:00+09:00\",\n \"views\": 9120,\n \"up\": 66,\n \"down\": 8,\n \"comment_cnt\": 30\n }\n ],\n \"hidden_at\": null,\n \"deleted_at\": null,\n \"deleted_by\": null\n }\n ]\n}"
response = http.request(request)
puts response.read_body{
"received": 1,
"created": 1,
"updated": 0
}{
"error": {
"code": "bad_request",
"message": "2 fields failed validation",
"fields": [
{
"path": "candidates[0].created_at",
"problem": "timestamp must include an explicit offset"
},
{
"path": "engagement[3].views",
"problem": "must be a non-negative integer or null"
}
]
}
}{
"error": {
"code": "unauthorized",
"message": "API key missing or unknown"
}
}{
"error": {
"code": "too_large",
"message": "JSON body exceeds 16 MiB after decompression"
}
}{
"error": {
"code": "unprocessable",
"message": "cycle_time cannot be in the future",
"fields": [
{
"path": "cycle_time",
"problem": "must not be in the future"
}
]
}
}{
"error": {
"code": "server_error",
"message": "internal error"
}
}Not in scope for trial. This outcomes endpoint is reference material for later integration. Daily operator outcomes may be shared separately by agreement; they are not required through this endpoint for the current trial.
Supporting outcome data
DCinside said that outcomes for operator-placed posts can flow daily during rehearsal. The model does not place posts at this stage. Outcomes are useful supporting data, but DCinside did not list their delivery as a rehearsal pass condition. The endpoint and field mapping below are retained for later review, outside the current trial integration scope. The formal live-trial choice between sending events as they occur and hourly batches can be settled later.Requested data
- Board counts at 1, 6, 24 and 48 hours after placement: views, up-votes, down-votes and comments.
- Hide times and deletion events, when available.
- Who picked the post: operator or model version.
- Score at placement, when available, together with the original post identity.
Updates and current implementation
placement_id identifies a placement. The current handler replaces the stored placement record on a repeated ID; it does not merge partial readings automatically. For current smoke tests, send the complete known snapshot for that placement. Agree snapshot-versus-incremental semantics before integration.
The current request protection is 5,000 records, not the 1,000 previously written in this document. It is an engineering limit, not an agreed business quota. Storage is process-local and must not be treated as durable outcome delivery.
The schema supports model-picked records for later publishing stages. Rehearsal operator outcomes use picked_by.type = operator; hypothetical model picks are logged separately on DCinside’s side and are not actual placements.Authorizations
Proposed API key sent as the whole Authorization header value. Long-lived credential scope, handoff and rotation need confirmation. Per-endpoint scopes are not currently enforced.
Headers
Optional compression. Set to gzip only for a gzip-compressed body; plain JSON is also supported.
Available options:
gzip Body
application/json
One record per placement. Current 5,000-record protection is an engineering limit, not an agreed quota. Daily operator-placed outcomes support rehearsal.
Maximum array length:
5000Show child attributes
Show child attributes