赞
踩
在前端(当前url)和后端(请求url)的JavaScript交互过程中,通常会存在两者具有不同的源的情况。
源就是协议(http,https),域(localhost,玛雅myapp.com)以及端口(80,8080)的组合。
当前端和后端的源不同时就是跨域。
下图是跨域问题形象解释图:
由于浏览器的同源策略,往往会导致跨域请求失败。
浏览器同源策略浏览器默认只允许同一个网站访问,不允许不同的网站访问。且同源策略只针对Javascript有效。
前端代码:
通过在本地页面中请求http://127.0.0.1:8001下的资源,由于非同源,故浏览器会报错。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<script type="text/javascript" src="https://cdn.jsdelivr.net/npm/vue@2.7.10/dist/vue.js"></script>
<script type="text/javascript" src="https://unpkg.com/axios/dist/axios.min.js"></script>
<title>Document</title>
</head>
<body>
<div id="app">
<h2>演示跨站请求</h2>
<label for="student_id">学号:</label>
<input type="text" id="student_id" v-model.number.lazy="student_id" @change="read_student" placeholder="请输入学生学号">
<p>查询结果为:</p>
<p>{{ stu }}</p>
</div>
<script type="text/javascript">
new Vue({
el:'#app',
data:{
student_id:"",
student:"",
},
methods:{
read_student(){
/*获取http://127.0.0.1:8001源下的资源*/
axios.get("http://127.0.0.1:8001/student",
{params:{student_id:this.student_id}}).then(res => {
this.student=res.data["student_id"]
console.log(this)
this.$set(this,"student",res.data["student_id"])
}),error => {
this.student="请求失败"
}
}
}
})
</script>
</body>
</html>
浏览器报错图片:
而后端服务器是没有报错的,进一步说明同源规则是限制在浏览器端的:
fastapi中解决跨域问题,是通过CORSMiddleware中间件完成的。
首先引入CORSMiddleware类。
from fastapi.middleware.cors import CORSMiddleware
后端处理跨域共享的问题就是通过向浏览器回复时添加上适当的响应头,标识授权了跨域请求,此时浏览器就不会产生跨域请求失败的警告了。
所以后端中要设置是否允许:
参数 | 参数说明 |
---|---|
allow_origins | 一个允许跨域请求的源列表 |
allow_origin_regex | 一个正则表达式字符串,匹配的源允许跨域请求的源 |
allow_methods | 一个允许跨域请求的HTTP方法的列表,[‘GET’]为默认值,可以用[’*’]表示允许所有标准方法 |
allow_headers | 一个允许跨域请求的HTTP请求头列表,默认为[]。 |
allow_credentials | 指示跨域请求支持cookies。默认为False。另外此处为True时,allow_origins不能为[’*’],必须指定源 |
expose_headers | 指示可以被浏览器访问的响应头,默认为[] |
max_age | 设定浏览器缓存CORS相应的最长时间,默认为600S |
#此处仅配置允许跨域请求的源列表
allow_origins = ['*']
通过app.add_middleware函数添加中间件。
app.add_middleware(CORSMiddleware,allow_origins=allow_origins)
这样该app下的路径操作函数就支持了跨域源共享。
完整代码:
from fastapi import FastAPI,Query
# 导入CORSMiddleware类
from fastapi.middleware.cors import CORSMiddleware
app = FastAPI()
#配置跨域配置项
origins = [
"*"
]
# 在app中添加CORSMiddleware中间件
app.add_middleware(
CORSMiddleware,
allow_origins = origins
)
@app.get("/student")
async def read_student(student_id=Query()):
return {"student_id":student_id}
if __name__ == "__main__":
import uvicorn
uvicorn.run(app='main:app',host="127.0.0.1",port=8001,reload=True)
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。