C# - 如何将文件上传到 Azure 存储 Blob(未知物理路径)
C# - How to upload files to Azure Storage Blob (unknown phisic path)
在我的网络应用程序中,我需要允许用户从他们的机器上选择一个图像并上传它,并将该图像物理存储到我的容器中32=]存储 在 Azure 中。
我在很多地方都找到了这样做的方法,它对我有用,但是 重要例外 在所有示例中,他们都从自己的机器上传文件并了解或编码物理路径。
但是出于安全考虑,输入文件无法读取客户端的物理地址,我只好使用了策略:
- 我将图像上传到网络服务器的已知路径。
- 我走那条路,我用它上传到 Azure 存储 Blob。
- 已确认,我不希望该文件保留在服务器上,我只希望它在我的容器中, 所以我继续删除文件。
- 我得到以下异常:
The process cannot access the file.
'C:\My_folders\MyFile.jpg' because it is being used by another process.
注意:我尝试使用项目目录和操作系统的临时目录。对于这两种情况,我得到相同的结果。
所以,总而言之:我需要上传到 Azure S Blob,但据我所知,为此我需要文件的物理路径,所以我需要将它上传到我的服务器,然后从那里上传。
我希望你能帮助我做出这些选择:
- 能够在没有物理路径的情况下上传它。
或者能够关闭我现在的进程,确保删除服务器上的临时文件。
- 您的任何建议。
非常感谢!
_________________________代码________________________
前面
<form method="POST" enctype="multipart/form-data" id="fileUploadForm">
<div class="row">
<div class="col-md-12" id="conten_CargaImagenes">
<div class="card card-success">
<div class="card-header">
<h3 class="card-title" id="tituloAbmHorarios">
<i class="far fa-image"></i> Nueva Imagen
</h3>
</div>
<div class="card-body">
<div class="row">
<div class="col-md-12">
<div class="form-group">
<input asp-for="File" class="form-control custom-file-input" />
<label id="fileImageLabel" asp-for="File" class="custom-file-label "></label>
</div>
</div>
<div class="col-md-3">
<button type="button" class="btn bg-gradient-success btn-sm pull-left" onclick="GuardarImagen()">
<i class="fas fa-file-upload"></i> Grabar Imagen
</button>
</div>
</div>
</div>
</div>
</div>
</div>
JS 方法
function GuardarImagen() {
var form = $('#fileUploadForm')[0];
var model = new FormData(form);
model.append('IdComercio', $('#Id').val());
$.ajax({
type: "POST",
enctype: 'multipart/form-data',
url: "/Comercios/GrabaFile",
data: model,
processData: false,
contentType: false,
cache: false,
timeout: 600000,
success: function (e) {
if (!e.isError) {
$("#File").val(null);
document.getElementById("fileImageLabel").innerHTML = '';
toastr.success(textos.imagenGrabadaOk, { timeOut: 2000 });
InjectarNuevaImagenEnPantalla(e.data);
} else {
toastr.error(e.data, { timeOut: 2000 });
}
}
});
}
返回
[HttpPost]
public ReturnData GrabaFile(UploadFileComercioDTO pData)
{
if (pData.File != null)
{
try
{
var result = UploaderFilesService.UploadToAzure(pData.File, FolderPath, pData.IdComercio.ToString());
}
catch (Exception ex)
{
do something...
}
}
else
{
return messageError
}
}
public static ReturnData UploadToAzure(IFormFile pFile, string pFolder, string pIdComercio)
{
ReturnData returnData = new();
if (pFile != null)
{
if (ValidaFile(pFile.ContentType, pFile.Length))
{
try
{
string nombreOriginal = pFile.FileName;
var nombrePartes = nombreOriginal.Split(".");
string extension = nombrePartes[(nombrePartes.Length - 1)];
string nombreFinal = GenerarTextoUnico() + "." + extension;
string soloNOmbre = nombreFinal; // ****
pFolder = Path.GetTempPath(); // *************
string filePath = Path.Combine(pFolder, nombreFinal);
using (var stream = File.Create(filePath))
{
pFile.CopyTo(stream);
}
string connectionString = "adsfasfasdfasdf";
string containerName = "asdfasdf";
nombreFinal = pIdComercio + "/" + nombreFinal;
BlobContainerClient container = new BlobContainerClient(connectionString, containerName);
var upload = container.UploadBlob(nombreFinal, File.OpenRead(filePath));
try
{
File.Delete(filePath);
}
catch (IOException e)
{
Console.WriteLine(e.Message);
}
}
catch (Exception ex)
{
...
}
}
else
{
...
}
}
else
{
...
}
return returnData;
}
我找到了问题和解决方案。
问题是上传时没有关闭流。
要进行的修改是在 UploadToAzure 方法中,更改以下行
var upload = container.UploadBlob(finalName, File.OpenRead(filePath));
为此
using (var stream = File.OpenRead(filePath))
{
var upload = container.UploadBlob(endName, stream);
}
那样当我退出时 使用 流已经关闭,我可以继续删除它。
在我的网络应用程序中,我需要允许用户从他们的机器上选择一个图像并上传它,并将该图像物理存储到我的容器中32=]存储 在 Azure 中。
我在很多地方都找到了这样做的方法,它对我有用,但是 重要例外 在所有示例中,他们都从自己的机器上传文件并了解或编码物理路径。
但是出于安全考虑,输入文件无法读取客户端的物理地址,我只好使用了策略:
- 我将图像上传到网络服务器的已知路径。
- 我走那条路,我用它上传到 Azure 存储 Blob。
- 已确认,我不希望该文件保留在服务器上,我只希望它在我的容器中, 所以我继续删除文件。
- 我得到以下异常:
The process cannot access the file. 'C:\My_folders\MyFile.jpg' because it is being used by another process.
注意:我尝试使用项目目录和操作系统的临时目录。对于这两种情况,我得到相同的结果。
所以,总而言之:我需要上传到 Azure S Blob,但据我所知,为此我需要文件的物理路径,所以我需要将它上传到我的服务器,然后从那里上传。
我希望你能帮助我做出这些选择:
- 能够在没有物理路径的情况下上传它。 或者能够关闭我现在的进程,确保删除服务器上的临时文件。
- 您的任何建议。
非常感谢! _________________________代码________________________ 前面
<form method="POST" enctype="multipart/form-data" id="fileUploadForm">
<div class="row">
<div class="col-md-12" id="conten_CargaImagenes">
<div class="card card-success">
<div class="card-header">
<h3 class="card-title" id="tituloAbmHorarios">
<i class="far fa-image"></i> Nueva Imagen
</h3>
</div>
<div class="card-body">
<div class="row">
<div class="col-md-12">
<div class="form-group">
<input asp-for="File" class="form-control custom-file-input" />
<label id="fileImageLabel" asp-for="File" class="custom-file-label "></label>
</div>
</div>
<div class="col-md-3">
<button type="button" class="btn bg-gradient-success btn-sm pull-left" onclick="GuardarImagen()">
<i class="fas fa-file-upload"></i> Grabar Imagen
</button>
</div>
</div>
</div>
</div>
</div>
</div>
JS 方法
function GuardarImagen() {
var form = $('#fileUploadForm')[0];
var model = new FormData(form);
model.append('IdComercio', $('#Id').val());
$.ajax({
type: "POST",
enctype: 'multipart/form-data',
url: "/Comercios/GrabaFile",
data: model,
processData: false,
contentType: false,
cache: false,
timeout: 600000,
success: function (e) {
if (!e.isError) {
$("#File").val(null);
document.getElementById("fileImageLabel").innerHTML = '';
toastr.success(textos.imagenGrabadaOk, { timeOut: 2000 });
InjectarNuevaImagenEnPantalla(e.data);
} else {
toastr.error(e.data, { timeOut: 2000 });
}
}
});
}
返回
[HttpPost]
public ReturnData GrabaFile(UploadFileComercioDTO pData)
{
if (pData.File != null)
{
try
{
var result = UploaderFilesService.UploadToAzure(pData.File, FolderPath, pData.IdComercio.ToString());
}
catch (Exception ex)
{
do something...
}
}
else
{
return messageError
}
}
public static ReturnData UploadToAzure(IFormFile pFile, string pFolder, string pIdComercio)
{
ReturnData returnData = new();
if (pFile != null)
{
if (ValidaFile(pFile.ContentType, pFile.Length))
{
try
{
string nombreOriginal = pFile.FileName;
var nombrePartes = nombreOriginal.Split(".");
string extension = nombrePartes[(nombrePartes.Length - 1)];
string nombreFinal = GenerarTextoUnico() + "." + extension;
string soloNOmbre = nombreFinal; // ****
pFolder = Path.GetTempPath(); // *************
string filePath = Path.Combine(pFolder, nombreFinal);
using (var stream = File.Create(filePath))
{
pFile.CopyTo(stream);
}
string connectionString = "adsfasfasdfasdf";
string containerName = "asdfasdf";
nombreFinal = pIdComercio + "/" + nombreFinal;
BlobContainerClient container = new BlobContainerClient(connectionString, containerName);
var upload = container.UploadBlob(nombreFinal, File.OpenRead(filePath));
try
{
File.Delete(filePath);
}
catch (IOException e)
{
Console.WriteLine(e.Message);
}
}
catch (Exception ex)
{
...
}
}
else
{
...
}
}
else
{
...
}
return returnData;
}
我找到了问题和解决方案。
问题是上传时没有关闭流。
要进行的修改是在 UploadToAzure 方法中,更改以下行
var upload = container.UploadBlob(finalName, File.OpenRead(filePath));
为此
using (var stream = File.OpenRead(filePath))
{
var upload = container.UploadBlob(endName, stream);
}
那样当我退出时 使用 流已经关闭,我可以继续删除它。