feat: add image upload method to http client (#108)

* feat: add image upload method to http client

* fix: Make files optional on UploadImageResponse

* fix: Fix comment typo

* fix: replace loose equals with strict equals

* fix: Remove useless awaits

* fix: Add explicit return types to image upload helper functions

* fix: Include client headers in image upload request

* fix: Change type of uploadImage arg to File | Buffer instead of Blob | Buffer

* doc: Add doc string

* refactor: Switch to using cross-fetch instead of node-fetch v3

* chore: remove unnecessary asyncs
This commit is contained in:
SleeplessOne1917 2023-03-22 14:33:54 -04:00 committed by GitHub
parent 1e6ddc3587
commit 360196c8ae
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 198 additions and 111 deletions

View file

@ -26,11 +26,11 @@
]
},
"dependencies": {
"node-fetch": "2.6.6"
"cross-fetch": "^3.1.5",
"form-data": "^4.0.0"
},
"devDependencies": {
"@types/node": "^18.6.2",
"@types/node-fetch": "2.6.2",
"@typescript-eslint/eslint-plugin": "^5.31.0",
"@typescript-eslint/parser": "^5.31.0",
"eslint": "^8.20.0",

View file

@ -1,4 +1,6 @@
import fetch from "node-fetch";
import fetch from "cross-fetch";
import FormData from "form-data";
import {
CommentReportResponse,
CommentResponse,
@ -131,7 +133,7 @@ import {
SearchResponse,
SiteResponse,
} from "./interfaces/api/site";
import { VERSION } from "./interfaces/others";
import { UploadImage, UploadImageResponse, VERSION } from "./interfaces/others";
enum HttpType {
Get = "GET",
@ -145,6 +147,7 @@ enum HttpType {
export class LemmyHttp {
private apiUrl: string;
private headers: { [key: string]: string } = {};
private pictrsUrl: string;
/**
* Generates a new instance of LemmyHttp.
@ -153,6 +156,7 @@ export class LemmyHttp {
*/
constructor(baseUrl: string, headers?: { [key: string]: string }) {
this.apiUrl = `${baseUrl}/api/${VERSION}`;
this.pictrsUrl = `${baseUrl}/pictrs/image`;
if (headers) {
this.headers = headers;
@ -164,7 +168,7 @@ export class LemmyHttp {
*
* `HTTP.GET /site`
*/
async getSite(form: GetSite) {
getSite(form: GetSite) {
return this.wrapper<GetSite, GetSiteResponse>(HttpType.Get, "/site", form);
}
@ -173,7 +177,7 @@ export class LemmyHttp {
*
* `HTTP.POST /site`
*/
async createSite(form: CreateSite) {
createSite(form: CreateSite) {
return this.wrapper<CreateSite, SiteResponse>(HttpType.Post, "/site", form);
}
@ -182,7 +186,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /site`
*/
async editSite(form: EditSite) {
editSite(form: EditSite) {
return this.wrapper<EditSite, SiteResponse>(HttpType.Put, "/site", form);
}
@ -191,7 +195,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/leave_admin`
*/
async leaveAdmin(form: LeaveAdmin) {
leaveAdmin(form: LeaveAdmin) {
return this.wrapper<LeaveAdmin, GetSiteResponse>(
HttpType.Post,
"/user/leave_admin",
@ -204,7 +208,7 @@ export class LemmyHttp {
*
* `HTTP.GET /modlog`
*/
async getModlog(form: GetModlog) {
getModlog(form: GetModlog) {
return this.wrapper<GetModlog, GetModlogResponse>(
HttpType.Get,
"/modlog",
@ -217,7 +221,7 @@ export class LemmyHttp {
*
* `HTTP.GET /search`
*/
async search(form: Search) {
search(form: Search) {
return this.wrapper<Search, SearchResponse>(HttpType.Get, "/search", form);
}
@ -226,7 +230,7 @@ export class LemmyHttp {
*
* `HTTP.GET /resolve_object`
*/
async resolveObject(form: ResolveObject) {
resolveObject(form: ResolveObject) {
return this.wrapper<ResolveObject, ResolveObjectResponse>(
HttpType.Get,
"/resolve_object",
@ -239,7 +243,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community`
*/
async createCommunity(form: CreateCommunity) {
createCommunity(form: CreateCommunity) {
return this.wrapper<CreateCommunity, CommunityResponse>(
HttpType.Post,
"/community",
@ -252,7 +256,7 @@ export class LemmyHttp {
*
* `HTTP.GET /community`
*/
async getCommunity(form: GetCommunity) {
getCommunity(form: GetCommunity) {
return this.wrapper<GetCommunity, GetCommunityResponse>(
HttpType.Get,
"/community",
@ -265,7 +269,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /community`
*/
async editCommunity(form: EditCommunity) {
editCommunity(form: EditCommunity) {
return this.wrapper<EditCommunity, CommunityResponse>(
HttpType.Put,
"/community",
@ -278,7 +282,7 @@ export class LemmyHttp {
*
* `HTTP.GET /community/list`
*/
async listCommunities(form: ListCommunities) {
listCommunities(form: ListCommunities) {
return this.wrapper<ListCommunities, ListCommunitiesResponse>(
HttpType.Get,
"/community/list",
@ -291,7 +295,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/follow`
*/
async followCommunity(form: FollowCommunity) {
followCommunity(form: FollowCommunity) {
return this.wrapper<FollowCommunity, CommunityResponse>(
HttpType.Post,
"/community/follow",
@ -304,7 +308,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/block`
*/
async blockCommunity(form: BlockCommunity) {
blockCommunity(form: BlockCommunity) {
return this.wrapper<BlockCommunity, BlockCommunityResponse>(
HttpType.Post,
"/community/block",
@ -317,7 +321,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/delete`
*/
async deleteCommunity(form: DeleteCommunity) {
deleteCommunity(form: DeleteCommunity) {
return this.wrapper<DeleteCommunity, CommunityResponse>(
HttpType.Post,
"/community/delete",
@ -330,7 +334,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/remove`
*/
async removeCommunity(form: RemoveCommunity) {
removeCommunity(form: RemoveCommunity) {
return this.wrapper<RemoveCommunity, CommunityResponse>(
HttpType.Post,
"/community/remove",
@ -343,7 +347,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/transfer`
*/
async transferCommunity(form: TransferCommunity) {
transferCommunity(form: TransferCommunity) {
return this.wrapper<TransferCommunity, GetCommunityResponse>(
HttpType.Post,
"/community/transfer",
@ -356,7 +360,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/ban_user`
*/
async banFromCommunity(form: BanFromCommunity) {
banFromCommunity(form: BanFromCommunity) {
return this.wrapper<BanFromCommunity, BanFromCommunityResponse>(
HttpType.Post,
"/community/ban_user",
@ -369,7 +373,7 @@ export class LemmyHttp {
*
* `HTTP.POST /community/mod`
*/
async addModToCommunity(form: AddModToCommunity) {
addModToCommunity(form: AddModToCommunity) {
return this.wrapper<AddModToCommunity, AddModToCommunityResponse>(
HttpType.Post,
"/community/mod",
@ -382,7 +386,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post`
*/
async createPost(form: CreatePost) {
createPost(form: CreatePost) {
return this.wrapper<CreatePost, PostResponse>(HttpType.Post, "/post", form);
}
@ -391,7 +395,7 @@ export class LemmyHttp {
*
* `HTTP.GET /post`
*/
async getPost(form: GetPost) {
getPost(form: GetPost) {
return this.wrapper<GetPost, GetPostResponse>(HttpType.Get, "/post", form);
}
@ -400,7 +404,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /post`
*/
async editPost(form: EditPost) {
editPost(form: EditPost) {
return this.wrapper<EditPost, PostResponse>(HttpType.Put, "/post", form);
}
@ -409,7 +413,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/delete`
*/
async deletePost(form: DeletePost) {
deletePost(form: DeletePost) {
return this.wrapper<DeletePost, PostResponse>(
HttpType.Post,
"/post/delete",
@ -422,7 +426,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/remove`
*/
async removePost(form: RemovePost) {
removePost(form: RemovePost) {
return this.wrapper<RemovePost, PostResponse>(
HttpType.Post,
"/post/remove",
@ -435,7 +439,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/mark_as_read`
*/
async markPostAsRead(form: MarkPostAsRead) {
markPostAsRead(form: MarkPostAsRead) {
return this.wrapper<MarkPostAsRead, PostResponse>(
HttpType.Post,
"/post/mark_as_read",
@ -448,7 +452,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/lock`
*/
async lockPost(form: LockPost) {
lockPost(form: LockPost) {
return this.wrapper<LockPost, PostResponse>(
HttpType.Post,
"/post/lock",
@ -461,7 +465,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/feature`
*/
async featurePost(form: FeaturePost) {
featurePost(form: FeaturePost) {
return this.wrapper<FeaturePost, PostResponse>(
HttpType.Post,
"/post/feature",
@ -474,7 +478,7 @@ export class LemmyHttp {
*
* `HTTP.GET /post/list`
*/
async getPosts(form: GetPosts) {
getPosts(form: GetPosts) {
return this.wrapper<GetPosts, GetPostsResponse>(
HttpType.Get,
"/post/list",
@ -487,7 +491,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/like`
*/
async likePost(form: CreatePostLike) {
likePost(form: CreatePostLike) {
return this.wrapper<CreatePostLike, PostResponse>(
HttpType.Post,
"/post/like",
@ -500,7 +504,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /post/save`
*/
async savePost(form: SavePost) {
savePost(form: SavePost) {
return this.wrapper<SavePost, PostResponse>(
HttpType.Put,
"/post/save",
@ -513,7 +517,7 @@ export class LemmyHttp {
*
* `HTTP.POST /post/report`
*/
async createPostReport(form: CreatePostReport) {
createPostReport(form: CreatePostReport) {
return this.wrapper<CreatePostReport, PostReportResponse>(
HttpType.Post,
"/post/report",
@ -526,7 +530,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /post/report/resolve`
*/
async resolvePostReport(form: ResolvePostReport) {
resolvePostReport(form: ResolvePostReport) {
return this.wrapper<ResolvePostReport, PostReportResponse>(
HttpType.Put,
"/post/report/resolve",
@ -539,7 +543,7 @@ export class LemmyHttp {
*
* `HTTP.GET /post/report/list`
*/
async listPostReports(form: ListPostReports) {
listPostReports(form: ListPostReports) {
return this.wrapper<ListPostReports, ListPostReportsResponse>(
HttpType.Get,
"/post/report/list",
@ -552,7 +556,7 @@ export class LemmyHttp {
*
* `HTTP.GET /post/site_metadata`
*/
async getSiteMetadata(form: GetSiteMetadata) {
getSiteMetadata(form: GetSiteMetadata) {
return this.wrapper<GetSiteMetadata, GetSiteMetadataResponse>(
HttpType.Get,
"/post/site_metadata",
@ -565,7 +569,7 @@ export class LemmyHttp {
*
* `HTTP.POST /comment`
*/
async createComment(form: CreateComment) {
createComment(form: CreateComment) {
return this.wrapper<CreateComment, CommentResponse>(
HttpType.Post,
"/comment",
@ -578,7 +582,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /comment`
*/
async editComment(form: EditComment) {
editComment(form: EditComment) {
return this.wrapper<EditComment, CommentResponse>(
HttpType.Put,
"/comment",
@ -591,7 +595,7 @@ export class LemmyHttp {
*
* `HTTP.POST /comment/delete`
*/
async deleteComment(form: DeleteComment) {
deleteComment(form: DeleteComment) {
return this.wrapper<DeleteComment, CommentResponse>(
HttpType.Post,
"/comment/delete",
@ -604,7 +608,7 @@ export class LemmyHttp {
*
* `HTTP.POST /comment/remove`
*/
async removeComment(form: RemoveComment) {
removeComment(form: RemoveComment) {
return this.wrapper<RemoveComment, CommentResponse>(
HttpType.Post,
"/comment/remove",
@ -617,7 +621,7 @@ export class LemmyHttp {
*
* `HTTP.POST /comment/mark_as_read`
*/
async markCommentReplyAsRead(form: MarkCommentReplyAsRead) {
markCommentReplyAsRead(form: MarkCommentReplyAsRead) {
return this.wrapper<MarkCommentReplyAsRead, CommentResponse>(
HttpType.Post,
"/comment/mark_as_read",
@ -630,7 +634,7 @@ export class LemmyHttp {
*
* `HTTP.POST /comment/like`
*/
async likeComment(form: CreateCommentLike) {
likeComment(form: CreateCommentLike) {
return this.wrapper<CreateCommentLike, CommentResponse>(
HttpType.Post,
"/comment/like",
@ -643,7 +647,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /comment/save`
*/
async saveComment(form: SaveComment) {
saveComment(form: SaveComment) {
return this.wrapper<SaveComment, CommentResponse>(
HttpType.Put,
"/comment/save",
@ -656,7 +660,7 @@ export class LemmyHttp {
*
* `HTTP.GET /comment/list`
*/
async getComments(form: GetComments) {
getComments(form: GetComments) {
return this.wrapper<GetComments, GetCommentsResponse>(
HttpType.Get,
"/comment/list",
@ -669,7 +673,7 @@ export class LemmyHttp {
*
* `HTTP.POST /comment/report`
*/
async createCommentReport(form: CreateCommentReport) {
createCommentReport(form: CreateCommentReport) {
return this.wrapper<CreateCommentReport, CommentReportResponse>(
HttpType.Post,
"/comment/report",
@ -682,7 +686,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /comment/report/resolve`
*/
async resolveCommentReport(form: ResolveCommentReport) {
resolveCommentReport(form: ResolveCommentReport) {
return this.wrapper<ResolveCommentReport, CommentReportResponse>(
HttpType.Put,
"/comment/report/resolve",
@ -695,7 +699,7 @@ export class LemmyHttp {
*
* `HTTP.GET /comment/report/list`
*/
async listCommentReports(form: ListCommentReports) {
listCommentReports(form: ListCommentReports) {
return this.wrapper<ListCommentReports, ListCommentReportsResponse>(
HttpType.Get,
"/comment/report/list",
@ -708,7 +712,7 @@ export class LemmyHttp {
*
* `HTTP.GET /private_message/list`
*/
async getPrivateMessages(form: GetPrivateMessages) {
getPrivateMessages(form: GetPrivateMessages) {
return this.wrapper<GetPrivateMessages, PrivateMessagesResponse>(
HttpType.Get,
"/private_message/list",
@ -721,7 +725,7 @@ export class LemmyHttp {
*
* `HTTP.POST /private_message`
*/
async createPrivateMessage(form: CreatePrivateMessage) {
createPrivateMessage(form: CreatePrivateMessage) {
return this.wrapper<CreatePrivateMessage, PrivateMessageResponse>(
HttpType.Post,
"/private_message",
@ -734,7 +738,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /private_message`
*/
async editPrivateMessage(form: EditPrivateMessage) {
editPrivateMessage(form: EditPrivateMessage) {
return this.wrapper<EditPrivateMessage, PrivateMessageResponse>(
HttpType.Put,
"/private_message",
@ -747,7 +751,7 @@ export class LemmyHttp {
*
* `HTTP.POST /private_message/delete`
*/
async deletePrivateMessage(form: DeletePrivateMessage) {
deletePrivateMessage(form: DeletePrivateMessage) {
return this.wrapper<DeletePrivateMessage, PrivateMessageResponse>(
HttpType.Post,
"/private_message/delete",
@ -760,7 +764,7 @@ export class LemmyHttp {
*
* `HTTP.POST /private_message/mark_as_read`
*/
async markPrivateMessageAsRead(form: MarkPrivateMessageAsRead) {
markPrivateMessageAsRead(form: MarkPrivateMessageAsRead) {
return this.wrapper<MarkPrivateMessageAsRead, PrivateMessageResponse>(
HttpType.Post,
"/private_message/mark_as_read",
@ -773,7 +777,7 @@ export class LemmyHttp {
*
* `HTTP.POST /private_message/report`
*/
async createPrivateMessageReport(form: CreatePrivateMessageReport) {
createPrivateMessageReport(form: CreatePrivateMessageReport) {
return this.wrapper<
CreatePrivateMessageReport,
PrivateMessageReportResponse
@ -785,7 +789,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /private_message/report/resolve`
*/
async resolvePrivateMessageReport(form: ResolvePrivateMessageReport) {
resolvePrivateMessageReport(form: ResolvePrivateMessageReport) {
return this.wrapper<
ResolvePrivateMessageReport,
PrivateMessageReportResponse
@ -797,7 +801,7 @@ export class LemmyHttp {
*
* `HTTP.GET /private_message/report/list`
*/
async listPrivateMessageReports(form: ListPrivateMessageReports) {
listPrivateMessageReports(form: ListPrivateMessageReports) {
return this.wrapper<
ListPrivateMessageReports,
ListPrivateMessageReportsResponse
@ -809,7 +813,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/register`
*/
async register(form: Register) {
register(form: Register) {
return this.wrapper<Register, LoginResponse>(
HttpType.Post,
"/user/register",
@ -822,7 +826,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/login`
*/
async login(form: Login) {
login(form: Login) {
return this.wrapper<Login, LoginResponse>(
HttpType.Post,
"/user/login",
@ -835,7 +839,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user`
*/
async getPersonDetails(form: GetPersonDetails) {
getPersonDetails(form: GetPersonDetails) {
return this.wrapper<GetPersonDetails, GetPersonDetailsResponse>(
HttpType.Get,
"/user",
@ -848,7 +852,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user/mention`
*/
async getPersonMentions(form: GetPersonMentions) {
getPersonMentions(form: GetPersonMentions) {
return this.wrapper<GetPersonMentions, GetPersonMentionsResponse>(
HttpType.Get,
"/user/mention",
@ -861,7 +865,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/mention/mark_as_read`
*/
async markPersonMentionAsRead(form: MarkPersonMentionAsRead) {
markPersonMentionAsRead(form: MarkPersonMentionAsRead) {
return this.wrapper<MarkPersonMentionAsRead, PersonMentionResponse>(
HttpType.Post,
"/user/mention/mark_as_read",
@ -874,7 +878,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user/replies`
*/
async getReplies(form: GetReplies) {
getReplies(form: GetReplies) {
return this.wrapper<GetReplies, GetRepliesResponse>(
HttpType.Get,
"/user/replies",
@ -887,7 +891,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/ban`
*/
async banPerson(form: BanPerson) {
banPerson(form: BanPerson) {
return this.wrapper<BanPerson, BanPersonResponse>(
HttpType.Post,
"/user/ban",
@ -900,7 +904,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user/banned`
*/
async getBannedPersons(form: GetBannedPersons) {
getBannedPersons(form: GetBannedPersons) {
return this.wrapper<GetBannedPersons, BannedPersonsResponse>(
HttpType.Get,
"/user/banned",
@ -913,7 +917,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/block`
*/
async blockPerson(form: BlockPerson) {
blockPerson(form: BlockPerson) {
return this.wrapper<BlockPerson, BlockPersonResponse>(
HttpType.Post,
"/user/block",
@ -926,7 +930,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user/get_captcha`
*/
async getCaptcha() {
getCaptcha() {
return this.wrapper<any, GetCaptchaResponse>(
HttpType.Get,
"/user/get_captcha",
@ -939,7 +943,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/delete_account`
*/
async deleteAccount(form: DeleteAccount) {
deleteAccount(form: DeleteAccount) {
return this.wrapper<DeleteAccount, DeleteAccountResponse>(
HttpType.Post,
"/user/delete_account",
@ -952,7 +956,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/password_reset`
*/
async passwordReset(form: PasswordReset) {
passwordReset(form: PasswordReset) {
return this.wrapper<PasswordReset, PasswordResetResponse>(
HttpType.Post,
"/user/password_reset",
@ -965,7 +969,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/password_change`
*/
async passwordChange(form: PasswordChange) {
passwordChange(form: PasswordChange) {
return this.wrapper<PasswordChange, LoginResponse>(
HttpType.Post,
"/user/password_change",
@ -978,7 +982,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/mark_all_as_read`
*/
async markAllAsRead(form: MarkAllAsRead) {
markAllAsRead(form: MarkAllAsRead) {
return this.wrapper<MarkAllAsRead, GetRepliesResponse>(
HttpType.Post,
"/user/mark_all_as_read",
@ -991,7 +995,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /user/save_user_settings`
*/
async saveUserSettings(form: SaveUserSettings) {
saveUserSettings(form: SaveUserSettings) {
return this.wrapper<SaveUserSettings, LoginResponse>(
HttpType.Put,
"/user/save_user_settings",
@ -1004,7 +1008,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /user/change_password`
*/
async changePassword(form: ChangePassword) {
changePassword(form: ChangePassword) {
return this.wrapper<ChangePassword, LoginResponse>(
HttpType.Put,
"/user/change_password",
@ -1017,7 +1021,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user/report_count`
*/
async getReportCount(form: GetReportCount) {
getReportCount(form: GetReportCount) {
return this.wrapper<GetReportCount, GetReportCountResponse>(
HttpType.Get,
"/user/report_count",
@ -1030,7 +1034,7 @@ export class LemmyHttp {
*
* `HTTP.GET /user/unread_count`
*/
async getUnreadCount(form: GetUnreadCount) {
getUnreadCount(form: GetUnreadCount) {
return this.wrapper<GetUnreadCount, GetUnreadCountResponse>(
HttpType.Get,
"/user/unread_count",
@ -1043,7 +1047,7 @@ export class LemmyHttp {
*
* `HTTP.POST /user/verify_email`
*/
async verifyEmail(form: VerifyEmail) {
verifyEmail(form: VerifyEmail) {
return this.wrapper<VerifyEmail, VerifyEmailResponse>(
HttpType.Post,
"/user/verify_email",
@ -1056,7 +1060,7 @@ export class LemmyHttp {
*
* `HTTP.POST /admin/add`
*/
async addAdmin(form: AddAdmin) {
addAdmin(form: AddAdmin) {
return this.wrapper<AddAdmin, AddAdminResponse>(
HttpType.Post,
"/admin/add",
@ -1069,7 +1073,7 @@ export class LemmyHttp {
*
* `HTTP.GET /admin/registration_application/count`
*/
async getUnreadRegistrationApplicationCount(
getUnreadRegistrationApplicationCount(
form: GetUnreadRegistrationApplicationCount
) {
return this.wrapper<
@ -1083,7 +1087,7 @@ export class LemmyHttp {
*
* `HTTP.GET /admin/registration_application/list`
*/
async listRegistrationApplications(form: ListRegistrationApplications) {
listRegistrationApplications(form: ListRegistrationApplications) {
return this.wrapper<
ListRegistrationApplications,
ListRegistrationApplicationsResponse
@ -1095,7 +1099,7 @@ export class LemmyHttp {
*
* `HTTP.PUT /admin/registration_application/approve`
*/
async approveRegistrationApplication(form: ApproveRegistrationApplication) {
approveRegistrationApplication(form: ApproveRegistrationApplication) {
return this.wrapper<
ApproveRegistrationApplication,
RegistrationApplicationResponse
@ -1107,7 +1111,7 @@ export class LemmyHttp {
*
* `HTTP.POST /admin/purge/person`
*/
async purgePerson(form: PurgePerson) {
purgePerson(form: PurgePerson) {
return this.wrapper<PurgePerson, PurgeItemResponse>(
HttpType.Post,
"/admin/purge/person",
@ -1120,7 +1124,7 @@ export class LemmyHttp {
*
* `HTTP.POST /admin/purge/community`
*/
async purgeCommunity(form: PurgeCommunity) {
purgeCommunity(form: PurgeCommunity) {
return this.wrapper<PurgeCommunity, PurgeItemResponse>(
HttpType.Post,
"/admin/purge/community",
@ -1133,7 +1137,7 @@ export class LemmyHttp {
*
* `HTTP.POST /admin/purge/post`
*/
async purgePost(form: PurgePost) {
purgePost(form: PurgePost) {
return this.wrapper<PurgePost, PurgeItemResponse>(
HttpType.Post,
"/admin/purge/post",
@ -1146,7 +1150,7 @@ export class LemmyHttp {
*
* `HTTP.POST /admin/purge/comment`
*/
async purgeComment(form: PurgeComment) {
purgeComment(form: PurgeComment) {
return this.wrapper<PurgeComment, PurgeItemResponse>(
HttpType.Post,
"/admin/purge/comment",
@ -1154,7 +1158,52 @@ export class LemmyHttp {
);
}
private buildFullUrl(endpoint: string): string {
/**
* Upload an image to the server.
*/
async uploadImage({
image,
auth,
}: UploadImage): Promise<UploadImageResponse> {
const formData = createFormData(image);
// If jwt cookie not already set by browser, set it with passed in auth
const headers = {} as any;
if (
!globalThis?.document?.cookie?.includes("jwt=") &&
!this.headers?.Cookie?.includes("jwt=")
) {
headers.Cookie = `jwt=${auth}`;
}
let url: string | undefined = undefined;
let delete_url: string | undefined = undefined;
const response = await fetch(this.pictrsUrl, {
method: HttpType.Post,
body: formData as unknown as BodyInit,
headers: {
...this.headers,
...headers,
},
});
const responseJson = await response.json();
if (responseJson.msg === "ok") {
const { file: hash, delete_token: deleteToken } = responseJson.files[0];
delete_url = `${this.pictrsUrl}/delete/${deleteToken}/${hash}`;
url = `${this.pictrsUrl}/${hash}`;
}
return {
...responseJson,
url,
delete_url,
};
}
private buildFullUrl(endpoint: string) {
return `${this.apiUrl}${endpoint}`;
}
@ -1163,21 +1212,25 @@ export class LemmyHttp {
endpoint: string,
form: BodyType
): Promise<ResponseType> {
if (type_ == HttpType.Get) {
let getUrl = `${this.buildFullUrl(endpoint)}?${encodeGetParams(form)}`;
return fetch(getUrl, {
method: "GET",
if (type_ === HttpType.Get) {
const getUrl = `${this.buildFullUrl(endpoint)}?${encodeGetParams(form)}`;
const response = await fetch(getUrl, {
method: HttpType.Get,
headers: this.headers,
}).then(d => d.json() as Promise<ResponseType>);
});
return await response.json();
} else {
return fetch(this.buildFullUrl(endpoint), {
const response = await fetch(this.buildFullUrl(endpoint), {
method: type_,
headers: {
"Content-Type": "application/json",
...this.headers,
},
body: JSON.stringify(form),
}).then(d => d.json() as Promise<ResponseType>);
});
return await response.json();
}
}
}
@ -1188,3 +1241,16 @@ function encodeGetParams<BodyType extends object>(p: BodyType): string {
.map(kv => kv.map(encodeURIComponent).join("="))
.join("&");
}
function createFormData(image: File | Buffer): FormData {
let formData = new FormData();
if (image.constructor.name === "File") {
formData.append("images[]", image);
} else {
// The filename doesn't affect the file type or file name that ends up in pictrs
formData.append("images[]", image, { filename: "image.jpg" });
}
return formData;
}

View file

@ -230,3 +230,26 @@ export interface SiteMetadata {
image?: string;
html?: string;
}
export interface UploadImage {
image: File | Buffer;
/**
* Optional if cookie with jwt set is already present. Otherwise, auth is required.
*/
auth?: string;
}
export interface UploadImageResponse {
/**
* Is "ok" if the upload was successful; is something else otherwise.
*/
msg: string;
files?: ImageFile[];
url?: string;
delete_url?: string;
}
export interface ImageFile {
file: string;
delete_token: string;
}

View file

@ -9,10 +9,9 @@
"target": "ES5",
"experimentalDecorators": true,
"strictNullChecks": true,
"moduleResolution": "Node"
"moduleResolution": "Node",
"esModuleInterop": true
},
"include": [
"src/**/*"
],
"include": ["src/**/*"],
"exclude": ["node_modules", "dist"]
}

View file

@ -303,14 +303,6 @@
resolved "https://registry.yarnpkg.com/@types/minimatch/-/minimatch-5.1.2.tgz#07508b45797cb81ec3f273011b054cd0755eddca"
integrity sha512-K0VQKziLUWkVKiRVrx4a40iPaxTUefQmjtkQofBkYRcoaaL/8rhwDWww9qWbrgicNOgnpIsMxyNIUM4+n6dUIA==
"@types/node-fetch@2.6.2":
version "2.6.2"
resolved "https://registry.yarnpkg.com/@types/node-fetch/-/node-fetch-2.6.2.tgz#d1a9c5fd049d9415dce61571557104dec3ec81da"
integrity sha512-DHqhlq5jeESLy19TYhLakJ07kNumXWjcDdxXsLUMJZ6ue8VZJj4kLPQVE/2mdHh3xZziNF1xppu5lwmS53HR+A==
dependencies:
"@types/node" "*"
form-data "^3.0.0"
"@types/node@*", "@types/node@^18.6.2":
version "18.11.18"
resolved "https://registry.yarnpkg.com/@types/node/-/node-18.11.18.tgz#8dfb97f0da23c2293e554c5a50d61ef134d7697f"
@ -665,6 +657,13 @@ cosmiconfig@^5.0.5:
js-yaml "^3.13.1"
parse-json "^4.0.0"
cross-fetch@^3.1.5:
version "3.1.5"
resolved "https://registry.yarnpkg.com/cross-fetch/-/cross-fetch-3.1.5.tgz#e1389f44d9e7ba767907f7af8454787952ab534f"
integrity sha512-lvb1SBsI0Z7GDwmuid+mU3kWVBwTVUbe7S0H52yaaAdQOXq2YktTCZdlAcNKFzE6QtRz0snpw9bNiPeOIkkQvw==
dependencies:
node-fetch "2.6.7"
cross-spawn@^7.0.2, cross-spawn@^7.0.3:
version "7.0.3"
resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6"
@ -988,10 +987,10 @@ flatted@^3.1.0:
resolved "https://registry.yarnpkg.com/flatted/-/flatted-3.2.7.tgz#609f39207cb614b89d0765b477cb2d437fbf9787"
integrity sha512-5nqDSxl8nn5BSNxyR3n4I6eDmbolI6WT+QqR547RwxQapgjQBmtktdP+HTBb/a/zLsbzERTONyUB5pefh5TtjQ==
form-data@^3.0.0:
version "3.0.1"
resolved "https://registry.yarnpkg.com/form-data/-/form-data-3.0.1.tgz#ebd53791b78356a99af9a300d4282c4d5eb9755f"
integrity sha512-RHkBKtLWUVwd7SqRIvCZMEvAMoGUp0XU+seQiZejj0COz3RI3hWP4sCv3gZWWLjJTd7rGwcsF5eKZGii0r/hbg==
form-data@^4.0.0:
version "4.0.0"
resolved "https://registry.yarnpkg.com/form-data/-/form-data-4.0.0.tgz#93919daeaf361ee529584b9b31664dc12c9fa452"
integrity sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==
dependencies:
asynckit "^0.4.0"
combined-stream "^1.0.8"
@ -1513,10 +1512,10 @@ neo-async@^2.6.0:
resolved "https://registry.yarnpkg.com/neo-async/-/neo-async-2.6.2.tgz#b4aafb93e3aeb2d8174ca53cf163ab7d7308305f"
integrity sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==
node-fetch@2.6.6:
version "2.6.6"
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.6.tgz#1751a7c01834e8e1697758732e9efb6eeadfaf89"
integrity sha512-Z8/6vRlTUChSdIgMa51jxQ4lrw/Jy5SOW10ObaA47/RElsAN2c5Pn8bTgFGWn/ibwzXTE8qwr1Yzx28vsecXEA==
node-fetch@2.6.7:
version "2.6.7"
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad"
integrity sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==
dependencies:
whatwg-url "^5.0.0"