https://github.com/Chen11111112/flask--AI-.git
你現在是一個專業的flask工程師,你要協助我完成一個專案,運用以下技術:
- Flask,app.py
- Jinja ,includes,macros,base.html,extands
製作專案: AI應用系統: user可以在我的系統,透過前端,與gemini AI 進行互動。
我是初學者,請你一步驟一步驟地仔細教導我。
我會給你error提示,你要告訴我發生的原因以及如何解決。
pip install flask google-generativeai python-dotenv
templates/base.html
<!DOCTYPE html>
<html lang="zh-Hant">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{% block title %}AI 互動系統{% endblock %}</title>
<link href="<https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css>" rel="stylesheet">
<style>
body { background-color: #f8f9fa; }
.chat-container { max-width: 800px; margin: 30px auto; }
</style>
</head>
<body>
{% block navbar %}
{% endblock %}
<div class="container chat-container">
{% block content %}
{% endblock %}
</div>
<script src="<https://cdn.jsdelivr.net/npm/[email protected]/dist/js/bootstrap.bundle.min.js>"></script>
{% block scripts %}
{% endblock %}
</body>
</html>
templates/index.html
{% extends "base.html" %}
{% block title %}首頁 - Gemini AI{% endblock %}
{% block content %}
<div class="card shadow">
<div class="card-header bg-primary text-white">
<h4>與 Gemini 對話</h4>
</div>
<div class="card-body" id="chat-box" style="height: 400px; overflow-y: auto;">
<div class="text-center text-muted mt-5">
<p>你好!請在下方輸入訊息開始對話。</p>
</div>
</div>
<div class="card-footer">
<form id="chat-form" class="d-flex gap-2">
<input type="text" id="user-input" class="form-control" placeholder="輸入你的問題..." required>
<button type="submit" class="btn btn-primary">發送</button>
</form>
</div>
</div>
{% endblock %}
.env
GEMINI_API_KEY=你的_API_Key_貼在這裡
app.py
from flask import Flask, render_template, request, jsonify
import os
import google.generativeai as genai
from dotenv import load_dotenv
# 1. 載入環境變數
load_dotenv()
# 2. 設定 Gemini API
genai.configure(api_key=os.getenv("GEMINI_API_KEY"))
app = Flask(__name__)
# 首頁路由
@app.route('/')
def index():
return render_template('index.html')
# 3. 新增聊天接口 (POST 方法)
@app.route('/chat', methods=['POST'])
def chat():
try:
# 接收前端傳來的 JSON 資料
user_message = request.json.get('message')
if not user_message:
return jsonify({'error': '沒有收到訊息'}), 400
# 呼叫 Gemini 模型
model = genai.GenerativeModel('gemini-3-flash-preview')
response = model.generate_content(user_message)
# 回傳 AI 的回應文字
return jsonify({'response': response.text})
except Exception as e:
return jsonify({'error': str(e)}), 500
if __name__ == '__main__':
app.run(debug=True, port=5000)
補上static資料夾 並在其中寫上script.js檔案,實作功能: 讓使用者可以實現跟AI進行互動 1. 取得Gemini API 2. 實現串接功能 3. 完成UIUX
static/style.css
/* 聊天訊息的共用樣式 */
.message {
max-width: 75%;
padding: 10px 15px;
border-radius: 20px;
margin-bottom: 10px;
line-height: 1.5;
position: relative;
word-wrap: break-word;
}
/* 使用者的訊息:靠右,藍色 */
.user-message {
background-color: #0d6efd; /* Bootstrap Primary Color */
color: white;
align-self: flex-end; /* Flexbox 靠右對齊 */
border-bottom-right-radius: 5px;
margin-left: auto; /* 強制靠右 */
}
/* AI 的訊息:靠左,灰色 */
.ai-message {
background-color: #e9ecef;
color: #333;
align-self: flex-start; /* Flexbox 靠左對齊 */
border-bottom-left-radius: 5px;
margin-right: auto;
}
/* 聊天框框設定為 Flex 佈局,方便排版 */
#chat-box {
display: flex;
flex-direction: column;
}
static/script.js
document.addEventListener('DOMContentLoaded', function() {
const chatForm = document.getElementById('chat-form');
const userInput = document.getElementById('user-input');
const chatBox = document.getElementById('chat-box');
// 監聽表單送出事件
chatForm.addEventListener('submit', async function(e) {
e.preventDefault(); // 1. 阻止表單預設的跳頁行為
const message = userInput.value.trim();
if (!message) return;
// 2. 顯示使用者的訊息在畫面上
appendMessage(message, 'user-message');
userInput.value = ''; // 清空輸入框
// 顯示「思考中...」的提示 (UIUX 優化)
const loadingId = showLoading();
try {
// 3. 發送請求給後端 (Flask)
const response = await fetch('/chat', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({ message: message })
});
const data = await response.json();
// 移除讀取提示
removeLoading(loadingId);
if (response.ok) {
// 4. 顯示 AI 回傳的訊息
appendMessage(data.response, 'ai-message');
} else {
appendMessage('錯誤: ' + data.error, 'ai-message text-danger');
}
} catch (error) {
removeLoading(loadingId);
appendMessage('發生連線錯誤,請稍後再試。', 'ai-message text-danger');
console.error('Error:', error);
}
});
// 輔助函式:將訊息加入聊天視窗
function appendMessage(text, className) {
const messageDiv = document.createElement('div');
messageDiv.className = `message ${className}`;
// 為了安全,這裡使用 textContent,若要支援 Markdown 需用其他套件
messageDiv.textContent = text;
chatBox.appendChild(messageDiv);
// 自動捲動到底部
chatBox.scrollTop = chatBox.scrollHeight;
}
// UIUX: 顯示思考中
function showLoading() {
const id = 'loading-' + Date.now();
const loadingDiv = document.createElement('div');
loadingDiv.id = id;
loadingDiv.className = 'message ai-message text-muted fst-italic';
loadingDiv.textContent = 'Gemini 正在思考...';
chatBox.appendChild(loadingDiv);
chatBox.scrollTop = chatBox.scrollHeight;
return id;
}
function removeLoading(id) {
const element = document.getElementById(id);
if (element) element.remove();
}
});
**在 <head> 裡面,原本 <style> 的下方加入:**HTML
<link rel="stylesheet" href="{{ url_for('static', filename='style.css') }}">
**在 </body> 之前,{% block scripts %} 的區塊內加入:**HTML
{% block scripts %} <script src="{{ url_for('static', filename='script.js') }}"></script> {% endblock %}