feat: Add langPref config option

This commit is contained in:
Essem 2024-02-03 16:45:38 -06:00
parent 4f45e72799
commit 8a416cd302
No known key found for this signature in database
GPG key ID: 7D497397CC3A2A8C
13 changed files with 78 additions and 40 deletions

View file

@ -91,6 +91,8 @@ type Source = {
customMOTD?: string[];
langPref?: string[];
signToActivityPubGet?: boolean;
checkActivityPubGetSignature?: boolean;
@ -153,6 +155,7 @@ export type Config = {
customMOTD: string[] | undefined;
signToActivityPubGet: boolean;
checkActivityPubGetSignature: boolean | undefined;
langPref: string[];
version: string;
publishTarballInsteadOfProvideRepositoryUrl: boolean;
@ -269,6 +272,7 @@ export function loadConfig(): Config {
inboxJobMaxAttempts: config.inboxJobMaxAttempts,
proxyRemoteFiles: config.proxyRemoteFiles,
customMOTD: config.customMOTD,
langPref: config.langPref ?? ['en', 'ja'],
signToActivityPubGet: config.signToActivityPubGet ?? true,
checkActivityPubGetSignature: config.checkActivityPubGetSignature,
mediaProxy: externalMediaProxy ?? internalMediaProxy,

View file

@ -25,7 +25,7 @@ import { StatusError } from '@/misc/status-error.js';
import { UtilityService } from '@/core/UtilityService.js';
import { bindThis } from '@/decorators.js';
import { checkHttps } from '@/misc/check-https.js';
import { langmap } from '@/misc/langmap.js';
import { langs } from '@/misc/langmap.js';
import { getOneApId, getApId, getOneApHrefNullable, validPost, isEmoji, getApType } from '../type.js';
import { ApLoggerService } from '../ApLoggerService.js';
import { ApMfmService } from '../ApMfmService.js';
@ -241,25 +241,37 @@ export class ApNoteService {
const cw = note.summary === '' ? null : note.summary;
let lang: string | null = null;
if (note.contentMap != null) {
for (const preferredLang of this.config.langPref) {
if (note.contentMap[preferredLang]) {
lang = preferredLang;
break;
}
}
if (!lang) lang = Object.keys(note.contentMap)[0];
if (!langs.includes(lang)) lang = null;
}
// テキストのパース
let text: string | null = null;
if (note.source?.mediaType === 'text/x.misskeymarkdown' && typeof note.source.content === 'string') {
text = note.source.content;
} else if (note.contentMap != null) {
const entry = Object.entries(note.contentMap)[0];
text = this.apMfmService.htmlToMfm(entry[1], note.tag);
} else if (note.contentMap != null && Object.keys(note.contentMap).length !== 0) {
let content: string;
if (lang) {
content = note.contentMap[lang];
} else {
content = Object.values(note.contentMap)[0];
}
text = this.apMfmService.htmlToMfm(content, note.tag);
} else if (typeof note._misskey_content !== 'undefined') {
text = note._misskey_content;
} else if (typeof note.content === 'string') {
text = this.apMfmService.htmlToMfm(note.content, note.tag);
}
let lang: string | null = null;
if (note.contentMap != null) {
const key = Object.keys(note.contentMap)[0];
lang = Object.keys(langmap).includes(key) ? key : null;
}
// vote
if (reply && reply.hasPoll) {
const poll = await this.pollsRepository.findOneByOrFail({ noteId: reply.id });
@ -459,25 +471,37 @@ export class ApNoteService {
const cw = note.summary === '' ? null : note.summary;
let lang: string | null = null;
if (note.contentMap != null) {
for (const preferredLang of this.config.langPref) {
if (note.contentMap[preferredLang]) {
lang = preferredLang;
break;
}
}
if (!lang) lang = Object.keys(note.contentMap)[0];
if (!langs.includes(lang)) lang = null;
}
// テキストのパース
let text: string | null = null;
if (note.source?.mediaType === 'text/x.misskeymarkdown' && typeof note.source.content === 'string') {
text = note.source.content;
} else if (note.contentMap != null) {
const entry = Object.entries(note.contentMap)[0];
text = this.apMfmService.htmlToMfm(entry[1], note.tag);
} else if (note.contentMap != null && Object.keys(note.contentMap).length !== 0) {
let content: string;
if (lang) {
content = note.contentMap[lang];
} else {
content = Object.values(note.contentMap)[0];
}
text = this.apMfmService.htmlToMfm(content, note.tag);
} else if (typeof note._misskey_content !== 'undefined') {
text = note._misskey_content;
} else if (typeof note.content === 'string') {
text = this.apMfmService.htmlToMfm(note.content, note.tag);
}
let lang: string | null = null;
if (note.contentMap != null) {
const key = Object.keys(note.contentMap)[0];
lang = Object.keys(langmap).includes(key) ? key : null;
}
// vote
if (reply && reply.hasPoll) {
const poll = await this.pollsRepository.findOneByOrFail({ noteId: reply.id });

View file

@ -385,3 +385,4 @@ export const iso639Regional = {
};
export const langmap = Object.assign({}, langmapNoRegion, iso639Regional);
export const langs = Object.keys(langmap);

View file

@ -2,7 +2,7 @@
* SPDX-FileCopyrightText: syuilo and misskey-project
* SPDX-License-Identifier: AGPL-3.0-only
*/
import { langmap } from '@/misc/langmap.js';
import { langs } from '@/misc/langmap.js';
export const packedNoteSchema = {
type: 'object',
@ -29,7 +29,7 @@ export const packedNoteSchema = {
},
lang: {
type: 'string',
enum: [...Object.keys(langmap)],
enum: langs,
nullable: true,
},
cw: {

View file

@ -17,7 +17,7 @@ import { birthdaySchema, listenbrainzSchema, descriptionSchema, locationSchema,
import type { MiUserProfile } from '@/models/UserProfile.js';
import { notificationTypes } from '@/types.js';
import { normalizeForSearch } from '@/misc/normalize-for-search.js';
import { langmap } from '@/misc/langmap.js';
import { langs } from '@/misc/langmap.js';
import { Endpoint } from '@/server/api/endpoint-base.js';
import { UserEntityService } from '@/core/entities/UserEntityService.js';
import { GlobalEventService } from '@/core/GlobalEventService.js';
@ -149,7 +149,7 @@ export const paramDef = {
location: { ...locationSchema, nullable: true },
birthday: { ...birthdaySchema, nullable: true },
listenbrainz: { ...listenbrainzSchema, nullable: true },
lang: { type: 'string', enum: [null, ...Object.keys(langmap)] as string[], nullable: true },
lang: { type: 'string', enum: [null, ...langs] as string[], nullable: true },
avatarId: { type: 'string', format: 'misskey:id', nullable: true },
avatarDecorations: { type: 'array', maxItems: 16, items: {
type: 'object',
@ -382,7 +382,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> { // eslint-
updates.backgroundUrl = null;
updates.backgroundBlurhash = null;
}
if (ps.avatarDecorations) {
const decorations = await this.avatarDecorationService.getAll(true);
const [myRoles, myPolicies] = await Promise.all([this.roleService.getUserRoles(user.id), this.roleService.getUserPolicies(user.id)]);

View file

@ -20,7 +20,7 @@ import { isPureRenote } from '@/misc/is-pure-renote.js';
import { MetaService } from '@/core/MetaService.js';
import { UtilityService } from '@/core/UtilityService.js';
import { IdentifiableError } from '@/misc/identifiable-error.js';
import { langmap } from '@/misc/langmap.js';
import { langs } from '@/misc/langmap.js';
import { ApiError } from '../../error.js';
export const meta = {
@ -137,7 +137,7 @@ export const paramDef = {
visibleUserIds: { type: 'array', uniqueItems: true, items: {
type: 'string', format: 'misskey:id',
} },
lang: { type: 'string', enum: Object.keys(langmap), nullable: true, maxLength: 10 },
lang: { type: 'string', enum: langs, nullable: true, maxLength: 10 },
cw: { type: 'string', nullable: true, minLength: 1, maxLength: 500 },
localOnly: { type: 'boolean', default: false },
reactionAcceptance: { type: 'string', nullable: true, enum: [null, 'likeOnly', 'likeOnlyForRemote', 'nonSensitiveOnly', 'nonSensitiveOnlyForLocalLikeOnlyForRemote'], default: null },

View file

@ -12,7 +12,7 @@ import { NoteEntityService } from '@/core/entities/NoteEntityService.js';
import { NoteEditService } from '@/core/NoteEditService.js';
import { DI } from '@/di-symbols.js';
import { IdentifiableError } from '@/misc/identifiable-error.js';
import { langmap } from '@/misc/langmap.js';
import { langs } from '@/misc/langmap.js';
import { ApiError } from '../../error.js';
export const meta = {
@ -165,7 +165,7 @@ export const paramDef = {
format: 'misskey:id',
},
},
lang: { type: 'string', enum: Object.keys(langmap), nullable: true, maxLength: 10 },
lang: { type: 'string', enum: langs, nullable: true, maxLength: 10 },
cw: { type: 'string', nullable: true, minLength: 1, maxLength: 500 },
localOnly: { type: 'boolean', default: false },
reactionAcceptance: { type: 'string', nullable: true, enum: [null, 'likeOnly', 'likeOnlyForRemote', 'nonSensitiveOnly', 'nonSensitiveOnlyForLocalLikeOnlyForRemote'], default: null },