private bool SeekBlob(BlobsTable table, BlobId id, bool includeUncompleted) { if (!table.Indexes.PrimaryIndex.Find(table.Indexes.PrimaryIndex.CreateKey(id.Id))) { return(false); } if (!includeUncompleted) { return(table.Columns.IsCompleted); } return(true); }
/// <summary> /// Для юнит тестов. Проверка на наличие Файла. /// </summary> /// <param name="id">Идентификатор.</param> /// <returns>Результат.</returns> public async Task <bool> IsFilePresent(BlobId id) { try { var f = await _filestreamFolder.GetFileAsync(BlobFileName(id.Id)); var s = await f.GetBasicPropertiesAsync(); return(s.Size > 0); } catch { return(false); } }
/// <summary> /// Получить размер файла. /// </summary> /// <param name="id">Идентификатор.</param> /// <returns>Информация о файле.</returns> public async Task <BlobInfo?> GetBlobInfo(BlobId id) { CheckModuleReady(); await WaitForTablesInitialize(); return(await OpenSessionAsync(async session => { BlobInfo?result = null; await session.Run(() => { using (var table = OpenBlobsTable(session, OpenTableGrbit.ReadOnly)) { result = LoadBlobInfo(table, id); } }); return await AddFileSize(result); })); }
private BlobInfo?LoadBlobInfo(BlobsTable table, BlobId id) { BlobInfo?result = null; if (SeekBlob(table, id, false)) { var data = table.Views.FullRowUpdate.Fetch(); result = new BlobInfo() { Id = id, UniqueName = data.Name, Category = data.Category, CreatedTime = data.CreatedDate, Size = data.Length, ReferenceId = data.ReferenceId, IsUncompleted = !data.IsCompleted, IsFilestream = data.IsFilestream }; } return(result); }
/// <summary> /// Конструктор. Должен вызываться из потока сессии. /// </summary> /// <param name="globalErrorHandler">Обработчик глобальных ошибок.</param> /// <param name="session">Сессия.</param> /// <param name="blobId">Идентификатор блоба.</param> public BlocksBlobStream(IGlobalErrorHandler globalErrorHandler, IEsentSession session, BlobId blobId) : base(globalErrorHandler) { _session = session ?? throw new ArgumentNullException(nameof(session)); var sid = _session.Session; try { _usage = _session.UseSession(); _transaction = new Transaction(session.Session); try { var tbl = session.OpenTable(BlobTableInfo.BlobsTableName, OpenTableGrbit.ReadOnly); _table = new BlobsTable(tbl.Session, tbl); try { Api.MakeKey(sid, _table, blobId.Id, MakeKeyGrbit.NewKey); if (!Api.TrySeek(sid, _table, SeekGrbit.SeekEQ)) { throw new BlobNotFoundException(blobId); } _inlinedStream = new ColumnStream(sid, _table, _table.GetColumnid(BlobsTable.Column.Data)); Length = _inlinedStream.Length; } catch { _table.Dispose(); } } catch { _transaction.Dispose(); throw; } } catch { _usage.Dispose(); throw; } }
/// <summary> /// Удалить файл. /// </summary> /// <param name="id">Идентификатор.</param> /// <returns>true, если файл найден и удалён. false, если нет такого файла или файл заблокирован на удаление.</returns> public async Task <bool> DeleteBlob(BlobId id) { CheckModuleReady(); await WaitForTablesInitialize(); return(await OpenSessionAsync(async session => { bool isFileStream = false; byte[] bookmark = null; bool result = false; await session.RunInTransaction(() => { using (var table = OpenBlobsTable(session, OpenTableGrbit.None)) { if (table.Indexes.PrimaryIndex.Find(table.Indexes.PrimaryIndex.CreateKey(id.Id))) { isFileStream = table.Columns.IsFilestream; if (!isFileStream) { table.DeleteCurrentRow(); result = true; } else { bookmark = table.GetBookmark(); } } return true; } }, 1.5); if (isFileStream) { bool isDeleted; try { await(await _filestreamFolder.GetFileAsync(BlobFileName(id.Id))).DeleteAsync(); isDeleted = true; } catch { isDeleted = false; } if (isDeleted) { await session.RunInTransaction(() => { using (var table = OpenBlobsTable(session, OpenTableGrbit.None)) { if (table.TryGotoBookmark(bookmark)) { table.DeleteCurrentRow(); result = true; } } return true; }, 1.5); } } return result; })); }
/// <summary> /// Загрузить файл. /// </summary> /// <param name="id">Идентификатор.</param> /// <returns>Результат.</returns> public async Task <Stream> LoadBlob(BlobId id) { CheckModuleReady(); await WaitForTablesInitialize(); return(await OpenSessionAsync(async session => { BlobStreamBase result = null; BlobId?filestream = null; void DoLoad() { using (var table = OpenBlobsTable(session, OpenTableGrbit.ReadOnly)) { if (table.Indexes.PrimaryIndex.Find(table.Indexes.PrimaryIndex.CreateKey(id.Id))) { var isFilestream = table.Columns.IsFilestream; if (isFilestream) { filestream = id; return; } else { var size = Api.RetrieveColumnSize(table.Session, table, table.GetColumnid(BlobsTable.Column.Data)) ?? 0; if (size <= MaxInlineSize) { var data = table.Columns.Data; if (data == null) { throw new BlobException($"Неверные данные в таблице {BlobsTableName}"); } result = new InlineBlobStream(GlobalErrorHandler, data); } else { result = new BlocksBlobStream(GlobalErrorHandler, session, id); } } } else { throw new BlobNotFoundException(id); } } } await session.Run(DoLoad); if (filestream != null) { return new InlineFileStream(GlobalErrorHandler, await _filestreamFolder.OpenStreamForReadAsync(BlobFileName(id.Id))); } if (result == null) { throw new BlobException($"Неверные данные в таблице {BlobsTableName}"); } return result; })); }