2019-03-08 05:24:23 +01:00
|
|
|
import { Injectable } from '@angular/core';
|
2019-03-11 00:23:33 +01:00
|
|
|
import { BehaviorSubject } from 'rxjs';
|
2019-03-08 05:24:23 +01:00
|
|
|
|
|
|
|
import { AccountInfo } from '../states/accounts.state';
|
|
|
|
import { Attachment } from './models/mastodon.interfaces';
|
2019-10-02 06:14:40 +02:00
|
|
|
import { MastodonWrapperService } from './mastodon-wrapper.service';
|
2019-03-10 19:36:22 +01:00
|
|
|
import { NotificationService } from './notification.service';
|
2019-03-08 05:24:23 +01:00
|
|
|
|
|
|
|
|
|
|
|
@Injectable({
|
|
|
|
providedIn: 'root'
|
|
|
|
})
|
2019-03-11 00:23:33 +01:00
|
|
|
export class MediaService {
|
2019-03-08 05:24:23 +01:00
|
|
|
mediaSubject: BehaviorSubject<MediaWrapper[]> = new BehaviorSubject<MediaWrapper[]>([]);
|
2020-05-17 22:26:33 +02:00
|
|
|
fileCache: { [url: string]: File } = {};
|
2019-03-08 05:24:23 +01:00
|
|
|
|
2019-03-10 19:36:22 +01:00
|
|
|
constructor(
|
|
|
|
private readonly notificationService: NotificationService,
|
2019-10-02 06:14:40 +02:00
|
|
|
private readonly mastodonService: MastodonWrapperService) { }
|
2019-03-08 05:24:23 +01:00
|
|
|
|
2019-03-11 00:23:33 +01:00
|
|
|
uploadMedia(account: AccountInfo, files: File[]) {
|
2019-03-08 05:24:23 +01:00
|
|
|
for (let file of files) {
|
2019-03-10 19:36:22 +01:00
|
|
|
this.postMedia(account, file);
|
2019-03-11 00:23:33 +01:00
|
|
|
}
|
2019-03-08 05:24:23 +01:00
|
|
|
}
|
|
|
|
|
2019-03-11 00:23:33 +01:00
|
|
|
private postMedia(account: AccountInfo, file: File) {
|
2019-03-08 05:24:23 +01:00
|
|
|
const uniqueId = `${file.name}${file.size}${Math.random()}`;
|
2019-03-11 00:23:33 +01:00
|
|
|
const wrapper = new MediaWrapper(uniqueId, file, null);
|
2019-03-08 05:24:23 +01:00
|
|
|
|
|
|
|
let medias = this.mediaSubject.value;
|
|
|
|
medias.push(wrapper);
|
2019-07-26 05:24:29 +02:00
|
|
|
if (medias.length > 4) {
|
2019-04-10 04:16:25 +02:00
|
|
|
medias.splice(0, 1);
|
|
|
|
}
|
2019-03-08 05:24:23 +01:00
|
|
|
this.mediaSubject.next(medias);
|
|
|
|
|
2019-03-11 00:50:09 +01:00
|
|
|
this.mastodonService.uploadMediaAttachment(account, file, null)
|
2019-03-08 05:24:23 +01:00
|
|
|
.then((attachment: Attachment) => {
|
2020-05-17 22:26:33 +02:00
|
|
|
this.fileCache[attachment.url] = file;
|
2019-03-08 05:24:23 +01:00
|
|
|
let currentMedias = this.mediaSubject.value;
|
|
|
|
let currentMedia = currentMedias.filter(x => x.id === uniqueId)[0];
|
2019-03-11 00:23:33 +01:00
|
|
|
if (currentMedia) {
|
2019-03-08 05:24:23 +01:00
|
|
|
currentMedia.attachment = attachment;
|
|
|
|
this.mediaSubject.next(currentMedias);
|
|
|
|
}
|
|
|
|
})
|
2019-03-11 00:23:33 +01:00
|
|
|
.catch((err) => {
|
2019-03-10 19:36:22 +01:00
|
|
|
this.remove(wrapper);
|
2019-09-07 23:52:07 +02:00
|
|
|
this.notificationService.notifyHttpError(err, account);
|
2019-03-10 19:36:22 +01:00
|
|
|
});
|
|
|
|
}
|
2019-03-08 05:24:23 +01:00
|
|
|
|
2023-04-24 06:17:13 +02:00
|
|
|
loadMedia(attachments: Attachment[]) {
|
|
|
|
const wrappers: MediaWrapper[] = [];
|
|
|
|
|
|
|
|
for (const att of attachments) {
|
|
|
|
const uniqueId = `${att.id}${Math.random()}`;
|
|
|
|
const wrapper = new MediaWrapper(uniqueId, null, att);
|
|
|
|
wrapper.description = att.description;
|
|
|
|
wrapper.isEdited = true;
|
|
|
|
wrappers.push(wrapper);
|
|
|
|
}
|
|
|
|
|
|
|
|
this.mediaSubject.next(wrappers);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2023-04-24 00:27:47 +02:00
|
|
|
update(account: AccountInfo, media: MediaWrapper): Promise<void> {
|
2019-03-11 00:23:33 +01:00
|
|
|
if (media.attachment.description === media.description) return;
|
|
|
|
|
2023-04-24 06:17:13 +02:00
|
|
|
if (media.isEdited) {
|
|
|
|
media.attachment.description = media.description;
|
|
|
|
|
|
|
|
let medias = this.mediaSubject.value;
|
|
|
|
let updatedMedia = medias.filter(x => x.id === media.id)[0];
|
|
|
|
updatedMedia.attachment.description = media.attachment.description;
|
|
|
|
this.mediaSubject.next(medias);
|
|
|
|
} else {
|
|
|
|
return this.mastodonService.updateMediaAttachment(account, media.attachment.id, media.description)
|
|
|
|
.then((att: Attachment) => {
|
|
|
|
let medias = this.mediaSubject.value;
|
|
|
|
let updatedMedia = medias.filter(x => x.id === media.id)[0];
|
|
|
|
updatedMedia.attachment.description = att.description;
|
|
|
|
this.mediaSubject.next(medias);
|
|
|
|
})
|
|
|
|
.catch((err) => {
|
|
|
|
console.warn('failing update');
|
|
|
|
this.notificationService.notifyHttpError(err, account);
|
|
|
|
});
|
|
|
|
}
|
2019-03-08 05:24:23 +01:00
|
|
|
}
|
2019-03-10 19:36:22 +01:00
|
|
|
|
2023-04-24 00:27:47 +02:00
|
|
|
async retrieveUpToDateMedia(account: AccountInfo): Promise<MediaWrapper[]> {
|
|
|
|
const allMedia = this.mediaSubject.value;
|
|
|
|
let allPromises: Promise<any>[] = [];
|
2023-04-24 06:17:13 +02:00
|
|
|
|
|
|
|
for (const m of allMedia) {
|
2023-04-24 00:27:47 +02:00
|
|
|
let t = this.update(account, m);
|
|
|
|
allPromises.push(t);
|
|
|
|
}
|
|
|
|
|
|
|
|
await Promise.all(allPromises);
|
|
|
|
|
|
|
|
return allMedia;
|
|
|
|
}
|
|
|
|
|
2023-04-24 06:17:13 +02:00
|
|
|
addExistingMedia(media: MediaWrapper) {
|
|
|
|
if (!this.fileCache[media.attachment.url]) return;
|
|
|
|
|
2020-05-17 22:26:33 +02:00
|
|
|
media.file = this.fileCache[media.attachment.url];
|
|
|
|
let medias = this.mediaSubject.value;
|
|
|
|
medias.push(media);
|
|
|
|
this.mediaSubject.next(medias);
|
|
|
|
}
|
|
|
|
|
2019-03-11 00:47:15 +01:00
|
|
|
remove(media: MediaWrapper) {
|
2019-03-10 19:36:22 +01:00
|
|
|
let medias = this.mediaSubject.value;
|
|
|
|
let filteredMedias = medias.filter(x => x.id !== media.id);
|
|
|
|
this.mediaSubject.next(filteredMedias);
|
|
|
|
}
|
2019-03-11 00:23:33 +01:00
|
|
|
|
|
|
|
clearMedia() {
|
|
|
|
this.mediaSubject.next([]);
|
|
|
|
}
|
|
|
|
|
2019-03-11 00:47:15 +01:00
|
|
|
migrateMedias(account: AccountInfo) {
|
|
|
|
let medias = this.mediaSubject.value;
|
|
|
|
medias.forEach(media => {
|
2023-04-24 06:17:13 +02:00
|
|
|
if (!media.isEdited) {
|
|
|
|
media.isMigrating = true;
|
|
|
|
}
|
2019-03-11 00:47:15 +01:00
|
|
|
});
|
|
|
|
this.mediaSubject.next(medias);
|
|
|
|
|
|
|
|
for (let media of medias) {
|
2023-04-24 06:17:13 +02:00
|
|
|
if (media.isEdited) continue;
|
|
|
|
|
2019-03-11 00:50:09 +01:00
|
|
|
this.mastodonService.uploadMediaAttachment(account, media.file, media.description)
|
2019-03-11 00:47:15 +01:00
|
|
|
.then((attachment: Attachment) => {
|
2020-05-17 22:26:33 +02:00
|
|
|
this.fileCache[attachment.url] = media.file;
|
2019-03-11 00:47:15 +01:00
|
|
|
let currentMedias = this.mediaSubject.value;
|
|
|
|
let currentMedia = currentMedias.filter(x => x.id === media.id)[0];
|
|
|
|
if (currentMedia) {
|
|
|
|
currentMedia.attachment = attachment;
|
|
|
|
currentMedia.isMigrating = false;
|
|
|
|
this.mediaSubject.next(currentMedias);
|
|
|
|
}
|
|
|
|
})
|
|
|
|
.catch((err) => {
|
|
|
|
this.remove(media);
|
2019-09-07 23:52:07 +02:00
|
|
|
this.notificationService.notifyHttpError(err, account);
|
2019-03-11 00:47:15 +01:00
|
|
|
});
|
|
|
|
}
|
|
|
|
}
|
2019-03-08 05:24:23 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
export class MediaWrapper {
|
|
|
|
constructor(
|
|
|
|
public id: string,
|
2019-03-11 00:23:33 +01:00
|
|
|
public file: File,
|
2019-07-26 05:24:29 +02:00
|
|
|
attachment: Attachment) {
|
2023-04-24 06:17:13 +02:00
|
|
|
this.attachment = attachment;
|
2019-07-26 05:24:29 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
private _attachment: Attachment;
|
|
|
|
public get attachment(): Attachment {
|
|
|
|
return this._attachment;
|
|
|
|
}
|
|
|
|
|
2023-04-24 06:17:13 +02:00
|
|
|
public set attachment(value: Attachment) {
|
2019-07-26 05:24:29 +02:00
|
|
|
if (value && value.meta && value.meta.audio_encode) {
|
|
|
|
this.audioType = `audio/${value.meta.audio_encode}`;
|
|
|
|
} else if (value && value.pleroma && value.pleroma.mime_type) {
|
|
|
|
this.audioType = value.pleroma.mime_type;
|
|
|
|
}
|
|
|
|
|
|
|
|
this._attachment = value;
|
|
|
|
}
|
2019-03-11 00:23:33 +01:00
|
|
|
|
|
|
|
public description: string;
|
|
|
|
public isMigrating: boolean;
|
2019-07-26 05:24:29 +02:00
|
|
|
public audioType: string;
|
2023-04-24 06:17:13 +02:00
|
|
|
|
|
|
|
public isEdited: boolean;
|
2019-03-08 05:24:23 +01:00
|
|
|
}
|