🚀 软件工程初体验:从环境搭建到 AI 实战

这个作业属于哪个课程 H202601软件工程与软件工程实践
这个作业要求在哪里 2026秋软件工程第一次个人作业
这个作业的目标 熟悉 Markdown 排版与 GitHub/博客园使用;实践 Hugging Face API 调用与前后端交互;深度剖析个人技能树,明确未来规划
学号 102402101

💡 摘要:本次作业是软件工程课程的首次实践。从平台注册到云端 AI 模型的接口调用,从代码调试到未来规划的思考,这篇随笔记录了我在工程化道路上的初步探索与反思。


🛠️ 第一部分:基础筹备与环境搭建

在开启技术实践前,我完成了基础的数字空间搭建:

  1. 账号准备:完成 GitHub Luminance-l和博客园账号Luminance的注册与信息完善(头像、昵称、博客样式等)。
  2. 关注动态:关注了黄兆武老师及李怡涵、焦圣蒙两位助教。
  3. 加入班级:实名制加入“H202601软件工程与软件工程实践”班级博客。

💡 本部分心得:干净的“数字门面”是程序员走向正规化的第一步。配置博客主题的过程,也是梳理个人品牌意识的开始。


🤖 第二部分:硬核实操——Hugging Face API 调用

本次作业的核心任务:注册 Hugging Face,调用 XLabs-AI/flux-RealismLora 模型,并结合前端接口实现交互生成。

🛠️ 操作步骤与核心代码
步骤1:获取通行证与模型授权
在 Hugging Face 官网注册账号,在 Settings -> Access Tokens 中创建 Read 权限的 Token。同时,访问模型页面 XLabs-AI/flux-RealismLora 并同意用户协议。

步骤2:搭建本地后端 (app.py)
使用 Flask 搭建本地后端,通过 huggingface_hub 库的 InferenceClient 封装底层请求。核心代码如下(⚠️ 注意:为了不暴露真实 Token,代码中改成了“你的token”):

import os
import io
import base64
from flask import Flask, request, jsonify, render_template
from flask_cors import CORS
from huggingface_hub import InferenceClient

app = Flask(__name__)
CORS(app)

# 读取环境变量中的 Token
HF_TOKEN = "hf_你的token"
MODEL_ID = "XLabs-AI/flux-RealismLora"

# 创建 InferenceClient
client = InferenceClient(
    model=MODEL_ID,
    provider="fal-ai", # 推荐使用 fal-ai 提供商,速度较快
    token=HF_TOKEN,
    timeout=180,
)

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

@app.route('/generate', methods=['POST'])
def generate_image():
    try:
        data = request.get_json()
        prompt = data.get('prompt', '').strip()
        if not prompt:
            return jsonify({'error': '请输入提示词'}), 400

        print(f"\n[API调用] 开始生成,提示词: {prompt}")
        
        # 调用模型生成图像
        image = client.text_to_image(prompt=prompt)
        
        print("[API调用] ✅ 成功生成图像!")

        # 将图片转为 base64 编码返回给前端
        buffered = io.BytesIO()
        image.save(buffered, format="PNG")
        img_base64 = base64.b64encode(buffered.getvalue()).decode('utf-8')

        return jsonify({'success': True, 'image': img_base64})
    except Exception as e:
        print(f"[API调用] ❌ 失败: {str(e)}")
        return jsonify({'error': str(e)}), 500

if __name__ == '__main__':
    app.run(debug=True, host='127.0.0.1', port=5000)
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <title>Flux 写实图像生成器</title>
    <style>
        body { font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; background-color: #f4f7f6; padding: 40px 20px; }
        .container { max-width: 800px; margin: 0 auto; background: white; padding: 30px; border-radius: 12px; box-shadow: 0 5px 15px rgba(0,0,0,0.1); }
        h1 { text-align: center; color: #333; }
        textarea { width: 100%; height: 100px; padding: 15px; border: 1px solid #ddd; border-radius: 8px; margin-bottom: 20px; font-size: 16px; resize: vertical; box-sizing: border-box; }
        button { width: 100%; padding: 15px; background-color: #4a90e2; color: white; border: none; border-radius: 8px; font-size: 18px; cursor: pointer; transition: background 0.3s; }
        button:hover { background-color: #357abd; }
        button:disabled { background-color: #ccc; cursor: not-allowed; }
        .status { text-align: center; margin: 15px 0; color: #666; font-weight: bold; }
        #imageContainer { text-align: center; margin-top: 20px; }
        #imageContainer img { max-width: 100%; border-radius: 8px; box-shadow: 0 4px 10px rgba(0,0,0,0.15); }
    </style>
</head>
<body>
    <div class="container">
        <h1>Flux 写实图像生成器</h1>
        <p style="text-align: center; color: #888;">基于 XLabs-AI/flux-RealismLora 模型</p>
        <textarea id="promptInput" placeholder="请输入英文提示词。例如:photorealistic photo, a quiet city street at sunrise, soft natural golden sunlight, realistic texture, depth of field, shot on Sony A7M4, 8k, lifelike"></textarea>
        <button id="generateBtn" onclick="generate()">开始生成</button>
        <div class="status" id="status"></div>
        <div id="imageContainer"></div>
    </div>
    <script>
        async function generate() {
            const prompt = document.getElementById('promptInput').value.trim();
            const btn = document.getElementById('generateBtn');
            const status = document.getElementById('status');
            const container = document.getElementById('imageContainer');

            if (!prompt) {
                status.textContent = '❌ 请输入提示词!';
                return;
            }

            btn.disabled = true;
            btn.textContent = '生成中,请耐心等待...';
            status.textContent = '⏳ 正在调用 API,首次调用可能需要 30-60 秒...';
            container.innerHTML = '';

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

                if (data.success) {
                    status.textContent = '✅ 生成成功!';
                    container.innerHTML = `<img src="data:image/png;base64,${data.image}" alt="Generated Image">`;
                } else {
                    status.textContent = '❌ 生成失败:' + data.error;
                }
            } catch (error) {
                status.textContent = '❌ 请求出错:' + error.message;
            } finally {
                btn.disabled = false;
                btn.textContent = '开始生成';
            }
        }
    </script>
</body>
</html>

【📸 截图1:API 调用成功的终端记录】

记录显示 Running on http://127.0.0.1:5000[API调用] ✅ 成功生成图像!

【📸 截图2:前端页面最终生成图像】

🎨 提示词设计思路与修改过程

为了生成“最贴近真实世界的图像”,我经历了三次提示词迭代,逐渐理解了模型对语义的响应机制:

版本 提示词内容 (Prompt) 生成效果分析与不足 改进思路
初稿 a quiet city street at sunrise 画面像普通的AI插画,光影平淡,缺乏真实空间感。 增加写实风格限定词。
第二版 photorealistic photo, a quiet city street at sunrise, natural light 真实感提升,但远景没有虚化,缺乏镜头感。 加入摄影专业术语:景深、相机型号。
最终版 photorealistic photo, a quiet city street at sunrise, soft natural golden sunlight, realistic texture, depth of field, shot on Sony A7M4, 8k, hyper detailed, lifelike 效果符合预期。 光影自然(夕阳逆光),景深明显,具备单反写实水平。 确认最终版提交。

💡 设计心得:单靠描述物体是不够的,必须结合摄影专业术语(如 soft natural lightshot on Sony A7M4),引导模型模拟真实相机的成像规律,从而消除AI常见的“塑料感”。

🎯 体验与心得

  • 调试能力:初次运行遇到 ModuleNotFoundError,通过 pip 排查并安装依赖解决。此外,初次调用云端 API 存在“冷启动”延迟,这启示我在前端必须添加“生成中”的状态反馈,优化用户体验。
  • 原理思考:这是一个典型的客户端-服务端(C/S)架构。前端负责采集用户输入,后端负责携带 Token 向 API 网关鉴权;Hugging Face 作为模型枢纽,将请求路由给算力服务商(如 fal-ai)执行推理。

🪪 第三部分:个人名片——GitHub 个人主页搭建

本次作业我选择 方案一:创建个人资料自述文件(Profile README)。在 GitHub 上创建了与用户名同名的仓库,并在根目录编写 README.md,利用 Markdown 语法、Emoji 以及 Shields.io 徽章,完成了一个具有个人特色的主页搭建。

🔗 我的 GitHub 个人主页:Luminance-l

💡 本部分心得:GitHub不仅是代码托管平台,更是程序员的技术名片。通过搭建个人主页,我梳理了自己的技术栈,也对未来的发展路径有了更清晰的认知。


🧠 第四部分:自我审视——技能树与课程规划

  1. 技能树与技术偏好自我评估
  • 能力A:编程基础 —— 掌握 Python、C++ 基本语法,理解面向对象思想。
  • 能力B:Web开发基础 —— 能使用 Flask 搭建简单后端,了解 HTML/JS 及数据库基础。
  • 能力C:工具使用 —— 熟练使用 Git、Ubuntu、VS Code 等。
  • 感兴趣的领域:AI 应用开发、大数据处理、后端架构设计、VLA。
  • 需提升的短板:缺乏大型项目的工程化思维,前后端分离架构实战经验不足。
  1. 代码量目标
  • 截至目前代码量:约 3000 行。
  • 本学期目标:希望完成课程后突破 8000 行,在实战中提升代码规范性与逻辑严谨性。
  1. 课程期待
    最期待学习软件工程的生命周期管理(需求分析、系统设计、测试与维护)以及大模型在实际软件工程中的应用。希望能获得真实的团队开发经验。

  2. AI 参谋:软件工程学习指南分析
    我让 DeepSeek 生成了一份学习指南:

  1. 基础理论夯实:掌握软件生命周期模型(瀑布、敏捷)、需求工程、软件设计模式。
  2. 工具链熟悉:熟练 Git,掌握 UML 建模工具(StarUML),项目协同工具(Jira)。
  3. 实践出真知:参与完整团队项目,从需求到测试部署。
  4. 代码规范:遵循 Google 或阿里代码规范。
  5. 测试驱动:学习 JUnit,尝试 TDD(测试驱动开发)。

【我的分析与感悟】
这份指南结构严谨,大方向正确。但我认为,对初学者而言,盲目追求 TDD 可能会增加心智负担。结论:AI 是高效的学习参谋,但工程能力只能在不断的动手实践中获得。我会在后续课程中吸收其精髓,但保持独立思考。


📝 第五部分:格式规范与提交

  1. 已使用 Markdown 编写本篇随笔,并附上后台博文编辑页面的截图:
    【📸 截图4:后台博文编辑页面截图(证明使用Markdown)】

  2. 发布博客后,已进入班级博客,点击进入作业界面并点击“提交”按钮,确保助教能够评分。

posted on 2026-09-11 19:36  Luminance  阅读(13)  评论(0)    收藏  举报