Gemini API 모델명 헷갈릴 땐? 직접 조회하는 ‘모델 체커’ 웹앱 만들기 (React + Vite)

“gemini-1.5-pro? 2.0-flash? 더 이상 모델명을 추측하다 404 오류를 겪지 마세요. Google GenAI SDK와 React를 사용해 내 API 키로 사용 가능한 정확한 모델 목록을 실시간으로 확인하는 도구를 5분 만에 만들어 봅니다.”

Gemini API 모델명 헷갈릴 땐? 직접 조회하는 ‘모델 체커’ 웹앱 만들기 (React + Vite)
Gemini API 모델명 헷갈릴 땐? 직접 조회하는 ‘모델 체커’

Gemini API를 사용하다 보면 가장 빈번하게 마주치는 문제가 있습니다. 바로 "404 Not Found" 오류입니다. 분명 문서를 보고 모델명을 입력했는데, 내 API 키에서는 작동하지 않거나 Preview, Experimental 버전이 혼재되어 있어 어떤 것이 '정식'인지 헷갈릴 때가 많습니다.

오늘은 추측을 멈추고, 팩트(Fact)를 확인하는 시간을 가져봅니다. React와 Vite, 그리고 Google GenAI SDK를 사용하여 "내 API 키로 현재 사용 가능한 모델 리스트"를 즉시 조회해주는 간단한 웹 애플리케이션을 만들어 보겠습니다.

왜 직접 조회해야 하나요?

Google AI Studio에는 다양한 모델이 존재하지만, API 키의 생성 시점이나 리전(Region), 권한에 따라 접근 가능한 모델이 다를 수 있습니다.

  • gemini-1.5-pro vs gemini-1.5-pro-001
  • preview 버전의 가용성 여부

이 도구를 사용하면 내 환경에서 **100% 확실하게 작동하는 모델명(ID)**을 눈으로 확인할 수 있습니다.

준비물

  • Node.js 설치 완료
  • Google AI Studio API Key
  • 터미널 (Terminal)

1. 프로젝트 생성 (Vite)

가장 빠르고 가벼운 빌드 도구인 Vite를 사용해 React TypeScript 프로젝트를 생성합니다.

# 프로젝트 생성
npm create vite@latest gemini-model-checker -- --template react-ts

# 폴더 이동
cd gemini-model-checker

# 필수 패키지 설치 (Google SDK 포함)
npm install
npm install @google/genai

2. 코드 작성 (App.tsx)

src/App.tsx 파일을 열고 아래 코드로 전체를 교체합니다. 이 코드는 SDK의 models.list() 메서드를 호출하여, 콘텐츠 생성(generateContent)이 가능한 모델만 필터링해서 보여줍니다.

(참고: 최신 SDK의 페이지네이션 처리와 타입 호환성 문제를 모두 해결한 코드입니다.)

import { useState } from 'react';
import { GoogleGenAI } from "@google/genai";
import './App.css';

interface ModelInfo {
  name: string;
  displayName: string;
}

function App() {
  const [apiKey, setApiKey] = useState('');
  const [models, setModels] = useState<ModelInfo[]>([]);
  const [loading, setLoading] = useState(false);
  const [error, setError] = useState<string | null>(null);

  const checkModels = async () => {
    if (!apiKey) {
      setError("API 키를 입력해주세요.");
      return;
    }

    setLoading(true);
    setError(null);
    setModels([]);

    try {
      // SDK 초기화
      const ai = new GoogleGenAI({ apiKey });
      
      // 모델 리스트 요청 (비동기 이터러블 반환)
      const response = await ai.models.list();
      
      const availableModels: ModelInfo[] = [];

      // @ts-ignore (SDK 타입 호환성 이슈 방지)
      for await (const m of response) {
        const model = m as any;
        // 텍스트/멀티모달 생성이 가능한 모델만 필터링
        if (!model.supportedGenerationMethods || model.supportedGenerationMethods.includes("generateContent")) {
          availableModels.push({
            name: model.name.replace("models/", ""),
            displayName: model.displayName || "(설명 없음)"
          });
        }
      }

      setModels(availableModels);
      
      if (availableModels.length === 0) {
        setError("조회된 모델이 없습니다. 권한을 확인해주세요.");
      }

    } catch (err: any) {
      console.error(err);
      setError(`조회 실패: ${err.message || JSON.stringify(err)}`);
    } finally {
      setLoading(false);
    }
  };

  return (
    <div style={{ maxWidth: '800px', margin: '0 auto', padding: '2rem', fontFamily: 'sans-serif' }}>
      <h1>🤖 Gemini 모델 체커</h1>
      
      <div style={{ marginBottom: '20px', display: 'flex', gap: '10px' }}>
        <input 
          type="password" 
          placeholder="Google API Key를 입력하세요" 
          value={apiKey}
          onChange={(e) => setApiKey(e.target.value)}
          style={{ flex: 1, padding: '10px', fontSize: '16px' }}
        />
        <button 
          onClick={checkModels} 
          disabled={loading}
          style={{ padding: '10px 20px', fontSize: '16px', cursor: 'pointer' }}
        >
          {loading ? '조회 중...' : '모델 조회'}
        </button>
      </div>

      {error && (
        <div style={{ padding: '10px', backgroundColor: '#ffebee', color: '#c62828', borderRadius: '4px', marginBottom: '20px' }}>
          ⚠️ {error}
        </div>
      )}

      <div style={{ border: '1px solid #ddd', borderRadius: '8px', padding: '10px' }}>
        <h2>사용 가능한 모델 ({models.length}개)</h2>
        {models.length === 0 && !loading && <p style={{ color: '#666' }}>조회 버튼을 눌러주세요.</p>}
        
        <ul style={{ listStyle: 'none', padding: 0 }}>
          {models.map((model) => (
            <li key={model.name} style={{ borderBottom: '1px solid #eee', padding: '10px 0' }}>
              <strong style={{ color: '#1a73e8', fontSize: '1.1em' }}>{model.name}</strong>
              <div style={{ fontSize: '0.9em', color: '#555', marginTop: '4px' }}>
                {model.displayName}
              </div>
            </li>
          ))}
        </ul>
      </div>
    </div>
  );
}

export default App;

3. 실행 및 확인

터미널에서 아래 명령어로 로컬 서버를 실행합니다.

npm run dev

브라우저가 열리면 API 키를 입력하고 조회 버튼을 눌러보세요. gemini-2.5-pro 혹은 gemini-1.5-flash-002 처럼 현재 내 키로 즉시 사용할 수 있는 정확한 모델 ID 목록이 출력될 것입니다.

마치며

이제 프로젝트의 설정 파일(config 또는 상수 파일)에 방금 확인한 모델명을 복사해서 붙여넣기만 하면 됩니다. 더 이상 불안정한 Preview 버전을 쓰다가 에러를 겪지 말고, 가장 안정적인 정식 버전을 골라 사용하시기 바랍니다.