
在充满活力的技术领域中,创新不断塑造着可能的边界,而人工智能(AI)从未停止过吸引我们的想象力。
人工智能是指计算机系统对人类智能过程的模拟。这些过程包括学习、推理、解决问题、感知、和决策等任务。
如今,个人和公司已经开发并训练出了多个人工智能模型,可以比人类更好地实时执行某些任务。在人工智能的无数应用中,一个特别引人关注的领域是人工智能驱动的图像生成。
本指南介绍如何构建一个 React 应用程序,通过 后端与 无缝集成,并根据文本提示生成图像。

运行中的人工智能图像生成器,使用 DALL-E API 生成生动而富有创意的图像。
要参与本项目,您应具备以下条件
OpenAI API 是一个基于云的平台,它允许开发者访问 OpenAI 预先训练好的人工智能模型,如 DALL-E 和 GPT-3(我们使用该模型在此 中的代码)。它允许开发人员在程序中添加摘要、翻译、图像生成和修改等人工智能功能,而无需开发和训练自己的模型。
要使用 OpenAI API,请使用 Google 账户或电子邮件在 上创建一个账户,并获取一个 API 密钥。要生成 API 密钥,请单击网站右上角的 “Personal“,然后选择 “View API keys“。

创建 OpenAI API 密钥的过程。
单击 “Create new secret key” 按钮,并将密匙保存在某处。您将在本应用程序中使用它与 OpenAI 的 DALL-E API 进行交互。
您可以从头开始创建 React 应用程序并开发自己的界面,也可以按照以下步骤获取我们的 Git 启动模板:
git checkout starter-files 。npm install 命令安装必要的依赖项。安装完成后,就可以在本地电脑上使用 npm run start 启动项目。这样,项目就可以在 http://localhost:3000/ 上运行了。

AI 图像生成器应用程序的用户界面,展示了人工智能在图像创建方面的强大功能。
在本项目中,我们为 React 应用程序添加了所有必要的依赖项。以下是已安装内容的概览:
React 应用程序的核心是 src 文件夹。这里存放着 Webpack 的基本 JavaScript 代码。让我们来了解一下 src 文件夹中的文件和文件夹:
了解 Utils 文件夹
在该文件夹中,index.js 文件定义了两个可重复使用的函数。之一个函数会随机选择描述可生成的各种图像的提示。
import { randomPrompts } from '../data';
export const getRandomPrompt = () => {
const randomIndex = Math.floor(Math.random() * randomPrompts.length);
const randomPrompt = randomPrompts[randomIndex];
return randomPrompt;
}
第二个函数利用 file-saver 依赖关系处理生成图像的下载。这两个函数的创建都是为了提供模块化和高效性,在需要时可以方便地导入到组件中。
import FileSaver from 'file-saver';
import { v4 as uuidv4 } from 'uuid';
export async function downloadImage(photo) {
const _id = uuidv4();
FileSaver.saveAs(photo, `download-${_id}.jpg`);
}
在上面的代码中,uuid 属性为每个生成的图像文件提供了一个唯一的 ID,因此它们不会有相同的文件名。
了解组件
组件是分隔开来的小代码块,使代码易于维护和理解。本项目创建了三个组件: Header.jsx、Footer.jsx 和 Form.jsx。主要组件是表单组件,在该组件中,输入被接收并传递到 App.jsx 文件,generateImage 函数被添加为 Generate Image 按钮的 onClick 事件。
在表单组件中,创建了一个状态来存储和更新提示。此外,您还可以通过点击随机图标来生成随机提示。这是通过 handleRandomPrompt 函数实现的,该函数使用了已设置的 getRandomPrompt 函数。当你点击图标时,它会获取随机提示并更新状态:
const handleRandomPrompt = () => {
const randomPrompt = getRandomPrompt();
setPrompt(randomPrompt)
}
了解 App.jsx 文件
大部分代码都在这里。所有组件都集中在这里。还有一个指定区域用于显示生成的图片。如果尚未生成图像,则会显示一个占位符图像(预览图像)。
在该文件中,有两种状态需要管理:
isGenerating: 用于跟踪图像当前是否正在生成。默认设置为 false。generatedImage: 该状态存储已生成图像的相关信息。此外,还导入了 downloadImage 实用程序函数,使您可以在单击 Download 按钮时触发生成图像的下载:
<button
className="btn"
onClick={() => downloadImage(generatedImage.photo)}
>
现在,您已经了解了启动文件并设置了项目。让我们开始处理这个应用程序的逻辑。
要利用 OpenAI 的 DALL-E API 功能,您需要使用 Node.js 建立一个服务器。在该服务器中,您将创建一个 POST 路由。该路由将负责接收从 React 应用程序发送的提示文本,然后利用它生成图像。
要开始工作,请运行以下命令在项目目录中安装必要的依赖项:
npm i express cors openai
此外,将以下依赖项安装为开发依赖项。这些工具将帮助您设置 Node.js 服务器:
npm i -D dotenv nodemon
已安装的依赖项说明如下:
安装成功后,在项目根目录下创建 server.js 文件。所有服务器代码都将存放在这里。
在 server.js 文件中,导入刚安装的并将其实例化:
// Import the necessary libraries
const express = require('express');
const cors = require('cors');
require('dotenv').config();
const OpenAI = require('openai');
// Create an instance of the Express application
const app = express();
// Enable Cross-Origin Resource Sharing (CORS)
app.use(cors());
// Configure Express to parse *** ON data and set a data limit
app.use(express.json({ limit: '50mb' }));
// Create an instance of the OpenAI class and provide your API key
const openai = new OpenAI({
apiKey: process.env.OPENAI_API_KEY,
});
// Define a function to start the server
const startServer = async () => {
app.listen(8080, () => console.log('Server started on port 8080'));
};
// Call the startServer function to begin listening on the specified port
startServer();
在上面的代码中,你需要导入必要的库。然后,使用 const app = express(); 建立一个 Express 应用程序实例。然后,启用 CORS。接下来,配置 Express 以处理传入的 *** ON 数据,并指定数据大小限制为 50MB。
随后,使用 OpenAI API 密钥创建 OpenAI 类实例。在项目根目录下创建 .env 文件,并使用 OPENAI_API_KEY 变量添加 API 密钥。最后,定义异步 startServer 函数并调用它来启动服务器。
现在你已经配置好了 server.js 文件。让我们创建一个 POST 路由,您可以在 React 应用程序中使用该路由与服务器交互:
app.post('/api', async (req, res) => {
try {
const { prompt } = req.body;
const response = await openai.images.generate({
prompt,
n: 1,
size: '1024x1024',
response_format: 'b64_json',
});
const image = response.data[0].b64_json;
res.status(200).json({ photo: image });
} catch (error) {
console.error(error);
}
});
在这段代码中,路由设置为 /api ,旨在处理传入的 POST 请求。在路由的回调函数中,您将使用 req.body 接收到从 React 应用程序发送的数据,特别是 prompt 值。
随后,会调用 OpenAI 库的 images.generate *** 。该 *** 接收所提供的提示并生成图像作为响应。n 等参数决定了要生成的图片数量(这里只有一张),size 指定了图片的尺寸,response_format 则指示了应提供的响应格式(本例中为 b64_json )。
生成图片后,从响应中提取图片数据并存储到 image 变量中。然后,使用 res.status(200).json({ photo: image }) 向 React 应用程序发送包含生成的图像数据的 *** ON 响应,并将 HTTP 状态设置为 200(表示成功)。
如果在此过程中出现任何错误,将执行 catch 代码块中的代码,并将错误记录到控制台以便调试。
现在服务器已经准备就绪!让我们在 package.json 文件 scripts 对象中指定用于运行服务器的命令:
"scripts": {
"dev:frontend": "react-scripts start",
"dev:backend": "nodemon server.js",
"build": "react-scripts build",
},
现在运行 npm run dev:backend 时,服务器将在 http://localhost:8080/ 上启动,而运行 npm run dev:frontend 时,React 应用程序将在 http://localhost:3000/ 上启动。确保两者在不同的终端运行。
在 App.jsx 文件中,您将创建一个 generateImage 函数,当点击 Form.jsx 组件中的 Generate Image(生成图片)按钮时触发该函数。该函数接受两个参数:来自 Form.jsx 组件的 prompt 和 setPrompt 。
在 generateImage 函数中,向 Node.js 服务器发出 HTTP POST 请求:
const generateImage = async (prompt, setPrompt) => {
if (prompt) {
try {
setIsGenerating(true);
const response = await fetch(
'http://localhost:8080/api',
{
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: *** ON.stringify({
prompt,
}),
}
);
const data = await response.json();
setGeneratedImage({
photo: `data:image/jpeg;base64,${data.photo}`,
altText: prompt,
});
} catch (err) {
alert(err);
} finally {
setPrompt('');
setIsGenerating(false);
}
} else {
alert('Please provide proper prompt');
}
};
在上面的代码中,您要检查 prompt 参数是否有值,然后将 isGenerating 状态设为 true ,因为操作正在开始。这将使加载器显示在屏幕上,因为在 App.jsx 文件中,我们有这段代码控制加载器的显示:
{isGenerating && (
<div> className="loader-comp">
<img src={Loader} alt="" className='loader-img' />
</div>
)}
接下来,使用 fetch() *** ,使用 http://localhost:8080/api 向服务器发出 POST 请求–这就是我们安装 CORS 的原因,因为我们正在与另一个 URL 上的 API 交互。我们使用提示作为消息正文。然后,提取 Node.js 服务器返回的响应,并将其设置为 generatedImage 状态。
一旦 generatedImage 状态有了值,图片就会显示出来:
{generatedImage.photo ? (
<img
src={generatedImage.photo}
alt={generatedImage.altText}
className="imgg ai-img"
/>
) : (
<img
src={preview}
alt="preview"
className="imgg preview-img"
/>
)}
这就是 App.jsx 文件的完整内容:
import { Form, Footer, Header } from './components';
import preview from './assets/preview.png';
import Loader from './assets/loader-3.gif'
import { downloadImage } from './utils';
import { useState } from 'react';
const App = () => {
const [isGenerating, setIsGenerating] = useState(false);
const [generatedImage, setGeneratedImage] = useState({
photo: null,
altText: null,
});
const generateImage = async (prompt, setPrompt) => {
if (prompt) {
try {
setIsGenerating(true);
const response = await fetch(
'http://localhost:8080/api',
{
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: *** ON.stringify({
prompt,
}),
}
);
const data = await response.json();
setGeneratedImage({
photo: `data:image/jpeg;base64,${data.photo}`,
altText: prompt,
});
} catch (err) {
alert(err);
} finally {
setPrompt('');
setIsGenerating(false);
}
} else {
alert('Please provide proper prompt');
}
};
return (
<div className='container'>
<Header />
<main className="flex-container">
<Form generateImage={generateImage} prompt={prompt} />
<div className="image-container">
{generatedImage.photo ? (
<img
src={generatedImage.photo}
alt={generatedImage.altText}
className="imgg ai-img"
/>
) : (
<img
src={preview}
alt="preview"
className="imgg preview-img"
/>
)}
{isGenerating && (
<div className="loader-comp">
<img src={Loader} alt="" className='loader-img' />
</div>
)}
<button
className="btn"
onClick={() => downloadImage(generatedImage.photo)}
>
Download
</button>
</div>
</main>
<Footer />
</div>
);
};
export default App;
到目前为止,您已经成功构建了一个能与 Node.js 交互的 React 应用程序,这使它成为一个全栈应用程序。现在让我们将此应用程序部署到 Kinsta。
首先,配置服务器,以便为 React 应用程序构建过程中生成的静态文件提供服务。这可以通过导入 path 模块并使用它来提供静态文件来实现:
const path = require('path');
app.use(express.static(path.resolve(__dirname, './build')));
当您执行 npm run build && npm run dev:backend 命令时,您的全栈 React 应用程序将加载到 http://localhost:8080/。这是因为 React 应用程序已编译成 build 文件夹中的静态文件。然后,这些文件将作为静态目录并入 Node.js 服务器。因此,当您运行 Node 服务器时,就可以访问应用程序。
在将代码部署到您选择的 Git 提供商(Bitbucket、GitHub 或 Gitlab)之前,请记住修改 App.jsx 文件中的 HTTP 请求 URL。将 http://localhost:8080/api 改为 /api ,因为 URL 将被预输入。
最后,在 package.json 文件中,为用于部署的 Node.js 服务器添加一个脚本命令:
"scripts": {
// …
"start": "node server.js",
},
接下来,按照以下步骤将代码推送到您首选的 Git 提供商,并将您的仓库部署到 Kinsta:
OPENAI_API_KEY 添加为环境变量。Kinsta 会自动为你设置一个 Dockerfile。npm run build && npm run start 。Kinsta 会从 package.json 安装应用程序的依赖项,然后构建并部署应用程序。小结在本指南中,您将学习如何利用 OpenAI 的 DALL-E API 的强大功能来生成图像。您还学会了如何使用 React 和 Node.js 构建基本的全栈应用程序。
人工智能的可能性是无限的,因为每天都有新的模型问世,您可以创建令人惊叹的项目,并将其部署到应用程序托管中。
不久前,PHP 8.0大张旗鼓地发布了。它带来了许多新特性、性能增强和变化——其中最令人兴奋的是新的JIT编译器。 技术世界总是在向前发展,PHP也是如此。 ,包含了几个令人兴奋的特性。它定于今年晚些时候于2021年11月25日发布。 在本文中,我们将详细介绍PHP 8.1将带来哪些新的东...
宝塔的数据库管理,是基于phpmyadmin管理和新建数据库。其最大的便利性就是类似,通过面板可以快速访问进行管理操作,无需单独访问phpmyadmin的主页。 此外,在宝塔面板进行数据库管理,你也对数据库名、用户名及密码等信息一目了然,及可以对数据库执行快速备份或者导入。 添加数据...
宝塔面板另外一个特质是,你无需通过Linux命令行来查看服务器各项指标状况,即可以阿里云服务器类似的可视化图表,查看资源使用、负载、CPU占用及内容使用百分比等指标。 默认监控是关闭,有需要的,可以开启,监控数据默认保存30天,可以自行修改,默认监控数据保存在日志,可手动清理该日志。 监控管理,...
宝塔面板其中一个最为便捷的功能之一,无需SFTP或者FTP即可对服务器的文件内容进行上传、下载、编辑及删除等管理操作。 文件管理,用于管理该服务器上的文件内容。 文件的基础操作 文件的基础操作有哪些了,主要有这些方面:复制、粘贴、剪切、删除、重命名、压缩、刷新、新建文件、新建目录。...
宝塔面板的计划任务,主要用于安排和管理需要定时执行的任务,如备份、内存清理等。其实对于大部分站长来说,主要使用该板块的备份网站、备份数据库及释放内存的三个定时任务计划。 Shell脚本的添加 输入任务名称,选择执行周期,输入执行的脚本内容。 注意事项: 输入脚本内容...
经过几个小时的努力工作后,您是否感到眼睛疲劳或难以阅读代码?许多程序员在开始头疼之前从没想过要切换字体。 如果您经常发现在尝试扫描一千行代码时眼睛模糊不清,或者在停止编码数小时后头疼,那么可能是时候尝试一种新字体了。即使您没有遇到这些症状,设计良好的字体通常也比默认系统字体具有更好的可读性。...