API 요청
/rest/youtube_thumbnail요청 파라미터 1개 · 필수 1
url- 예시
https://www.youtube.com/watch?v=dQw4w9WgXcQ
응답 필드 파일
정상 응답은 파일 본문입니다. 실패 시 JSON 오류가 올 수 있으므로 HTTP 상태와 Content-Type을 먼저 확인하세요.
공개 영상에서 제공하는 가장 큰 썸네일을 JPG 파일로 받습니다. 성공하면 응답 본문이 이미지 파일 자체입니다.
https://apick.app/rest/youtube_thumbnail왜 유튜브 썸네일 다운로드인가
썸네일 하나 받으려고 화면을 캡처하고 자르던 번거로움을 끝내세요. 공개 영상의 가장 큰 썸네일을 JPG 파일로 바로 받아 카드·미리보기·아카이브에 씁니다.
성공한 다운로드 한 건당 20P가 차감됩니다. 파일 응답에는 form-data 본문이 없으므로 차감액은 응답 헤더 cost에서 확인하세요. 입력 오류·영상 없음·연령 제한·회원 전용·시간 초과처럼 실패한 호출은 이미지 대신 JSON 오류(data.error)가 오고 과금되지 않습니다(api.cost 0).
성공과 실패의 본문 형식이 다르므로, 저장하기 전에 HTTP 상태가 200이고 Content-Type이 image/jpeg인지 먼저 확인하세요. 썸네일 주소만 필요하면 유튜브 영상 정보 조회의 thumbnail·thumbnails[]를 쓰세요.
응답 시간은 보통 6초 이내이고 최대 약 60초입니다. 요청 시간 제한을 90초 이상으로 잡으세요.
인증키는 서버 환경변수에 보관하고 공개 저장소·웹페이지에 넣지 마세요.
/rest/youtube_thumbnailurlhttps://www.youtube.com/watch?v=dQw4w9WgXcQ정상 응답은 파일 본문입니다. 실패 시 JSON 오류가 올 수 있으므로 HTTP 상태와 Content-Type을 먼저 확인하세요.
POST https://apick.app/rest/youtube_thumbnailAuthorization: Bearer — 내 계정의 API 인증키multipart/form-data썸네일을 파일로 저장하는 예입니다. 성공 시 과금되는 실제 요청입니다. --fail을 붙이면 실패 응답(JSON)을 이미지 파일로 저장하지 않습니다.
상황별로 보내는 값과 응답에서 확인할 값을 모았습니다. 언어 탭에서 그대로 복사해 쓸 수 있습니다.
응답 본문이 JPG 이미지입니다. 파일로 저장할 때는 HTTP 상태와 Content-Type을 먼저 확인합니다.
/rest/youtube_thumbnailcurl --fail-with-body --request POST 'https://apick.app/rest/youtube_thumbnail' \
--header "Authorization: Bearer $APICK_API_KEY" \
--form-string 'url=https://www.youtube.com/watch?v=dQw4w9WgXcQ' \
--dump-header response.headers --output result.bin
# response.headers의 Content-Type을 확인한 뒤 파일을 사용하세요.const form = new FormData();
form.append("url", "https://www.youtube.com/watch?v=dQw4w9WgXcQ");
const response = await fetch("https://apick.app/rest/youtube_thumbnail", {
method: "POST",
headers: { Authorization: "Bearer " + process.env.APICK_API_KEY },
body: form,
signal: AbortSignal.timeout(120_000),
});
if (!response.ok) throw new Error(`HTTP ${response.status}: ${await response.text()}`);
if ((response.headers.get("content-type") || "").includes("json")) {
throw new Error(JSON.stringify(await response.json()));
}
const { writeFile } = await import("node:fs/promises");
await writeFile("result.bin", new Uint8Array(await response.arrayBuffer()));import os
import requests
parts = [
("url", (None, "https://www.youtube.com/watch?v=dQw4w9WgXcQ")),
]
response = requests.request("POST", "https://apick.app/rest/youtube_thumbnail",
headers={"Authorization": "Bearer " + os.environ["APICK_API_KEY"]},
files=parts,
timeout=(10, 120), stream=True)
response.raise_for_status()
if "json" in response.headers.get("Content-Type", ""):
raise RuntimeError(response.json())
with open("result.bin", "wb") as output:
for chunk in response.iter_content(65536):
output.write(chunk)<?php
$headers = ["Authorization: Bearer " . getenv("APICK_API_KEY")];
$form = [
'url' => 'https://www.youtube.com/watch?v=dQw4w9WgXcQ',
];
$curl = curl_init('https://apick.app/rest/youtube_thumbnail');
curl_setopt_array($curl, [
CURLOPT_CUSTOMREQUEST => 'POST',
CURLOPT_HTTPHEADER => $headers,
CURLOPT_POSTFIELDS => $form,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_CONNECTTIMEOUT => 10, CURLOPT_TIMEOUT => 120,
]);
$body = curl_exec($curl);
if ($body === false) { throw new RuntimeException(curl_error($curl)); }
$status = curl_getinfo($curl, CURLINFO_HTTP_CODE);
$type = curl_getinfo($curl, CURLINFO_CONTENT_TYPE) ?: "";
curl_close($curl);
if ($status >= 400) { throw new RuntimeException($body); }
if (strpos($type, "json") !== false) { throw new RuntimeException($body); }
file_put_contents('result.bin', $body);영상ID.jpg입니다.data.error가 옵니다. 이 응답을 이미지로 저장하지 마세요.쇼츠 주소도 그대로 보냅니다.
/rest/youtube_thumbnailcurl --fail-with-body --request POST 'https://apick.app/rest/youtube_thumbnail' \
--header "Authorization: Bearer $APICK_API_KEY" \
--form-string 'url=https://www.youtube.com/shorts/dQw4w9WgXcQ' \
--dump-header response.headers --output result.bin
# response.headers의 Content-Type을 확인한 뒤 파일을 사용하세요.const form = new FormData();
form.append("url", "https://www.youtube.com/shorts/dQw4w9WgXcQ");
const response = await fetch("https://apick.app/rest/youtube_thumbnail", {
method: "POST",
headers: { Authorization: "Bearer " + process.env.APICK_API_KEY },
body: form,
signal: AbortSignal.timeout(120_000),
});
if (!response.ok) throw new Error(`HTTP ${response.status}: ${await response.text()}`);
if ((response.headers.get("content-type") || "").includes("json")) {
throw new Error(JSON.stringify(await response.json()));
}
const { writeFile } = await import("node:fs/promises");
await writeFile("result.bin", new Uint8Array(await response.arrayBuffer()));import os
import requests
parts = [
("url", (None, "https://www.youtube.com/shorts/dQw4w9WgXcQ")),
]
response = requests.request("POST", "https://apick.app/rest/youtube_thumbnail",
headers={"Authorization": "Bearer " + os.environ["APICK_API_KEY"]},
files=parts,
timeout=(10, 120), stream=True)
response.raise_for_status()
if "json" in response.headers.get("Content-Type", ""):
raise RuntimeError(response.json())
with open("result.bin", "wb") as output:
for chunk in response.iter_content(65536):
output.write(chunk)<?php
$headers = ["Authorization: Bearer " . getenv("APICK_API_KEY")];
$form = [
'url' => 'https://www.youtube.com/shorts/dQw4w9WgXcQ',
];
$curl = curl_init('https://apick.app/rest/youtube_thumbnail');
curl_setopt_array($curl, [
CURLOPT_CUSTOMREQUEST => 'POST',
CURLOPT_HTTPHEADER => $headers,
CURLOPT_POSTFIELDS => $form,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_CONNECTTIMEOUT => 10, CURLOPT_TIMEOUT => 120,
]);
$body = curl_exec($curl);
if ($body === false) { throw new RuntimeException(curl_error($curl)); }
$status = curl_getinfo($curl, CURLINFO_HTTP_CODE);
$type = curl_getinfo($curl, CURLINFO_CONTENT_TYPE) ?: "";
curl_close($curl);
if ($status >= 400) { throw new RuntimeException($body); }
if (strpos($type, "json") !== false) { throw new RuntimeException($body); }
file_put_contents('result.bin', $body);검색·채널 조회 결과의 id를 하나씩 넣어 썸네일을 차례로 받습니다.
/rest/youtube_thumbnailcurl --fail-with-body --request POST 'https://apick.app/rest/youtube_thumbnail' \
--header "Authorization: Bearer $APICK_API_KEY" \
--form-string 'url=dQw4w9WgXcQ' \
--dump-header response.headers --output result.bin
# response.headers의 Content-Type을 확인한 뒤 파일을 사용하세요.const form = new FormData();
form.append("url", "dQw4w9WgXcQ");
const response = await fetch("https://apick.app/rest/youtube_thumbnail", {
method: "POST",
headers: { Authorization: "Bearer " + process.env.APICK_API_KEY },
body: form,
signal: AbortSignal.timeout(120_000),
});
if (!response.ok) throw new Error(`HTTP ${response.status}: ${await response.text()}`);
if ((response.headers.get("content-type") || "").includes("json")) {
throw new Error(JSON.stringify(await response.json()));
}
const { writeFile } = await import("node:fs/promises");
await writeFile("result.bin", new Uint8Array(await response.arrayBuffer()));import os
import requests
parts = [
("url", (None, "dQw4w9WgXcQ")),
]
response = requests.request("POST", "https://apick.app/rest/youtube_thumbnail",
headers={"Authorization": "Bearer " + os.environ["APICK_API_KEY"]},
files=parts,
timeout=(10, 120), stream=True)
response.raise_for_status()
if "json" in response.headers.get("Content-Type", ""):
raise RuntimeError(response.json())
with open("result.bin", "wb") as output:
for chunk in response.iter_content(65536):
output.write(chunk)<?php
$headers = ["Authorization: Bearer " . getenv("APICK_API_KEY")];
$form = [
'url' => 'dQw4w9WgXcQ',
];
$curl = curl_init('https://apick.app/rest/youtube_thumbnail');
curl_setopt_array($curl, [
CURLOPT_CUSTOMREQUEST => 'POST',
CURLOPT_HTTPHEADER => $headers,
CURLOPT_POSTFIELDS => $form,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_CONNECTTIMEOUT => 10, CURLOPT_TIMEOUT => 120,
]);
$body = curl_exec($curl);
if ($body === false) { throw new RuntimeException(curl_error($curl)); }
$status = curl_getinfo($curl, CURLINFO_HTTP_CODE);
$type = curl_getinfo($curl, CURLINFO_CONTENT_TYPE) ?: "";
curl_close($curl);
if ($status >= 400) { throw new RuntimeException($body); }
if (strpos($type, "json") !== false) { throw new RuntimeException($body); }
file_put_contents('result.bin', $body);HTTP 성공과 업무 결과를 구분하세요. 경로별 응답 필드와 예시는 위 요청과 응답에 함께 있습니다.
성공하면 HTTP 200과 함께 JPG 이미지가 본문으로 옵니다. 크기는 영상마다 다르므로 표시 영역에 맞춰 축소하세요.
image/jpegattachment; filename=영상ID.jpgdQw4w9WgXcQ.jpg1실패하면 이미지 대신 아래 형식의 JSON이 옵니다. 이 응답을 이미지로 저장하지 마세요.
{
"data": { "error": "영상을 찾을 수 없습니다. 삭제·비공개 영상이거나 잘못된 주소입니다.", "success": 0 },
"api": { "cost": 0, "success": true, "ms": 2100 }
}
응답을 아래 순서로 확인하세요. 결과 유무와 과금 여부는 서로 다릅니다.
아래 경우는 JSON의 data.error로 응답하며 과금되지 않습니다(api.cost 0). 실패 응답은 표의 HTTP 상태 코드와 함께 옵니다. 화면에 보여 줄 안내는 본문의 data.error를 쓰세요.
입력 항목이 잘못됐습니다. 유튜브 영상 주소 또는 11자리 영상 ID를 입력해 주세요.영상을 찾을 수 없습니다. 삭제·비공개 영상이거나 잘못된 주소입니다.영상의 썸네일을 찾을 수 없습니다.thumbnails[]를 확인합니다.연령 제한 영상은 조회할 수 없습니다.채널 회원 전용 영상은 조회할 수 없습니다.처리 시간 초과로 실패했습니다. 잠시 후 다시 시도해 주세요.일시적으로 영상 정보를 가져오지 못했습니다. 잠시 후 다시 시도해 주세요.FORM_DATA_INVALIDFORM_DATA_FIELD_CONFLICTMULTIPART_LIMIT_OR_PARSE_ERROR실제 차감 금액은 응답의 api.cost로 확인하세요. 상세 요금은 요금정책에서 볼 수 있습니다.
같은 요청을 JavaScript(Node.js 18 이상)와 Python으로 옮긴 예시입니다. 키는 환경변수 APICK_API_KEY 에서 읽고, 성공 응답만 파일로 저장합니다.