Introduce OpenAPI specs (#4351)
* wip * wip * wip * Update index.ts * Update gen-openapi-spec.ts * Update api.ja-JP.md * Fix * Improve doc * Update gen-openapi-spec.ts * Update redoc.html * Improve doc * Update gen-openapi-spec.ts * Improve doc * Update CHANGELOG.md
This commit is contained in:
		
							parent
							
								
									68a6758302
								
							
						
					
					
						commit
						52774bbe64
					
				
					 173 changed files with 1091 additions and 876 deletions
				
			
		|  | @ -3,6 +3,7 @@ ChangeLog | |||
| 
 | ||||
| unreleasded | ||||
| ---------- | ||||
| * APIドキュメント刷新 | ||||
| * /api/v1/instance/peers 復活 | ||||
| * 「返信が遷移後も残り続ける問題を修正」([9beddc9](https://github.com/syuilo/misskey/commit/9beddc941a716f1322ae0b7d71d159edd642a399)) によって遷移前に返信が表示されなくなった問題を修正 | ||||
| * デッキモードにてユーザーのプロフィールを連続で見たとき、アクティビティや画像が前のユーザーのもののまま表示される問題を修正 | ||||
|  |  | |||
							
								
								
									
										
											BIN
										
									
								
								assets/api-doc.png
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										
											BIN
										
									
								
								assets/api-doc.png
									
										
									
									
									
										Normal file
									
								
							
										
											Binary file not shown.
										
									
								
							| After Width: | Height: | Size: 5.9 KiB | 
|  | @ -102,7 +102,7 @@ | |||
| 		"bcryptjs": "2.4.3", | ||||
| 		"bee-queue": "1.2.2", | ||||
| 		"bootstrap-vue": "2.0.0-rc.11", | ||||
| 		"cafy": "14.0.1", | ||||
| 		"cafy": "15.1.0", | ||||
| 		"chai": "4.2.0", | ||||
| 		"chai-http": "4.2.1", | ||||
| 		"chalk": "2.4.2", | ||||
|  |  | |||
							
								
								
									
										24
									
								
								src/client/assets/redoc.html
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										24
									
								
								src/client/assets/redoc.html
									
										
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,24 @@ | |||
| <!DOCTYPE html> | ||||
| <html> | ||||
| 	<head> | ||||
| 		<title>Misskey API</title> | ||||
| 		<!-- needed for adaptive design --> | ||||
| 		<meta charset="utf-8"/> | ||||
| 		<meta name="viewport" content="width=device-width, initial-scale=1"> | ||||
| 		<link href="https://fonts.googleapis.com/css?family=Montserrat:300,400,700|Roboto:300,400,700" rel="stylesheet"> | ||||
| 
 | ||||
| 		<!-- | ||||
| 		ReDoc doesn't change outer page styles | ||||
| 		--> | ||||
| 		<style> | ||||
| 			body { | ||||
| 				margin: 0; | ||||
| 				padding: 0; | ||||
| 			} | ||||
| 		</style> | ||||
| 	</head> | ||||
| 	<body> | ||||
| 		<redoc spec-url='/api.json'></redoc> | ||||
| 		<script src="https://cdn.jsdelivr.net/npm/redoc@next/bundles/redoc.standalone.js"> </script> | ||||
| 	</body> | ||||
| </html> | ||||
|  | @ -74,7 +74,7 @@ APIはすべてリクエストのパラメータ・レスポンスともにJSON | |||
| 
 | ||||
| ストリーミングAPIも提供しています。 | ||||
| 
 | ||||
| APIリファレンスもご確認ください。 | ||||
| [APIリファレンス](/api-doc)もご確認ください。 | ||||
| 
 | ||||
| ### レートリミット | ||||
| Misskey APIにはレートリミットがあり、短時間のうちに多数のリクエストを送信すると、一定時間APIを利用することができなくなることがあります。 | ||||
|  |  | |||
|  | @ -1,40 +0,0 @@ | |||
| @import "../style" | ||||
| 
 | ||||
| #url | ||||
| 	padding 8px 12px 8px 8px | ||||
| 	font-family Consolas, 'Courier New', Courier, Monaco, monospace | ||||
| 	color #fff | ||||
| 	background #222e40 | ||||
| 	border-radius 4px | ||||
| 	overflow auto | ||||
| 	white-space nowrap | ||||
| 
 | ||||
| 	> .method | ||||
| 		display inline-block | ||||
| 		margin 0 8px 0 0 | ||||
| 		padding 0 6px | ||||
| 		color #fff | ||||
| 		background #17afc7 | ||||
| 		border-radius 4px | ||||
| 		user-select none | ||||
| 		pointer-events none | ||||
| 
 | ||||
| 	> .host | ||||
| 		opacity 0.7 | ||||
| 
 | ||||
| #stability | ||||
| 	padding 8px 12px | ||||
| 	color #fff | ||||
| 	border-radius 4px | ||||
| 
 | ||||
| 	&.deprecated | ||||
| 		background #f42443 | ||||
| 
 | ||||
| 	&.experimental | ||||
| 		background #f2781a | ||||
| 
 | ||||
| 	&.stable | ||||
| 		background #3dcc90 | ||||
| 
 | ||||
| 	> b | ||||
| 		margin-left 4px | ||||
|  | @ -1,81 +0,0 @@ | |||
| extends ../../base | ||||
| include ../mixins | ||||
| 
 | ||||
| block meta | ||||
| 	link(rel="stylesheet" href="/docs/assets/api/endpoints/style.css") | ||||
| 
 | ||||
| block main | ||||
| 	h1= title | ||||
| 
 | ||||
| 	p#url | ||||
| 		span.method POST | ||||
| 		span.host | ||||
| 			= endpointUrl.host | ||||
| 			| / | ||||
| 		span.path= endpointUrl.path | ||||
| 
 | ||||
| 	- var stability = endpoint.stability || 'experimental'; | ||||
| 	p#stability(class=stability) | ||||
| 		| Stability: | ||||
| 		b= stability | ||||
| 
 | ||||
| 	if endpoint.desc | ||||
| 		p#desc= endpoint.desc[lang] || endpoint.desc['ja-JP'] | ||||
| 
 | ||||
| 	if endpoint.requireCredential | ||||
| 		div.ui.info: p | ||||
| 			i.fas.fa-id-card-alt(style="margin-right: 4px") | ||||
| 			= i18n('docs.api.endpoints.require-credential') | ||||
| 
 | ||||
| 		if endpoint.kind | ||||
| 			div.ui.info: p | ||||
| 				i.fas.fa-unlock-alt(style="margin-right: 4px") | ||||
| 				!= i18n('docs.api.endpoints.require-permission').replace('{permission}', `<code>${endpoint.kind}</code>`) | ||||
| 
 | ||||
| 	if endpoint.limit | ||||
| 		div.ui.info.warn: p | ||||
| 			i.far.fa-clock(style="margin-right: 4px") | ||||
| 			b!= i18n('docs.api.endpoints.has-limit') | ||||
| 			if endpoint.limit.duration | ||||
| 				!= i18n('docs.api.endpoints.duration-limit').replace('{duration}', endpoint.limit.duration).replace('{max}', endpoint.limit.max) | ||||
| 			if endpoint.limit.minInterval | ||||
| 				!= i18n('docs.api.endpoints.min-interval-limit').replace('{interval}', endpoint.limit.minInterval) | ||||
| 
 | ||||
| 	if params && Object.keys(params).length > 0 | ||||
| 		section | ||||
| 			h2= i18n('docs.api.endpoints.params') | ||||
| 			+propTable(params) | ||||
| 
 | ||||
| 			if paramDefs | ||||
| 				each paramDef in paramDefs | ||||
| 					section(id= paramDef.name) | ||||
| 						h3= paramDef.name | ||||
| 						+propTable(paramDef.params) | ||||
| 	if params && Object.keys(params).length == 0 | ||||
| 		section | ||||
| 			h2= i18n('docs.api.endpoints.params') | ||||
| 			p= i18n('docs.api.endpoints.no-params') | ||||
| 
 | ||||
| 	if res | ||||
| 		section | ||||
| 			h2= i18n('docs.api.endpoints.res') | ||||
| 
 | ||||
| 			if resProps | ||||
| 				+propTable(resProps) | ||||
| 
 | ||||
| 				if resDefs | ||||
| 					each resDef in resDefs | ||||
| 						section(id= resDef.name) | ||||
| 							h3= resDef.name | ||||
| 							+propTable(resDef.props) | ||||
| 			else | ||||
| 				if res.type.startsWith('entity') | ||||
| 					a(href=`/docs/${lang}/api/entities/${kebab(res.entity)}`)= res.entity | ||||
| 
 | ||||
| block footer | ||||
| 	div.ui.info: p | ||||
| 		i.fas.fa-info-circle(style="margin-right: 4px") | ||||
| 		= i18n('docs.api.endpoints.generated') | ||||
| 	p | ||||
| 		= i18n('docs.api.endpoints.show-src') | ||||
| 		a(href=src target="_blank")= i18n('docs.api.endpoints.show-src-link') | ||||
|  | @ -1,90 +0,0 @@ | |||
| name: "DriveFile" | ||||
| 
 | ||||
| desc: | ||||
|   ja-JP: "ドライブのファイル。" | ||||
|   en-US: "A file of Drive." | ||||
| 
 | ||||
| props: | ||||
|   id: | ||||
|     type: "id" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ファイルID" | ||||
|       en-US: "The ID of this file" | ||||
| 
 | ||||
|   createdAt: | ||||
|     type: "date" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "アップロード日時" | ||||
|       en-US: "The upload date of this file" | ||||
| 
 | ||||
|   userId: | ||||
|     type: "id(User)" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "所有者ID" | ||||
|       en-US: "The ID of the owner of this file" | ||||
| 
 | ||||
|   user: | ||||
|     type: "entity(User)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "所有者" | ||||
|       en-US: "The owner of this file" | ||||
| 
 | ||||
|   name: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ファイル名" | ||||
|       en-US: "The name of this file" | ||||
| 
 | ||||
|   md5: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ファイルのMD5ハッシュ値" | ||||
|       en-US: "The md5 hash value of this file" | ||||
| 
 | ||||
|   type: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ファイルの種類" | ||||
|       en-US: "The type of this file" | ||||
| 
 | ||||
|   datasize: | ||||
|     type: "number" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ファイルサイズ(bytes)" | ||||
|       en-US: "The size of this file (bytes)" | ||||
| 
 | ||||
|   url: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ファイルのURL" | ||||
|       en-US: "The URL of this file" | ||||
| 
 | ||||
|   folderId: | ||||
|     type: "id(DriveFolder)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "フォルダID" | ||||
|       en-US: "The ID of the folder of this file" | ||||
| 
 | ||||
|   folder: | ||||
|     type: "entity(DriveFolder)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "フォルダ" | ||||
|       en-US: "The folder of this file" | ||||
| 
 | ||||
|   isSensitive: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "このメディアが「閲覧注意」(NSFW)かどうか" | ||||
|       en-US: "Whether this media is NSFW" | ||||
|  | @ -1,41 +0,0 @@ | |||
| name: "DriveFolder" | ||||
| 
 | ||||
| desc: | ||||
|   ja-JP: "ドライブのフォルダを表します。" | ||||
|   en-US: "A folder of Drive." | ||||
| 
 | ||||
| props: | ||||
|   id: | ||||
|     type: "id" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "フォルダID" | ||||
|       en-US: "The ID of this folder" | ||||
| 
 | ||||
|   createdAt: | ||||
|     type: "date" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "作成日時" | ||||
|       en-US: "The created date of this folder" | ||||
| 
 | ||||
|   userId: | ||||
|     type: "id(User)" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "所有者ID" | ||||
|       en-US: "The ID of the owner of this folder" | ||||
| 
 | ||||
|   parentId: | ||||
|     type: "entity(DriveFolder)" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "親フォルダのID (ルートなら null)" | ||||
|       en-US: "The ID of parent folder" | ||||
| 
 | ||||
|   name: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "フォルダ名" | ||||
|       en-US: "The name of this folder" | ||||
|  | @ -1,211 +0,0 @@ | |||
| name: "Note" | ||||
| 
 | ||||
| desc: | ||||
|   ja-JP: "投稿。" | ||||
|   en-US: "A note." | ||||
| 
 | ||||
| props: | ||||
|   id: | ||||
|     type: "id" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "投稿ID" | ||||
|       en-US: "The ID of this note" | ||||
| 
 | ||||
|   createdAt: | ||||
|     type: "date" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "投稿日時" | ||||
|       en-US: "The posted date of this note" | ||||
| 
 | ||||
|   viaMobile: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "モバイル端末から投稿したか否か(自己申告であることに留意)" | ||||
|       en-US: "Whether this note sent via a mobile device" | ||||
| 
 | ||||
|   localOnly: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "ローカルのみに公開する投稿か否か" | ||||
|       en-US: "Whether this note is no federation" | ||||
| 
 | ||||
|   text: | ||||
|     type: "string" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "投稿の本文" | ||||
|       en-US: "The text of this note" | ||||
| 
 | ||||
|   fileIds: | ||||
|     type: "id(DriveFile)[]" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "添付されているファイルのID (なければレスポンスでは空配列)" | ||||
|       en-US: "The IDs of the attached files (empty array for response if no files is attached)" | ||||
| 
 | ||||
|   files: | ||||
|     type: "entity(DriveFile)[]" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "添付されているファイル" | ||||
|       en-US: "The attached files" | ||||
| 
 | ||||
|   userId: | ||||
|     type: "id(User)" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "投稿者ID" | ||||
|       en-US: "The ID of author of this note" | ||||
| 
 | ||||
|   user: | ||||
|     type: "entity(User)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "投稿者" | ||||
|       en-US: "The author of this note" | ||||
| 
 | ||||
|   myReaction: | ||||
|     type: "string" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "この投稿に対する自分の<a href='/docs/api/reactions'>リアクション</a>" | ||||
|       en-US: "The your <a href='/docs/api/reactions'>reaction</a> of this note" | ||||
| 
 | ||||
|   renoteCount: | ||||
|     type: "number" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "この投稿がRenoteされた数" | ||||
|       en-US: "The number of renotes for this post" | ||||
| 
 | ||||
|   repliesCount: | ||||
|     type: "number" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "この投稿に返信された数" | ||||
|       en-US: "The number of replies to this post" | ||||
| 
 | ||||
|   reactionCounts: | ||||
|     type: "object" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "<a href='/docs/api/reactions'>リアクション</a>をキーとし、この投稿に対するそのリアクションの数を値としたオブジェクト" | ||||
| 
 | ||||
|   replyId: | ||||
|     type: "id(Note)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "返信した投稿のID" | ||||
|       en-US: "The ID of the replyed note" | ||||
| 
 | ||||
|   reply: | ||||
|     type: "entity(Note)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "返信した投稿" | ||||
|       en-US: "The replyed note" | ||||
| 
 | ||||
|   renoteId: | ||||
|     type: "id(Note)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "引用した投稿のID" | ||||
|       en-US: "The ID of the quoted note" | ||||
| 
 | ||||
|   renote: | ||||
|     type: "entity(Note)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "引用した投稿" | ||||
|       en-US: "The quoted note" | ||||
| 
 | ||||
|   poll: | ||||
|     type: "object" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "投票" | ||||
|       en-US: "The poll" | ||||
| 
 | ||||
|     props: | ||||
|       choices: | ||||
|         type: "object[]" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "投票の選択肢" | ||||
|           en-US: "The choices of this poll" | ||||
| 
 | ||||
|         props: | ||||
|           id: | ||||
|             type: "number" | ||||
|             optional: false | ||||
|             desc: | ||||
|               ja-JP: "選択肢ID" | ||||
|               en-US: "The ID of this choice" | ||||
| 
 | ||||
|           isVoted: | ||||
|             type: "boolean" | ||||
|             optional: true | ||||
|             desc: | ||||
|               ja-JP: "自分がこの選択肢に投票したかどうか" | ||||
|               en-US: "Whether you voted to this choice" | ||||
| 
 | ||||
|           text: | ||||
|             type: "string" | ||||
|             optional: false | ||||
|             desc: | ||||
|               ja-JP: "選択肢本文" | ||||
|               en-US: "The text of this choice" | ||||
| 
 | ||||
|           votes: | ||||
|             type: "number" | ||||
|             optional: false | ||||
|             desc: | ||||
|               ja-JP: "この選択肢に投票された数" | ||||
|               en-US: "The number voted for this choice" | ||||
|   geo: | ||||
|     type: "object" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "位置情報" | ||||
|       en-US: "Geo location" | ||||
| 
 | ||||
|     props: | ||||
|       coordinates: | ||||
|         type: "number[]" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "座標。最初に経度:-180〜180で表す。最後に緯度:-90〜90で表す。" | ||||
| 
 | ||||
|       altitude: | ||||
|         type: "number" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "高度。メートル単位で表す。" | ||||
| 
 | ||||
|       accuracy: | ||||
|         type: "number" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "緯度、経度の精度。メートル単位で表す。" | ||||
| 
 | ||||
|       altitudeAccuracy: | ||||
|         type: "number" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "高度の精度。メートル単位で表す。" | ||||
| 
 | ||||
|       heading: | ||||
|         type: "number" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "方角。0〜360の角度で表す。0が北、90が東、180が南、270が西。" | ||||
| 
 | ||||
|       speed: | ||||
|         type: "number" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "速度。メートル / 秒数で表す。" | ||||
|  | @ -1 +0,0 @@ | |||
| @import "../style" | ||||
|  | @ -1,174 +0,0 @@ | |||
| name: "User" | ||||
| 
 | ||||
| desc: | ||||
|   ja-JP: "ユーザー。" | ||||
|   en-US: "A user." | ||||
| 
 | ||||
| props: | ||||
|   id: | ||||
|     type: "id" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ユーザーID" | ||||
|       en-US: "The ID of this user" | ||||
| 
 | ||||
|   createdAt: | ||||
|     type: "date" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "アカウント作成日時" | ||||
|       en-US: "The registered date of this user" | ||||
| 
 | ||||
|   username: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ユーザー名" | ||||
|       en-US: "The username of this user" | ||||
| 
 | ||||
|   description: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "アカウントの説明(自己紹介)" | ||||
|       en-US: "The description of this user" | ||||
| 
 | ||||
|   avatarId: | ||||
|     type: "id(DriveFile)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "アバターのID" | ||||
|       en-US: "The ID of the avatar of this user" | ||||
| 
 | ||||
|   avatarUrl: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "アバターのURL" | ||||
|       en-US: "The URL of the avatar of this user" | ||||
| 
 | ||||
|   bannerId: | ||||
|     type: "id(DriveFile)" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "バナーのID" | ||||
|       en-US: "The ID of the banner of this user" | ||||
| 
 | ||||
|   bannerUrl: | ||||
|     type: "string" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "バナーのURL" | ||||
|       en-US: "The URL of the banner of this user" | ||||
| 
 | ||||
|   followersCount: | ||||
|     type: "number" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "フォロワーの数" | ||||
|       en-US: "The number of the followers for this user" | ||||
| 
 | ||||
|   followingCount: | ||||
|     type: "number" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "フォローしているユーザーの数" | ||||
|       en-US: "The number of the following users for this user" | ||||
| 
 | ||||
|   isFollowing: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "自分がこのユーザーをフォローしているか" | ||||
| 
 | ||||
|   isFollowed: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "自分がこのユーザーにフォローされているか" | ||||
| 
 | ||||
|   isMuted: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "自分がこのユーザーをミュートしているか" | ||||
|       en-US: "Whether you muted this user" | ||||
| 
 | ||||
|   notesCount: | ||||
|     type: "number" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "投稿の数" | ||||
|       en-US: "The number of the notes of this user" | ||||
| 
 | ||||
|   pinnedNotes: | ||||
|     type: "entity(Note)[]" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "ピン留めされた投稿" | ||||
|       en-US: "The pinned note of this user" | ||||
| 
 | ||||
|   pinnedNoteIds: | ||||
|     type: "id(Note)[]" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "ピン留めされた投稿のID" | ||||
|       en-US: "The ID of the pinned note of this user" | ||||
| 
 | ||||
|   host: | ||||
|     type: "string | null" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "ホスト (例: example.com:3000)" | ||||
|       en-US: "Host (e.g. example.com:3000)" | ||||
| 
 | ||||
|   twitter: | ||||
|     type: "object" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "連携されているTwitterアカウント情報" | ||||
|       en-US: "The info of the connected twitter account of this user" | ||||
| 
 | ||||
|     props: | ||||
|       userId: | ||||
|         type: "string" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "ユーザーID" | ||||
|           en-US: "The user ID" | ||||
| 
 | ||||
|       screenName: | ||||
|         type: "string" | ||||
|         optional: false | ||||
|         desc: | ||||
|           ja-JP: "ユーザー名" | ||||
|           en-US: "The screen name of this user" | ||||
| 
 | ||||
|   isBot: | ||||
|     type: "boolean" | ||||
|     optional: true | ||||
|     desc: | ||||
|       ja-JP: "botか否か(自己申告であることに留意)" | ||||
|       en-US: "Whether is bot or not" | ||||
| 
 | ||||
|   profile: | ||||
|     type: "object" | ||||
|     optional: false | ||||
|     desc: | ||||
|       ja-JP: "プロフィール" | ||||
|       en-US: "The profile of this user" | ||||
| 
 | ||||
|     props: | ||||
|       location: | ||||
|         type: "string" | ||||
|         optional: true | ||||
|         desc: | ||||
|           ja-JP: "場所" | ||||
|           en-US: "The location of this user" | ||||
| 
 | ||||
|       birthday: | ||||
|         type: "string" | ||||
|         optional: true | ||||
|         desc: | ||||
|           ja-JP: "誕生日 (YYYY-MM-DD)" | ||||
|           en-US: "The birthday of this user (YYYY-MM-DD)" | ||||
|  | @ -1,20 +0,0 @@ | |||
| extends ../../base | ||||
| include ../mixins | ||||
| 
 | ||||
| block meta | ||||
| 	link(rel="stylesheet" href="/docs/assets/api/entities/style.css") | ||||
| 
 | ||||
| block main | ||||
| 	h1= name | ||||
| 
 | ||||
| 	p#desc= desc[lang] || desc['ja-JP'] | ||||
| 
 | ||||
| 	section | ||||
| 		h2= i18n('docs.api.entities.properties') | ||||
| 		+propTable(props) | ||||
| 
 | ||||
| 		if propDefs | ||||
| 			each propDef in propDefs | ||||
| 				section(id= propDef.name) | ||||
| 					h3= propDef.name | ||||
| 					+propTable(propDef.props) | ||||
|  | @ -1,34 +0,0 @@ | |||
| mixin type(prop) | ||||
| 	i= prop.type | ||||
| 	if prop.kind == 'id' | ||||
| 		if prop.entity | ||||
| 			|  ( | ||||
| 			a(href=`/docs/${lang}/api/entities/${kebab(prop.entity)}`)= prop.entity | ||||
| 			|  ID) | ||||
| 		else | ||||
| 			|  (ID) | ||||
| 	else if prop.kind == 'entity' | ||||
| 		|   ( | ||||
| 		a(href=`/docs/${lang}/api/entities/${kebab(prop.entity)}`)= prop.entity | ||||
| 		| ) | ||||
| 	else if prop.kind == 'object' | ||||
| 		if prop.hasDef | ||||
| 			|  ( | ||||
| 			a(href=`#${prop.name}`)= prop.name | ||||
| 			| ) | ||||
| 	else if prop.kind == 'date' | ||||
| 		|  (Date) | ||||
| 
 | ||||
| mixin propTable(props) | ||||
| 	table.props | ||||
| 		thead: tr | ||||
| 			th= i18n('docs.api.props.name') | ||||
| 			th= i18n('docs.api.props.type') | ||||
| 			th= i18n('docs.api.props.description') | ||||
| 		tbody | ||||
| 			each prop in props | ||||
| 				tr | ||||
| 					td.name= prop.name | ||||
| 					td.type | ||||
| 						+type(prop) | ||||
| 					td.desc!= prop.desc ? prop.desc[lang] || prop.desc['ja-JP'] : null | ||||
|  | @ -1,11 +0,0 @@ | |||
| @import "../style" | ||||
| 
 | ||||
| table.props | ||||
| 	.name | ||||
| 		font-weight bold | ||||
| 
 | ||||
| 	.name | ||||
| 	.type | ||||
| 	.optional | ||||
| 		font-family Consolas, 'Courier New', Courier, Monaco, monospace | ||||
| 
 | ||||
|  | @ -17,17 +17,6 @@ html(lang= lang) | |||
| 			ul | ||||
| 				each doc in docs | ||||
| 					li: a(href=`/docs/${lang}/${doc.name}`)= doc.title[lang] || doc.title['ja-JP'] | ||||
| 			section | ||||
| 				h2 API | ||||
| 				ul | ||||
| 					li Entities | ||||
| 						ul | ||||
| 							each entity in entities | ||||
| 								li: a(href=`/docs/${lang}/api/entities/${kebab(entity)}`)= entity | ||||
| 					li Endpoints | ||||
| 						ul | ||||
| 							each endpoint in endpoints | ||||
| 								li: a(href=`/docs/${lang}/api/endpoints/${kebab(endpoint.name)}`)= endpoint.name | ||||
| 		main | ||||
| 			article | ||||
| 				block main | ||||
|  |  | |||
|  | @ -26,6 +26,8 @@ export type ObjectId = mongo.ObjectID; | |||
|  * ID | ||||
|  */ | ||||
| export default class ID<Maybe = string> extends Context<string | Maybe> { | ||||
| 	public readonly name = 'ID'; | ||||
| 
 | ||||
| 	constructor(optional = false, nullable = false) { | ||||
| 		super(optional, nullable); | ||||
| 
 | ||||
|  | @ -38,7 +40,7 @@ export default class ID<Maybe = string> extends Context<string | Maybe> { | |||
| 	} | ||||
| 
 | ||||
| 	public getType() { | ||||
| 		return super.getType('string'); | ||||
| 		return super.getType('String'); | ||||
| 	} | ||||
| 
 | ||||
| 	public makeOptional(): ID<undefined> { | ||||
|  |  | |||
|  | @ -26,7 +26,7 @@ export default (endpoint: IEndpoint, ctx: Koa.BaseContext) => new Promise((res) | |||
| 		call(endpoint.name, user, app, body, (ctx.req as any).file).then(res => { | ||||
| 			reply(res); | ||||
| 		}).catch(e => { | ||||
| 			reply(e.kind == 'client' ? 400 : 500, e); | ||||
| 			reply(e.httpStatusCode ? e.httpStatusCode :  e.kind == 'client' ? 400 : 500, e); | ||||
| 		}); | ||||
| 	}).catch(() => { | ||||
| 		reply(403, new ApiError({ | ||||
|  |  | |||
|  | @ -21,6 +21,7 @@ export default async (endpoint: string, user: IUser, app: IApp, data: any, file? | |||
| 			message: 'No such endpoint.', | ||||
| 			code: 'NO_SUCH_ENDPOINT', | ||||
| 			id: 'f8080b67-5f9c-4eb7-8c18-7f1eeae8f709', | ||||
| 			httpStatusCode: 404 | ||||
| 		}); | ||||
| 	} | ||||
| 
 | ||||
|  | @ -33,6 +34,7 @@ export default async (endpoint: string, user: IUser, app: IApp, data: any, file? | |||
| 			message: 'Credential required.', | ||||
| 			code: 'CREDENTIAL_REQUIRED', | ||||
| 			id: '1384574d-a912-4b81-8601-c7b1c4085df1', | ||||
| 			httpStatusCode: 401 | ||||
| 		}); | ||||
| 	} | ||||
| 
 | ||||
|  | @ -63,6 +65,7 @@ export default async (endpoint: string, user: IUser, app: IApp, data: any, file? | |||
| 				message: 'Rate limit exceeded. Please try again later.', | ||||
| 				code: 'RATE_LIMIT_EXCEEDED', | ||||
| 				id: 'd5826d14-3982-4d2e-8011-b9e9f02499ef', | ||||
| 				httpStatusCode: 429 | ||||
| 			}); | ||||
| 		}); | ||||
| 	} | ||||
|  |  | |||
|  | @ -2,18 +2,30 @@ import { Context } from 'cafy'; | |||
| import * as path from 'path'; | ||||
| import * as glob from 'glob'; | ||||
| 
 | ||||
| export type Param = { | ||||
| 	validator: Context<any>; | ||||
| 	transform?: any; | ||||
| 	default?: any; | ||||
| 	desc?: { [key: string]: string }; | ||||
| 	ref?: string; | ||||
| }; | ||||
| 
 | ||||
| export interface IEndpointMeta { | ||||
| 	stability?: string; //'deprecated' | 'experimental' | 'stable';
 | ||||
| 
 | ||||
| 	desc?: { [key: string]: string }; | ||||
| 
 | ||||
| 	tags?: string[]; | ||||
| 
 | ||||
| 	params?: { | ||||
| 		[key: string]: Param; | ||||
| 	}; | ||||
| 
 | ||||
| 	errors?: { | ||||
| 		[key: string]: { | ||||
| 			validator: Context<any>; | ||||
| 			transform?: any; | ||||
| 			default?: any; | ||||
| 			desc?: { [key: string]: string }; | ||||
| 			ref?: string; | ||||
| 			message: string; | ||||
| 			code: string; | ||||
| 			id: string; | ||||
| 		}; | ||||
| 	}; | ||||
| 
 | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import Report, { packMany } from '../../../../models/abuse-user-report'; | |||
| import define from '../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import define from '../../../define'; | |||
| import { fallback } from '../../../../../prelude/symbol'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -5,6 +5,8 @@ import DriveFile from '../../../../../models/drive-file'; | |||
| import { ApiError } from '../../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ export const meta = { | |||
| 		'ja-JP': 'カスタム絵文字を追加します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ export const meta = { | |||
| 		'ja-JP': 'カスタム絵文字を取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -8,6 +8,8 @@ export const meta = { | |||
| 		'ja-JP': 'カスタム絵文字を削除します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -8,6 +8,8 @@ export const meta = { | |||
| 		'ja-JP': 'カスタム絵文字を更新します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -5,6 +5,8 @@ import User from '../../../../../models/user'; | |||
| import deleteFollowing from '../../../../../services/following/delete'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -3,6 +3,8 @@ import define from '../../../define'; | |||
| import Instance from '../../../../../models/instance'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ export const meta = { | |||
| 		'ja-JP': '招待コードを発行します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Mark a user as moderator.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireAdmin: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Unmark a user as moderator.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireAdmin: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -2,6 +2,8 @@ import define from '../../../define'; | |||
| import { destroy } from '../../../../../queue'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import define from '../../define'; | |||
| import AbuseUserReport from '../../../../models/abuse-user-report'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ export const meta = { | |||
| 		'ja-JP': '指定したユーザーのパスワードをリセットします。', | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -8,6 +8,8 @@ export const meta = { | |||
| 		'ja-JP': '指定したユーザーの情報を取得します。', | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import define from '../../define'; | |||
| import { fallback } from '../../../../prelude/symbol'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Make silence a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Suspend a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Unsilence a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Unsuspend a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Mark a user as unverified.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ export const meta = { | |||
| 		'ja-JP': 'インスタンスの設定を更新します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -11,6 +11,8 @@ export const meta = { | |||
| 		'en-US': 'Update specified remote user information.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Mark a user as verified.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['admin'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 	requireModerator: true, | ||||
| 
 | ||||
|  |  | |||
|  | @ -3,6 +3,8 @@ import define from '../../define'; | |||
| import fetchMeta from '../../../../misc/fetch-meta'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['hashtags'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| }; | ||||
| 
 | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ import Resolver from '../../../../remote/activitypub/resolver'; | |||
| import { ApiError } from '../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['federation'], | ||||
| 
 | ||||
| 	desc: { | ||||
| 		'ja-JP': 'URIを指定してActivityPubオブジェクトを参照します。' | ||||
| 	}, | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import App, { pack } from '../../../../models/app'; | |||
| import define from '../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['app'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -5,6 +5,8 @@ import define from '../../define'; | |||
| import { ApiError } from '../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['app'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		appId: { | ||||
| 			validator: $.type(ID), | ||||
|  |  | |||
|  | @ -8,6 +8,8 @@ import define from '../../define'; | |||
| import { ApiError } from '../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['auth'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	secure: true, | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ import define from '../../../define'; | |||
| import { ApiError } from '../../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['auth'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import define from '../../../define'; | |||
| import { ApiError } from '../../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['auth'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ import define from '../../../define'; | |||
| import { ApiError } from '../../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['auth'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -16,6 +16,8 @@ export const meta = { | |||
| 		'en-US': 'Block a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['blocking', 'users'], | ||||
| 
 | ||||
| 	limit: { | ||||
| 		duration: ms('1hour'), | ||||
| 		max: 100 | ||||
|  |  | |||
|  | @ -16,6 +16,8 @@ export const meta = { | |||
| 		'en-US': 'Unblock a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['blocking', 'users'], | ||||
| 
 | ||||
| 	limit: { | ||||
| 		duration: ms('1hour'), | ||||
| 		max: 100 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Get blocking users.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['blocking', 'account'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'following-read', | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'アクティブユーザーのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'users'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -24,7 +26,14 @@ export const meta = { | |||
| 				'ja-JP': '最大数。例えば 30 を指定したとすると、スパンが"day"の場合は30日分のデータが、スパンが"hour"の場合は30時間分のデータが返ります。' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'ドライブのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'drive'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -24,7 +26,14 @@ export const meta = { | |||
| 				'ja-JP': '最大数。例えば 30 を指定したとすると、スパンが"day"の場合は30日分のデータが、スパンが"hour"の場合は30時間分のデータが返ります。' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'フェデレーションのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -24,7 +26,14 @@ export const meta = { | |||
| 				'ja-JP': '最大数。例えば 30 を指定したとすると、スパンが"day"の場合は30日分のデータが、スパンが"hour"の場合は30時間分のデータが返ります。' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'ハッシュタグごとのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'hashtags'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -31,7 +33,14 @@ export const meta = { | |||
| 				'ja-JP': '対象のハッシュタグ' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'インスタンスごとのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -32,7 +34,14 @@ export const meta = { | |||
| 				'en-US': 'Target instance host' | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'ネットワークのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -24,7 +26,14 @@ export const meta = { | |||
| 				'ja-JP': '最大数。例えば 30 を指定したとすると、スパンが"day"の場合は30日分のデータが、スパンが"hour"の場合は30時間分のデータが返ります。' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': '投稿のチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'notes'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -24,7 +26,14 @@ export const meta = { | |||
| 				'ja-JP': '最大数。例えば 30 を指定したとすると、スパンが"day"の場合は30日分のデータが、スパンが"hour"の場合は30時間分のデータが返ります。' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ export const meta = { | |||
| 		'ja-JP': 'ユーザーごとのドライブのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'drive', 'users'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -34,7 +36,14 @@ export const meta = { | |||
| 				'en-US': 'Target user ID' | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ export const meta = { | |||
| 		'ja-JP': 'ユーザーごとのフォロー/フォロワーのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'users', 'following'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -34,7 +36,14 @@ export const meta = { | |||
| 				'en-US': 'Target user ID' | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ export const meta = { | |||
| 		'ja-JP': 'ユーザーごとの投稿のチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'users', 'notes'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -34,7 +36,14 @@ export const meta = { | |||
| 				'en-US': 'Target user ID' | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ export const meta = { | |||
| 		'ja-JP': 'ユーザーごとの被リアクション数のチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'users', 'reactions'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -34,7 +36,14 @@ export const meta = { | |||
| 				'en-US': 'Target user ID' | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'ja-JP': 'ユーザーのチャートを取得します。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['charts', 'users'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		span: { | ||||
| 			validator: $.str.or(['day', 'hour']), | ||||
|  | @ -24,7 +26,14 @@ export const meta = { | |||
| 				'ja-JP': '最大数。例えば 30 を指定したとすると、スパンが"day"の場合は30日分のデータが、スパンが"hour"の場合は30時間分のデータが返ります。' | ||||
| 			} | ||||
| 		}, | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'object', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps) => { | ||||
|  |  | |||
|  | @ -8,6 +8,8 @@ export const meta = { | |||
| 		'en-US': 'Get drive information.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive', 'account'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read' | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Get files of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  | @ -38,7 +40,14 @@ export const meta = { | |||
| 		type: { | ||||
| 			validator: $.optional.str.match(/^[a-zA-Z\/\-\*]+$/) | ||||
| 		} | ||||
| 	} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'array', | ||||
| 		items: { | ||||
| 			type: 'DriveFile', | ||||
| 		}, | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| export default define(meta, async (ps, user) => { | ||||
|  |  | |||
|  | @ -13,6 +13,8 @@ export const meta = { | |||
| 		'en-US': 'Get the notes that specified file of drive attached.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive', 'notes'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  |  | |||
|  | @ -8,6 +8,8 @@ export const meta = { | |||
| 		'en-US': 'Returns whether the file with the given MD5 hash exists in the user\'s drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  |  | |||
|  | @ -13,6 +13,8 @@ export const meta = { | |||
| 		'en-US': 'Upload a file to drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	limit: { | ||||
|  | @ -35,7 +37,7 @@ export const meta = { | |||
| 		}, | ||||
| 
 | ||||
| 		isSensitive: { | ||||
| 			validator: $.optional.or($.bool, $.str), | ||||
| 			validator: $.optional.either($.bool, $.str), | ||||
| 			default: false, | ||||
| 			transform: (v: any): boolean => v === true || v === 'true', | ||||
| 			desc: { | ||||
|  | @ -45,7 +47,7 @@ export const meta = { | |||
| 		}, | ||||
| 
 | ||||
| 		force: { | ||||
| 			validator: $.optional.or($.bool, $.str), | ||||
| 			validator: $.optional.either($.bool, $.str), | ||||
| 			default: false, | ||||
| 			transform: (v: any): boolean => v === true || v === 'true', | ||||
| 			desc: { | ||||
|  | @ -54,6 +56,10 @@ export const meta = { | |||
| 		} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'DriveFile', | ||||
| 	}, | ||||
| 
 | ||||
| 	errors: { | ||||
| 		invalidFileName: { | ||||
| 			message: 'Invalid file name.', | ||||
|  |  | |||
|  | @ -14,6 +14,8 @@ export const meta = { | |||
| 		'en-US': 'Delete a file of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-write', | ||||
|  |  | |||
|  | @ -6,6 +6,8 @@ import define from '../../../define'; | |||
| export const meta = { | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -14,6 +14,8 @@ export const meta = { | |||
| 		'en-US': 'Get specified file of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  | @ -37,6 +39,10 @@ export const meta = { | |||
| 		} | ||||
| 	}, | ||||
| 
 | ||||
| 	res: { | ||||
| 		type: 'DriveFile', | ||||
| 	}, | ||||
| 
 | ||||
| 	errors: { | ||||
| 		noSuchFile: { | ||||
| 			message: 'No such file.', | ||||
|  |  | |||
|  | @ -13,6 +13,8 @@ export const meta = { | |||
| 		'en-US': 'Update specified file of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-write', | ||||
|  |  | |||
|  | @ -10,6 +10,8 @@ export const meta = { | |||
| 		'ja-JP': 'ドライブに指定されたURLに存在するファイルをアップロードします。' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	limit: { | ||||
| 		duration: ms('1hour'), | ||||
| 		max: 60 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ export const meta = { | |||
| 		'en-US': 'Get folders of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  |  | |||
|  | @ -13,6 +13,8 @@ export const meta = { | |||
| 		'en-US': 'Create a folder of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-write', | ||||
|  |  | |||
|  | @ -14,6 +14,8 @@ export const meta = { | |||
| 		'en-US': 'Delete specified folder of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-write', | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import DriveFolder, { pack } from '../../../../../models/drive-folder'; | |||
| import define from '../../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  |  | |||
|  | @ -12,6 +12,8 @@ export const meta = { | |||
| 		'en-US': 'Get specified folder of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  |  | |||
|  | @ -13,6 +13,8 @@ export const meta = { | |||
| 		'en-US': 'Update specified folder of drive.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-write', | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import DriveFile, { packMany } from '../../../../models/drive-file'; | |||
| import define from '../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['drive'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'drive-read', | ||||
|  |  | |||
|  | @ -3,6 +3,8 @@ import define from '../../define'; | |||
| import Instance from '../../../../models/instance'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['federation'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -3,6 +3,8 @@ import define from '../../define'; | |||
| import Instance from '../../../../models/instance'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['federation'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -16,6 +16,8 @@ export const meta = { | |||
| 		'en-US': 'Follow a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['following', 'users'], | ||||
| 
 | ||||
| 	limit: { | ||||
| 		duration: ms('1hour'), | ||||
| 		max: 100 | ||||
|  |  | |||
|  | @ -16,6 +16,8 @@ export const meta = { | |||
| 		'en-US': 'Unfollow a user.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['following', 'users'], | ||||
| 
 | ||||
| 	limit: { | ||||
| 		duration: ms('1hour'), | ||||
| 		max: 100 | ||||
|  |  | |||
|  | @ -11,6 +11,8 @@ export const meta = { | |||
| 		'en-US': 'Accept a follow request.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['following', 'account'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'following-write', | ||||
|  |  | |||
|  | @ -12,6 +12,8 @@ export const meta = { | |||
| 		'en-US': 'Cancel a follow request.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['following', 'account'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'following-write', | ||||
|  |  | |||
|  | @ -7,6 +7,8 @@ export const meta = { | |||
| 		'en-US': 'Get all pending received follow requests.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['following', 'account'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'following-read' | ||||
|  |  | |||
|  | @ -11,6 +11,8 @@ export const meta = { | |||
| 		'en-US': 'Reject a follow request.' | ||||
| 	}, | ||||
| 
 | ||||
| 	tags: ['following', 'account'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	kind: 'following-write', | ||||
|  |  | |||
|  | @ -4,6 +4,8 @@ import ReversiGame, { pack } from '../../../../../models/games/reversi/game'; | |||
| import define from '../../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['games'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		limit: { | ||||
| 			validator: $.optional.num.range(1, 100), | ||||
|  |  | |||
|  | @ -6,6 +6,8 @@ import define from '../../../../define'; | |||
| import { ApiError } from '../../../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['games'], | ||||
| 
 | ||||
| 	params: { | ||||
| 		gameId: { | ||||
| 			validator: $.type(ID), | ||||
|  |  | |||
|  | @ -6,6 +6,8 @@ import define from '../../../../define'; | |||
| import { ApiError } from '../../../../error'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['games'], | ||||
| 
 | ||||
| 	desc: { | ||||
| 		'ja-JP': '指定したリバーシの対局で投了します。' | ||||
| 	}, | ||||
|  |  | |||
|  | @ -2,6 +2,8 @@ import Matching, { pack as packMatching } from '../../../../../models/games/reve | |||
| import define from '../../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['games'], | ||||
| 
 | ||||
| 	requireCredential: true | ||||
| }; | ||||
| 
 | ||||
|  |  | |||
|  | @ -9,6 +9,8 @@ import { ApiError } from '../../../error'; | |||
| import { getUser } from '../../../common/getters'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['games'], | ||||
| 
 | ||||
| 	requireCredential: true, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
|  | @ -2,6 +2,8 @@ import Matching from '../../../../../../models/games/reversi/matching'; | |||
| import define from '../../../../define'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['games'], | ||||
| 
 | ||||
| 	requireCredential: true | ||||
| }; | ||||
| 
 | ||||
|  |  | |||
|  | @ -3,6 +3,8 @@ import define from '../../define'; | |||
| import Hashtag from '../../../../models/hashtag'; | ||||
| 
 | ||||
| export const meta = { | ||||
| 	tags: ['hashtags'], | ||||
| 
 | ||||
| 	requireCredential: false, | ||||
| 
 | ||||
| 	params: { | ||||
|  |  | |||
Some files were not shown because too many files have changed in this diff Show more
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue