Merge branch 'main' into forkey-rebrand
Some checks failed
Check Misskey JS version / Check version (pull_request) Successful in 1m24s
Lint / pnpm_install (pull_request) Successful in 2m48s
API report (misskey.js) / report (push) Successful in 8m24s
Test (backend) / unit (22.x) (pull_request) Successful in 9m5s
Test (frontend) / vitest (22.x) (pull_request) Successful in 3m35s
Test (backend) / e2e (22.x) (pull_request) Successful in 9m54s
Test (production install and build) / production (22.x) (pull_request) Successful in 2m59s
Test (backend) / validate-api-json (22.x) (pull_request) Successful in 3m52s
Lint / lint (backend) (pull_request) Successful in 3m9s
Lint / lint (misskey-js) (pull_request) Successful in 2m45s
Lint / lint (sw) (pull_request) Successful in 2m58s
Lint / lint (frontend) (pull_request) Failing after 9m17s
Lint / typecheck (backend) (pull_request) Successful in 3m33s
Lint / typecheck (misskey-js) (pull_request) Successful in 2m52s

This commit is contained in:
ashten 2025-01-18 23:56:50 +00:00
commit b94aadf72f
47 changed files with 126 additions and 350 deletions

View file

@ -1,7 +1,7 @@
**/.git **/.git
.autogen .autogen
.github .forgejo
.travis .travis
.vscode .vscode
.config .config

View file

@ -0,0 +1,16 @@
# Workaround for Forgejo not supporting port redirection
url: 'http://misskey.local'
port: 61812
db:
host: postgres
port: 5432
db: test-misskey
user: postgres
pass: ''
redis:
host: dragonfly
port: 6379
id: aidx

View file

@ -21,7 +21,7 @@ jobs:
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false

View file

@ -3,9 +3,7 @@ name: Check Misskey JS version
on: on:
push: push:
branches: branches:
- beta - main
- io
- host
paths: paths:
- packages/misskey-js/package.json - packages/misskey-js/package.json
- package.json - package.json

View file

@ -3,9 +3,7 @@ name: Lint
on: on:
push: push:
branches: branches:
- beta - main
- io
- host
paths: paths:
- packages/backend/** - packages/backend/**
- packages/frontend/** - packages/frontend/**
@ -28,7 +26,7 @@ jobs:
with: with:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- uses: pnpm/action-setup@v4 - uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- uses: actions/setup-node@v4.1.0 - uses: actions/setup-node@v4.1.0
@ -53,7 +51,7 @@ jobs:
with: with:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- uses: pnpm/action-setup@v4 - uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- uses: actions/setup-node@v4.1.0 - uses: actions/setup-node@v4.1.0
@ -77,7 +75,7 @@ jobs:
with: with:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- uses: pnpm/action-setup@v4 - uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- uses: actions/setup-node@v4.1.0 - uses: actions/setup-node@v4.1.0

View file

@ -3,9 +3,7 @@ name: Test (backend)
on: on:
push: push:
branches: branches:
- beta - main
- io
- host
paths: paths:
- packages/backend/** - packages/backend/**
# for permissions # for permissions
@ -27,8 +25,6 @@ jobs:
services: services:
postgres: postgres:
image: postgres:15 image: postgres:15
ports:
- 54312:5432
env: env:
POSTGRES_DB: test-misskey POSTGRES_DB: test-misskey
POSTGRES_HOST_AUTH_METHOD: trust POSTGRES_HOST_AUTH_METHOD: trust
@ -44,8 +40,6 @@ jobs:
DFLY_conn_io_threads: 4 DFLY_conn_io_threads: 4
DFLY_epoll_file_threads: 4 DFLY_epoll_file_threads: 4
DFLY_proactor_threads: 4 DFLY_proactor_threads: 4
ports:
- 56312:6379
steps: steps:
- uses: actions/checkout@v4 - uses: actions/checkout@v4
@ -53,11 +47,11 @@ jobs:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- name: Install FFmpeg - name: Install FFmpeg
uses: FedericoCarboni/setup-ffmpeg@v3 uses: https://github.com/FedericoCarboni/setup-ffmpeg@v3
- name: Use Node.js ${{ matrix.node-version }} - name: Use Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v4.1.0 uses: actions/setup-node@v4.1.0
with: with:
@ -67,16 +61,11 @@ jobs:
- name: Check pnpm-lock.yaml - name: Check pnpm-lock.yaml
run: git diff --exit-code pnpm-lock.yaml run: git diff --exit-code pnpm-lock.yaml
- name: Copy Configure - name: Copy Configure
run: cp .github/misskey/test.yml .config run: cp .forgejo/misskey/test-forgejo.yml .config/test.yml
- name: Build - name: Build
run: pnpm build run: pnpm build
- name: Test - name: Test
run: pnpm --filter backend test-and-coverage run: pnpm --filter backend test
- name: Upload to Codecov
uses: codecov/codecov-action@v5
with:
token: ${{ secrets.CODECOV_TOKEN }}
files: ./packages/backend/coverage/coverage-final.json
e2e: e2e:
runs-on: ubuntu-latest runs-on: ubuntu-latest
@ -88,8 +77,6 @@ jobs:
services: services:
postgres: postgres:
image: postgres:15 image: postgres:15
ports:
- 54312:5432
env: env:
POSTGRES_DB: test-misskey POSTGRES_DB: test-misskey
POSTGRES_HOST_AUTH_METHOD: trust POSTGRES_HOST_AUTH_METHOD: trust
@ -105,8 +92,6 @@ jobs:
DFLY_conn_io_threads: 4 DFLY_conn_io_threads: 4
DFLY_epoll_file_threads: 4 DFLY_epoll_file_threads: 4
DFLY_proactor_threads: 4 DFLY_proactor_threads: 4
ports:
- 56312:6379
steps: steps:
- uses: actions/checkout@v4 - uses: actions/checkout@v4
@ -114,7 +99,7 @@ jobs:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- name: Use Node.js ${{ matrix.node-version }} - name: Use Node.js ${{ matrix.node-version }}
@ -126,13 +111,8 @@ jobs:
- name: Check pnpm-lock.yaml - name: Check pnpm-lock.yaml
run: git diff --exit-code pnpm-lock.yaml run: git diff --exit-code pnpm-lock.yaml
- name: Copy Configure - name: Copy Configure
run: cp .github/misskey/test.yml .config run: cp .forgejo/misskey/test-forgejo.yml .config/test.yml
- name: Build - name: Build
run: pnpm build run: pnpm build
- name: Test - name: Test
run: pnpm --filter backend test-and-coverage:e2e run: pnpm --filter backend test:e2e
- name: Upload to Codecov
uses: codecov/codecov-action@v5
with:
token: ${{ secrets.CODECOV_TOKEN }}
files: ./packages/backend/coverage/coverage-final.json

View file

@ -35,7 +35,7 @@ jobs:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- name: Use Node.js ${{ matrix.node-version }} - name: Use Node.js ${{ matrix.node-version }}
@ -47,13 +47,8 @@ jobs:
- name: Check pnpm-lock.yaml - name: Check pnpm-lock.yaml
run: git diff --exit-code pnpm-lock.yaml run: git diff --exit-code pnpm-lock.yaml
- name: Copy Configure - name: Copy Configure
run: cp .github/misskey/test.yml .config run: cp .forgejo/misskey/test-forgejo.yml .config/test.yml
- name: Build - name: Build
run: pnpm build run: pnpm build
- name: Test - name: Test
run: pnpm --filter frontend test-and-coverage run: pnpm --filter frontend test
- name: Upload Coverage
uses: codecov/codecov-action@v5
with:
token: ${{ secrets.CODECOV_TOKEN }}
files: ./packages/frontend/coverage/coverage-final.json

View file

@ -6,9 +6,7 @@ name: Test (misskey.js)
on: on:
push: push:
branches: branches:
- beta - main
- io
- host
paths: paths:
- packages/misskey-js/** - packages/misskey-js/**
pull_request: pull_request:
@ -33,7 +31,7 @@ jobs:
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
@ -56,9 +54,3 @@ jobs:
run: pnpm --filter misskey-js test run: pnpm --filter misskey-js test
env: env:
CI: true CI: true
- name: Upload Coverage
uses: codecov/codecov-action@v5
with:
token: ${{ secrets.CODECOV_TOKEN }}
files: ./packages/misskey-js/coverage/coverage-final.json

View file

@ -3,9 +3,7 @@ name: Test (production install and build)
on: on:
push: push:
branches: branches:
- beta - main
- io
- host
pull_request: pull_request:
env: env:
@ -25,7 +23,7 @@ jobs:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- name: Use Node.js ${{ matrix.node-version }} - name: Use Node.js ${{ matrix.node-version }}
@ -37,6 +35,6 @@ jobs:
- name: Check pnpm-lock.yaml - name: Check pnpm-lock.yaml
run: git diff --exit-code pnpm-lock.yaml run: git diff --exit-code pnpm-lock.yaml
- name: Copy Configure - name: Copy Configure
run: cp .github/misskey/test.yml .config/default.yml run: cp .forgejo/misskey/test-forgejo.yml .config/default.yml
- name: Build - name: Build
run: pnpm build run: pnpm build

View file

@ -3,9 +3,7 @@ name: Test (backend)
on: on:
push: push:
branches: branches:
- beta - main
- io
- host
paths: paths:
- packages/backend/** - packages/backend/**
pull_request: pull_request:
@ -26,7 +24,7 @@ jobs:
fetch-depth: 0 fetch-depth: 0
submodules: true submodules: true
- name: Install pnpm - name: Install pnpm
uses: pnpm/action-setup@v4 uses: pnpm/action-setup@v4.0.0
with: with:
run_install: false run_install: false
- name: Use Node.js ${{ matrix.node-version }} - name: Use Node.js ${{ matrix.node-version }}

View file

@ -1,52 +0,0 @@
name: Publish Docker image (beta)
on:
push:
branches:
- beta
workflow_dispatch:
jobs:
push_to_registry:
name: Push Docker image to GitHub Container Registry
runs-on: ubuntu-22.04
if: github.repository == 'MisskeyIO/misskey'
steps:
- name: Check out the repo
uses: actions/checkout@v4
with:
fetch-depth: 0
submodules: true
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v3
with:
platforms: linux/amd64
- name: Docker meta
id: meta
uses: docker/metadata-action@v5
with:
images: ghcr.io/misskeyio/misskey
- name: Log in to GitHub Container Registry
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Prepare image tags
run: |
echo "FORMATTED_BRANCH_NAME=$(echo ${{ github.ref_name }} | sed -e 's/\//-/g' )" >> $GITHUB_ENV
- name: Build and Push to GitHub Container Registry
uses: docker/build-push-action@v6
with:
builder: ${{ steps.buildx.outputs.name }}
context: .
push: true
platforms: ${{ steps.buildx.outputs.platforms }}
provenance: false
labels: ${{ env.FORMATTED_BRANCH_NAME }}
cache-from: type=registry,ref=ghcr.io/misskeyio/misskey:io-buildcache
cache-to: type=registry,ref=ghcr.io/misskeyio/misskey:io-buildcache,mode=max
tags: |
ghcr.io/misskeyio/misskey:beta
ghcr.io/misskeyio/misskey:${{ env.FORMATTED_BRANCH_NAME }}

View file

@ -1,54 +0,0 @@
name: Publish Docker image (host)
on:
push:
branches:
- host
tags:
- '**-host.*'
workflow_dispatch:
jobs:
push_to_registry:
name: Push Docker image to GitHub Container Registry
runs-on: ubuntu-22.04
if: github.repository == 'MisskeyIO/misskey'
steps:
- name: Check out the repo
uses: actions/checkout@v4
with:
fetch-depth: 0
submodules: true
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v3
with:
platforms: linux/amd64
- name: Docker meta
id: meta
uses: docker/metadata-action@v5
with:
images: ghcr.io/misskeyio/misskey
- name: Log in to GitHub Container Registry
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Prepare image tags
run: |
echo "FORMATTED_BRANCH_NAME=$(echo ${{ github.ref_name }} | sed -e 's/\//-/g' )" >> $GITHUB_ENV
- name: Build and Push to GitHub Container Registry
uses: docker/build-push-action@v6
with:
builder: ${{ steps.buildx.outputs.name }}
context: .
push: true
platforms: ${{ steps.buildx.outputs.platforms }}
provenance: false
labels: ${{ env.FORMATTED_BRANCH_NAME }}
cache-from: type=registry,ref=ghcr.io/misskeyio/misskey:host-buildcache
cache-to: type=registry,ref=ghcr.io/misskeyio/misskey:host-buildcache,mode=max
tags: |
ghcr.io/misskeyio/misskey:host
ghcr.io/misskeyio/misskey:${{ env.FORMATTED_BRANCH_NAME }}

View file

@ -1,54 +0,0 @@
name: Publish Docker image (io)
on:
push:
branches:
- io
tags:
- '**-io.*'
workflow_dispatch:
jobs:
push_to_registry:
name: Push Docker image to GitHub Container Registry
runs-on: ubuntu-22.04
if: github.repository == 'MisskeyIO/misskey'
steps:
- name: Check out the repo
uses: actions/checkout@v4
with:
fetch-depth: 0
submodules: true
- name: Set up Docker Buildx
id: buildx
uses: docker/setup-buildx-action@v3
with:
platforms: linux/amd64
- name: Docker meta
id: meta
uses: docker/metadata-action@v5
with:
images: ghcr.io/misskeyio/misskey
- name: Log in to GitHub Container Registry
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Prepare image tags
run: |
echo "FORMATTED_BRANCH_NAME=$(echo ${{ github.ref_name }} | sed -e 's/\//-/g' )" >> $GITHUB_ENV
- name: Build and Push to GitHub Container Registry
uses: docker/build-push-action@v6
with:
builder: ${{ steps.buildx.outputs.name }}
context: .
push: true
platforms: ${{ steps.buildx.outputs.platforms }}
provenance: false
labels: ${{ env.FORMATTED_BRANCH_NAME }}
cache-from: type=registry,ref=ghcr.io/misskeyio/misskey:io-buildcache
cache-to: type=registry,ref=ghcr.io/misskeyio/misskey:io-buildcache,mode=max
tags: |
ghcr.io/misskeyio/misskey:latest
ghcr.io/misskeyio/misskey:${{ env.FORMATTED_BRANCH_NAME }}

View file

@ -1,38 +0,0 @@
name: Dockle
on:
push:
branches:
- beta
- io
- host
pull_request:
jobs:
dockle:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
with:
fetch-depth: 0
submodules: true
- name: Build an image from Dockerfile
uses: docker/build-push-action@v6
with:
context: .
push: false
provenance: false
cache-from: type=registry,ref=ghcr.io/misskeyio/misskey:io-buildcache
tags: |
misskey:scan
- name: Run dockle
uses: docker://goodwithtech/dockle:v0.4.14
env:
DOCKLE_OUTPUT_FORMAT: list
DOCKLE_EXIT_CODE: 1
DOCKLE_EXIT_LEVEL: WARN
DOCKLE_IGNORES: CIS-DI-0005,CIS-DI-0010
DOCKLE_DEBUG: true
with:
args: 'misskey:scan'

View file

@ -1,16 +0,0 @@
name: "Pull Request Labeler"
on:
pull_request_target:
branches-ignore:
- 'l10n_develop'
jobs:
triage:
permissions:
contents: read
pull-requests: write
runs-on: ubuntu-latest
steps:
- uses: actions/labeler@v5
with:
repo-token: "${{ secrets.GITHUB_TOKEN }}"

View file

@ -161,7 +161,7 @@ pnpm dev
### Run test ### Run test
Create a config file. Create a config file.
``` ```
cp .github/misskey/test.yml .config/ cp .forgejo/misskey/test.yml .config/
``` ```
Prepare DB/Redis for testing. Prepare DB/Redis for testing.
``` ```
@ -188,8 +188,8 @@ TODO
- `MISSKEY_WEBFINGER_USE_HTTP`: If it's set true, WebFinger requests will be http instead of https, useful for testing federation between servers in localhost. NEVER USE IN PRODUCTION. - `MISSKEY_WEBFINGER_USE_HTTP`: If it's set true, WebFinger requests will be http instead of https, useful for testing federation between servers in localhost. NEVER USE IN PRODUCTION.
## Continuous integration ## Continuous integration
Misskey uses GitHub Actions for executing automated tests. Misskey uses Forgejo Actions for executing automated tests.
Configuration files are located in [`/.github/workflows`](/.github/workflows). Configuration files are located in [`/.forgejo/workflows`](/.forgejo/workflows).
## Vue ## Vue
Misskey uses Vue(v3) as its front-end framework. Misskey uses Vue(v3) as its front-end framework.

View file

@ -58,9 +58,9 @@ export class ChartManagementService implements OnApplicationShutdown {
@bindThis @bindThis
public async start() { public async start() {
// 20分おきにメモリ情報をDBに書き込み // 20分おきにメモリ情報をDBに書き込み
this.saveIntervalId = setInterval(() => { this.saveIntervalId = setInterval(async () => {
for (const chart of this.charts) { for (const chart of this.charts) {
chart.save(); await chart.save();
} }
}, 1000 * 60 * 20); }, 1000 * 60 * 20);
} }
@ -69,9 +69,9 @@ export class ChartManagementService implements OnApplicationShutdown {
public async dispose(): Promise<void> { public async dispose(): Promise<void> {
clearInterval(this.saveIntervalId); clearInterval(this.saveIntervalId);
if (process.env.NODE_ENV !== 'test') { if (process.env.NODE_ENV !== 'test') {
await Promise.all( for (const chart of this.charts) {
this.charts.map(chart => chart.save()), await chart.save();
); }
} }
} }

View file

@ -9,17 +9,9 @@ export const L_CHARS = '0123456789abcdefghijklmnopqrstuvwxyz';
const LU_CHARS = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'; const LU_CHARS = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
export function secureRndstr(length = 32, { chars = LU_CHARS } = {}): string { export function secureRndstr(length = 32, { chars = LU_CHARS } = {}): string {
const chars_len = chars.length;
let str = ''; let str = '';
for (let i = 0; i < length; i++) { for (let i = 0; i < length; i++) {
let rand = Math.floor((crypto.randomBytes(1).readUInt8(0) / 0xFF) * chars_len); str += chars.charAt(crypto.randomInt(chars.length));
if (rand === chars_len) {
rand = chars_len - 1;
} }
str += chars.charAt(rand);
}
return str; return str;
} }

View file

@ -651,6 +651,14 @@ export const packedMeDetailedOnlySchema = {
type: 'boolean', type: 'boolean',
nullable: true, optional: true, nullable: true, optional: true,
}, },
approved: {
type: 'boolean',
nullable: false, optional: true,
},
signupReason: {
type: 'string',
nullable: true, optional: true,
},
securityKeysList: { securityKeysList: {
type: 'array', type: 'array',
nullable: false, optional: true, nullable: false, optional: true,

View file

@ -48,20 +48,18 @@ export class CleanChartsProcessorService {
public async process(): Promise<void> { public async process(): Promise<void> {
this.logger.info('Clean charts...'); this.logger.info('Clean charts...');
await Promise.all([ await this.federationChart.clean();
this.federationChart.clean(), await this.notesChart.clean();
this.notesChart.clean(), await this.usersChart.clean();
this.usersChart.clean(), await this.activeUsersChart.clean();
this.activeUsersChart.clean(), await this.instanceChart.clean();
this.instanceChart.clean(), await this.perUserNotesChart.clean();
this.perUserNotesChart.clean(), await this.perUserPvChart.clean();
this.perUserPvChart.clean(), await this.driveChart.clean();
this.driveChart.clean(), await this.perUserReactionsChart.clean();
this.perUserReactionsChart.clean(), await this.perUserFollowingChart.clean();
this.perUserFollowingChart.clean(), await this.perUserDriveChart.clean();
this.perUserDriveChart.clean(), await this.apRequestChart.clean();
this.apRequestChart.clean(),
]);
this.logger.succ('All charts successfully cleaned.'); this.logger.succ('All charts successfully cleaned.');
} }

View file

@ -31,11 +31,9 @@ export class ResyncChartsProcessorService {
// TODO: ユーザーごとのチャートも更新する // TODO: ユーザーごとのチャートも更新する
// TODO: インスタンスごとのチャートも更新する // TODO: インスタンスごとのチャートも更新する
await Promise.all([ await this.driveChart.resync();
this.driveChart.resync(), await this.notesChart.resync();
this.notesChart.resync(), await this.usersChart.resync();
this.usersChart.resync(),
]);
this.logger.succ('All charts successfully resynced.'); this.logger.succ('All charts successfully resynced.');
} }

View file

@ -48,20 +48,18 @@ export class TickChartsProcessorService {
public async process(): Promise<void> { public async process(): Promise<void> {
this.logger.info('Tick charts...'); this.logger.info('Tick charts...');
await Promise.all([ await this.federationChart.tick(false);
this.federationChart.tick(false), await this.notesChart.tick(false);
this.notesChart.tick(false), await this.usersChart.tick(false);
this.usersChart.tick(false), await this.activeUsersChart.tick(false);
this.activeUsersChart.tick(false), await this.instanceChart.tick(false);
this.instanceChart.tick(false), await this.perUserNotesChart.tick(false);
this.perUserNotesChart.tick(false), await this.perUserPvChart.tick(false);
this.perUserPvChart.tick(false), await this.driveChart.tick(false);
this.driveChart.tick(false), await this.perUserReactionsChart.tick(false);
this.perUserReactionsChart.tick(false), await this.perUserFollowingChart.tick(false);
this.perUserFollowingChart.tick(false), await this.perUserDriveChart.tick(false);
this.perUserDriveChart.tick(false), await this.apRequestChart.tick(false);
this.apRequestChart.tick(false),
]);
this.logger.succ('All charts successfully ticked.'); this.logger.succ('All charts successfully ticked.');
} }

View file

@ -244,7 +244,7 @@ export class SignupApiService {
} else { } else {
try { try {
const { account, secret } = await this.signupService.signup({ const { account, secret } = await this.signupService.signup({
username, password, host, reason username, password, host, reason,
}); });
if (instance.approvalRequiredForSignup) { if (instance.approvalRequiredForSignup) {

View file

@ -63,12 +63,10 @@ export default class extends Endpoint<typeof meta, typeof paramDef> { // eslint-
await this.usedUsernamesRepository.delete({ username: user.username }); await this.usedUsernamesRepository.delete({ username: user.username });
//Actually delete it since the last function doesnt actually delete the account //Actually delete it since the last function doesnt actually delete the account
//Note: Before approval these accounts wont federate so this is totally fine. //Note: Before approval these accounts wont federate so this is totally fine.
await this.usersRepository.delete(user.id); await this.usersRepository.delete(user.id);
this.moderationLogService.log(me, 'decline', { this.moderationLogService.log(me, 'decline', {
userId: user.id, userId: user.id,
userUsername: user.username, userUsername: user.username,

View file

@ -40,7 +40,7 @@ export const meta = {
res: { res: {
type: 'object', type: 'object',
optional: false, nullable: false, optional: true, nullable: false,
properties: { properties: {
createdNote: { createdNote: {
type: 'object', type: 'object',
@ -207,6 +207,7 @@ export const paramDef = {
}, },
required: ['choices'], required: ['choices'],
}, },
noCreatedNote: { type: 'boolean', default: false },
}, },
// (re)note with text, files and poll are optional // (re)note with text, files and poll are optional
if: { if: {
@ -281,7 +282,8 @@ export default class extends Endpoint<typeof meta, typeof paramDef> { // eslint-
const note = await this.notesRepository.findOneBy({ id: idempotent }); const note = await this.notesRepository.findOneBy({ id: idempotent });
if (note) { if (note) {
logger.info('The request has already been processed.', { noteId: note.id }); logger.info('The request has already been processed.', { noteId: note.id });
return { createdNote: await this.noteEntityService.pack(note, me) }; if (ps.noCreatedNote) return;
else return { createdNote: await this.noteEntityService.pack(note, me) };
} }
} }
@ -453,7 +455,8 @@ export default class extends Endpoint<typeof meta, typeof paramDef> { // eslint-
await this.redisForTimelines.set(`note:idempotent:${me.id}:${hash}`, note.id, 'EX', 60); await this.redisForTimelines.set(`note:idempotent:${me.id}:${hash}`, note.id, 'EX', 60);
logger.info('Successfully created a note.', { noteId: note.id }); logger.info('Successfully created a note.', { noteId: note.id });
return { if (ps.noCreatedNote) return;
else return {
createdNote: await this.noteEntityService.pack(note, me), createdNote: await this.noteEntityService.pack(note, me),
}; };
} catch (err) { } catch (err) {

View file

@ -41,7 +41,8 @@ window.onload = async () => {
document.getElementById('submit').addEventListener('click', () => { document.getElementById('submit').addEventListener('click', () => {
api('notes/create', { api('notes/create', {
text: document.getElementById('text').value text: document.getElementById('text').value,
noCreatedNote: true,
}).then(() => { }).then(() => {
location.reload(); location.reload();
}); });

View file

@ -151,6 +151,8 @@ describe('ユーザー', () => {
...(security ? { ...(security ? {
email: user.email, email: user.email,
emailVerified: user.emailVerified, emailVerified: user.emailVerified,
approved: user.approved,
signupReason: user.signupReason,
securityKeysList: user.securityKeysList, securityKeysList: user.securityKeysList,
} : {}), } : {}),
}); });

View file

@ -798,6 +798,7 @@ async function post(ev?: MouseEvent) {
visibility: visibility.value, visibility: visibility.value,
visibleUserIds: visibility.value === 'specified' ? visibleUsers.value.map(u => u.id) : undefined, visibleUserIds: visibility.value === 'specified' ? visibleUsers.value.map(u => u.id) : undefined,
reactionAcceptance: reactionAcceptance.value, reactionAcceptance: reactionAcceptance.value,
noCreatedNote: true,
}; };
if (withHashtags.value && hashtags.value && hashtags.value.trim() !== '') { if (withHashtags.value && hashtags.value && hashtags.value.trim() !== '') {

View file

@ -46,7 +46,7 @@ const pagination = {
function deleted(id: string) { function deleted(id: string) {
if (paginationComponent.value) { if (paginationComponent.value) {
paginationComponent.value.items = paginationComponent.value.items.filter( paginationComponent.value.items = paginationComponent.value.items.filter(
(item: any) => item.id !== id (item: any) => item.id !== id,
); );
} }
} }

View file

@ -46,6 +46,7 @@ function start(_game: Misskey.entities.ReversiGameDetailed) {
misskeyApi('notes/create', { misskeyApi('notes/create', {
text: i18n.ts._reversi.iStartedAGame + '\n' + location.href, text: i18n.ts._reversi.iStartedAGame + '\n' + location.href,
visibility: 'home', visibility: 'home',
noCreatedNote: true,
}); });
} }

View file

@ -490,7 +490,7 @@ const routes: RouteDef[] = [{
path: '/', path: '/',
component: page(() => import('@/pages/_empty_.vue')), component: page(() => import('@/pages/_empty_.vue')),
}], }],
},{ }, {
path: '/my/notifications', path: '/my/notifications',
component: page(() => import('@/pages/notifications.vue')), component: page(() => import('@/pages/notifications.vue')),
loginRequired: true, loginRequired: true,

View file

@ -543,6 +543,7 @@ export function getRenoteMenu(props: {
misskeyApi('notes/create', { misskeyApi('notes/create', {
renoteId: appearNote.id, renoteId: appearNote.id,
channelId: appearNote.channelId, channelId: appearNote.channelId,
noCreatedNote: true,
}).then(() => { }).then(() => {
os.toast(i18n.ts.renoted); os.toast(i18n.ts.renoted);
}); });
@ -589,6 +590,7 @@ export function getRenoteMenu(props: {
localOnly, localOnly,
visibility, visibility,
renoteId: appearNote.id, renoteId: appearNote.id,
noCreatedNote: true,
}).then(() => { }).then(() => {
os.toast(i18n.ts.renoted); os.toast(i18n.ts.renoted);
}); });
@ -630,6 +632,7 @@ export function getRenoteMenu(props: {
misskeyApi('notes/create', { misskeyApi('notes/create', {
renoteId: appearNote.id, renoteId: appearNote.id,
channelId: channel.id, channelId: channel.id,
noCreatedNote: true,
}).then(() => { }).then(() => {
os.toast(i18n.tsx.renotedToX({ name: channel.name })); os.toast(i18n.tsx.renotedToX({ name: channel.name }));
}); });

View file

@ -298,7 +298,7 @@ export function getUserMenu(user: Misskey.entities.UserDetailed, router: IRouter
const { canceled: canceled3, result: memo } = await os.inputText({ const { canceled: canceled3, result: memo } = await os.inputText({
title: i18n.ts.addMemo, title: i18n.ts.addMemo,
type: 'textarea', type: 'textarea',
placeholder: i18n.ts.memo, default: '',
}); });
if (canceled3) return; if (canceled3) return;

View file

@ -4103,6 +4103,8 @@ export type components = {
policies: components['schemas']['RolePolicies']; policies: components['schemas']['RolePolicies'];
email?: string | null; email?: string | null;
emailVerified?: boolean | null; emailVerified?: boolean | null;
approved?: boolean;
signupReason?: string | null;
securityKeysList?: { securityKeysList?: {
/** /**
* Format: id * Format: id
@ -15517,6 +15519,8 @@ export type operations = {
type?: string | null; type?: string | null;
/** @enum {string|null} */ /** @enum {string|null} */
sort?: '+createdAt' | '-createdAt' | '+name' | '-name' | '+size' | '-size' | null; sort?: '+createdAt' | '-createdAt' | '+name' | '-name' | '+size' | '-size' | null;
/** @default */
searchQuery?: string;
}; };
}; };
}; };
@ -16116,6 +16120,8 @@ export type operations = {
* @default null * @default null
*/ */
folderId?: string | null; folderId?: string | null;
/** @default */
searchQuery?: string;
}; };
}; };
}; };
@ -23459,6 +23465,8 @@ export type operations = {
expiresAt?: number | null; expiresAt?: number | null;
expiredAfter?: number | null; expiredAfter?: number | null;
}) | null; }) | null;
/** @default false */
noCreatedNote?: boolean;
}; };
}; };
}; };
@ -23471,6 +23479,10 @@ export type operations = {
}; };
}; };
}; };
/** @description OK (without any results) */
204: {
content: never;
};
/** @description Client error */ /** @description Client error */
400: { 400: {
content: { content: {

View file

@ -114,7 +114,7 @@ globalThis.addEventListener('notificationclick', (ev: ServiceWorkerGlobalScopeEv
if ('note' in data.body) client = await swos.openPost({ reply: data.body.note }, loginId); if ('note' in data.body) client = await swos.openPost({ reply: data.body.note }, loginId);
break; break;
case 'renote': case 'renote':
if ('note' in data.body) await swos.api('notes/create', loginId, { renoteId: data.body.note.id }); if ('note' in data.body) await swos.api('notes/create', loginId, { renoteId: data.body.note.id, noCreatedNote: true });
break; break;
case 'accept': case 'accept':
switch (data.body.type) { switch (data.body.type) {