hippofish/packages/backend/src/server/api/endpoints/i/import-antennas.ts
Chocolate Pie 39748ea0c3
feat: アンテナのエクスポート・インポート (#10754)
* feat: アンテナのエクスポートに対応 (misskey-dev/misskey#10690)

* feat: アンテナのインポートに対応 (misskey-dev/misskey#10690)

* fix: タイポを修正

* feat: ユーザーリストをサポート

* fix: バグを直した

* fix: バグを直した

* fix: 適当に決めた変数名を変更

* fix

* fix: 変数の変更、リファクタリング
2023-05-06 08:17:55 +09:00

81 lines
2.7 KiB
TypeScript

import { Inject, Injectable } from '@nestjs/common';
import ms from 'ms';
import { Endpoint } from '@/server/api/endpoint-base.js';
import { QueueService } from '@/core/QueueService.js';
import type { AntennasRepository, DriveFilesRepository, UsersRepository, Antenna as _Antenna } from '@/models/index.js';
import { DI } from '@/di-symbols.js';
import { ApiError } from '../../error.js';
import { RoleService } from '@/core/RoleService.js';
import { DownloadService } from '@/core/DownloadService.js';
export const meta = {
secure: true,
requireCredential: true,
prohibitMoved: true,
limit: {
duration: ms('1hour'),
max: 1,
},
errors: {
noSuchFile: {
message: 'No such file.',
code: 'NO_SUCH_FILE',
id: '3b71d086-c3fa-431c-b01d-ded65a777172',
},
noSuchUser: {
message: 'No such user.',
code: 'NO_SUCH_USER',
id: 'e842c379-8ac7-4cf7-b07a-4d4de7e4671c',
},
emptyFile: {
message: 'That file is empty.',
code: 'EMPTY_FILE',
id: '7f60115d-8d93-4b0f-bd0e-3815dcbb389f',
},
tooManyAntennas: {
message: 'You cannot create antenna any more.',
code: 'TOO_MANY_ANTENNAS',
id: '600917d4-a4cb-4cc5-8ba8-7ac8ea3c7779',
},
},
} as const;
export const paramDef = {
type: 'object',
properties: {
fileId: { type: 'string', format: 'misskey:id' },
},
required: ['fileId'],
} as const;
@Injectable() // eslint-disable-next-line import/no-default-export
export default class extends Endpoint<typeof meta, typeof paramDef> {
constructor (
@Inject(DI.driveFilesRepository)
private driveFilesRepository: DriveFilesRepository,
@Inject(DI.antennasRepository)
private antennasRepository: AntennasRepository,
@Inject(DI.usersRepository)
private usersRepository: UsersRepository,
private roleService: RoleService,
private queueService: QueueService,
private downloadService: DownloadService
) {
super(meta, paramDef, async (ps, me) => {
const users = await this.usersRepository.findOneBy({ id: me.id });
if (users === null) throw new ApiError(meta.errors.noSuchUser);
const file = await this.driveFilesRepository.findOneBy({ id: ps.fileId });
if (file === null) throw new ApiError(meta.errors.noSuchFile);
if (file.size === 0) throw new ApiError(meta.errors.emptyFile);
const antennas: (_Antenna & { userListAcct: string[] | null })[] = JSON.parse(await this.downloadService.downloadTextFile(file.url));
const currentAntennasCount = await this.antennasRepository.countBy({ userId: me.id });
if (currentAntennasCount + antennas.length > (await this.roleService.getUserPolicies(me.id)).antennaLimit) {
throw new ApiError(meta.errors.tooManyAntennas);
}
this.queueService.createImportAntennasJob(me, antennas);
});
}
}
export type Antenna = (_Antenna & { userListAcct: string[] | null })[];