Tôi đang trích xuất nội dung của tệp trong tệp tệp SQL. Mã sau đây hoạt động nếu tôi không sử dụng song song.Luồng và SqlFileStream. Quá trình không thể truy cập tệp được chỉ định bởi vì nó đã được mở trong một giao dịch khác
Tôi nhận được ngoại lệ sau, khi đọc tệp luồng sql đồng thời (Song song).
Quy trình không thể truy cập tệp được chỉ định vì tệp đã được mở trong giao dịch khác.
TL; DR:
Khi đọc một tập tin từ FileTable (sử dụng GET_FILESTREAM_TRANSACTION_CONTEXT) trong một Parallel.ForEach tôi nhận được ngoại lệ trên.
mẫu mã cho bạn thử:
https://gist.github.com/NerdPad/6d9b399f2f5f5e5c6519
Còn Version:
Fetch đính kèm, và trích xuất nội dung:
var documents = new List<ExtractedContent>();
using (var ts = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled))
{
var attachments = await dao.GetAttachmentsAsync();
// Extract the content simultaneously
// documents = attachments.ToDbDocuments().ToList(); // This works
Parallel.ForEach(attachments, a => documents.Add(a.ToDbDocument())); // this doesn't
ts.Complete();
}
DAO đọc File Table:
public async Task<IEnumerable<SearchAttachment>> GetAttachmentsAsync()
{
try
{
var commandStr = "....";
IEnumerable<SearchAttachment> attachments = null;
using (var connection = new SqlConnection(this.DatabaseContext.Database.Connection.ConnectionString))
using (var command = new SqlCommand(commandStr, connection))
{
connection.Open();
using (var reader = await command.ExecuteReaderAsync())
{
attachments = reader.ToSearchAttachments().ToList();
}
}
return attachments;
}
catch (System.Exception)
{
throw;
}
}
Tạo đối tượng cho mỗi tập tin: Đối tượng chứa một tham chiếu đến GET_FILESTREAM_TRANSACTION_CONTEXT
public static IEnumerable<SearchAttachment> ToSearchAttachments(this SqlDataReader reader)
{
if (!reader.HasRows)
{
yield break;
}
// Convert each row to SearchAttachment
while (reader.Read())
{
yield return new SearchAttachment
{
...
...
UNCPath = reader.To<string>(Constants.UNCPath),
ContentStream = reader.To<byte[]>(Constants.Stream) // GET_FILESTREAM_TRANSACTION_CONTEXT()
...
...
};
}
}
đọc các tập tin sử dụng SqlFileStream: ngoại lệ là ném ở đây
public static ExtractedContent ToDbDocument(this SearchAttachment attachment)
{
// Read the file
// Exception is thrown here
using (var stream = new SqlFileStream(attachment.UNCPath, attachment.ContentStream, FileAccess.Read, FileOptions.SequentialScan, 4096))
{
...
// extract content from the file
}
....
}
Cập nhật 1:
Theo this bài viết nó có vẻ như nó có thể là một vấn đề cấp độ Isolation. Có ai từng phải đối mặt với vấn đề tương tự không?
Thử mở tệp trên cùng một chuỗi đã làm phần còn lại của SQL. Có lẽ điều này chỉ đơn giản là không được phép. – usr
Bạn đang viết thư cho 'tài liệu' trên nhiều chủ đề, 'Danh sách' không phải là chủ đề an toàn và bạn không thể làm điều này (Nó không có khả năng là nguồn của vấn đề của bạn nhưng nó là một vấn đề) –