ユーザーが写真をアップロードできるプログラムがあり、それはアプリケーション内に保存されます (例: ~/files/ac9ff990-273c-4fda-a51a-155c54db72ab/original/photo1.jpg)。後で、ユーザーはファイルを削除できます。これは正常に機能しますが、すべてのサブファイルとフォルダーが削除されても、指定されたレベルのフォルダー (この GUID フォルダー) が残り、Unauthorizedaccessexception エラーがスローされる場合を除きます。何千ものアップロードを処理するときに本当に面倒な空のフォルダーがたくさん残っています。
アクセス許可について奇妙なことは何もなく、デスクトップでもライブサーバーと同じ問題が発生するため、それがどのようにアクセス許可になるのかわかりません。私はインデックス作成をオフにして、「EVERYONE」権限を運なしで与え、フォルダー所有者を別のユーザーに設定してみました。(Windowsエクスプローラーでフォルダーを開いていません)
.NET は作成と削除に同じフォルダーを使用する必要があるため、これがどのようにアクセス許可の問題になるかわかりません。何か案は?
public class FileManager { private static ILog log = LogManager.GetLogger(typeof(FileManager)); public enum UPLOAD_TYPE : int { ORIGINAL_FILE = 1、PROCESSED_FILE = 2、ANCILLARY_FILE = 3 }
private const string userFilesFolder = "~/files/";
private const string originalSubFolder = "original/";
private const string processedSubFolder = "processed/";
private const string ancillarySubFolder = "ancillary/";
internal static void DeleteJobItemFiles(Guid jobItemId)
{
if (jobItemId == Guid.Empty)
throw new ApplicationException("jobItemId is Empty");
try
{
var directory = GetDirectory(jobItemId);
string routePath = HttpContext.Current.Server.MapPath(HttpUtility.UrlDecode(directory.AbsolutePath));
if (Directory.Exists(routePath))
Directory.Delete(routePath, true);
}
catch (HttpException exception)
{
throw new UploadManagerException(ERROR_CODE.HTTP_CONTEXT_NULL, exception);
}
catch (Exception exception)
{
throw new UploadManagerException(ERROR_CODE.GENERAL_FILE, exception);
}
}
internal static string SaveFile(Guid jobItemId, Stream inputStream, UPLOAD_TYPE uploadType, string fileName)
{
if (jobItemId == Guid.Empty)
throw new ArgumentException("jobItemId is Empty");
if (inputStream == null)
throw new ArgumentNullException("inputStream");
if (fileName == null)
throw new ArgumentNullException("fileName");
if (inputStream.CanSeek)
inputStream.Position = 0;
Regex rgx = new Regex("[^a-zA-Z0-9 -_\\.]");
fileName = rgx.Replace(fileName, "");
fileName = fileName.Replace(" ", "");
var directoryPathUri = GetDirectory(jobItemId, uploadType);
// New file Uri
var fileUri = new Uri(directoryPathUri, fileName);
try
{
string localDirectoryPath = HttpContext.Current.Server.MapPath(HttpUtility.UrlDecode(directoryPathUri.AbsolutePath));
string localFilePath = HttpContext.Current.Server.MapPath(HttpUtility.UrlDecode(fileUri.AbsolutePath));
if (!Directory.Exists(localDirectoryPath))
Directory.CreateDirectory(localDirectoryPath);
using (FileStream outputStream = File.Create(localFilePath))
{
Byte[] buffer = new Byte[256];
inputStream.Position = 0;
int bytesRead;
do
{
bytesRead = inputStream.Read(buffer, 0, buffer.Length);
if (bytesRead > 0)
outputStream.Write(buffer, 0, bytesRead);
}
while (bytesRead > 0);
}
}
catch (IOException exception)
{
log.Error("Unexpected exception in FileManager.SaveFile", exception);
throw new UploadManagerException(ERROR_CODE.FILE_SAVE, exception);
}
catch (HttpException exception)
{
throw new UploadManagerException(ERROR_CODE.HTTP_CONTEXT_NULL, exception);
}
catch (Exception exception)
{
throw new UploadManagerException(ERROR_CODE.GENERAL_FILE, exception);
}
var rootUri = GetDirectory();
return VirtualPathUtility.ToAppRelative(fileUri.AbsolutePath);
}
private static Uri GetDirectory()
{
// Root of site
try
{
return new Uri(HttpContext.Current.Request.Url, HttpContext.Current.Request.ApplicationPath);
}
catch (HttpException exception)
{
throw new UploadManagerException(ERROR_CODE.HTTP_CONTEXT_NULL, exception);
}
}
private static Uri GetDirectory(Guid jobItemId)
{
if (jobItemId == Guid.Empty)
throw new ArgumentException("jobItemId is Empty");
var rootUri = GetDirectory();
//Folder where all files are stored
var userFilesUri = new Uri(rootUri, VirtualPathUtility.ToAbsolute(userFilesFolder));
//Folder for job
return new Uri(userFilesUri, jobItemId.ToString() + "/");
}
private static Uri GetDirectory(Guid jobItemId, UPLOAD_TYPE uploadType)
{
if (jobItemId == Guid.Empty)
throw new ArgumentException("jobItemId is Empty");
string subFolder;
switch (uploadType)
{
case UPLOAD_TYPE.ORIGINAL_FILE:
subFolder = originalSubFolder;
break;
case UPLOAD_TYPE.PROCESSED_FILE:
subFolder = processedSubFolder;
break;
case UPLOAD_TYPE.ANCILLARY_FILE:
subFolder = ancillarySubFolder;
break;
default:
throw new NotImplementedException();
}
//Folder for file
return new Uri(GetDirectory(jobItemId), subFolder);
}
}
重要な更新: これは、IIS のロック ファイルなどによって引き起こされているようです。削除しようとしている画像がページに表示されます。ページを削除するために WCF 呼び出しが行われると、フォルダーを削除できません。画像が表示されないように HTML を編集すると、フォルダを削除できます。誰にとっても意味がありますか?