Compare commits

...

72 Commits

Author SHA1 Message Date
syuilo
6d5bd0c484 10.21.0 2018-10-16 20:19:55 +09:00
syuilo
cfbb6e8092 オブジェクトストレージのURLにファイル名を含めるのを廃止 2018-10-16 20:14:06 +09:00
syuilo
feef4a933e Update src/tools/clean-remote-files.ts 2018-10-16 20:10:46 +09:00
syuilo
468bc67569 Improve test 2018-10-16 19:52:14 +09:00
syuilo
0d517fa52f Greenkeeper/monorepo.fortawesome 5.4.1 (#2917)
* fix(package): update @fortawesome/fontawesome-svg-core to version 1.2.6

Closes #2861

* fix(package): update @fortawesome/free-regular-svg-icons to version 5.4.1

Closes #2861

* fix(package): update @fortawesome/free-solid-svg-icons to version 5.4.1

Closes #2861
2018-10-16 12:28:45 +09:00
syuilo
d9054367c1 fix(package): update @fortawesome/free-brands-svg-icons to version 5.4.1 (#2916)
Closes #2859
2018-10-16 12:27:03 +09:00
MeiMei
1213373027 Use cache with RSS (#2915) 2018-10-16 12:24:54 +09:00
Acid Chicken (硫酸鶏)
100a525507 Update autogen.sh (#2914)
refs: 8b98c08a81 (commitcomment-30911933)
2018-10-16 11:45:11 +09:00
syuilo
1bec4e2d12 10.20.0 2018-10-16 11:44:35 +09:00
syuilo
03cd1d27bf New Crowdin translations (#2910)
* New translations ja-JP.yml (German)

* New translations ja-JP.yml (German)

* New translations ja-JP.yml (German)
2018-10-16 11:38:43 +09:00
syuilo
9427a756c9 Update mongodb 2018-10-16 11:38:09 +09:00
greenkeeper[bot]
d32b2a8ce5 fix(package): update @types/node to version 10.12.0 (#2912) 2018-10-16 10:46:45 +09:00
greenkeeper[bot]
15473b4368 fix(package): update @types/webpack to version 4.4.17 (#2911) 2018-10-16 10:46:38 +09:00
syuilo
54de0dc4a7 Update config for CI 2018-10-16 10:36:27 +09:00
syuilo
0162eaf826 Update signin.ts 2018-10-16 10:33:05 +09:00
syuilo
572cfafbe1 Add some API tests 2018-10-16 10:18:47 +09:00
syuilo
4d6335ce9a Add some tests and fix 2018-10-16 09:45:36 +09:00
syuilo
1c9c4af9f1 Merge branch 'develop' of https://github.com/syuilo/misskey into develop 2018-10-16 08:58:54 +09:00
syuilo
a6844ebc9d Add some tests 2018-10-16 08:58:45 +09:00
MeiMei
072492c29b Implement /api/v1/instance/peers (#2913)
* Implement /api/v1/instance/peers

* Use punycode

* Remove Cache-Control

* Rename
2018-10-16 08:55:55 +09:00
syuilo
99da4f9839 Add some tests and some fixes 2018-10-16 08:54:36 +09:00
syuilo
88664486af Refactor 2018-10-16 08:27:20 +09:00
syuilo
80daf7c749 Implement API tests 2018-10-16 06:37:21 +09:00
greenkeeper[bot]
beb2f7e558 fix(package): update @types/sharp to version 0.21.0 (#2908) 2018-10-16 05:21:07 +09:00
greenkeeper[bot]
6243184c95 fix(package): update @types/gulp-uglify to version 3.0.6 (#2906) 2018-10-16 05:20:57 +09:00
syuilo
1b3baef966 Merge pull request #2898 from syuilo/l10n_develop
New Crowdin translations
2018-10-16 05:20:40 +09:00
greenkeeper[bot]
98f38ee29b fix(package): update vue-svg-inline-loader to version 1.2.1 (#2909) 2018-10-16 05:20:17 +09:00
greenkeeper[bot]
09b82bfea4 fix(package): update chart.js to version 2.7.3 (#2907) 2018-10-16 05:20:02 +09:00
syuilo
937f686264 New translations ja-JP.yml (Russian) 2018-10-15 20:53:38 +09:00
syuilo
9bc9cbac21 New translations ja-JP.yml (English) 2018-10-15 18:22:42 +09:00
syuilo
6024550158 New translations ja-JP.yml (Norwegian) 2018-10-15 18:14:29 +09:00
syuilo
4ae5f82171 New translations ja-JP.yml (Dutch) 2018-10-15 18:14:23 +09:00
syuilo
6d2c9dcee9 New translations ja-JP.yml (Japanese, Kansai) 2018-10-15 18:14:18 +09:00
syuilo
0f1b0e1870 New translations ja-JP.yml (Spanish) 2018-10-15 18:14:11 +09:00
syuilo
81c682cdc8 New translations ja-JP.yml (Russian) 2018-10-15 18:14:05 +09:00
syuilo
ab9fa67d9f New translations ja-JP.yml (Portuguese) 2018-10-15 18:14:00 +09:00
syuilo
9537fce335 New translations ja-JP.yml (Polish) 2018-10-15 18:13:53 +09:00
syuilo
9d97e7e348 New translations ja-JP.yml (Korean) 2018-10-15 18:13:48 +09:00
syuilo
ebe7939412 New translations ja-JP.yml (Italian) 2018-10-15 18:13:43 +09:00
syuilo
807e3e8ca7 New translations ja-JP.yml (German) 2018-10-15 18:13:37 +09:00
syuilo
a59faf9117 New translations ja-JP.yml (French) 2018-10-15 18:13:32 +09:00
syuilo
d786036155 New translations ja-JP.yml (English) 2018-10-15 18:13:25 +09:00
syuilo
61d6ed5489 New translations ja-JP.yml (Chinese Simplified) 2018-10-15 18:13:21 +09:00
syuilo
b38200d48a New translations ja-JP.yml (Catalan) 2018-10-15 18:13:16 +09:00
syuilo
a13319fd86 New translations ja-JP.yml (Norwegian) 2018-10-14 19:52:13 +09:00
syuilo
be8765278c New translations ja-JP.yml (Dutch) 2018-10-14 19:52:08 +09:00
syuilo
c8bb3dc209 New translations ja-JP.yml (Japanese, Kansai) 2018-10-14 19:52:03 +09:00
syuilo
ea16befb73 New translations ja-JP.yml (Spanish) 2018-10-14 19:51:59 +09:00
syuilo
20b1bb7681 New translations ja-JP.yml (Russian) 2018-10-14 19:51:55 +09:00
syuilo
bd10eb50eb New translations ja-JP.yml (Portuguese) 2018-10-14 19:51:50 +09:00
syuilo
d47c0eb31a New translations ja-JP.yml (Polish) 2018-10-14 19:51:45 +09:00
syuilo
177e8bb19f New translations ja-JP.yml (Korean) 2018-10-14 19:51:41 +09:00
syuilo
d156111637 New translations ja-JP.yml (Italian) 2018-10-14 19:51:37 +09:00
syuilo
8c13d3e50b New translations ja-JP.yml (German) 2018-10-14 19:51:33 +09:00
syuilo
6ff01016f0 New translations ja-JP.yml (French) 2018-10-14 19:51:30 +09:00
syuilo
5d659da012 New translations ja-JP.yml (English) 2018-10-14 19:51:26 +09:00
syuilo
28e7552a1a New translations ja-JP.yml (Chinese Simplified) 2018-10-14 19:51:21 +09:00
syuilo
53d264814b New translations ja-JP.yml (Catalan) 2018-10-14 19:51:15 +09:00
syuilo
935b074a7a New translations ja-JP.yml (Norwegian) 2018-10-13 20:12:19 +09:00
syuilo
9d9c609bfb New translations ja-JP.yml (Dutch) 2018-10-13 20:12:15 +09:00
syuilo
f6a664f181 New translations ja-JP.yml (Japanese, Kansai) 2018-10-13 20:12:10 +09:00
syuilo
fce68d1f75 New translations ja-JP.yml (Spanish) 2018-10-13 20:12:06 +09:00
syuilo
88739c2444 New translations ja-JP.yml (Russian) 2018-10-13 20:12:02 +09:00
syuilo
7e2f10fce3 New translations ja-JP.yml (Portuguese) 2018-10-13 20:11:58 +09:00
syuilo
a494c3a5cc New translations ja-JP.yml (Polish) 2018-10-13 20:11:53 +09:00
syuilo
d6bb702883 New translations ja-JP.yml (Korean) 2018-10-13 20:11:48 +09:00
syuilo
d15a972c68 New translations ja-JP.yml (Italian) 2018-10-13 20:11:44 +09:00
syuilo
2ae7d31725 New translations ja-JP.yml (German) 2018-10-13 20:11:40 +09:00
syuilo
2e329b1888 New translations ja-JP.yml (French) 2018-10-13 20:11:36 +09:00
syuilo
522d40328b New translations ja-JP.yml (English) 2018-10-13 20:11:32 +09:00
syuilo
2ecbff45bf New translations ja-JP.yml (Chinese Simplified) 2018-10-13 20:11:28 +09:00
syuilo
b6f7282c13 New translations ja-JP.yml (Catalan) 2018-10-13 20:11:24 +09:00
60 changed files with 1456 additions and 143 deletions

View File

@@ -30,7 +30,7 @@ while :
touch patreon.cache && \
rm patreon.cache && \
cat patreon.raw.cache | \
jq -r '(.data|map(select(.relationships.currently_entitled_tiers.data[]))|map(.relationships.user.data.id))as$data|.included|map(select(.attributes.hide_pledges==false))|map(select(.id as$id|$data|contains([$id])))|map(.attributes|[.full_name,.thumb_url,.url]|@tsv)|.[]|@text' >> patreon.cache && \
jq -r '(.data|map(select(.relationships.currently_entitled_tiers.data[]))|map(.relationships.user.data.id))as$data|.included|map(select(.id as$id|$data|contains([$id])))|map(.attributes|[.full_name,.thumb_url,.url]|@tsv)|.[]|@text' >> patreon.cache && \
echo '<table><tr>' >> patreon.md.cache && \
cat patreon.cache | \
awk -F'\t' '{print $2,$1}' | \

View File

@@ -1,12 +1,8 @@
maintainer: '@syuilo'
url: 'https://misskey.xyz'
secondary_url: 'https://himasaku.net'
maintainer:
name: syuilo
url: 'https://syuilo.com'
url: 'http://misskey.local'
port: 80
https:
enable: false
key: null
cert: null
ca: null
mongodb:
host: localhost
port: 27017
@@ -21,6 +17,3 @@ elasticsearch:
host: localhost
port: 9200
pass: ''
recaptcha:
site_key: hima
secret_key: saku

View File

@@ -1,12 +1,8 @@
maintainer: '@syuilo'
url: 'https://misskey.xyz'
secondary_url: 'https://himasaku.net'
maintainer:
name: syuilo
url: 'https://syuilo.com'
url: 'http://misskey.local'
port: 80
https:
enable: false
key: null
cert: null
ca: null
mongodb:
host: localhost
port: 27017
@@ -21,6 +17,3 @@ elasticsearch:
host: localhost
port: 9200
pass: ''
recaptcha:
site_key: hima
secret_key: saku

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -3,16 +3,16 @@ meta:
lang: "Deutsch"
divider: ""
common:
misskey: "A ⭐ of fediverse"
about-title: "A ⭐ of fediverse."
misskey: "Ein ⭐ des Fediversums"
about-title: "Ein ⭐ des Fediversums."
about: "Misskeyを見つけていただき、ありがとうございます。Misskeyは、地球で生まれた<b>分散マイクロブログSNS</b>です。Fediverse(様々なSNSで構成される宇宙)の中に存在するため、他のSNSと相互に繋がっています。暫し都会の喧騒から離れて、新しいインターネットにダイブしてみませんか。"
intro:
title: "Misskeyって?"
title: "Was ist Misskey?"
about: "Misskeyはオープンソースの<b>分散型マイクロブログSNS</b>です。リッチで高度にカスタマイズできるUI、投稿へのリアクション、ファイルを一元管理できるドライブなど、先進的な機能を揃えています。また、Fediverseと呼ばれるネットワークに接続できるため、他のSNSともやり取りできます。例えば、あなたが何か投稿すると、その投稿はMisskeyだけでなく他のSNSにも伝わります。ちょうどある惑星から他の惑星に電波を発信している様子をイメージしてください。"
features: "特徴"
rich-contents: "投稿"
features: "Funktionen"
rich-contents: "Notizen"
rich-contents-desc: "自分の考え、話題の出来事、皆と共有したいことについて発信してください。必要であれば、様々な構文を使って投稿を装飾したり、好きな画像、動画などのファイルやアンケートを添付することもできます。"
reaction: "リアクション"
reaction: "Reaktionen"
reaction-desc: "あなたの気持ちを伝える最も簡単な方法です。Misskeyは、他のユーザーの投稿に様々なリアクションを付けることができます。いちどMisskeyのリアクション機能を体験してしまうと、もう「いいね」の概念しか存在しないSNSには戻れなくなるかもしれません。"
ui: "インターフェース"
ui-desc: "どのようなUIが使いやすいかは人それぞれです。だから、Misskeyは自由度の高いUIを持っています。レイアウトやデザインを調整したり、カスタマイズ可能な様々なウィジェットを配置したりして、自分だけのホームを作ってください。"
@@ -23,7 +23,7 @@ common:
detected: "広告ブロッカーを無効にしてください"
warning: "<strong>Misskeyは広告を掲載していません</strong>が、広告をブロックする機能が有効だと一部の機能が利用できなかったり、不具合が発生する場合があります。"
application-authorization: "アプリの連携"
close: "閉じる"
close: "Schließen"
do-not-copy-paste: "ここにコードを入力したり張り付けたりしないでください。アカウントが不正利用される可能性があります。"
got-it: "わかった"
customization-tips:
@@ -34,13 +34,13 @@ common:
paragraph4: "カスタマイズを終了するには、右上の「完了」をクリックします。"
gotit: "Got it!"
notification:
file-uploaded: "ファイルがアップロードされました"
file-uploaded: "Datei hochgeladen!"
message-from: "{}さんからメッセージ:"
reversi-invited: "対局への招待があります"
reversi-invited-by: "{}さんから"
notified-by: "{}さんから"
reply-from: "{}さんから返信:"
quoted-by: "{}さんが引用:"
notified-by: "Benachrichtigt von {}:"
reply-from: "Antwort von {}:"
quoted-by: "Zitiert von {}:"
time:
unknown: "Unbekannt"
future: "Zukunft"
@@ -53,7 +53,7 @@ common:
months_ago: "vor {0} Monat{0:en}"
years_ago: "vor {} Jahr{0:en}"
month-and-day: "{month}月 {day}日"
trash: "ゴミ箱"
trash: "Papierkorb"
weekday-short:
sunday: "So"
monday: "Mo"
@@ -63,13 +63,13 @@ common:
friday: "Fr"
saturday: "Sa"
weekday:
sunday: "日曜日"
monday: "月曜日"
tuesday: "火曜日"
wednesday: "水曜日"
thursday: "木曜日"
friday: "金曜日"
saturday: "土曜日"
sunday: "Sonntag"
monday: "Montag"
tuesday: "Dienstag"
wednesday: "Mittwoch"
thursday: "Donnerstag"
friday: "Freitag"
saturday: "Samstag"
reactions:
like: "いいね"
love: "Lieben"
@@ -82,10 +82,10 @@ common:
rip: "RIP"
pudding: "Pudding"
note-visibility:
public: "公開"
public: "Öffentlich"
home: "ホーム"
home-desc: "ホームタイムラインにのみ公開"
followers: "フォロワー"
followers: "Abonnenten"
followers-desc: "自分のフォロワーにのみ公開"
specified: "ダイレクト"
specified-desc: "指定したユーザーにのみ公開"
@@ -122,9 +122,9 @@ common:
turn-of: "{}のターンです"
past-turn-of: "{}のターン"
won: "{}の勝ち"
black: ""
white: ""
total: "合計"
black: "Schwarz"
white: "Weiß"
total: "Gesamt"
this-turn: "{}ターン目"
widgets:
analog-clock: "Analoge Uhr"
@@ -142,23 +142,23 @@ common:
broadcast: "ブロードキャスト"
notifications: "Benachrichtigungen"
users: "Empfohlene Benutzer"
polls: "アンケート"
polls: "Umfrage"
post-form: "Beitragsform"
messaging: "Nachrichten"
server: "Server-Info"
donation: "Spenden"
nav: "Navigation"
tips: "Tipps"
hashtags: "ハッシュタグ"
hashtags: "Hashtags"
deck:
widgets: "Widget hinzufügen:"
home: "Startseite"
local: "Lokal"
hybrid: "ソーシャル"
hashtag: "ハッシュタグ"
hashtag: "Hashtag"
global: "Global"
mentions: "あなた宛て"
direct: "ダイレクト投稿"
mentions: "Erwähnungen"
direct: "Direktnachrichten"
notifications: "Mitteilungen"
list: "Listen"
swap-left: "Nach links"
@@ -182,10 +182,10 @@ auth/views/form.vue:
drive-write: "ドライブを操作する。"
notification-read: "通知を見る。"
notification-write: "通知を操作する。"
cancel: "キャンセル"
accept: "アクセスを許可"
cancel: "Abbrechen"
accept: "Zugriff erlauben."
auth/views/index.vue:
loading: "読み込み中"
loading: "Lädt"
denied: "アプリケーションの連携をキャンセルしました。"
denied-paragraph: "このアプリがあなたのアカウントにアクセスすることはありません。"
already-authorized: "このアプリは既に連携済みです"
@@ -196,10 +196,10 @@ auth/views/index.vue:
sign-in: "サインインしてください"
common/views/components/games/reversi/reversi.vue:
matching:
waiting-for: "{}を待っています"
cancel: "キャンセル"
waiting-for: "Warten auf {}"
cancel: "Abbrechen"
common/views/components/games/reversi/reversi.game.vue:
surrender: "投了"
surrender: "Aufgeben"
surrendered: "投了により"
is-llotheo: "石の少ない方が勝ち(ロセオ)"
looped-map: "ループマップ"
@@ -208,9 +208,9 @@ common/views/components/games/reversi/reversi.index.vue:
title: "Misskey Reversi"
sub-title: "他のMisskeyユーザーとリバーシで対戦しよう"
invite: "招待"
rule: "遊び方"
rule: "Spielanleitung"
rule-desc: "リバーシは、相手と交互に石をボードに置いて、相手の石を挟んで自分の色に変えてゆき、最終的に残った石が多い方が勝ちというボードゲームです。"
mode-invite: "招待"
mode-invite: "Einladen"
mode-invite-desc: "指定したユーザーと対戦するモードです。"
invitations: "対局の招待があります!"
my-games: "自分の対局"
@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Werkzeuge"
task-manager: "Taskmanager"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Profil aktualisieren"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Tools"
task-manager: "Task Manager"
third-parties: "Third-parties"
navbar-position: "Navigation bar position"
navbar-position-top: "Top"
navbar-position-left: "Left"
navbar-position-right: "Right"
desktop/views/components/settings.2fa.vue:
intro: "If you set up 2-step verification, you will not only need a password at sign-in, but also a pre-registered physical device (such as your smartphone), which will improve security."
detail: "Details…"
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Update profile"
locked-account: "Protect your account"
is-locked: "Follow request needs approval"
careful-bot: "Botからのフォローだけ承認制にする"
other: "Other"
is-bot: "This account is a Bot"
is-cat: "This account is a Cat"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "Hash (md5)"
exif: "EXIF"
nsfw: "NSFW"
mark-as-sensitive: "Mark as 'sensitive'"
unmark-as-sensitive: "Unmark as 'sensitive'"
mobile/views/components/media-image.vue:
sensitive: "NSFW"
click-to-show: "Click to show"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "Banner"
is-cat: "This account is a Cat"
is-locked: "Follow request needs approval"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "Advanced"
privacy: "Privacy"
save: "Update profile"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Herramientas"
task-manager: "Navegador de tareas"
third-parties: "Servicios externos"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "Ver detalles..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Perfil actualizado"
locked-account: "Protege tu cuenta"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Outils"
task-manager: "Gestionnaire de tâches"
third-parties: "Services tiers"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "Si vous configurez la vérication en deux étapes vous aurez non seulement besoin de votre mot de passe mais aussi un appareil déjà pré-enregistré(tel que votre smartphone) ce qui ameliora grandement la sécurité de votre compte."
detail: "Voir les détails..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Mettre à jour le profil"
locked-account: "Protéger votre compte"
is-locked: "Demande dabonnement en attente dapprobation"
careful-bot: "Botからのフォローだけ承認制にする"
other: "Autre"
is-bot: "Ce compte est un Bot"
is-cat: "Ce compte est un Chat"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "Hash (md5)"
exif: "EXIF"
nsfw: "CW"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "Le contenu est NSFW"
click-to-show: "Cliquer pour afficher"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "Bannière"
is-cat: "Ce compte est un Bot"
is-locked: "Demande dabonnement en attente dapprobation"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "Avancé"
privacy: "Vie privée"
save: "Mettre à jour le profil"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけとちゃうくて、予め登録しておいた物理的なデバイス(例えばあんさんのスマートフォンなど)も必要になり、よりセキュリティが向上すんで。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウント守る"
is-locked: "他人のフォローは許可してからや!"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotやで"
is-cat: "このアカウントはCatやで"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ(md5)"
exif: "EXIF"
nsfw: "ちょっと見せられへんわ"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "見たらあかんで"
click-to-show: "押してみ、見せたるわ"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatや"
is-locked: "他人のフォローは許可してからや!"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシーってなんや?オカンの年齢か?"
save: "保存"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Hulpmiddelen"
task-manager: "Taakbeheer"
third-parties: "Derde partij"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "Als je verificatie in twee stappen instelt, dan heb je niet alleen een wachtwoord nodig bij het inloggen, maar ook een geregistreerd fysiek apparaat (zoals je smartphone). Dit verhoogt de veiligheid. "
detail: "Details bekijken..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Profiel bijwerken"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "Dit account is een Bot"
is-cat: "Dit account is een Kat"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "Hash (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "Omslagfoto"
is-cat: "Dit account is een Kat"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "Profiel bijwerken"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Verktøy"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "Detaljer..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Lagre profilen"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "Annet"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "NSFW"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "NSFW"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "Banner"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "Avansert"
privacy: "プライバシー"
save: "Lagre profilen"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "Narzędzia"
task-manager: "Menedżer zadań"
third-parties: "Autorzy trzeci"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "Jeżeli skonfigurujesz uwierzytelnianie dwuetapowe, aby zablokować się będziesz potrzebować (oprócz hasła) kodu ze skonfigurowanego urządzenia (np. smartfonu), co zwiększy bezpieczeństwo."
detail: "Zobacz szczegóły…"
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "Aktualizuj profil"
locked-account: "Zabezpiecz swoje konto"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "Inne"
is-bot: "To konto jest prowadzone przez bota"
is-cat: "To konto jest prowadzone przez kota"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "Hash (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "To jest zawartość NSFW"
click-to-show: "Naciśnij aby wyświetlić"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "Baner"
is-cat: "To konto jest prowadzone przez kota"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "Aktualizuj profil"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "Capa"
is-cat: "Esta conta é gato"
is-locked: "Pedido para seguir precisa ser aprovado"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "Avançado"
privacy: "Provacidade"
save: "Atualizar perfil"

View File

@@ -3,9 +3,9 @@ meta:
lang: "Русский язык"
divider: ""
common:
misskey: "A ⭐ of fediverse"
about-title: "A ⭐ of fediverse."
about: "Misskeyを見つけていただき、ありがとうございます。Misskeyは、地球で生まれた<b>分散マイクロブログSNS</b>です。Fediverse(様々なSNSで構成される宇宙)の中に存在するため、他のSNSと相互に繋がっています。暫し都会の喧騒から離れて、新しいインターネットにダイブしてみませんか。"
misskey: "Мы — ⭐ fediverse"
about-title: "Мы — ⭐ fediverse"
about: "Спасибо, что нашли Misskey. Misskey — это <b>децентрализованная платформа для микроблоггинга</b> родом с планеты Земля. Поскольку она существует внутри Fediverse (вселенной различных социальных платформ), она связана с другими платформами. Отдохните от шума большого города — и познакомьтесь с новым интернетом."
intro:
title: "Misskeyって"
about: "Misskeyはオープンソースの<b>分散型マイクロブログSNS</b>です。リッチで高度にカスタマイズできるUI、投稿へのリアクション、ファイルを一元管理できるドライブなど、先進的な機能を揃えています。また、Fediverseと呼ばれるネットワークに接続できるため、他のSNSともやり取りできます。例えば、あなたが何か投稿すると、その投稿はMisskeyだけでなく他のSNSにも伝わります。ちょうどある惑星から他の惑星に電波を発信している様子をイメージしてください。"
@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -785,6 +785,10 @@ desktop/views/components/settings.vue:
tools: "ツール"
task-manager: "タスクマネージャ"
third-parties: "サードパーティ"
navbar-position: "ナビゲーションバーの位置"
navbar-position-top: "上"
navbar-position-left: "左"
navbar-position-right: "右"
desktop/views/components/settings.2fa.vue:
intro: "二段階認証を設定すると、サインイン時にパスワードだけでなく、予め登録しておいた物理的なデバイス(例えばあなたのスマートフォンなど)も必要になり、よりセキュリティが向上します。"
detail: "詳細..."
@@ -834,6 +838,7 @@ desktop/views/components/settings.profile.vue:
save: "保存"
locked-account: "アカウントの保護"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
other: "その他"
is-bot: "このアカウントはBotです"
is-cat: "このアカウントはCatです"
@@ -1074,6 +1079,8 @@ mobile/views/components/drive.file-detail.vue:
hash: "ハッシュ (md5)"
exif: "EXIF"
nsfw: "閲覧注意"
mark-as-sensitive: "閲覧注意に設定"
unmark-as-sensitive: "閲覧注意を解除"
mobile/views/components/media-image.vue:
sensitive: "閲覧注意"
click-to-show: "クリックして表示"
@@ -1225,6 +1232,7 @@ mobile/views/pages/settings/settings.profile.vue:
banner: "バナー"
is-cat: "このアカウントはCatです"
is-locked: "フォローを承認制にする"
careful-bot: "Botからのフォローだけ承認制にする"
advanced: "その他"
privacy: "プライバシー"
save: "保存"

View File

@@ -1,8 +1,8 @@
{
"name": "misskey",
"author": "syuilo <i@syuilo.com>",
"version": "10.19.0",
"clientVersion": "1.0.10543",
"version": "10.21.0",
"clientVersion": "1.0.10615",
"codename": "nighthike",
"main": "./built/index.js",
"private": true,
@@ -20,14 +20,15 @@
"format": "gulp format"
},
"dependencies": {
"@fortawesome/fontawesome-svg-core": "1.2.4",
"@fortawesome/free-brands-svg-icons": "5.3.1",
"@fortawesome/free-regular-svg-icons": "5.3.1",
"@fortawesome/free-solid-svg-icons": "5.3.1",
"@fortawesome/fontawesome-svg-core": "1.2.6",
"@fortawesome/free-brands-svg-icons": "5.4.1",
"@fortawesome/free-regular-svg-icons": "5.4.1",
"@fortawesome/free-solid-svg-icons": "5.4.1",
"@koa/cors": "2.2.2",
"@prezzemolo/rap": "0.1.2",
"@prezzemolo/zip": "0.0.3",
"@types/bcryptjs": "2.4.2",
"@types/chai-http": "3.0.5",
"@types/dateformat": "1.0.1",
"@types/debug": "0.0.31",
"@types/deep-equal": "1.0.1",
@@ -39,7 +40,7 @@
"@types/gulp-mocha": "0.0.32",
"@types/gulp-rename": "0.0.33",
"@types/gulp-replace": "0.0.31",
"@types/gulp-uglify": "3.0.5",
"@types/gulp-uglify": "3.0.6",
"@types/gulp-util": "3.0.34",
"@types/is-root": "1.0.0",
"@types/is-url": "1.2.28",
@@ -60,7 +61,7 @@
"@types/mocha": "5.2.3",
"@types/mongodb": "3.1.12",
"@types/ms": "0.7.30",
"@types/node": "10.11.7",
"@types/node": "10.12.0",
"@types/portscanner": "2.1.0",
"@types/pug": "2.0.4",
"@types/qrcode": "1.3.0",
@@ -70,7 +71,7 @@
"@types/request-promise-native": "1.0.15",
"@types/rimraf": "2.0.2",
"@types/seedrandom": "2.4.27",
"@types/sharp": "0.17.10",
"@types/sharp": "0.21.0",
"@types/showdown": "1.7.5",
"@types/single-line-log": "1.1.0",
"@types/speakeasy": "2.0.2",
@@ -78,7 +79,7 @@
"@types/tinycolor2": "1.4.1",
"@types/tmp": "0.0.33",
"@types/uuid": "3.4.4",
"@types/webpack": "4.4.16",
"@types/webpack": "4.4.17",
"@types/webpack-stream": "3.2.10",
"@types/websocket": "0.0.40",
"@types/ws": "6.0.1",
@@ -90,8 +91,10 @@
"bee-queue": "1.2.2",
"bootstrap-vue": "2.0.0-rc.11",
"cafy": "11.3.0",
"chai": "4.2.0",
"chai-http": "4.2.0",
"chalk": "2.4.1",
"chart.js": "2.7.2",
"chart.js": "2.7.3",
"commander": "2.19.0",
"crc-32": "1.2.0",
"css-loader": "1.0.0",
@@ -157,7 +160,7 @@
"mkdirp": "0.5.1",
"mocha": "5.2.0",
"moji": "0.5.1",
"mongodb": "3.1.1",
"mongodb": "3.1.8",
"monk": "6.0.6",
"ms": "2.1.1",
"nan": "2.11.1",
@@ -220,7 +223,7 @@
"vue-loader": "15.4.2",
"vue-router": "3.0.1",
"vue-style-loader": "4.1.2",
"vue-svg-inline-loader": "1.2.0",
"vue-svg-inline-loader": "1.2.1",
"vue-sweetalert2": "1.5.5",
"vue-template-compiler": "2.5.17",
"vuedraggable": "2.16.0",

View File

@@ -44,7 +44,6 @@ export default define({
},
fetch() {
fetch(`https://api.rss2json.com/v1/api.json?rss_url=${this.props.url}`, {
cache: 'no-cache'
}).then(res => {
res.json().then(feed => {
this.items = feed.items;

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import { Context } from 'cafy';
import isObjectId from './is-objectid';
export const isAnId = (x: any) => mongo.ObjectID.isValid(x);
export const isNotAnId = (x: any) => !isAnId(x);
@@ -12,7 +13,7 @@ export default class ID extends Context<mongo.ObjectID> {
super();
this.transform = v => {
if (isAnId(v) && !mongo.ObjectID.prototype.isPrototypeOf(v)) {
if (isAnId(v) && !isObjectId(v)) {
return new mongo.ObjectID(v);
} else {
return v;
@@ -20,7 +21,7 @@ export default class ID extends Context<mongo.ObjectID> {
};
this.push(v => {
if (!mongo.ObjectID.prototype.isPrototypeOf(v) && isNotAnId(v)) {
if (!isObjectId(v) && isNotAnId(v)) {
return new Error('must-be-an-id');
}
return true;

3
src/misc/is-objectid.ts Normal file
View File

@@ -0,0 +1,3 @@
export default function(x: any): boolean {
return x.hasOwnProperty('toHexString') || x.hasOwnProperty('_bsontype');
}

View File

@@ -1,7 +1,8 @@
import * as mongo from 'mongodb';
import isObjectId from './is-objectid';
function toString(id: any) {
return mongo.ObjectID.prototype.isPrototypeOf(id) ? (id as mongo.ObjectID).toHexString() : id;
return isObjectId(id) ? (id as mongo.ObjectID).toHexString() : id;
}
export default function(note: any, mutedUserIds: string[]): boolean {

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const AccessToken = db.get<IAccessToken>('accessTokens');
AccessToken.createIndex('token');
@@ -22,7 +23,7 @@ export async function deleteAccessToken(accessToken: string | mongo.ObjectID | I
let a: IAccessToken;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(accessToken)) {
if (isObjectId(accessToken)) {
a = await AccessToken.findOne({
_id: accessToken
});

View File

@@ -2,6 +2,7 @@ import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import AccessToken from './access-token';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import config from '../config';
const App = db.get<IApp>('apps');
@@ -43,7 +44,7 @@ export const pack = (
let _app: any;
// Populate the app if 'app' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(app)) {
if (isObjectId(app)) {
_app = await App.findOne({
_id: app
});
@@ -56,7 +57,7 @@ export const pack = (
}
// Me
if (me && !mongo.ObjectID.prototype.isPrototypeOf(me)) {
if (me && !isObjectId(me)) {
if (typeof me === 'string') {
me = new mongo.ObjectID(me);
} else {

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import { pack as packApp } from './app';
const AuthSession = db.get<IAuthSession>('authSessions');
@@ -31,7 +32,7 @@ export const pack = (
_session = deepcopy(session);
// Me
if (me && !mongo.ObjectID.prototype.isPrototypeOf(me)) {
if (me && !isObjectId(me)) {
if (typeof me === 'string') {
me = new mongo.ObjectID(me);
} else {

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import monkDb, { nativeDbConn } from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const DriveFileThumbnail = monkDb.get<IDriveFileThumbnail>('driveFileThumbnails.files');
DriveFileThumbnail.createIndex('metadata.originalId', { sparse: true, unique: true });
@@ -35,7 +36,7 @@ export async function deleteDriveFileThumbnail(driveFile: string | mongo.ObjectI
let d: IDriveFileThumbnail;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(driveFile)) {
if (isObjectId(driveFile)) {
d = await DriveFileThumbnail.findOne({
_id: driveFile
});

View File

@@ -3,6 +3,7 @@ const deepcopy = require('deepcopy');
import { pack as packFolder } from './drive-folder';
import config from '../config';
import monkDb, { nativeDbConn } from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import Note, { deleteNote } from './note';
import MessagingMessage, { deleteMessagingMessage } from './messaging-message';
import User from './user';
@@ -78,7 +79,7 @@ export async function deleteDriveFile(driveFile: string | mongo.ObjectID | IDriv
let d: IDriveFile;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(driveFile)) {
if (isObjectId(driveFile)) {
d = await DriveFile.findOne({
_id: driveFile
});
@@ -154,7 +155,7 @@ export const pack = (
let _file: any;
// Populate the file if 'file' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(file)) {
if (isObjectId(file)) {
_file = await DriveFile.findOne({
_id: file
});

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import DriveFile from './drive-file';
const DriveFolder = db.get<IDriveFolder>('driveFolders');
@@ -29,7 +30,7 @@ export async function deleteDriveFolder(driveFolder: string | mongo.ObjectID | I
let d: IDriveFolder;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(driveFolder)) {
if (isObjectId(driveFolder)) {
d = await DriveFolder.findOne({
_id: driveFolder
});
@@ -83,7 +84,7 @@ export const pack = (
let _folder: any;
// Populate the folder if 'folder' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(folder)) {
if (isObjectId(folder)) {
_folder = await DriveFolder.findOne({ _id: folder });
} else if (typeof folder === 'string') {
_folder = await DriveFolder.findOne({ _id: new mongo.ObjectID(folder) });

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import { pack as packNote } from './note';
const Favorite = db.get<IFavorite>('favorites');
@@ -21,7 +22,7 @@ export async function deleteFavorite(favorite: string | mongo.ObjectID | IFavori
let f: IFavorite;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(favorite)) {
if (isObjectId(favorite)) {
f = await Favorite.findOne({
_id: favorite
});
@@ -58,7 +59,7 @@ export const pack = (
let _favorite: any;
// Populate the favorite if 'favorite' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(favorite)) {
if (isObjectId(favorite)) {
_favorite = await Favorite.findOne({
_id: favorite
});

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import { pack as packUser } from './user';
const FollowRequest = db.get<IFollowRequest>('followRequests');
@@ -34,7 +35,7 @@ export async function deleteFollowRequest(followRequest: string | mongo.ObjectID
let f: IFollowRequest;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(followRequest)) {
if (isObjectId(followRequest)) {
f = await FollowRequest.findOne({
_id: followRequest
});
@@ -64,7 +65,7 @@ export const pack = (
let _request: any;
// Populate the request if 'request' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(request)) {
if (isObjectId(request)) {
_request = await FollowRequest.findOne({
_id: request
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const FollowedLog = db.get<IFollowedLog>('followedLogs');
export default FollowedLog;
@@ -18,7 +19,7 @@ export async function deleteFollowedLog(followedLog: string | mongo.ObjectID | I
let f: IFollowedLog;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(followedLog)) {
if (isObjectId(followedLog)) {
f = await FollowedLog.findOne({
_id: followedLog
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const FollowingLog = db.get<IFollowingLog>('followingLogs');
export default FollowingLog;
@@ -18,7 +19,7 @@ export async function deleteFollowingLog(followingLog: string | mongo.ObjectID |
let f: IFollowingLog;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(followingLog)) {
if (isObjectId(followingLog)) {
f = await FollowingLog.findOne({
_id: followingLog
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const Following = db.get<IFollowing>('following');
Following.createIndex(['followerId', 'followeeId'], { unique: true });
@@ -32,7 +33,7 @@ export async function deleteFollowing(following: string | mongo.ObjectID | IFoll
let f: IFollowing;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(following)) {
if (isObjectId(following)) {
f = await Following.findOne({
_id: following
});

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../../../db/mongodb';
import isObjectId from '../../../misc/is-objectid';
import { IUser, pack as packUser } from '../../user';
const ReversiGame = db.get<IReversiGame>('reversiGames');
@@ -62,7 +63,7 @@ export const pack = (
let _game: any;
// Populate the game if 'game' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(game)) {
if (isObjectId(game)) {
_game = await ReversiGame.findOne({
_id: game
});
@@ -76,7 +77,7 @@ export const pack = (
// Me
const meId: mongo.ObjectID = me
? mongo.ObjectID.prototype.isPrototypeOf(me)
? isObjectId(me)
? me as mongo.ObjectID
: typeof me === 'string'
? new mongo.ObjectID(me)

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../../../db/mongodb';
import isObjectId from '../../../misc/is-objectid';
import { IUser, pack as packUser } from '../../user';
const Matching = db.get<IMatching>('reversiMatchings');
@@ -23,7 +24,7 @@ export const pack = (
// Me
const meId: mongo.ObjectID = me
? mongo.ObjectID.prototype.isPrototypeOf(me)
? isObjectId(me)
? me as mongo.ObjectID
: typeof me === 'string'
? new mongo.ObjectID(me)

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const MessagingHistory = db.get<IMessagingHistory>('messagingHistories');
export default MessagingHistory;
@@ -19,7 +20,7 @@ export async function deleteMessagingHistory(messagingHistory: string | mongo.Ob
let m: IMessagingHistory;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(messagingHistory)) {
if (isObjectId(messagingHistory)) {
m = await MessagingHistory.findOne({
_id: messagingHistory
});

View File

@@ -3,6 +3,7 @@ const deepcopy = require('deepcopy');
import { pack as packUser } from './user';
import { pack as packFile } from './drive-file';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import MessagingHistory, { deleteMessagingHistory } from './messaging-history';
import { length } from 'stringz';
@@ -30,7 +31,7 @@ export async function deleteMessagingMessage(messagingMessage: string | mongo.Ob
let m: IMessagingMessage;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(messagingMessage)) {
if (isObjectId(messagingMessage)) {
m = await MessagingMessage.findOne({
_id: messagingMessage
});
@@ -72,7 +73,7 @@ export const pack = (
let _message: any;
// Populate the message if 'message' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(message)) {
if (isObjectId(message)) {
_message = await MessagingMessage.findOne({
_id: message
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const Mute = db.get<IMute>('mute');
Mute.createIndex(['muterId', 'muteeId'], { unique: true });
@@ -19,7 +20,7 @@ export async function deleteMute(mute: string | mongo.ObjectID | IMute) {
let m: IMute;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(mute)) {
if (isObjectId(mute)) {
m = await Mute.findOne({
_id: mute
});

View File

@@ -2,6 +2,7 @@ import * as mongo from 'mongodb';
import $ from 'cafy';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import Reaction from './note-reaction';
import { pack as packUser } from './user';
@@ -37,7 +38,7 @@ export async function deleteNoteReaction(noteReaction: string | mongo.ObjectID |
let n: INoteReaction;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(noteReaction)) {
if (isObjectId(noteReaction)) {
n = await NoteReaction.findOne({
_id: noteReaction
});
@@ -67,7 +68,7 @@ export const pack = (
let _reaction: any;
// Populate the reaction if 'reaction' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(reaction)) {
if (isObjectId(reaction)) {
_reaction = await Reaction.findOne({
_id: reaction
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const NoteWatching = db.get<INoteWatching>('noteWatching');
NoteWatching.createIndex(['userId', 'noteId'], { unique: true });
@@ -19,7 +20,7 @@ export async function deleteNoteWatching(noteWatching: string | mongo.ObjectID |
let n: INoteWatching;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(noteWatching)) {
if (isObjectId(noteWatching)) {
n = await NoteWatching.findOne({
_id: noteWatching
});

View File

@@ -2,6 +2,7 @@ import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import rap from '@prezzemolo/rap';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import { length } from 'stringz';
import { IUser, pack as packUser } from './user';
import { pack as packApp } from './app';
@@ -107,7 +108,7 @@ export async function deleteNote(note: string | mongo.ObjectID | INote) {
let n: INote;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(note)) {
if (isObjectId(note)) {
n = await Note.findOne({
_id: note
});
@@ -259,7 +260,7 @@ export const pack = async (
// Me
const meId: mongo.ObjectID = me
? mongo.ObjectID.prototype.isPrototypeOf(me)
? isObjectId(me)
? me as mongo.ObjectID
: typeof me === 'string'
? new mongo.ObjectID(me)
@@ -269,7 +270,7 @@ export const pack = async (
let _note: any;
// Populate the note if 'note' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(note)) {
if (isObjectId(note)) {
_note = await Note.findOne({
_id: note
});

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import { IUser, pack as packUser } from './user';
import { pack as packNote } from './note';
@@ -57,7 +58,7 @@ export async function deleteNotification(notification: string | mongo.ObjectID |
let n: INotification;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(notification)) {
if (isObjectId(notification)) {
n = await Notification.findOne({
_id: notification
});
@@ -90,7 +91,7 @@ export const pack = (notification: any) => new Promise<any>(async (resolve, reje
let _notification: any;
// Populate the notification if 'notification' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(notification)) {
if (isObjectId(notification)) {
_notification = await Notification.findOne({
_id: notification
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const PollVote = db.get<IPollVote>('pollVotes');
export default PollVote;
@@ -19,7 +20,7 @@ export async function deletePollVote(pollVote: string | mongo.ObjectID | IPollVo
let p: IPollVote;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(pollVote)) {
if (isObjectId(pollVote)) {
p = await PollVote.findOne({
_id: pollVote
});

View File

@@ -1,5 +1,6 @@
import * as mongo from 'mongodb';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const SwSubscription = db.get<ISwSubscription>('swSubscriptions');
export default SwSubscription;
@@ -19,7 +20,7 @@ export async function deleteSwSubscription(swSubscription: string | mongo.Object
let s: ISwSubscription;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(swSubscription)) {
if (isObjectId(swSubscription)) {
s = await SwSubscription.findOne({
_id: swSubscription
});

View File

@@ -1,6 +1,7 @@
import * as mongo from 'mongodb';
const deepcopy = require('deepcopy');
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
const UserList = db.get<IUserList>('userList');
export default UserList;
@@ -20,7 +21,7 @@ export async function deleteUserList(userList: string | mongo.ObjectID | IUserLi
let u: IUserList;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(userList)) {
if (isObjectId(userList)) {
u = await UserList.findOne({
_id: userList
});
@@ -45,7 +46,7 @@ export const pack = (
) => new Promise<any>(async (resolve, reject) => {
let _userList: any;
if (mongo.ObjectID.prototype.isPrototypeOf(userList)) {
if (isObjectId(userList)) {
_userList = await UserList.findOne({
_id: userList
});

View File

@@ -3,6 +3,7 @@ const deepcopy = require('deepcopy');
const sequential = require('promise-sequential');
import rap from '@prezzemolo/rap';
import db from '../db/mongodb';
import isObjectId from '../misc/is-objectid';
import Note, { packMany as packNoteMany, deleteNote } from './note';
import Following, { deleteFollowing } from './following';
import Mute, { deleteMute } from './mute';
@@ -175,7 +176,7 @@ export async function deleteUser(user: string | mongo.ObjectID | IUser) {
let u: IUser;
// Populate
if (mongo.ObjectID.prototype.isPrototypeOf(user)) {
if (isObjectId(user)) {
u = await User.findOne({
_id: user
});
@@ -340,7 +341,6 @@ export const pack = (
includeHasUnreadNotes?: boolean
}
) => new Promise<any>(async (resolve, reject) => {
const opts = Object.assign({
detail: false,
includeSecrets: false
@@ -358,7 +358,7 @@ export const pack = (
};
// Populate the user if 'user' is ID
if (mongo.ObjectID.prototype.isPrototypeOf(user)) {
if (isObjectId(user)) {
_user = await User.findOne({
_id: user
}, { fields });
@@ -378,7 +378,7 @@ export const pack = (
// Me
const meId: mongo.ObjectID = me
? mongo.ObjectID.prototype.isPrototypeOf(me)
? isObjectId(me)
? me as mongo.ObjectID
: typeof me === 'string'
? new mongo.ObjectID(me)

View File

@@ -1,4 +1,5 @@
import * as mongo from 'mongodb';
import isObjectId from '../../../misc/is-objectid';
import Message from '../../../models/messaging-message';
import { IMessagingMessage as IMessage } from '../../../models/messaging-message';
import { publishMainStream } from '../../../stream';
@@ -15,21 +16,21 @@ export default (
message: string | string[] | IMessage | IMessage[] | mongo.ObjectID | mongo.ObjectID[]
) => new Promise<any>(async (resolve, reject) => {
const userId = mongo.ObjectID.prototype.isPrototypeOf(user)
const userId = isObjectId(user)
? user
: new mongo.ObjectID(user);
const otherpartyId = mongo.ObjectID.prototype.isPrototypeOf(otherparty)
const otherpartyId = isObjectId(otherparty)
? otherparty
: new mongo.ObjectID(otherparty);
const ids: mongo.ObjectID[] = Array.isArray(message)
? mongo.ObjectID.prototype.isPrototypeOf(message[0])
? isObjectId(message[0])
? (message as mongo.ObjectID[])
: typeof message[0] === 'string'
? (message as string[]).map(m => new mongo.ObjectID(m))
: (message as IMessage[]).map(m => m._id)
: mongo.ObjectID.prototype.isPrototypeOf(message)
: isObjectId(message)
? [(message as mongo.ObjectID)]
: typeof message === 'string'
? [new mongo.ObjectID(message)]

View File

@@ -1,4 +1,5 @@
import * as mongo from 'mongodb';
import isObjectId from '../../../misc/is-objectid';
import { default as Notification, INotification } from '../../../models/notification';
import { publishMainStream } from '../../../stream';
import Mute from '../../../models/mute';
@@ -12,17 +13,17 @@ export default (
message: string | string[] | INotification | INotification[] | mongo.ObjectID | mongo.ObjectID[]
) => new Promise<any>(async (resolve, reject) => {
const userId = mongo.ObjectID.prototype.isPrototypeOf(user)
const userId = isObjectId(user)
? user
: new mongo.ObjectID(user);
const ids: mongo.ObjectID[] = Array.isArray(message)
? mongo.ObjectID.prototype.isPrototypeOf(message[0])
? isObjectId(message[0])
? (message as mongo.ObjectID[])
: typeof message[0] === 'string'
? (message as string[]).map(m => new mongo.ObjectID(m))
: (message as INotification[]).map(m => m._id)
: mongo.ObjectID.prototype.isPrototypeOf(message)
: isObjectId(message)
? [(message as mongo.ObjectID)]
: typeof message === 'string'
? [new mongo.ObjectID(message)]

View File

@@ -101,7 +101,7 @@ export const meta = {
export default async (params: any, user: ILocalUser, app: IApp) => new Promise(async (res, rej) => {
const [ps, psErr] = getParams(meta, params);
if (psErr) throw psErr;
if (psErr) return rej(psErr);
const isSecure = user != null && app == null;

View File

@@ -46,6 +46,8 @@ router.post('/signin', require('./private/signin').default);
router.use(require('./service/github').routes());
router.use(require('./service/twitter').routes());
router.use(require('./mastodon').routes());
// Return 404 for unknown API
router.all('*', async ctx => {
ctx.status = 404;
@@ -54,4 +56,4 @@ router.all('*', async ctx => {
// Register router
app.use(router.routes());
module.exports = app;
export default app;

View File

@@ -0,0 +1,14 @@
import * as Router from 'koa-router';
import User from '../../models/user';
import { toASCII } from 'punycode';
// Init router
const router = new Router();
router.get('/v1/instance/peers', async ctx => {
const peers = await User.distinct('host', { host: { $ne: null } }) as any as string[];
const punyCodes = peers.map(peer => toASCII(peer));
ctx.body = punyCodes;
});
module.exports = router;

View File

@@ -12,9 +12,8 @@ export default async (ctx: Koa.Context) => {
ctx.set('Access-Control-Allow-Credentials', 'true');
const body = ctx.request.body as any;
// See: https://github.com/syuilo/misskey/issues/2384
const username = body['username'] || body['x'];
const password = body['password'] || body['y'];
const username = body['username'];
const password = body['password'];
const token = body['token'];
if (typeof username != 'string') {

View File

@@ -132,6 +132,12 @@ export default async (ctx: Koa.Context) => {
updateUserStats(account, true);
// Response
ctx.body = await pack(account);
const res = await pack(account, account, {
detail: true,
includeSecrets: true
});
res.token = secret;
ctx.body = res;
};

View File

@@ -18,6 +18,7 @@ import activityPub from './activitypub';
import webFinger from './webfinger';
import config from '../config';
import { updateNetworkStats } from '../services/update-chart';
import apiServer from './api';
// Init app
const app = new Koa();
@@ -47,7 +48,7 @@ if (config.url.startsWith('https')) {
});
}
app.use(mount('/api', require('./api')));
app.use(mount('/api', apiServer));
app.use(mount('/files', require('./file')));
// Init router

View File

@@ -37,10 +37,8 @@ async function save(path: string, name: string, type: string, hash: string, size
if (config.drive && config.drive.storage == 'minio') {
const minio = new Minio.Client(config.drive.config);
const keyDir = `${config.drive.prefix}/${uuid.v4()}`;
const key = `${keyDir}/${name}`;
const thumbnailKeyDir = `${config.drive.prefix}/${uuid.v4()}`;
const thumbnailKey = `${thumbnailKeyDir}/${name}.thumbnail.jpg`;
const key = `${config.drive.prefix}/${uuid.v4()}`;
const thumbnailKey = `${config.drive.prefix}/${uuid.v4()}`;
const baseUrl = config.drive.baseUrl
|| `${ config.drive.config.useSSL ? 'https' : 'http' }://${ config.drive.config.endPoint }${ config.drive.config.port ? `:${config.drive.config.port}` : '' }/${ config.drive.bucket }`;
@@ -64,8 +62,8 @@ async function save(path: string, name: string, type: string, hash: string, size
key: key,
thumbnailKey: thumbnailKey
},
url: `${ baseUrl }/${ keyDir }/${ encodeURIComponent(name) }`,
thumbnailUrl: thumbnail ? `${ baseUrl }/${ thumbnailKeyDir }/${ encodeURIComponent(name) }.thumbnail.jpg` : null
url: `${ baseUrl }/${ key }`,
thumbnailUrl: thumbnail ? `${ baseUrl }/${ thumbnailKey }` : null
});
const file = await DriveFile.insert({

View File

@@ -26,7 +26,7 @@ export default async (user: IUser, note: INote, reaction: string) => new Promise
} catch (e) {
// duplicate key error
if (e.code === 11000) {
return res(null);
return rej('already reacted');
}
console.error(e);

View File

@@ -1,4 +1,5 @@
import * as mongo from 'mongodb';
import isObjectId from '../../misc/is-objectid';
import { publishMainStream } from '../../stream';
import User from '../../models/user';
import NoteUnread from '../../models/note-unread';
@@ -11,11 +12,11 @@ export default (
note: string | mongo.ObjectID
) => new Promise<any>(async (resolve, reject) => {
const userId: mongo.ObjectID = mongo.ObjectID.prototype.isPrototypeOf(user)
const userId: mongo.ObjectID = isObjectId(user)
? user as mongo.ObjectID
: new mongo.ObjectID(user);
const noteId: mongo.ObjectID = mongo.ObjectID.prototype.isPrototypeOf(note)
const noteId: mongo.ObjectID = isObjectId(note)
? note as mongo.ObjectID
: new mongo.ObjectID(note);

View File

@@ -0,0 +1,30 @@
import * as promiseLimit from 'promise-limit';
import DriveFile, { IDriveFile } from '../models/drive-file';
import del from '../services/drive/delete-file';
const limit = promiseLimit(16);
DriveFile.find({
'metadata._user.host': {
$ne: null
},
'metadata.deletedAt': { $exists: false }
}, {
fields: {
_id: true
}
}).then(async files => {
console.log(`there is ${files.length} files`);
await Promise.all(files.map(file => limit(() => job(file))));
console.log('ALL DONE');
});
async function job(file: IDriveFile): Promise<any> {
file = await DriveFile.findOne({ _id: file._id });
await del(file, true);
console.log('done', file._id);
}

1128
test/api.ts Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -1,3 +1,7 @@
/*
* Tests of MFM
*/
import * as assert from 'assert';
import analyze from '../src/mfm/parse';