From 07a0436ec896bdd282a045d4db233470fd7a0130 Mon Sep 17 00:00:00 2001 From: Tobias Klika Date: Sat, 18 Dec 2021 01:51:38 +0100 Subject: [PATCH] start media upload --- .../ZeroApiEntityStoreController.cs | 22 +- .../Media/Maps/MediaMapperProfile.cs | 10 +- zero.Api/Endpoints/Media/MediaController.cs | 10 +- zero.Backoffice.UI/app/modules/media/api.ts | 22 +- .../{createfolder.vue => editfolder.vue} | 35 +-- .../modules/media/overlays/upload-status.vue | 209 ++++++++++++++++++ .../app/modules/media/pages/overview/drop.vue | 44 +++- .../modules/media/pages/overview/overview.vue | 28 ++- zero.Backoffice.UI/app/ui/app-overlays.vue | 10 + .../app/ui/overlays/confirm.vue | 14 +- .../pages/media/overlays/upload-status.vue | 10 +- zero.Backoffice/ZeroVue.cs | 2 +- zero.Core/Media/Indexes/Media_ByParent.cs | 2 +- zero.Core/Media/MediaManagement.cs | 4 +- zero.Core/Media/Models/Media.cs | 16 -- zero.Core/Media/Models/MediaImageMetadata.cs | 16 ++ 16 files changed, 352 insertions(+), 102 deletions(-) rename zero.Backoffice.UI/app/modules/media/overlays/{createfolder.vue => editfolder.vue} (65%) create mode 100644 zero.Backoffice.UI/app/modules/media/overlays/upload-status.vue diff --git a/zero.Api/Abstractions/ZeroApiEntityStoreController.cs b/zero.Api/Abstractions/ZeroApiEntityStoreController.cs index 8e589240..9761333c 100644 --- a/zero.Api/Abstractions/ZeroApiEntityStoreController.cs +++ b/zero.Api/Abstractions/ZeroApiEntityStoreController.cs @@ -198,19 +198,21 @@ public abstract class ZeroApiEntityStoreController : ZeroApiCont return BadRequest(Result.Fail(nameof(id), "@errors.onupdate.noidmatch")); } - TModel model = await Store.Load(id); + // TODO throws error on save: Attempted to associate a different object with id ... + // we need to map props to new object + //TModel model = await Store.Load(id); - if (model == null) - { - return BadRequest(Result.Fail(nameof(id), "@errors.idnotfound")); - } + //if (model == null) + //{ + // return BadRequest(Result.Fail(nameof(id), "@errors.idnotfound")); + //} - string storedChangeToken = Store.GetChangeToken(model); + //string storedChangeToken = Store.GetChangeToken(model); - if (!changeToken.IsNullOrEmpty() && storedChangeToken != changeToken) - { - return BadRequest(Result.Fail("@errors.onupdate.changetokenmismatch")); - } + //if (!changeToken.IsNullOrEmpty() && storedChangeToken != changeToken) + //{ + // return BadRequest(Result.Fail("@errors.onupdate.changetokenmismatch")); + //} Result result = await Store.Update(updateModel); diff --git a/zero.Api/Endpoints/Media/Maps/MediaMapperProfile.cs b/zero.Api/Endpoints/Media/Maps/MediaMapperProfile.cs index 15eae4fc..9946192d 100644 --- a/zero.Api/Endpoints/Media/Maps/MediaMapperProfile.cs +++ b/zero.Api/Endpoints/Media/Maps/MediaMapperProfile.cs @@ -30,9 +30,9 @@ public class MediaMapperProfile : ZeroMapperProfile target.Children = 0; target.Size = source.Size; - if (source.Thumbnails.Any()) + if (source.ImageMeta != null && source.ImageMeta.Thumbnails.Any()) { - string path = source.Thumbnails.GetValueOrDefault("preview"); + string path = source.ImageMeta.Thumbnails.GetValueOrDefault("preview"); target.Image = path.IsNullOrEmpty() ? null : FileSystem.MapToPublicPath(path); } } @@ -54,13 +54,13 @@ public class MediaMapperProfile : ZeroMapperProfile protected virtual void Map(zero.Media.Media source, MediaFileEdit target, IZeroMapperContext ctx) { Map(source, (MediaEdit)target, ctx); - target.AlternativeText = source.AlternativeText; + target.AlternativeText = source.ImageMeta?.AlternativeText; target.Caption = source.Caption; target.Path = source.Path; - target.Thumbnails = source.Thumbnails; + target.Thumbnails = source.ImageMeta?.Thumbnails; target.Size = source.Size; target.ImageMeta = source.ImageMeta; - target.FocalPoint = source.FocalPoint; + target.FocalPoint = source.ImageMeta?.FocalPoint; } diff --git a/zero.Api/Endpoints/Media/MediaController.cs b/zero.Api/Endpoints/Media/MediaController.cs index 73f00b7a..4ad2c108 100644 --- a/zero.Api/Endpoints/Media/MediaController.cs +++ b/zero.Api/Endpoints/Media/MediaController.cs @@ -1,4 +1,5 @@ -using Microsoft.AspNetCore.Mvc; +using Microsoft.AspNetCore.Http; +using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.StaticFiles; using Microsoft.Net.Http.Headers; using Raven.Client.Documents; @@ -40,6 +41,13 @@ public class MediaController : ZeroApiTreeEntityStoreController Upload(IFormFile file) + { + await Task.Delay(2000); + return Ok(); + } + #region bulk operations [HttpPut("bulk/move")] diff --git a/zero.Backoffice.UI/app/modules/media/api.ts b/zero.Backoffice.UI/app/modules/media/api.ts index dc6e37bf..30ba34f9 100644 --- a/zero.Backoffice.UI/app/modules/media/api.ts +++ b/zero.Backoffice.UI/app/modules/media/api.ts @@ -17,7 +17,27 @@ const files = { move: (id: string, parentId: string, config?: ApiRequestConfig) => put(`media/${id}/move/${parentId}`, {}, { ...config }), - delete: (id: string, config?: ApiRequestConfig) => del('media/' + id, config) + delete: (id: string, config?: ApiRequestConfig) => del('media/' + id, config), + + //uploadtest: (model: any, config?: ApiRequestConfig) => post('media/uploadtest', model, config), + + uploadtest: async (file, onProgress) => + { + var data = new FormData(); + data.append('file', file); + //data.append('folderId', folderId); + + return await post('media/uploadtest', data, { + onUploadProgress: (progressEvent) => + { + if (typeof onProgress === 'function') + { + var percentCompleted = Math.round((progressEvent.loaded * 100) / progressEvent.total); + onProgress(percentCompleted); + } + } + }); + } }; diff --git a/zero.Backoffice.UI/app/modules/media/overlays/createfolder.vue b/zero.Backoffice.UI/app/modules/media/overlays/editfolder.vue similarity index 65% rename from zero.Backoffice.UI/app/modules/media/overlays/createfolder.vue rename to zero.Backoffice.UI/app/modules/media/overlays/editfolder.vue index ef6f54d0..848f3df4 100644 --- a/zero.Backoffice.UI/app/modules/media/overlays/createfolder.vue +++ b/zero.Backoffice.UI/app/modules/media/overlays/editfolder.vue @@ -8,11 +8,9 @@ -

- + -
@@ -58,37 +56,6 @@ { this.config.confirm(response.data); } - }, - - - //onDelete(item, opts) - //{ - // opts.hide(); - // thi - - //onLoad(form) - //{ - // form.load(!this.model.id ? MediaFolderApi.getEmpty() : MediaFolderApi.getById(this.model.id)).then(response => - // { - // this.disabled = false; //!response.canEdit; - // this.item = response.entity; - // this.item.parentId = this.model.parentId; - // this.loading = false; - // }); - //}, - - - //onSubmit(form) - //{ - // form.handle(MediaFolderApi.save(this.item)).then(response => - // { - // this.config.confirm(response, this.config); - // }); - //}, - - onDelete() - { - //this.config.confirm({ deleted: true }); } } } diff --git a/zero.Backoffice.UI/app/modules/media/overlays/upload-status.vue b/zero.Backoffice.UI/app/modules/media/overlays/upload-status.vue new file mode 100644 index 00000000..74ff5944 --- /dev/null +++ b/zero.Backoffice.UI/app/modules/media/overlays/upload-status.vue @@ -0,0 +1,209 @@ + + + + + + \ No newline at end of file diff --git a/zero.Backoffice.UI/app/modules/media/pages/overview/drop.vue b/zero.Backoffice.UI/app/modules/media/pages/overview/drop.vue index cd7d0715..93ab4ef4 100644 --- a/zero.Backoffice.UI/app/modules/media/pages/overview/drop.vue +++ b/zero.Backoffice.UI/app/modules/media/pages/overview/drop.vue @@ -1,15 +1,48 @@  - @@ -27,6 +60,11 @@ box-shadow: var(--shadow-short); border: 1px dashed var(--color-line-dashed-onbg); color: var(--color-text); + + &.is-dragging + { + border-color: var(--color-accent); + } } .ui-datagrid-outer.is-selecting .media-overview-drop diff --git a/zero.Backoffice.UI/app/modules/media/pages/overview/overview.vue b/zero.Backoffice.UI/app/modules/media/pages/overview/overview.vue index 8fb0234e..1b480b03 100644 --- a/zero.Backoffice.UI/app/modules/media/pages/overview/overview.vue +++ b/zero.Backoffice.UI/app/modules/media/pages/overview/overview.vue @@ -16,7 +16,7 @@ @@ -30,12 +30,20 @@ -