본문 바로가기

AI

LM Studio로 나만의 AI 비서 만들기

반응형
SMALL

LM Studio로 나만의 AI 비서 만들기: Windows에서 웹 서버 구축 가이드

LM Studio를 활용하여 로컬 AI 모델을 실행하고, 웹 인터페이스를 통해 어디서나 접속할 수 있는 개인 AI 비서 시스템을 구축하는 방법을 단계별로 알려드립니다.

1단계: LM Studio 설치 및 설정

LM Studio는 로컬 컴퓨터에서 대형 언어 모델을 쉽게 실행할 수 있게 해주는 도구입니다.

  1. LM Studio 공식 웹사이트(https://lmstudio.ai/)에서 Windows용 설치 파일을 다운로드합니다.
  2. 다운로드한 설치 파일을 실행하고 설치 마법사의 지시에 따라 LM Studio를 설치합니다.
  3. 설치가 완료되면 LM Studio를 실행합니다.

2단계: 로컬 모델 다운로드 및 설정

  1. LM Studio를 실행한 후, "Models" 탭으로 이동합니다.
  2. 목록에서 원하는 모델을 선택하거나 검색할 수 있습니다. 처음 사용하는 경우 Mistral 7B이나 Llama 2 7B와 같은 작은 크기의 모델부터 시작하는 것이 좋습니다.
  3. 선택한 모델 옆의 다운로드 버튼을 클릭하여 모델을 다운로드합니다.
  4. 다운로드가 완료되면 모델을 선택하고 "Local Server" 탭으로 이동합니다.

3단계: LM Studio 로컬 서버 실행

  1. "Local Server" 탭에서 "Start Server" 버튼을 클릭하여 로컬 API 서버를 시작합니다.
  2. 서버가 시작되면 기본적으로 http://localhost:1234 주소에서 실행됩니다.
  3. 이 API 서버는 OpenAI와 호환되는 API를 제공하므로, OpenAI API를 사용하는 코드를 활용할 수 있습니다.

4단계: 파이썬으로 웹 서버 개발 환경 준비

  1. 파이썬을 아직 설치하지 않았다면, Python 공식 웹사이트(https://www.python.org/downloads/)에서 최신 버전을 다운로드하고 설치합니다.
  2. 명령 프롬프트나 PowerShell을 열고 필요한 라이브러리를 설치합니다:
    pip install flask openai requests

5단계: AI 비서 웹 서버 코드 작성

  1. 새로운 폴더를 만들고 그 안에 app.py 파일을 생성합니다.
  2. 아래와 같이 기본적인 Flask 앱 코드를 작성합니다:
from flask import Flask, request, render_template, jsonify
import openai

app = Flask(__name__)

# LM Studio 로컬 서버 설정
openai.api_base = "http://localhost:1234/v1"
openai.api_key = "lm-studio"  # 아무 값이나 설정해도 됩니다

@app.route('/')
def index():
    return render_template('index.html')

@app.route('/chat', methods=['POST'])
def chat():
    data = request.json
    user_message = data.get('message', '')

    try:
        response = openai.ChatCompletion.create(
            model="local-model",  # LM Studio에서 실행 중인 모델
            messages=[
                {"role": "system", "content": "당신은 도움이 되는 AI 비서입니다."},
                {"role": "user", "content": user_message}
            ]
        )

        ai_response = response.choices[0].message.content
        return jsonify({"response": ai_response})

    except Exception as e:
        return jsonify({"error": str(e)}), 500

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=5000, debug=True)

6단계: HTML 템플릿 작성

  1. 프로젝트 폴더 안에 templates 폴더를 생성합니다.
  2. templates 폴더 안에 index.html 파일을 생성하고 다음 코드를 작성합니다:
<!DOCTYPE html>
<html>
<head>
    <title>나만의 AI 비서</title>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <style>
        body {
            font-family: Arial, sans-serif;
            max-width: 800px;
            margin: 0 auto;
            padding: 20px;
        }
        #chat-container {
            height: 400px;
            overflow-y: auto;
            border: 1px solid #ccc;
            padding: 10px;
            margin-bottom: 10px;
        }
        .user-message {
            background-color: #e1f5fe;
            padding: 8px;
            border-radius: 5px;
            margin-bottom: 10px;
        }
        .ai-message {
            background-color: #f1f1f1;
            padding: 8px;
            border-radius: 5px;
            margin-bottom: 10px;
        }
        #message-input {
            width: 70%;
            padding: 8px;
        }
        #send-button {
            padding: 8px 15px;
        }
    </style>
</head>
<body>
    <h1>나만의 AI 비서</h1>
    <div id="chat-container"></div>
    <div>
        <input type="text" id="message-input" placeholder="메시지를 입력하세요...">
        <button id="send-button">전송</button>
    </div>

    <script>
        const chatContainer = document.getElementById('chat-container');
        const messageInput = document.getElementById('message-input');
        const sendButton = document.getElementById('send-button');

        function addMessage(content, isUser) {
            const messageDiv = document.createElement('div');
            messageDiv.className = isUser ? 'user-message' : 'ai-message';
            messageDiv.textContent = content;
            chatContainer.appendChild(messageDiv);
            chatContainer.scrollTop = chatContainer.scrollHeight;
        }

        async function sendMessage() {
            const message = messageInput.value.trim();
            if (!message) return;

            // 사용자 메시지 추가
            addMessage(message, true);
            messageInput.value = '';

            try {
                const response = await fetch('/chat', {
                    method: 'POST',
                    headers: {
                        'Content-Type': 'application/json'
                    },
                    body: JSON.stringify({ message })
                });

                const data = await response.json();

                if (data.error) {
                    addMessage('오류가 발생했습니다: ' + data.error, false);
                } else {
                    addMessage(data.response, false);
                }
            } catch (error) {
                addMessage('서버 연결 오류가 발생했습니다.', false);
                console.error('Error:', error);
            }
        }

        sendButton.addEventListener('click', sendMessage);
        messageInput.addEventListener('keypress', (event) => {
            if (event.key === 'Enter') {
                sendMessage();
            }
        });
    </script>
</body>
</html>

7단계: 웹 서버 실행 및 테스트

  1. 프로젝트 폴더에서 명령 프롬프트를 열고 다음 명령어로 Flask 앱을 실행합니다:
    python app.py
  2. 서버가 실행되면 웹 브라우저를 열고 http://localhost:5000으로 접속하여 AI 비서와 대화할 수 있습니다.
  3. LM Studio의 로컬 서버가 계속 실행 중인지 확인하세요. 만약 중지되었다면 다시 시작해야 합니다.

8단계: 외부 접속을 위한 설정

  1. 같은 네트워크 내에서 다른 기기로 접속하려면 컴퓨터의 로컬 IP 주소를 확인해야 합니다:

    ipconfig

    명령어를 실행하여 IPv4 주소를 확인합니다.

  2. 확인한 IP 주소(예: 192.168.1.5)와 포트를 사용하여 다른 기기에서 http://192.168.1.5:5000으로 접속할 수 있습니다.

9단계: Ngrok을 사용한 외부 접속 설정

인터넷을 통해 외부에서 접속하려면 Ngrok과 같은 터널링 서비스를 사용할 수 있습니다:

  1. Ngrok 웹사이트(https://ngrok.com/)에서 계정을 만들고 Ngrok을 다운로드합니다.
  2. 다운로드한 파일의 압축을 풀고 Ngrok 실행 파일을 적절한 위치에 저장합니다.
  3. 명령 프롬프트를 열고 Ngrok이 있는 디렉토리로 이동한 후, 다음 명령어를 실행합니다:
    ngrok http 5000
  4. Ngrok이 제공하는 URL(예: https://abcd1234.ngrok.io)을 통해 인터넷에서 어디서나 AI 비서에 접속할 수 있습니다.

10단계: 시스템 기능 확장하기

대화 기록 저장 기능 추가

  1. app.py 파일에 대화 기록을 저장하는 기능을 추가합니다:
import json
from datetime import datetime

# 대화 기록을 저장할 함수
def save_conversation(user_message, ai_response):
    try:
        # 대화 기록 파일 열기 (없으면 새로 생성)
        try:
            with open('conversations.json', 'r', encoding='utf-8') as f:
                conversations = json.load(f)
        except FileNotFoundError:
            conversations = []

        # 새 대화 추가
        conversations.append({
            'timestamp': datetime.now().strftime('%Y-%m-%d %H:%M:%S'),
            'user': user_message,
            'ai': ai_response
        })

        # 파일에 저장
        with open('conversations.json', 'w', encoding='utf-8') as f:
            json.dump(conversations, f, ensure_ascii=False, indent=2)

    except Exception as e:
        print(f"대화 저장 중 오류 발생: {e}")

# chat 함수 수정
@app.route('/chat', methods=['POST'])
def chat():
    data = request.json
    user_message = data.get('message', '')

    try:
        response = openai.ChatCompletion.create(
            model="local-model",
            messages=[
                {"role": "system", "content": "당신은 도움이 되는 AI 비서입니다."},
                {"role": "user", "content": user_message}
            ]
        )

        ai_response = response.choices[0].message.content

        # 대화 저장
        save_conversation(user_message, ai_response)

        return jsonify({"response": ai_response})

    except Exception as e:
        return jsonify({"error": str(e)}), 500

다중 사용자 지원 기능 추가

  1. 사용자 인증을 위한 간단한 로그인 시스템을 추가합니다:
  2. app.py 파일에 다음 코드를 추가합니다:
from flask import session, redirect, url_for
import os

app.secret_key = os.urandom(24)  # 세션을 위한 비밀 키

# 사용자 계정 (실제 시스템에서는 데이터베이스를 사용해야 함)
users = {
    "user1": "password1",
    "user2": "password2"
}

@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':
        username = request.form.get('username')
        password = request.form.get('password')

        if username in users and users[username] == password:
            session['username'] = username
            return redirect(url_for('index'))
        else:
            return render_template('login.html', error='잘못된 사용자 이름 또는 비밀번호입니다.')

    return render_template('login.html')

@app.route('/logout')
def logout():
    session.pop('username', None)
    return redirect(url_for('login'))

# 기존 index 함수 수정
@app.route('/')
def index():
    if 'username' not in session:
        return redirect(url_for('login'))
    return render_template('index.html', username=session['username'])
  1. templates 폴더에 login.html 파일을 생성하고 다음 코드를 작성합니다:
<!DOCTYPE html>
<html>
<head>
    <title>AI 비서 - 로그인</title>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <style>
        body {
            font-family: Arial, sans-serif;
            max-width: 400px;
            margin: 0 auto;
            padding: 20px;
        }
        .login-form {
            border: 1px solid #ccc;
            padding: 20px;
            border-radius: 5px;
        }
        .form-group {
            margin-bottom: 15px;
        }
        label {
            display: block;
            margin-bottom: 5px;
        }
        input[type="text"], input[type="password"] {
            width: 100%;
            padding: 8px;
            box-sizing: border-box;
        }
        button {
            padding: 10px 15px;
            background-color: #4CAF50;
            color: white;
            border: none;
            border-radius: 4px;
            cursor: pointer;
        }
        .error {
            color: red;
            margin-bottom: 15px;
        }
    </style>
</head>
<body>
    <h1>AI 비서 로그인</h1>

    <div class="login-form">
        {% if error %}
        <div class="error">{{ error }}</div>
        {% endif %}

        <form method="post" action="/login">
            <div class="form-group">
                <label for="username">사용자 이름:</label>
                <input type="text" id="username" name="username" required>
            </div>

            <div class="form-group">
                <label for="password">비밀번호:</label>
                <input type="password" id="password" name="password" required>
            </div>

            <button type="submit">로그인</button>
        </form>
    </div>
</body>
</html>

11단계: 서비스 유지 및 관리

윈도우에서 자동 시작 설정

  1. 시작 폴더에 바로가기 파일 추가하기:

    • Windows 탐색기에서 Win+R을 눌러 실행 대화상자를 엽니다.
    • shell:startup을 입력하고 확인을 클릭합니다.
    • 시작 폴더가 열리면, 여기에 Python 스크립트를 실행하는 배치 파일의 바로가기를 만듭니다.
  2. 배치 파일 생성:

    • 메모장을 열고 다음 내용을 입력합니다:
      @echo off
      cd /d C:\path\to\your\project
      start "" "C:\Program Files\LM Studio\LM Studio.exe"
      timeout /t 10
      python app.py
    • 이 파일을 start_ai_assistant.bat로 저장합니다.
    • 이 배치 파일의 바로가기를 시작 폴더에 추가합니다.

서비스로 등록하기 (더 안정적인 방법)

Windows에서는 NSSM(Non-Sucking Service Manager)을 사용하여 Python 스크립트를 서비스로 등록할 수 있습니다:

  1. NSSM을 다운로드하고 설치합니다(https://nssm.cc/download)
  2. 관리자 권한으로 명령 프롬프트를 열고 다음 명령어를 실행합니다:
    nssm install AI_Assistant "C:\Path\to\Python\python.exe" "C:\path\to\your\project\app.py"
  3. 서비스 설정 창이 열리면 추가 옵션을 구성하고 저장합니다.
  4. 다음 명령어로 서비스를 시작합니다:
    nssm start AI_Assistant

마무리

이제 여러분만의 개인 AI 비서 시스템이 완성되었습니다! 이 시스템은 LM Studio를 사용하여 로컬에서 AI 모델을 실행하고, Flask 웹 서버를 통해 원격에서 접속할 수 있도록 해줍니다. 필요에 따라 기능을 확장하거나 사용자 인터페이스를 개선할 수 있습니다.

추가적으로 고려할 수 있는 기능:

  • 음성 인식 및 음성 합성 추가
  • 다양한 명령어 처리 기능(일정 관리, 날씨 정보 등)
  • 모바일 앱 인터페이스 개발
  • 데이터베이스 연동으로 정보 저장 및 검색 기능 강화

이 튜토리얼이 여러분만의 AI 비서 시스템을 구축하는 데 도움이 되길 바랍니다!

반응형
LIST