var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var __metadata = (this && this.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};
var __param = (this && this.__param) || function (paramIndex, decorator) {
    return function (target, key) { decorator(target, key, paramIndex); }
};
import { EntityPermissionType, Metadata, FieldValueCollection } from '@memberjunction/core';
import { Arg, Ctx, DeleteOptionsInput, Field, FieldResolver, InputType, Mutation, ObjectType, PubSub, PubSubEngine, Resolver, Root, } from '@memberjunction/server';
import { createDownloadUrl, createUploadUrl, deleteObject, moveObject } from '@memberjunction/storage';
import { CreateMJFileInput, MJFileResolver as FileResolverBase, MJFile_, UpdateMJFileInput } from '../generated/generated.js';
import { FieldMapper } from '@memberjunction/graphql-dataprovider';
import { GetReadOnlyProvider } from '../util.js';
let CreateUploadURLInput = class CreateUploadURLInput {
    FileID;
};
__decorate([
    Field(() => String),
    __metadata("design:type", String)
], CreateUploadURLInput.prototype, "FileID", void 0);
CreateUploadURLInput = __decorate([
    InputType()
], CreateUploadURLInput);
export { CreateUploadURLInput };
let CreateFilePayload = class CreateFilePayload {
    File;
    UploadUrl;
    NameExists;
};
__decorate([
    Field(() => MJFile_),
    __metadata("design:type", MJFile_)
], CreateFilePayload.prototype, "File", void 0);
__decorate([
    Field(() => String),
    __metadata("design:type", String)
], CreateFilePayload.prototype, "UploadUrl", void 0);
__decorate([
    Field(() => Boolean),
    __metadata("design:type", Boolean)
], CreateFilePayload.prototype, "NameExists", void 0);
CreateFilePayload = __decorate([
    ObjectType()
], CreateFilePayload);
export { CreateFilePayload };
let FileExt = class FileExt extends MJFile_ {
    DownloadUrl;
};
__decorate([
    Field(() => String),
    __metadata("design:type", String)
], FileExt.prototype, "DownloadUrl", void 0);
FileExt = __decorate([
    ObjectType()
], FileExt);
export { FileExt };
let FileResolver = class FileResolver extends FileResolverBase {
    async CreateFile(input, context, pubSub) {
        const provider = GetReadOnlyProvider(context.providers, { allowFallbackToReadWrite: true });
        const user = this.GetUserFromPayload(context.userPayload);
        const fileEntity = await provider.GetEntityObject('Files', user);
        const providerEntity = await provider.GetEntityObject('File Storage Providers', user);
        fileEntity.CheckPermissions(EntityPermissionType.Create, true);
        const [sameName] = await this.findBy(provider, 'Files', { Name: input.Name, ProviderID: input.ProviderID }, context.userPayload.userRecord);
        const NameExists = Boolean(sameName);
        const success = fileEntity.NewRecord(FieldValueCollection.FromObject({ ...input, Status: 'Pending' }));
        if (!success) {
            return null;
        }
        const { updatedInput, UploadUrl } = await createUploadUrl(providerEntity, fileEntity);
        const mapper = new FieldMapper();
        fileEntity.SetMany(mapper.ReverseMapFields({ ...updatedInput }), true, true);
        await fileEntity.Save();
        const File = mapper.MapFields({ ...fileEntity.GetAll() });
        return { File, UploadUrl, NameExists };
    }
    async DownloadUrl(file, { userPayload }) {
        const md = new Metadata();
        const user = this.GetUserFromPayload(userPayload);
        const fileEntity = await md.GetEntityObject('Files', user);
        fileEntity.CheckPermissions(EntityPermissionType.Read, true);
        const providerEntity = await md.GetEntityObject('File Storage Providers', user);
        await providerEntity.Load(file.ProviderID);
        const url = await createDownloadUrl(providerEntity, file.ProviderKey ?? file.Name);
        return url;
    }
    async UpdateFile(input, context, pubSub) {
        const md = GetReadOnlyProvider(context.providers, { allowFallbackToReadWrite: true });
        const user = this.GetUserFromPayload(context.userPayload);
        const fileEntity = await md.GetEntityObject('Files', user);
        fileEntity.CheckPermissions(EntityPermissionType.Update, true);
        await fileEntity.Load(input.ID);
        if (fileEntity.Name !== input.Name) {
            const providerEntity = await md.GetEntityObject('File Storage Providers', user);
            await providerEntity.Load(fileEntity.ProviderID);
            const success = await moveObject(providerEntity, fileEntity.Name, input.Name);
            if (!success) {
                throw new Error('Error updating object name');
            }
        }
        const updatedFile = await super.UpdateMJFile(input, context, pubSub);
        return updatedFile;
    }
    async DeleteFile(ID, options, context, pubSub) {
        const md = GetReadOnlyProvider(context.providers, { allowFallbackToReadWrite: true });
        const userInfo = this.GetUserFromPayload(context.userPayload);
        const fileEntity = await md.GetEntityObject('Files', userInfo);
        await fileEntity.Load(ID);
        if (!fileEntity) {
            return null;
        }
        fileEntity.CheckPermissions(EntityPermissionType.Delete, true);
        if (fileEntity.Status === 'Uploaded') {
            const providerEntity = await md.GetEntityObject('File Storage Providers', userInfo);
            await providerEntity.Load(fileEntity.ProviderID);
            await deleteObject(providerEntity, fileEntity.ProviderKey ?? fileEntity.Name);
        }
        return super.DeleteMJFile(ID, options, context, pubSub);
    }
};
__decorate([
    Mutation(() => CreateFilePayload),
    __param(0, Arg('input', () => CreateMJFileInput)),
    __param(1, Ctx()),
    __param(2, PubSub()),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [CreateMJFileInput, Object, PubSubEngine]),
    __metadata("design:returntype", Promise)
], FileResolver.prototype, "CreateFile", null);
__decorate([
    FieldResolver(() => String),
    __param(0, Root()),
    __param(1, Ctx()),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [MJFile_, Object]),
    __metadata("design:returntype", Promise)
], FileResolver.prototype, "DownloadUrl", null);
__decorate([
    Mutation(() => MJFile_),
    __param(0, Arg('input', () => UpdateMJFileInput)),
    __param(1, Ctx()),
    __param(2, PubSub()),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [UpdateMJFileInput, Object, PubSubEngine]),
    __metadata("design:returntype", Promise)
], FileResolver.prototype, "UpdateFile", null);
__decorate([
    Mutation(() => MJFile_),
    __param(0, Arg('ID', () => String)),
    __param(1, Arg('options___', () => DeleteOptionsInput)),
    __param(2, Ctx()),
    __param(3, PubSub()),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [String, DeleteOptionsInput, Object, PubSubEngine]),
    __metadata("design:returntype", Promise)
], FileResolver.prototype, "DeleteFile", null);
FileResolver = __decorate([
    Resolver(MJFile_)
], FileResolver);
export { FileResolver };
//# sourceMappingURL=FileResolver.js.map