
제미나이 API는 무료로 사용할 수 있다. 이번 포스팅에서는 별도의 프레임워크 없이 JavaScript로 채팅 화면에 Gemini API를 연동하는 방법을 정리해본다.
Google AI Studio 에 접속해서 API 키를 발급받는다.
👉 https://aistudio.google.com/
접속 후 로그인 → "API 키 만들기" 클릭

생성된 키를 복사해둔다.

⚠️ 주의: API 키는 코드에 직접 하드코딩하지 말자.
config.js파일을 따로 만들어서 관리하고,.gitignore에 추가하는 것을 권장한다.
// config.js (git과 블로그에는 올리지 않음)
const CONFIG = {
API_KEY: "여기에_본인_API_KEY_입력"
};
// main.js
const API_KEY = CONFIG.API_KEY;
아래는 채팅 화면에 Gemini API를 연동한 전체 코드다.
async function ask() {
const inputElement = document.getElementById("questionInput");
const prompt = inputElement.value;
// 빈 입력 체크
if (!prompt || prompt.trim() === "") {
document.getElementById("output").innerText = "질문을 입력해주세요.";
return;
}
// 입력창 바로 초기화
inputElement.value = "";
// [1단계] 화면에 질문과 "...(생각 중)" 상태를 먼저 표시
const chatGrid = document.getElementById("chatMessagesGrid");
chatGrid.innerHTML = `
<article class='message-card active' role=listitem>
<div class='message-card-user'>${prompt}</div>
<div class='message-card-bot'>
<div class="bot-logo">
👩💻 Assistant AI
</div>
<div class="bot-answer thinking">...(생각 중)</div>
</div>
</article>`;
try {
// [2단계] Gemini API 호출
const res = await fetch(
`https://generativelanguage.googleapis.com/v1beta/models/gemini-2.5-flash-lite:generateContent?key=${API_KEY}`,
{
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
contents: [{ parts: [{ text: prompt }] }]
})
}
);
if (!res.ok) throw new Error("API 호출 실패");
const data = await res.json();
const text =
data.candidates?.[0]?.content?.parts?.[0]?.text ??
"응답을 가져올 수 없습니다.";
// [3단계] 자연스러운 UX를 위해 1.5초 딜레이
await new Promise(resolve => setTimeout(resolve, 1500));
// [4단계] "...(생각 중)"을 실제 답변으로 교체
const botAnswerDiv = chatGrid.querySelector('.bot-answer');
if (botAnswerDiv) {
botAnswerDiv.classList.remove('thinking');
botAnswerDiv.innerText = text;
}
} catch (err) {
console.error("에러 발생:", err);
const botAnswerDiv = chatGrid.querySelector('.bot-answer');
if (botAnswerDiv) botAnswerDiv.innerText = "오류가 발생했습니다.";
}
}
window.ask = ask;
질문을 입력하면 ...(생각 중) 상태가 먼저 표시되고,

응답이 오면 실제 답변으로 교체된다.

1. 질문 입력
↓
2. 화면에 질문 + "..." (로딩 상태) 즉시 표시
↓
3. Gemini API에 POST 요청
↓
4. 응답 수신 후 "..."을 실제 답변으로 교체
응답을 받아오는 경로는 다음과 같다.
const text =
data.candidates?.[0]?.content?.parts?.[0]?.text ??
"응답을 가져올 수 없습니다.";
Gemini API는 응답을 candidates 배열 형태로 반환하기 때문에, 옵셔널 체이닝(?.)으로 안전하게 접근한다.
| 항목 | 현재 상태 | 개선 방향 |
|---|---|---|
| 대화 기록 | ❌ 저장 안 됨 (매 질문마다 리셋) | 이전 메시지를 contents 배열에 누적해서 전달 |
| 마크다운 렌더링 | ❌ 텍스트 그대로 출력 | marked.js 등의 라이브러리로 렌더링 |
| 스트리밍 | ❌ 응답을 한 번에 받아옴 | streamGenerateContent 엔드포인트 + ReadableStream으로 처리 |
| API 키 보안 | ⚠️ 브라우저에서 노출됨 | 실서비스에서는 백엔드 서버를 통해 호출 |
현재는 응답이 완전히 생성된 후에 한 번에 화면에 출력된다. 스트리밍을 적용하면 ChatGPT처럼 글자가 순차적으로 타이핑되는 효과를 구현할 수 있다
별도의 프레임워크나 백엔드 서버 없이도 Gemini API를 빠르게 연동할 수 있었다.
다음 단계로는 대화 기록 누적, 마크다운 렌더링, 그리고 스트리밍 방식으로의 전환을 시도해볼 예정이다.