diff --git a/kahuna/public/js/components/gr-downloader/gr-downloader.html b/kahuna/public/js/components/gr-downloader/gr-downloader.html index dd4a277554b..2974341eaf6 100644 --- a/kahuna/public/js/components/gr-downloader/gr-downloader.html +++ b/kahuna/public/js/components/gr-downloader/gr-downloader.html @@ -26,6 +26,7 @@ href="{{ ctrl.firstImageUris.uris.downloadUri }}" download rel="noopener" target="_blank" aria-label="Download image" class="side-padded" + ng-click="ctrl.onSingleDownloadClicked()" > Download diff --git a/kahuna/public/js/components/gr-downloader/gr-downloader.js b/kahuna/public/js/components/gr-downloader/gr-downloader.js index 95e9c560c88..54de2ed5374 100644 --- a/kahuna/public/js/components/gr-downloader/gr-downloader.js +++ b/kahuna/public/js/components/gr-downloader/gr-downloader.js @@ -3,18 +3,24 @@ import './gr-downloader.css'; import template from './gr-downloader.html'; import '../../services/image/downloads'; +import '../../services/api/media-api'; + export const downloader = angular.module('gr.downloader', [ - 'gr.image-downloads.service' + 'gr.image-downloads.service', + 'kahuna.services.api.media' ]); downloader.controller('DownloaderCtrl', [ '$window', '$q', + '$rootScope', '$scope', 'inject$', 'imageDownloadsService', + 'apiPoll', + 'mediaApi', - function Controller($window, $q, $scope, inject$, imageDownloadsService) { + function Controller($window, $q, $rootScope, $scope, inject$, imageDownloadsService, apiPoll, mediaApi) { let ctrl = this; @@ -60,6 +66,23 @@ downloader.controller('DownloaderCtrl', [ inject$($scope, uris$, ctrl, 'firstImageUris'); + function pollForDownloadUsageUpdate(image, downloadedAt) { + return mediaApi.getSession().then(session => { + return apiPoll(() => image.get().then(updatedImage => { + const hasNewUsageByCurrentUser = updatedImage.data.usages.data.some( + u => u.data.platform === 'download' && + u.data.downloadUsageMetadata && + u.data.downloadUsageMetadata.downloadedBy === session.user.email && + new Date(u.data.dateAdded) > downloadedAt + ); + if (!hasNewUsageByCurrentUser) { + return $q.reject(); + } + $rootScope.$emit('images-updated', [updatedImage]); + })); + }); + } + ctrl.download = (downloadKey) => { ctrl.downloading = true; @@ -94,6 +117,12 @@ downloader.controller('DownloaderCtrl', [ throw e; }); }; + + ctrl.onSingleDownloadClicked = () => { + if (window._clientConfig.recordDownloadAsUsage && ctrl.firstImageUris && ctrl.firstImageUris.uris.downloadUri) { + pollForDownloadUsageUpdate(ctrl.imagesArray()[0], new Date()).catch(() => {}); + } + }; }; }]); diff --git a/kahuna/public/js/components/gr-image-usage/gr-image-usage.js b/kahuna/public/js/components/gr-image-usage/gr-image-usage.js index ff7b23b7789..62521ee2e04 100644 --- a/kahuna/public/js/components/gr-image-usage/gr-image-usage.js +++ b/kahuna/public/js/components/gr-image-usage/gr-image-usage.js @@ -22,21 +22,32 @@ export const module = angular.module('gr.imageUsage', [ module.controller('grImageUsageCtrl', [ '$scope', + '$rootScope', '$state', 'inject$', '$window', 'imageUsagesService', - function ($scope, $state, inject$, $window, imageUsagesService) { + function ($scope, $rootScope, $state, inject$, $window, imageUsagesService) { const ctrl = this; + const bindUsages = (image) => { + const usages = imageUsagesService.getUsages(image); + const usages$ = usages.groupedByState$ + .map((grouped) => grouped + .map(list => list.sortBy(usage => usage.get('dateAdded')).reverse()) + .toJS() + ); + inject$($scope, usages$, ctrl, 'usages'); + inject$($scope, usages.count$, ctrl, 'usagesCount'); + inject$($scope, usages.hasSyndicationUsages$, ctrl, 'hasSyndicationUsages'); + }; + ctrl.$onInit = () => { ctrl.showSendToPhotoSales = $window._clientConfig.showSendToPhotoSales; - const usages = imageUsagesService.getUsages(ctrl.image); - const usages$ = usages.groupedByState$.map((u) => u.toJS()); - const usagesCount$ = usages.count$; + bindUsages(ctrl.image); // TODO match on `platform` rather than `type` as `platform` includes more detail ctrl.usageTypeToName = (usageType) => { @@ -72,17 +83,18 @@ module.controller('grImageUsageCtrl', [ }; ctrl.onUsagesDeleted = () => { - // a bit nasty - but it updates the state of the page better than trying to do that in - // the client. $state.go('image', {imageId: ctrl.image.data.id, crop: undefined}, {reload: true}); }; - const hasSyndicationUsages$ = - imageUsagesService.getUsages(ctrl.image).hasSyndicationUsages$; + const freeImagesUpdateListener = $rootScope.$on('images-updated', (e, updatedImages) => { + const maybeUpdatedImage = updatedImages.find(u => u.data.id === ctrl.image.data.id); + if (maybeUpdatedImage) { + ctrl.image = maybeUpdatedImage; + bindUsages(ctrl.image); + } + }); - inject$($scope, usages$, ctrl, 'usages'); - inject$($scope, usagesCount$, ctrl, 'usagesCount'); - inject$($scope, hasSyndicationUsages$, ctrl, 'hasSyndicationUsages'); + $scope.$on('$destroy', freeImagesUpdateListener); }; }]); diff --git a/kahuna/public/js/image/controller.js b/kahuna/public/js/image/controller.js index e2a6247a64d..35d522d7c2c 100644 --- a/kahuna/public/js/image/controller.js +++ b/kahuna/public/js/image/controller.js @@ -190,9 +190,6 @@ image.controller('ImageCtrl', [ const usageTab = ctrl.tabs.find(_ => _.key === 'usages'); usageTab.value = `Usages (${value > 0 ? value : 'None'})`; usageTab.disabled = value === 0; - - // stop watching - freeUsageCountWatch(); }); // TODO: we should be able to rely on ctrl.crop.id instead once @@ -319,6 +316,7 @@ image.controller('ImageCtrl', [ const maybeUpdatedImage = updatedImages.find(updatedImage => ctrl.image.data.id === updatedImage.data.id); if (maybeUpdatedImage) { ctrl.image = maybeUpdatedImage; + ctrl.usagesCount = ctrl.image.data.usages.data.length; } }); @@ -340,5 +338,6 @@ image.controller('ImageCtrl', [ freeImagesUpdateListener(); freeImageDeleteListener(); freeImageDeleteFailListener(); + freeUsageCountWatch(); }); }]); diff --git a/kahuna/public/js/services/image/usages.js b/kahuna/public/js/services/image/usages.js index b94e1df5fc5..07519cb329e 100644 --- a/kahuna/public/js/services/image/usages.js +++ b/kahuna/public/js/services/image/usages.js @@ -87,7 +87,6 @@ imageUsagesService.factory('imageUsagesService', [function() { }); }); - const groupedByState$ = usages$ .map((usagesList) => usagesList.groupBy(usage => usage.get('status')));