사이드 메뉴
시작하기
로그인
커뮤니케이션
광고
카카오 로그인 구현하기
이 문서는 아래 언어를 이용해 카카오 로그인 기능을 직접 구현해보는 과정을 단계별로 설명합니다.
- Node.js
- PHP
- Python
이 튜토리얼에서 사용한 코드는 Github 저장소에서 확인할 수 있습니다. 직접 개발하는 데 어려움을 느낀다면 이미 구현된 샘플 코드로 테스트할 수 있습니다.
| 구분 | 내용 |
|---|---|
| 학습 내용 |
|
| 선행 작업 |
이 단계에서는 카카오 로그인 기능을 구현하기 위해 필요한 프로젝트를 설정합니다.
새 프로젝트 폴더를 생성 후, 생성한 폴더로 이동하기 위해 터미널에 아래 명령어를 차례로 입력합니다. 이 튜토리얼에서는 kakao-login 폴더에서 설정 파일과 코드 파일을 생성할 예정입니다.
mkdir kakao-logincd kakao-login
프로젝트 초기화
npm init -y
터미널에서 위 명령어 실행 시, 프로젝트의 메타데이터(이름, 버전, 라이선스 등)와 의존 패키지 목록, 실행 명령어 등을 관리되는 package.json 파일이 생성됩니다.
{"name": "kakao-login","version": "1.0.0","main": "index.js","scripts": {"test": "echo \"Error: no test specified\" && exit 1"},"keywords": [],"author": "","license": "ISC","description": ""}
npm install express express-session axios qs
터미널에서 위 명령어 실행 시, 프로젝트에 필요한 라이브러리가 설치됩니다.
카카오 로그인 기능을 사용하려면 카카오디벨로퍼스에서 설정이 필요합니다. 샘플 코드로 테스트하기 > 앱 설정하기를 참고합니다.
이 단계에서는 서버에서 로그인 요청을 처리하는 코드를 작성합니다.
- 코드 편집기(IDE)에서 앞서 생성한 프로젝트를 엽니다.
- 아래 디렉토리 구조를 참고해 폴더와 파일을 생성한 후, 단계별로 안내한 코드를 차례로 복사해 붙여 넣습니다. 각 언어별 예제 코드 상단에서 파일 위치와 파일 이름을 확인할 수 있습니다.
.├── index.html # 메인 HTML 파일├── app.js # 메인 애플리케이션 파일├── package.json # 프로젝트 메타데이터 및 의존성└── README.md # 프로젝트 설명 파일
//app.jsconst express = require('express')const session = require('express-session')const qs = require('qs')const axios = require('axios')const app = express()const port = 4000// 정적 파일 서빙 설정 추가app.use(express.static(__dirname))app.use(express.json()) // JSON 파싱을 위해 추가// 로그인 상태 유지를 위한 세션 설정app.use(session({secret: 'your session secret',resave: false,saveUninitialized: true,cookie: { secure: false },}))
카카오 API 요청에 반복적으로 사용되는 앱 키, 도메인, API 주소 등을 변수로 선언하고, 요청 함수를 정의합니다. 각 변수에 대한 내용은 샘플 코드로 테스트하기 > 앱 정보 반영하기를 참고합니다.
client_id 값에 앱 관리 페이지의 [앱] > [플랫폼 키] > [REST API 키]에서 확인한 REST API 키를 입력해야 합니다. 잘못된 앱 키 사용 시, KOE101 에러가 발생합니다.
// app.js// 이전 단계에서 입력한 코드// :// 변수 지정const client_id = '6f95e7e3146********' // 내 앱의 REST API 키로 변경 필수const client_secret = 'this is client secret key'const domain = 'http://localhost:4000'const redirect_uri = `${domain}/redirect`const token_uri = 'https://kauth.kakao.com/oauth/token' // 액세스 토큰 요청을 보낼 카카오 인증 서버 주소const api_host = 'https://kapi.kakao.com' // 카카오 API 호출 서버 주소// API 요청 함수 정의async function call(method, uri, param, header) {let rtntry {// 지정된 method, uri, param, header 값을 사용해 카카오 API 서버로 HTTP 요청 전송rtn = await axios({method: method, // "POST" 또는 "GET" 등 HTTP 메서드url: uri, // 요청할 API 주소headers: header, // 요청 헤더 (예: Content-Type, Authorization 등)data: param, // 전송할 요청 데이터 (body)})} catch (err) {// 오류 발생 시, 응답 객체에서 오류 응답 내용 저장rtn = err.response}// 요청 성공 또는 실패에 상관없이 응답 데이터 반환return rtn.data}
카카오 로그인 과정 중 1. 인가 코드 요청 과정을 구현합니다. 아래 코드는 사용자에게 카카오 로그인 및 동의화면을 보여줍니다. 사용자가 [카카오 계정으로 로그인] 버튼을 누르면 인가 코드 요청 API를 호출하고, 사용자에게 카카오 로그인 및 동의화면을 표시합니다.
사용자가 카카오 로그인 화면에서 카카오 계정으로 로그인 후, 동의화면에서 [동의하고 계속하기] 버튼을 누르면, 카카오로 인가 코드를 요청하는 코드가 실행됩니다. 이때, client_id에는 앱의 REST API 키가, redirect_uri에는 샘플 코드로 테스트하기 > 리다이렉트 URI 등록하기에서 설정한 경로를 전달합니다.
리다이렉트 URI 예시
카카오 계정으로 로그인 및 동의 과정으로 카카오가 사용자를 인증하면, 브라우저를 리다이렉트 URI로 이동시킵니다. 이 URI로 인가 코드가 전달됩니다.
https://${설정한_리다이렉트_URI}/?code=${전달_받은_인가_코드}# 예시http://localhost:4000/redirect?code=abc123xyz
// app.js// 이전 단계에서 입력한 코드// :// 카카오 인증 서버로 인가 코드 발급 요청app.get('/authorize', function (req, res) {// 선택: 사용자에게 추가 동의를 요청하는 경우, scope 값으로 동의항목 ID를 전달// 친구 목록, 메시지 전송 기능의 경우, 추가 기능 신청 필요// (예: /authorize?scope=friends,talk_message)let { scope } = req.querylet scopeParam = ''if (scope) {scopeParam = '&scope=' + scope}// 카카오 인증 서버로 리다이렉트// 사용자 동의 후 리다이렉트 URI로 인가 코드가 전달res.status(302).redirect(`https://kauth.kakao.com/oauth/authorize?client_id=${client_id}&redirect_uri=${redirect_uri}&response_type=code${scopeParam}`)})
서비스 서버는 카카오로부터 발급 받은 인가 코드를 사용해 액세스 토큰을 요청합니다.
액세스 토큰은 사용자 정보 조회나 메시지 전송 등 카카오 API를 호출할 때 필요한 인증 수단입니다. 이전 단계에서 인가 코드를 요청한 것은 최종적으로 이 액세스 토큰을 발급받기 위해 필요한 과정입니다. (참고: Q. 인가 코드와 액세스 토큰이 무엇인가요?)
카카오 API 서버에서 전달 받은 액세스 토큰은 사용자의 로그인 상태를 유지하기 위해 세션에 저장합니다. (참고: 세션이란?)
// app.js// 이전 단계에서 입력한 코드// :// 카카오 인증 서버에서 전달받은 인가 코드로 액세스 토큰 발급 요청app.get('/redirect', async function (req, res) {// 인가 코드 발급 요청에 필요한 파라미터 구성const param = qs.stringify({grant_type: 'authorization_code', // 인증 방식 고정값client_id: client_id, // 내 앱의 REST API 키redirect_uri: redirect_uri, // 등록된 리다이렉트 URIcode: req.query.code, // 전달받은 인가 코드client_secret: client_secret, // 클라이언트 시크릿(Client Secret) 사용 시 추가 필요})// API 요청 헤더 설정const header = { 'content-type': 'application/x-www-form-urlencoded' }// 카카오 인증 서버에 액세스 토큰 요청const rtn = await call('POST', token_uri, param, header)// 발급받은 액세스 토큰을 세션에 저장 (로그인 상태 유지 목적)req.session.key = rtn.access_token// 로그인 완료 후 메인 페이지로 이동res.status(302).redirect(`${domain}/index.html?login=success`)})
이 단계에서는 로그인한 사용자의 정보(회원번호, 닉네임, 프로필 이미지 등)를 요청합니다. 발급 받은 액세스 토큰을 Authorization 요청 헤더에 넣어 사용자 정보 조회 API를 호출합니다.
사용자가 로그인 후 사용자 정보 조회 API를 호출해야 사용자와 앱이 연결되어 카카오 로그인이 완료됩니다. (참고: 가입 미완료 사용자 연결 해제 처리)
// app.js// 이전 단계에서 입력한 코드// :// 액세스 토큰을 사용해 로그인한 사용자의 정보 조회 요청app.get('/profile', async function (req, res) {const uri = api_host + '/v2/user/me' // 사용자 정보 조회 API 주소const param = {} // 사용자 정보 요청 시 파라미터는 필요 없음const header = {'content-type': 'application/x-www-form-urlencoded', // 요청 헤더 Content-Type 지정Authorization: 'Bearer ' + req.session.key, // 세션에 저장된 액세스 토큰 전달}const rtn = await call('POST', uri, param, header) // 카카오 API에 요청 전송res.send(rtn) // 조회한 사용자 정보를 클라이언트에 반환})
이 단계에서는 로그인한 사용자가 로그아웃하거나 앱과 연결을 끊을 수 있는 기능을 구현합니다.
사용자의 세션을 종료하기 위해 로그아웃 API를 사용자와 앱과의 연결을 해제하기 위해 연결 해제 API를 호출하는 코드를 추가합니다.
// app.js// 이전 단계에서 입력한 코드// :// 로그아웃 요청: 세션을 종료하고 사용자 로그아웃 처리app.get('/logout', async function (req, res) {const uri = api_host + '/v1/user/logout' // 로그아웃 API 주소const header = {Authorization: 'Bearer ' + req.session.key, // 세션에 저장된 액세스 토큰 전달}const rtn = await call('POST', uri, null, header) // 카카오 API에 로그아웃 요청 전송req.session.destroy() // 세션 삭제 (로그아웃 처리)res.send(rtn) // 응답 결과 클라이언트에 반환})// 연결 해제 요청: 사용자와 앱의 연결을 해제하고 세션 종료app.get('/unlink', async function (req, res) {const uri = api_host + '/v1/user/unlink' // 연결 해제 API 주소const header = {Authorization: 'Bearer ' + req.session.key, // 세션에 저장된 액세스 토큰 전달}const rtn = await call('POST', uri, null, header) // 카카오 API에 연결 해제 요청 전송req.session.destroy() // 세션 삭제 (연결 해제 처리)res.send(rtn) // 응답 결과 클라이언트에 반환})
작성한 코드를 실제로 실행하기 위해 서버를 실행하는 코드를 파일의 마지막에 추가합니다.
// app.js// 이전 단계에서 입력한 코드// :app.listen(port, () => {console.log(`Server is running at ${domain}`)})
이 단계에서는 사용자에게 보이는 UI(User Interface, 사용자 인터페이스)를 구성합니다.
생성한 프로젝트 하위에 디렉토리 구조를 참고해 index.html 파일을 생성한 후, 아래 코드를 입력합니다. index.html은 UI를 구성하기 위한 파일입니다.
이 튜토리얼에서는 GitHub에 호스팅된 style.css 파일을 index.html에서 직접 임포트하여 사용합니다. style.css 파일은 UI 스타일을 설정하는 파일로, 기능 구현과 직접적인 관련은 없습니다.
<!-- index.html --><!DOCTYPE html><html lang="kr"><head><meta charset="utf-8" /><meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" /><title>Kakao REST-API Node.js example</title><!-- 카카오 JavaScript SDK를 불러오기 위한 스크립트 --><script src="https://developers.kakao.com/sdk/js/kakao.js"></script><!-- UI 스타일을 설정하는 CSS 파일 임포트 --><link rel="stylesheet" href="https://kakao-tam.github.io/developers-static/style.css" /><link rel="icon" type="image/png" href="https://devtalk.kakao.com/uploads/default/optimized/2X/9/9b7b5d9cbbe2e8d6a5410c2d28926804cd8b0bb1_2_32x32.png" /></head><body><div class="header"><h1>카카오 로그인 및 API 예제</h1></div><div class="main-container"><div class="container"><div class="vertical-layout"><script>const domain = window.location.originKakao.init(' JavaScript 키 ') // [JavaScript SDK로 로그인]을 테스트하려면 [플랫폼 키]에서 확인한 JavaScript 키를 입력하세요.function kakaoLogin() {Kakao.Auth.authorize({redirectUri: `${domain}/redirect`,})}function REST_Call(path) {fetch(domain + path).then((response) => response.text()) // 응답을 텍스트로 변환.then((data) => {try {// JSON 파싱 시도const jsonData = JSON.parse(data)setContents(JSON.stringify(jsonData, null, 2))} catch (e) {// JSON 파싱 실패 시 텍스트로 출력setContents(data)}}).catch((error) => {console.error('Fetch 에러:', error)})}function setContents(data) {document.getElementById('contents').value = data}// 로그인 성공 메시지 표시window.onload = function () {const urlParams = new URLSearchParams(window.location.search)if (urlParams.get('login') === 'success') {const successLabel = document.createElement('span')successLabel.textContent = '로그인 성공'successLabel.style.color = 'green'successLabel.style.marginLeft = '10px'document.querySelector('.login-buttons').appendChild(successLabel)}}</script><!-- 로그인 버튼 영역 --><div class="login-container"><div class="login-buttons"><!-- REST API로 로그인하기 위한 버튼 --><a href="/authorize"><img src="//k.kakaocdn.net/14/dn/btqCn0WEmI3/nijroPfbpCa4at5EIsjyf0/o.jpg" alt="카카오 로그인" /></a><!-- JavaScript SDK로 로그인하기 위한 버튼, 테스트하려면 JS SDK 초기화 필요 --><buttononclick="kakaoLogin()"style="background-color: white;border: 1px solid var(--kakao-yellow);">JavaScript SDK로 로그인</button></div></div><!-- 로그인 기능을 테스트할 수 있는 버튼 영역 --><div class="api-container"><div class="section-title">기본 기능</div><div class="button-group"><button onclick="REST_Call('/profile')">사용자 정보 조회</button><button onclick="REST_Call('/logout')" style="background-color: white; border: 1px solid #e5e5e5">로그아웃</button><buttononclick="REST_Call('/unlink')"style="background-color: white;color: #ff5c5c;border: 1px solid #ff5c5c;">연결 해제</button></div></div><!-- 응답 확인 영역 --><textarea id="contents" placeholder="이곳에 API 응답 결과가 표시됩니다."></textarea></div></div></div></body></html>
이 단계에서는 구성한 화면에서 API를 호출해 테스트할 수 있도록 서버를 실행합니다.
node app.js
서버 실행 후 터미널에 출력된 주소로 접속하면 아래와 같이 테스트 웹페이지를 확인할 수 있습니다. 자세한 설명은 샘플 코드로 테스트하기 > 테스트하기를 참고합니다.

- 샘플 코드로 테스트하기: 미리 구현된 샘플 코드로 카카오 로그인을 빠르게 테스트하는 방법 안내
- 카카오 API 시작하기: 카카오디벨로퍼스 앱 생성부터 카카오 API를 호출하는 방법까지 단계별로 안내
- 디자인 가이드: 카카오디벨로퍼스에서 제공하는 카카오 로그인 버튼 사용법 안내