我试图创建一个函数,让我从前端的输入中选择一个文件,然后将文件传递到后端FastAPI,并最终将文件上传到Azure Blob存储。我的前端代码如下:
//front end
async function handleSubmit(){
const formdata = new FormData();
formdata.append(
"file",
file[0],
)
const headers={'Content-Type': file[0].type}
await axios.post("/uploadfile",formdata,headers)
.then(function (response) {
console.log(response)
});
}
后端FastAPI -我尝试的两个方法
//Backend FastAPI
@app.post("/uploadfile") //currently using
async def create_upload_file(file: UploadFile):
name = file.filename
type = file.content_type
return uploadtoazure(file,name,type)
@app.post("/files") //another method I tried
async def create_file(file: bytes= File()):
await uploadtoazure(file)
和uploadtoazure()函数
//Backend uploadtoazure() function
async def uploadtoazure(f,n,t):
connect_str = ""//removed from sample code
blob_service_client = BlobServiceClient.from_connection_string(connect_str)
container_name = "notes"
file = f.read()
local_file_name = n
cnt_settings = ContentSettings(content_type=t)
blob_client = blob_service_client.get_blob_client(container=container_name, blob=local_file_name)
blob_client.upload_blob(file,cnt_settings)
错误不断出现,当我尝试另一种方法时,另一个新的错误使我无法继续前进。
我意识到一些问题:
blob_client.upload_blob()
只接受某些类型的文件,其中我从API传入的文件类型不是其中之一。- 我使用了https://fastapi.tiangolo.com/tutorial/request-files/In中的示例代码,我不太确定
UploadFile
和File()
类的特性。 - 当我使用文件传递给API的方法是
file: bytes= File()
时,文件类型似乎能够上传到blob存储,但它没有内容类型或后缀,因此我认为找到一种方法来传递文件的content_type可能是另一种解决方案,但它比我想象的更难。
我希望有足够的信息,我迫切需要有人来澄清我的困惑。非常感谢。
你已经很接近了,但是还有一些改进。例如,您同时使用同步和异步代码。这导致了一些令人困惑的问题,比如不等待f.read()
,而这是一个异步方法。此外,您不必将内容类型传递给azure存储blob客户端,只需将其留给azure即可。
我建议使用异步版本的azure-storage-blob包。
我重新写了一点。下面的代码将按原样运行,这是一个完整的工作示例。
from fastapi import FastAPI, HTTPException, UploadFile
from azure.storage.blob.aio import BlobServiceClient
app = FastAPI()
@app.post("/uploadfile")
async def create_upload_file(file: UploadFile):
name = file.filename
type = file.content_type
return await uploadtoazure(file,name,type)
async def uploadtoazure(file: UploadFile,file_name: str,file_type:str):
connect_str = "HERE_YUOUR_CONNECTION_STRING"
blob_service_client = BlobServiceClient.from_connection_string(connect_str)
container_name = "stackoverflow"
async with blob_service_client:
container_client = blob_service_client.get_container_client(container_name)
try:
blob_client = container_client.get_blob_client(file_name)
f = await file.read()
await blob_client.upload_blob(f)
except Exception as e:
print(e)
return HTTPException(401, "Something went terribly wrong..")
return "{'did_it_work':'yeah it did!'}"
if __name__ == "__main__":
import uvicorn
uvicorn.run(app, host="0.0.0.0", port=8000, )
希望这澄清了一些东西!