如何连接Vue.js作为前端和FastAPI作为后端?

omjgkv6w  于 2022-11-17  发布在  Vue.js
关注(0)|答案(3)|浏览(244)

我正在建立一个项目的工作门户,我需要Vue作为前端和FastAPI作为后端的添加,删除,更新。我想知道我是否可以连接这两个或没有。

hgc7kmma

hgc7kmma1#

我想知道我是否能将这两者联系起来。

快速解答:是的,您可以联机。

但是有很多方法,你可以用像Jinja这样的东西来渲染模板,或者你可以用像Vue CLI这样的东西来创建一个完全不同的项目,你可能想用像Nginx或Apache这样的东西来连接两者。
让我们使用Jinja创建一个示例应用程序
结构

├── main.py
└── templates
    └── home.html

后端-main.py

  • 我们在/中提供前端服务,并在该路径中呈现home.html
  • 我们使用templates文件夹来保存HTML并将其传递给Jinja。
  • 此外,我们将从前端向/add发送请求。
from fastapi import FastAPI, Request
from fastapi.templating import Jinja2Templates
from pydantic import BaseModel

templates = Jinja2Templates(directory="templates") 

app = FastAPI()

class TextArea(BaseModel):
    content: str

@app.post("/add")
async def post_textarea(data: TextArea):
    print(data.dict())
    return {**data.dict()}

@app.get("/")
async def serve_home(request: Request):
    return templates.TemplateResponse("home.html", {"request": request})

前端-home.html

  • 让我们创建一个虚拟应用程序,它有一个文本区域和按钮。
  • 我们正在使用Axios将请求发送到后端。
  • 由于它们在同一端口上运行,我们可以直接将/add传递给Axios。
<html>
<title></title>
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>

<body>
    <div id="app">
        <textarea name="" id="content" cols="30" rows="10" v-model="content"></textarea>
        <button @click="addText" id="add-textarea">click me</button>
    </div>

    <script>
        new Vue({
            el: "#app",
            data: {
                title: '',
                content: ''
            },
            methods: {
                addText() {
                    return axios.post("/add", {
                        content: this.content
                    }, {
                        headers: {
                            'Content-type': 'application/json',
                        }
                    }).then((response) => {
                        console.log("content: " + this.content);
                    });
                }
            }
        });
    </script>
</body>

</html>

最后,你会有一个看起来很糟糕的textarea和一个按钮。但它会帮助你更好地理解事情。

{'content': 'Hello textarea!'}
INFO:     127.0.0.1:51682 - "POST /add HTTP/1.1" 200 OK
zed5wv10

zed5wv102#

你可以这样做,在相当干净的方式海事组织。我能想出的最好的是使用节点。js/npm捆绑Vue应用程序到一个dist/文件夹(默认)

vue-cli-service build

然后,我使用如下所示的项目文件夹结构

├── dist/ <- Vue-CLI output
    └── index.html
├── src/ <- Vue source files
└── app.py

要归档相同的项目设置,只需使用vue create初始化一个Vue项目,然后在同一个文件夹中创建Python项目(例如,使用Pycharm之类的IDE,确保不要用另一个覆盖一个)。
然后您可以使用FastAPI.staticfiles.StaticFiles为它们服务

# app.py

app.mount('/', StaticFiles(directory='dist', html=True))

记住把上面的app.mount()行放在所有其他路由之后,因为它会覆盖后面的所有路由。
您甚至可以使用vue-cli-service build --watch,这样Vue代码中的每一个更改都会立即反映在HTML文件中,您所需要做的就是在浏览器上按F5键来查看这些更改。
您也可以使用vue-cli-service build --dest=<folder name>dist文件夹输出更改为其他内容,并更改上面app.mount()行中的directory参数。(根据Vue-CLI文档)
下面是我使用该设置的一个项目:https://github.com/KhanhhNe/sshmanager-v2

rekjcdws

rekjcdws3#

这里有两个解决方案,可以将Vue用于整个前端,您可以修改vue.config.js文件:

const { defineConfig } = require('@vue/cli-service')
const path = require('path');

module.exports = defineConfig({
  transpileDependencies: true,    //Transpile your dependencies
  publicPath: "/static",          //Path of static directory
  outputDir: path.resolve(__dirname, '../static'),   // Output path for the static files
  runtimeCompiler: true,
  devServer: {
    // Write files to disk in dev mode, so FastAPI can serve the assets
    port: 8080,
    devMiddleware: {
      writeToDisk: true,
    }
  },
})

然后,在vue-cli中,您可以运行build或serve(在任务页中),也可以在控制台中运行

npm run build

这将把你的静态文件转移到你在vue.config.js文件中设置的输出文件夹。
"没有Jinja"
接下来,转到Fastapi上的main.py,并添加以下两行

from fastapi import FastAPI
from fastapi.staticfiles import StaticFiles   #<-- Add this

app = FastAPI()

#static files & load
app.mount("/", StaticFiles(directory="static", html = True), name="static") #<-- Add this

静态文件夹中应该有一个index.html页面,带有app.mount("/", StaticFiles(directory="static", html = True), name="static")的行设置静态文件路径的目录,并将html文件加载到“/"。
您可以使用GraphQL库进行添加、删除、更新和查询

与金家2

转到Fastapi上的main.py并添加下面两行

from fastapi import FastAPI, Request
from fastapi.templating import Jinja2Templates 
from fastapi.staticfiles import StaticFiles   

app = FastAPI()

#static files & load
app.mount("/static", StaticFiles(directory="static", html = True), name="static") 
templates = Jinja2Templates(directory="static")

@app.get("/")
async def serve_home(request: Request):
    return templates.TemplateResponse("index.html", {"request": request})

在这里,被传输的index.html页面被加载为jinja模板。

相关问题