基于deepseek的图像生成系统

ops/2025/3/14 10:26:44/

目录

问题

核心思路

pollinations

提示词

基于deepseek的图像生成系统

项目说明

详细说明

1. 注册流程

2. 登录流程

3. 图片生成流程

4. 图片下载流程

项目结构

代码实现

1. 配置文件

config.py

2. 数据库模型

models.py

3. 解决循环引用

exts.py 

4. 登录和注册逻辑

auth.py

5. Deepseek API 封装

deepseek_api.py

6. Flask 主程序

app.py

7. 前端页面

templates/index.html

templates/login.html

templates/register.html

8. 前端脚本

static/scripts.js

9. 前端样式

static/style.css

10. 依赖文件

requirements.txt

运行项目

1. 安装依赖

2. 启动 MySQL 数据库,并确保数据库连接配置正确

3. 迁移数据库

4. 访问生成的API 


问题

        直接让deepseek模型去生成图像,实现不了

        但是它可以生成图像生成的描述词,那么是否可以使用deepseek生成描述词,然后用其他的AI绘画工具去生成呢?曲线救国

       deepseek它能支持Markdown格式显示图片呢!要是再搭配一个在线图像生成API,那可就方便了。只需要访问一个特定的网址,就能实时生成AI图片,就像过去用老式相机拍照,按下快门就能看到结果,多有意思呀!

核心思路

  • DeepSeek本身支持生成markdown格式的内容,而markdown可以嵌入图片链接。

  • 通过一个在线图像生成API,只需要提供提示词和参数,就能生成图片并返回URL。

  • 把生成的URL嵌入到markdown中,DeepSeek就能直接显示图片!

pollinations

        其实这是一个开源项目(pollinations),无需注册或API密钥,为大家提供免费的图像生成服务

        首先,咱们得给DeepSeek一个明确的指令,让它帮我们生成图片提示词并嵌入到markdown中。以下是亲测有效的提示词模板,大家可以直接复制使用,当然你也可以根据自己的实际需求来调整。

提示词

        你现在是一个ai图片生成机器人,我给你一些提示,你用你的想象力去生动描述这幅图片,并转换成英文填充到下面url的占位符中:![image](https://image.pollinations.ai/prompt/{prompt}?width=1024&height=1024&seed=100&model=flux&nologo=true)- {prompt}必须是英文,符合stable diffusion提示词格式;

        这个提示词中最主要要的就是这个URL:

https://image.pollinations.ai/prompt/{prompt}?width=1024&height=1024&seed=100&model=flux&nologo=true

        当你向这个URL发送请求Pollinations AI的服务器会根据URL中的参数生成一张图片,并将图片返回给你,其中包含了不少AI绘图所需的参数,内行人应该一眼就能看懂~

        作者在官方文档中找了一下,目前到这个生图次数是没有限制的。

        测试:沙漠日落

基于deepseek的图像生成系统

        作者想做一个基于本地deepseek-r1模型的图像生成系统。问为什么?就是玩玩,好玩,爱玩。。。

项目说明

整个项目包括 Flask 后端MySQL 数据库前端页面 和 Deepseek API 集成。项目实现了以下功能:

  1. 用户注册和登录(使用 Flask-Login 和 MySQL)。

  2. AI 图片生成(调用 ChatGPT API 生成提示词,并使用 Pollinations API 生成图片)。

  3. 图片下载(将生成的图片下载到本地)。

  4. 前端页面(包括登录、注册和图片生成页面)。

项目的业务逻辑:

        

详细说明

1. 注册流程
  • 前端:用户访问注册页面 (/register),填写用户名和密码,点击“Register”按钮。

  • 后端:接收 POST /register 请求,验证用户名是否已存在,将用户数据保存到数据库。

  • 数据库:存储用户数据(用户名和加密后的密码)。

2. 登录流程
  • 前端:用户访问登录页面 (/login),填写用户名和密码,点击“Login”按钮。

  • 后端:接收 POST /login 请求,验证用户名和密码是否正确,登录成功后返回用户信息。

  • 数据库:查询用户数据,验证用户名和密码。

3. 图片生成流程
  • 前端:用户访问主页 (/),输入提示词,点击“Generate Image”按钮。

  • 后端:接收 POST /generate 请求,调用Deepseek API 生成图片提示词,生成图片 URL 并返回给前端。

  • 第三方 API:调用 Deepseek API 和 Pollinations API 生成图片。

4. 图片下载流程
  • 前端:用户点击“Download Image”按钮,发送 POST /download 请求。

  • 后端:接收 POST /download 请求,从 Pollinations API 下载图片并返回给前端。

  • 前端:将图片保存到本地。

项目结构

代码实现

        前期准备工作,部署本地deepseek模型,可以参考本地部署Deeoseek,安装mysql数据库,创建数据库。

1. 配置文件

config.py
python">import osSECRET_KEY = os.environ.get("SECRET_KEY") or "your_secret_key_here"  # 设置一个随机的密钥
#mysql所在的主机名
HOSTNAME = '127.0.0.1'
#mysql监听的端口号
PORT = 3306
#连接Mysql的用户名
USERNAME = 'root'  #设置成你自己的
#连接mysql的密码
PASSWORD = '123456' #设置成你自己的
#mysql上创建的数据库
DATABASE = 'image_generator'  #设置成你自己的
DB_URI = 'mysql+pymysql://{}:{}@{}:{}/{}?charset=utf8mb4'.format(USERNAME,PASSWORD,HOSTNAME,PORT,DATABASE)
SQLALCHEMY_DATABASE_URI = DB_URI
SQLALCHEMY_TRACK_MODIFICATIONS = False

2. 数据库模型

models.py
python">from exts import dbclass User(db.Model):__tablename__ = 'user'id = db.Column(db.Integer, primary_key=True, autoincrement=True)username = db.Column(db.String(100), nullable=False)password = db.Column(db.String(1000), nullable=False)# Flask-Login 需要的属性和方法@propertydef is_active(self):return True  # 默认所有用户都是活跃的@propertydef is_authenticated(self):return True  # 默认所有用户都是已认证的@propertydef is_anonymous(self):return False  # 默认所有用户都不是匿名的def get_id(self):return str(self.id)  # 返回用户 ID 的字符串形式

3. 解决循环引用

exts.py 

为什么要这样做大家可以参考项目准备(flask+pyhon+MachineLearning)- 1

python">from flask_sqlalchemy import SQLAlchemy
db = SQLAlchemy()

4. 登录和注册逻辑

auth.py
python">from flask import Blueprint, request, jsonify, render_template
from werkzeug.security import generate_password_hash, check_password_hash
from flask_login import login_user, logout_user, login_required
from models import User, db
from flask import redirect, url_forauth = Blueprint("auth", __name__)@auth.route("/login", methods=["GET", "POST"])
def login():if request.method == "POST":data = request.jsonusername = data.get("username")password = data.get("password")user = User.query.filter_by(username=username).first()if not user or not check_password_hash(user.password, password):return jsonify({"error": "Invalid username or password"}), 401login_user(user)return jsonify({"message": "Logged in successfully"}), 200else:return render_template("login.html")@auth.route("/register", methods=["GET", "POST"])
def register():if request.method == "POST":data = request.jsonusername = data.get("username")password = data.get("password")if not username or not password:return jsonify({"error": "Username and password are required"}), 400if User.query.filter_by(username=username).first():return jsonify({"error": "Username already exists"}), 400new_user = User(username=username, password=generate_password_hash(password))db.session.add(new_user)db.session.commit()return jsonify({"message": "User registered successfully"}), 201else:return render_template("register.html")@auth.route("/logout")
@login_required
def logout():logout_user()  # 注销用户return redirect(url_for("auth.login"))  # 重定向到登录页面

5. Deepseek API 封装

deepseek_api.py
python">from openai import OpenAIclass DeepSeekLocalAPI:def __init__(self, api_base, api_key="none"):"""初始化 DeepSeek 本地模型 API:param api_base: DeepSeek 本地模型的 API 地址,例如 "http://localhost:5001/v1":param api_key: API 密钥(如果不需要可以设置为 "none")"""self.client = OpenAI(base_url=api_base,  # 设置本地模型的 API 地址api_key=api_key     # 设置 API 密钥)def generate_prompt(self, user_input):"""调用 DeepSeek 本地模型生成图片提示词"""# 系统提示:预设角色system_prompt = ("You are an AI image generation bot. I will give you some prompts, and you will use your imagination to vividly describe the image, ""then convert it into English to fill in the placeholder of the following URL: ""![image](https://image.pollinations.ai/prompt/{prompt}?width=1024&height=1024&seed=100&model=flux&nologo=true);只返回url")# 调用 DeepSeek 本地模型try:response = self.client.chat.completions.create(model="deepseek-r1:32b",  # 模型名称messages=[{"role": "system", "content": system_prompt},  # 系统提示{"role": "user", "content": user_input}        # 用户输入],max_tokens=500,  # 限制生成内容的长度temperature=0.7   # 控制生成内容的创造性)print('正在生成提示词。')# 提取生成的提示词generated_prompt1 = response.choices[0].message.contentreturn generated_prompt1except Exception as e:print(f"Error calling DeepSeek Local API: {e}")return ""# 示例用法
if __name__ == "__main__":# DeepSeek 本地模型的 API 地址api_base = "http://127.0.0.1:11434/v1"  # 替换为你的 DeepSeek 本地模型地址api_key = "none"  # 如果不需要 API 密钥,可以设置为 "none"# 初始化 DeepSeek 本地模型 APIdeepseek = DeepSeekLocalAPI(api_base, api_key)# 用户输入user_input = "一只凤凰在彩虹色星云中翱翔"# 生成提示词generated_prompt = deepseek.generate_prompt(user_input)if generated_prompt:print("Generated Prompt:", generated_prompt)else:print("Failed to generate prompt.")

6. Flask 主程序

app.py
python">from deepseek_api import DeepSeekLocalAPI
from flask import Flask, render_template, request, jsonify, send_file
from flask_login import LoginManager, current_user, login_required
from models import User
from auth import auth
import requests
import io
import config
from exts import db
from flask_migrate import Migrate
from werkzeug.security import generate_password_hashapp = Flask(__name__)
# 导入自定义配置
app.config.from_object(config)
# 数据库初始化
db.init_app(app)
migrate = Migrate(app,db)login_manager = LoginManager(app)
login_manager.login_view = "auth.login"  # 设置登录页面路由# 注册蓝图
app.register_blueprint(auth)deepseek_api_base = "http://127.0.0.1:11434/v1"  # 替换为你的 DeepSeek 本地模型地址
deepseek_api_key = "none"  # 如果不需要 API 密钥,可以设置为 "none"
deepseek = DeepSeekLocalAPI(deepseek_api_base, deepseek_api_key)@login_manager.user_loader
def load_user(user_id):return User.query.get(int(user_id))@app.route("/")
@login_required
def index():return render_template("index.html")@app.route("/generate", methods=["POST"])
@login_required
def generate():"""生成图片提示词并返回图片 URL"""user_input = request.form.get("prompt", "")if not user_input:return jsonify({"error": "Please provide a prompt"}), 400print(user_input)# 调用 DeepSeek 生成提示词image_url = deepseek.generate_prompt(user_input)generated_prompt = '图像渲染'print('url:',image_url)if not generated_prompt:return jsonify({"error": "Failed to generate prompt"}), 500return jsonify({"image_url": image_url, "prompt": generated_prompt})@app.route("/download", methods=["POST"])
@login_required
def download():image_url = request.json.get("image_url")if not image_url:return jsonify({"error": "Image URL is required"}), 400response = requests.get(image_url)if response.status_code != 200:return jsonify({"error": "Failed to download image"}), 500return send_file(io.BytesIO(response.content),mimetype="image/png",as_attachment=True,download_name="generated_image.png")
if __name__ == "__main__":app.run(debug=True)

7. 前端页面

templates/index.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>AI Image Generator</title><link rel="stylesheet" href="{{ url_for('static', filename='style.css') }}">
</head>
<body><div class="container"><h1>图像自动生成器</h1><form id="prompt-form"><textarea id="prompt-input" placeholder="Enter your prompt here..."></textarea><button type="submit">生成图像</button></form><div id="result"><p id="status-message"></p>  <!-- 显示生成状态 --><img id="generated-image" src="" alt="Generated Image"><p id="generated-prompt"></p><button id="download-button" style="display: none;">下载图像</button></div><a href="{{ url_for('auth.logout') }}">退出登录</a></div><script src="{{ url_for('static', filename='scripts.js') }}"></script>
</body>
</html>
templates/login.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>登录</title><link rel="stylesheet" href="{{ url_for('static', filename='style.css') }}">
</head>
<body><div class="container"><h1>登录</h1><form id="login-form"><input type="text" id="username" placeholder="Username" required><input type="password" id="password" placeholder="Password" required><button type="submit">登录</button></form><p>还没有账号? <a href="{{ url_for('auth.register') }}">注册</a></p></div><script src="{{ url_for('static', filename='scripts.js') }}"></script>
</body>
</html>
templates/register.html
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>注册</title><link rel="stylesheet" href="{{ url_for('static', filename='style.css') }}">
</head>
<body><div class="container"><h1>注册</h1><form id="register-form"><input type="text" id="username" placeholder="Username" required><input type="password" id="password" placeholder="Password" required><button type="submit">注册</button></form><p>已经有了账号?<a href="{{ url_for('auth.login') }}">登录</a></p></div><script src="{{ url_for('static', filename='scripts.js') }}"></script>
</body>
</html>

8. 前端脚本

static/scripts.js
// 登录表单提交
document.getElementById("login-form")?.addEventListener("submit", async (e) => {e.preventDefault();const data = {username: document.getElementById("username").value,password: document.getElementById("password").value,};const response = await fetch("/login", {method: "POST",headers: {"Content-Type": "application/json",},body: JSON.stringify(data),});const result = await response.json();if (response.ok) {window.location.href = "/";  // 登录成功后跳转到主页} else {alert(result.error);  // 显示错误信息}
});// 注册表单提交
document.getElementById("register-form")?.addEventListener("submit", async (e) => {e.preventDefault();const data = {username: document.getElementById("username").value,password: document.getElementById("password").value,};const response = await fetch("/register", {method: "POST",headers: {"Content-Type": "application/json",},body: JSON.stringify(data),});const result = await response.json();if (response.ok) {alert(result.message);  // 注册成功window.location.href = "/login";  // 跳转到登录页面} else {alert(result.error);  // 显示错误信息}
});document.getElementById("prompt-form")?.addEventListener("submit", async (e) => {e.preventDefault();  // 阻止表单默认提交行为const prompt = document.getElementById("prompt-input").value;const statusMessage = document.getElementById("status-message");// 显示“生成中”statusMessage.innerText = "Generating...";statusMessage.style.color = "blue";try {const response = await fetch("/generate", {method: "POST",headers: {"Content-Type": "application/x-www-form-urlencoded",},body: `prompt=${encodeURIComponent(prompt)}`,});const data = await response.json();if (data.image_url) {// 显示“生成完成”statusMessage.innerText = "Generation complete!";statusMessage.style.color = "green";// 显示生成的图片和提示词document.getElementById("generated-image").src = data.image_url;document.getElementById("generated-prompt").innerText = data.prompt;document.getElementById("download-button").style.display = "block";} else {// 显示错误信息statusMessage.innerText = "Error: " + (data.error || "Failed to generate image");statusMessage.style.color = "red";}} catch (error) {console.error("Error:", error);statusMessage.innerText = "An error occurred. Please try again.";statusMessage.style.color = "red";}
});// 图片下载
document.getElementById("download-button")?.addEventListener("click", async () => {const imageUrl = document.getElementById("generated-image").src;const response = await fetch("/download", {method: "POST",headers: {"Content-Type": "application/json",},body: JSON.stringify({ image_url: imageUrl }),});if (response.ok) {const blob = await response.blob();const url = window.URL.createObjectURL(blob);const a = document.createElement("a");a.href = url;a.download = "generated_image.png";document.body.appendChild(a);a.click();a.remove();} else {alert("Failed to download image");}
});

9. 前端样式

static/style.css
body {font-family: Arial, sans-serif;background-color: #f4f4f9;color: #333;margin: 0;padding: 0;display: flex;justify-content: center;align-items: center;height: 100vh;
}.container {background: white;padding: 2rem;border-radius: 8px;box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);max-width: 600px;width: 100%;text-align: center;
}h1 {margin-bottom: 1.5rem;
}input, textarea {width: 100%;padding: 0.75rem;margin-bottom: 1rem;border: 1px solid #ccc;border-radius: 4px;font-size: 1rem;
}button {width: 100%;padding: 0.75rem;background-color: #007bff;color: white;border: none;border-radius: 4px;font-size: 1rem;cursor: pointer;
}button:hover {background-color: #0056b3;
}#result {margin-top: 1.5rem;
}#generated-image {max-width: 100%;border-radius: 4px;margin-bottom: 1rem;
}#generated-prompt {font-size: 0.9rem;color: #666;
}#status-message {font-size: 1.2rem;font-weight: bold;margin-bottom: 1rem;
}a {color: #007bff;text-decoration: none;
}a:hover {text-decoration: underline;
}

10. 依赖文件

requirements.txt
Flask==2.3.2
Flask-SQLAlchemy==3.0.5
Flask-Login==0.6.2
mysql-connector-python==8.0.33
openai==1.0.0
requests==2.31.0

运行项目

1. 安装依赖

pip install -r requirements.txt

2. 启动 MySQL 数据库,并确保数据库连接配置正确

3. 迁移数据库

        这一步是为了创建数据库表,可以参考项目准备(flask+pyhon+MachineLearning)- 1

        在终端中依次执行

初始化(只需要执行一次)
flask db init
生成文件
flask db migrate
迁移数据库
flask db upgrade

4. 访问生成的API 

访问 http://localhost:5000,注册并登录后即可使用图片生成和下载功能。


http://www.ppmy.cn/ops/165638.html

相关文章

Axure PR 9 中继器 04 条件查询

​大家好&#xff0c;我是大明同学。 接着上期的内容&#xff0c;这期内容&#xff0c;我们来了解一下Axure中继器图表条件查询。 预览地址&#xff1a;https://rtb1qx.axshare.com 条件查询 1.打开上期RP 文件&#xff0c;在元件库中拖入一个文本框&#xff0c;在样式窗格中…

【蓝桥杯—单片机】第十五届省赛真题代码题解析 | 思路整理

第十五届省赛真题代码题解析 前言赛题代码思路笔记竞赛板配置建立模板明确基本要求显示功能部分频率界面正常显示高位熄灭 参数界面基础写法&#xff1a;两个界面分开来写优化写法&#xff1a;两个界面合一起写 时间界面回显界面校准校准过程校准错误显示 DAC输出部分按键功能部…

二叉树中堆的实现

1 堆的声明和定义 typedef int HPDateType; typedef struct Heap {HPDateType* arr;int size;int capcity; }HP; 与顺序表相似&#xff0c;我们需要一个数组&#xff0c;有效空间大小&#xff0c;有效元素个数 2 堆的初始化 void HPInit(HP*php) {assert(php);php->arr …

第十一届蓝桥杯单片机国赛

什么&#xff1f;4T模拟赛和省赛做起来轻轻松松&#xff1f;不妨来挑战一下第十一届国赛&#xff0c;这一届的国赛居然没考超声波、串口通信&#xff01;只要你正确地理解了题目的意思&#xff0c;规避出题人挖的坑&#xff0c;拿个国一轻轻松松。 附件&#xff1a;第十一届蓝桥…

socket编程与TCP协议

如果你想和远方的朋友通电话&#xff0c;但是&#xff0c;没有办法直接把自己的声音放在电线上变成电流信号&#xff0c;你需要使用电话机拿起听筒拨号&#xff0c;而这个电话就是Socket&#xff0c;它让你简单方便地完成电流通话&#xff0c;从我们编程的角度来看&#xff0c;…

字母金字塔

通过输入的字母&#xff0c;实现字母金字塔&#xff0c;效果如下面这个图&#xff1a; 代码示例&#xff1a; #include <stdio.h> int main(int argc, char const *argv[]) {// (1)、输入大写字母int n 0; char ch 0;printf("请输入任意大写字母:\n")…

批量测试IP和域名联通性

最近需要测试IP和域名的联通性&#xff0c;因数量很多&#xff0c;单个ping占用时间较长。考虑使用Python和Bat解决。考虑到依托的环境&#xff0c;Bat可以在Windows直接运行。所以直接Bat处理。 方法1 echo off for /f %%i in (E:\封禁IP\ipall.txt) do (ping %%i -n 1 &…

2025年第十届数维杯大学生数学建模挑战赛参赛规则

为了培养大学生的创新意识&#xff0c;运用数学方法和计算机技术解决实际问题的能力&#xff0c;培养造就一批具有国际视野的大学生科技创新人才&#xff0c;在中国国际科学技术合作协会的指导下&#xff0c;内蒙古创新教育学会决定于2025年举办第十届数维杯大学生数学建模挑战…