作者:Madars Bišs
React是一个流行的库,用于创建动态和交互式用户界面。 React出现了许多框架,以避免为全堆栈应用程序创建CRUD操作和其他功能的重复过程。
在本文中,我们将回顾两种常见的解决方案-refine和Blitz。通过提供一系列高级的工具和功能,均旨在加快和简化开发React应用程序的过程。
我们将仔细研究如何设置两个,它们的内部构建,如何处理数据源,如何实现CRUD功能,添加身份验证以及如何将它们部署到生产中。
关于框架
精炼
精炼是一个基于React的框架,专门设计用于加快数据密集型应用程序的创建。这是一个open-source项目,这意味着每个人都可以访问并贡献代码。
从其核心性质上讲,它是一个基于挂钩,组件和提供商的集合的无头框架。核心与UI和业务逻辑完全分离,这意味着用户具有完全灵活的环境。
精炼框架成立于2021年,目睹了快速增长,并从那以后吸引了一个积极的社区。截至写作时,该框架已经到达8k Github星星。
闪电战
Blitz是一个建立在NextJs顶部的全堆栈Web框架,这意味着它保留了许多核心功能,例如服务器端渲染,静态站点生成和自动代码分配。
此外,这是NextJS工具包,它提供了创建特征丰富的应用程序,添加身份验证,类型安全的API层等功能的必要部分。
Blitz也是一个open-source项目,允许用户访问代码并允许贡献。他们的社区也产生了很大的影响,自2020年创作以来,随着时间的流逝,他们的社区也迅速发展:
安装指南
精炼
PRIFINE随附项目启动工具,该工具允许用户在几分钟内设置一个完全工作的环境。
运行命令npm create refine-app@latest crud-refine
。这将启动CLI向导,要求您配置项目。为了本教程的目的,选择如下所示的值:
安装过程不得超过一分钟。
完成后,将工作目录更改为cd crud-refine
新创建的项目并运行npm run dev
以启动开发人员服务器。
应该自动打开一个新的浏览器窗口。如果不是这样,请手动导航到localhost:3000,您将获得精炼的欢迎屏幕:
闪电战
要设置Blitz应用程序,用户必须首先安装Blitz CLI。您可以通过在终端中执行命令npm install -g blitz
或yarn global add blitz
来执行此操作。
接下来,运行命令blitz new crud-blitz
。这将启动终端CLI向导要求您配置项目。为了本教程的目的,请选择以下所示值:
之后,通过运行cd crud-blitz
将工作目录更改为新创建的项目,并通过运行blitz dev
启动开发服务器。
最后,打开浏览器并导航到localhost:3000。这应该向您提供闪电战的欢迎屏幕:
内部结构
精炼
完善的文件结构非常简单,它们为用户提供了他们想要建立的所有灵活性。整个应用程序的主要构建块是src
文件夹。
它带有以下代码的App.tsx
文件:
import { Refine } from "@refinedev/core";
import { notificationProvider } from "@refinedev/antd";
import "@refinedev/antd/dist/reset.css";
import { useAuth0 } from "@auth0/auth0-react";
import routerBindings, {
UnsavedChangesNotifier,
} from "@refinedev/react-router-v6";
import dataProvider from "@refinedev/simple-rest";
import axios from "axios";
import { BrowserRouter } from "react-router-dom";
function App() {
const { isLoading, user, logout, getIdTokenClaims } = useAuth0();
if (isLoading) {
return <span>loading...</span>;
}
const authProvider: AuthBindings = {
login: async () => {
return {
success: true,
};
},
logout: async () => {
logout({ returnTo: window.location.origin });
return {
success: true,
};
},
onError: async (error) => {
console.error(error);
return { error };
},
check: async () => {
try {
const token = await getIdTokenClaims();
if (token) {
axios.defaults.headers.common = {
Authorization: `Bearer ${token.__raw}`,
};
return {
authenticated: true,
};
} else {
return {
authenticated: false,
error: new Error("Token not found"),
redirectTo: "/login",
logout: true,
};
}
} catch (error: any) {
return {
authenticated: false,
error: new Error(error),
redirectTo: "/login",
logout: true,
};
}
},
getPermissions: async () => null,
getIdentity: async () => {
if (user) {
return {
...user,
avatar: user.picture,
};
}
return null;
},
};
return (
<Refine
dataProvider={dataProvider("https://api.fake-rest.refine.dev")}
notificationProvider={notificationProvider}
Layout={Layout}
ReadyPage={ReadyPage}
catchAll={<ErrorComponent />}
routerProvider={routerProvider}
authProvider={authProvider}
LoginPage={Login}
/>
);
}
export default App;
首先,导入了主Refine
组件和必要的辅助组件,例如Layout
,ReadyPage
和ErrorComponent
。然后,导入了样式表文件,数据和路由器的提供商以及auth组件。
在App
函数中首先处理了身份逻辑,然后在渲染块中,所有导入的助手组件和提供商都将其传递给主Refine
组件。
为了在屏幕上显示结果,来自App.tsx
的所有导出内容均已导入并渲染到index.tsx
文件中的DOM:
import React from "react";
import { createRoot } from "react-dom/client";
import { Auth0Provider } from "@auth0/auth0-react";
import reportWebVitals from "./reportWebVitals";
import App from "./App";
const container = document.getElementById("root") as HTMLElement;
const root = createRoot(container);
root.render(
<React.StrictMode>
<Auth0Provider
domain="your-auth0-domain-address"
clientId="your-auth0-clientId"
redirectUri={window.location.origin}
>
<App />
</Auth0Provider>
</React.StrictMode>
);
请注意,App
组件包裹在Auth0Provider
中,以便可以在整个应用程序中访问身份验证。
闪电战
Blitz提供了更复杂的类似框架的文件结构,其中已经有预定义的方法处理和分开与全堆栈应用程序相关的通用概念。
文件结构如下:
├── src/
│ ├── auth/
│ │ ├── components/
│ │ │ ├── LoginForm.tsx
│ │ │ └── SignupForm.tsx
│ │ ├── mutations/
│ │ │ ├── changePassword.ts
│ │ │ ├── forgotPassword.test.ts
│ │ │ ├── forgotPassword.ts
│ │ │ ├── login.ts
│ │ │ ├── logout.ts
│ │ │ ├── resetPassword.test.ts
│ │ │ ├── resetPassword.ts
│ │ │ └── signup.ts
│ │ └── validations.ts
│ ├── core/
│ │ ├── components/
│ │ │ ├── Form.tsx
│ │ │ └── LabeledTextField.tsx
│ │ └── layouts/
│ │ └── Layout.tsx
│ ├── users/
│ │ ├── hooks/
│ │ │ └── useCurrentUser.ts
│ │ └── queries/
│ │ └── getCurrentUser.ts
│ ├── pages/
│ │ ├── api/
│ │ │ └── rpc/
│ │ │ └── [[...blitz]].ts
│ │ ├── auth/
│ │ │ ├── forgot-password.tsx
│ │ │ ├── login.tsx
│ │ │ └── signup.tsx
│ │ ├── _app.tsx
│ │ ├── _document.tsx
│ │ ├── 404.tsx
│ │ └── index.tsx
│ ├── blitz-client.ts
│ └── blitz-server.ts
├── db/
│ ├── migrations/
│ ├── index.ts
│ ├── schema.prisma
│ └── seeds.ts
├── integrations/
├── public/
│ ├── favicon.ico*
│ └── logo.png
├── test/
└── setup.ts
└── utils.tsx
项目结构分为多个主要块-src
,db
,integrations
,public
和test
。
核心应用程序代码在src
中列出,该代码在auth
中进一步划分,由用于身份验证的组件和突变组成,core
用于形式和布局组件,users
,用于处理用户和pages
的挂钩和查询,将创建API和路线。
db
文件夹包括项目数据库的所有必要配置,模式和迁移文件。
如果您使用一些第三方库或代码,则将它们与其他代码的其余部分分开是一个很好的做法。 Blitz为此保留了integrations
文件夹。
public
文件夹适用于该应用程序root URL静态提供的所有媒体资产和文件。
还有一个专用的test
文件夹,用于设置和实用程序附带的测试,以帮助您开始。
数据提供商
精炼
精炼带有一个假数据提供商,非常适合测试或创建一些您需要一些占位符数据的页面。
这是一个简单的REST API端点,包含有关用户,帖子,产品,类别等的示例数据,并且可以通过api.fake-rest.refine.dev访问。
如果我们单击用户界面中的任何路由,我们可以看到它们每个路由都包含JSON数据。例如,/products
端点以以下格式保存样本:
为了在精炼项目中使用数据提供商,用户需要将其传递给App.tsx
中的Refine
组件:
<Refine
dataProvider={dataProvider("https://api.fake-rest.refine.dev")}
// ...
/>
如果您遵循安装向导的说明,则应通过自动进行精炼进行设置。
闪电战
Blitz Framework并不是其自己的数据提供商,但是很棒的是,在安装过程中,它配置了SQLITE数据库,该数据库足以进行测试和实验。
数据库配置可在schema.prisma
文件中使用。您将在应用程序根的db
文件夹中找到它。它包括应用程序中使用的数据库配置和模型:
datasource db {
provider = "sqlite"
url = env("DATABASE_URL")
}
generator client {
provider = "prisma-client-js"
}
model User {
id Int @id @default(autoincrement())
createdAt DateTime @default(now()
name String?
email String @unique
}
// ...
另一个很棒的事情是,使用Blitz可以运行blitz prisma studio
在浏览器中打开Web界面并查看数据库中的所有数据。
如果UI不自动打开,请导航到localhost:5555:
验证
精炼
创建一个新的免费Auth0 account并登录。
创建一个新的Web应用程序。
它将为您提供域,客户端ID和秘密ID信息。
向下滚动并将localhost:3000添加到允许的URL列表中。
接下来,切换回您的代码编辑器,然后在项目root中创建一个新文件.env
,添加变量REACT_APP_AUTH0_DOMAIN
和REACT_APP_AUTH0_CLIENT_ID
,然后从auth0 dashboard中分配值。
接下来,在src
文件夹中编辑index.tsx
文件,因此现在看起来像这样:
import React from "react";
import { createRoot } from "react-dom/client";
import { Auth0Provider } from "@auth0/auth0-react";
import App from "./App";
const container = document.getElementById("root") as HTMLElement;
const root = createRoot(container);
root.render(
<React.StrictMode>
<Auth0Provider
domain={process.env.REACT_APP_AUTH0_DOMAIN as string}
clientId={process.env.REACT_APP_AUTH0_CLIENT_ID as string}
redirectUri={window.location.origin}
>
<App />
</Auth0Provider>
</React.StrictMode>
);
现在,通过按键盘上的Ctrl
+ C
重置开发人员服务器,然后运行命令npm run dev
重新启动它。这样,新的环境价值将生效。
现在打开您的浏览器并导航到localhost:3000,您应该在登录屏幕上显示:
闪电战
闪电战的伟大之处在于它已经具有注册和登录的身份验证视图。它还为其配置了数据库,因此您不必担心为此创建单独的模型和运行迁移。
注册页应在localhost:3000/auth/signup上找到:
登录页面应在localhost:3000/auth/login上找到:
创建一个新帐户并注册,因此我们在SQLite数据库中有一个用户记录,您可以登录以访问我们将进一步构建的页面。
创建页面
精炼
借助其内置命令create-resource
,在精炼中创建新页面真的很简单。由于它针对CRUD应用程序,因此允许用户选择要通过flags list
,create
,edit
和show
生成哪种类型的页面。
为了全面了解如何在精炼中创建新页面,我们将首先创建一个列出内容的页面。在您的终端中运行命令npm run refine create-resource products -- --actions list
。
导航回您的项目文件树,您会发现创建了一个新的文件夹pages
。里面有一个特定的路由文件夹products
,其中包括文件index.ts
和list.tsx
。
打开list.tsx
文件,您会注意到精炼甚至设计了Inferencer
组件,该组件将自动帮助您根据数据结构设计资源的视图:
import { IResourceComponentsProps, GetListResponse } from "@pankod/refine-core";
import { AntdInferencer } from "@pankod/refine-inferencer/antd";
export const ProductsList: React.FC<
IResourceComponentsProps<GetListResponse<{}>>
> = () => {
return <AntdInferencer />;
};
还注意,新创建的列表页面是自动导入的,并将其作为resource
prop中的Refine
组件中的cd crud-blitz
prop传递到App.tsx
:
<Refine
dataProvider={dataProvider("https://api.fake-rest.refine.dev")}
notificationProvider={notificationProvider}
Layout={Layout}
ReadyPage={ReadyPage}
catchAll={<ErrorComponent />}
routerProvider={routerProvider}
authProvider={authProvider}
LoginPage={Login}
resources={[
{
name: "products",
list: ProductsList,
},
]}
/>
现在打开浏览器并导航到localhost:3000/products。您应该向您提供页面,该页面列出了来自精炼的内置数据提供商的/products
路线的数据:
闪电战
Blitz不带Inferencer
组件,该组件会创建一个默认视图以显示数据,因此我们将创建一个自定义页面。
如果您以前曾与NextJS合作,则会注意到页面系统相同。对于一个新页面,您需要在pages
文件夹中创建一个新的.tsx
文件,并且它将成为一条新路线。
要测试它,创建一个新的文件greet.tsx
并包括以下代码:
const Greet = () => {
return (
<div>
<h1>Hello from Blitz!</h1>
<p>This is a custom Greetings page!</p>
</div>
);
};
export default Greet;
现在打开您的浏览器并导航到localhost:3000/greet,应该向您提供新创建的页面的渲染内容:
CRUD功能
精炼
精炼已经考虑了如何使Crud操作尽可能容易。运行命令npm run refine create-resource posts
。
这将从数据提供商中为/posts
路线创建一个新页面,但是由于我们没有提供有关支持哪些特定操作的任何标志,因此所有CRUD操作都将可用。
这意味着在运行命令后,在pages
中创建了一个名为posts
的新文件夹,并用文件填充了index.ts
,list.tsx
,create.tsx
,create.tsx
,edit.tsx
和show.tsx
。
现在,打开您的浏览器并导航到localhost:3000/posts。
您应该能够查看来自/posts
路线的所有数据,但是这次您会注意到有动作按钮可以创建,阅读,更新和删除记录:
闪电战
要演示CRUD功能以及在闪电战中实现一个功能的简单性,我们将构建一个待办事项应用程序,使我们能够创建,阅读,更新和删除每日任务。
运行命令blitz generate all todo name:string
。这将创建必要的模型,查询,突变和页面路由。我们还以待办事项任务值的string
类型传递。
与精炼型脚手架类似,Blitz负责为创建,读取,更新和删除待办事项的操作创建单独的文件。
要测试它,请按键盘上的Ctrl
+ C
重新启动开发人员服务器,然后运行blitz dev
。然后打开浏览器并导航到localhost:3000/todos。
这将显示CRUD页面的着陆,要求您创建第一个任务,因为我们当前在数据库中没有任何数据:
测试CRUD
精炼
创建记录单击右上角的“创建”按钮。
这将打开带有空字段的表单,允许您输入值并保存新记录。
要阅读已经存在的记录,请单击每个记录右侧的眼睛图标。
它将以仅读取模式以所有值打开记录。
为了更新现有记录,请单击“眼睛图标”旁边的铅笔图标。
这将打开所有值可编辑的表单。
要删除帖子,请单击“眼睛图标”旁边的bin图标。它还将显示一个确认弹出窗口,以确保您不会错误地删除记录。
闪电战
要创建一个新任务,请单击“创建todo”。它将打开一个空的表格,您可以在其中命名任务的名称。
读取创建的记录导航到任务列表,然后单击特定任务。这将在仅阅读模式下打开所选记录。
为了编辑现有记录,然后单击“编辑”按钮。这将使您可以更改创建的待办事项任务的标题。
删除任务打开它并单击“删除”按钮。
部署
精炼
首先,请确保您有GitHub account。如果您没有一个,请确保免费使用create one。
接下来,登录并创建一个new repository。
现在切换回您的代码编辑器,然后运行以下命令将代码推到新创建的存储库:
git remote add origin https://github.com/username/crud-refine.git
git branch -M main
git push -u origin main
将代码推回github存储库后,您应该看到所有的代码:
要确保您的应用程序已在生产中部署并在线访问中,您还必须将其部署给某些托管提供商,例如Vercel。
首先,创建一个新的free account,如果您还没有并登录。
然后通过从Git中选择“选项”来创建一个新项目。在列表中找到您的github项目,然后单击“导入”。
Vercel将自动为您配置所有内容,您要做的就是手动添加.env
文件中的环境密钥和值:
完成此操作后,单击部署,完成部署过程后,将为您提供实时访问链接。
您要做的最后一件事是切换回AUTH0,然后将允许的URL更改为Vercel给出的部署URL(以前这些值已将其设置为localhost:3000)。
闪电战
我们将使用Render,这将使我们可以部署应用程序和数据库。
首先,将数据库提供商更改为PostgreSQL。为此打开schema.prisma
文件并更改数据源,如下所示:
datasource db {
provider = "postgres"
url = env("DATABASE_URL")
}
// ...
然后删除db/migrations
文件夹,因此没有以前的迁移历史记录,也没有针对数据库类型的.lock
文件。
然后,在您的项目root中创建一个新文件render.yaml
,并包括以下配置设置:
services:
- type: web
name: crud-blitz
env: node
plan: free
buildCommand: npm i --prod=false &&
blitz prisma generate &&
blitz build &&
blitz prisma migrate deploy
startCommand: blitz start -p ${PORT}
envVars:
- key: NODE_ENV
value: production
- key: DATABASE_URL
fromDatabase:
name: crud-blitz-db
property: connectionString
- key: SESSION_SECRET_KEY
generateValue: true
databases:
- name: crud-blitz-db
plan: free
现在将代码推到GitHub。
创建一个free account如果您还没有并登录。
接下来,创建一个new repository。
切换回您的代码编辑器,然后在终端中运行以下命令:
git remote add origin https://github.com/username/crud-blitz.git
git branch -M main
git push -u origin main
然后切换回GitHub,您会发现所有同步的所有内容。
接下来,在渲染上创建一个free account并登录。
单击“ new”,然后选择“蓝图”选项。
接下来,连接您的github帐户并在列表中找到您的项目。
接下来,给蓝图一个名称,然后单击“应用”,因此使用您的.yaml
配置来设置所有内容。
设置可能需要几分钟。
完成后,它将为您提供实时访问链接。
结论
在本文中,我们比较了两个React框架 - 精炼和闪电战。默认情况下,两者都具有打字稿的支持,易于设置,带有CLI命令,并且不需要使用特定的UI框架。
精炼具有内置数据提供商。这非常适合测试和实验。相比之下,Blitz与SQLite和Prisma Studio有关,它为UI提供了与数据一起使用的。
对于数据表来说,精炼剂带有推论器,该推论器已经在易于感知的UI中构建了数据。对于Blitz,您必须自己构建桌子,操作按钮和其他组件。
Blitz应用程序已经设置为注册,登录和忘记密码视图,模型已经创建以存储用户和数据库中的会话。对于完善,您将必须从头开始创建。
从项目树的角度来看,Blitz看起来更像是一个框架。对于那些希望在如何构建项目方面具有很高灵活性的人,您将不得不处理大多数流量已经遵循某种模式的事实。
精炼实际上是挂钩,组件和提供商的集合,因此用户可以根据其个人需求完全设计该应用程序,并根据其业务模式遵循特定的逻辑模式。