Skip to content

Commit

Permalink
feat: add a way to reply to content
Browse files Browse the repository at this point in the history
  • Loading branch information
thislooksfun committed Mar 26, 2021
1 parent 0d71a50 commit f5cbf7e
Show file tree
Hide file tree
Showing 4 changed files with 93 additions and 5 deletions.
29 changes: 29 additions & 0 deletions src/controls/replyable.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
import BaseControls from "./base";

/** The base controls for all content that you can reply to. */
export default abstract class ReplyableControls extends BaseControls {
/**
* Report an item to the mods.
*
* The report will be anonymous if you are not a mod of the subreddit. If you
* are a mod the report will be tied to your username.
*
* @param id The ID of the item to report.
* @param reason The reason you are reporting the item.
*
* @returns A promise that resolves when the item has been reported.
*/
async report(id: string, reason?: string): Promise<void> {
await this.client.post("api/report", {
reason: "other",
other_reason: reason,
thing_id: this.namespace(id),
});
}

/** @internal */
async replyImpl<T>(id: string, text: string): Promise<T> {
const body = { text, thing_id: this.namespace(id) };
return await this.client.post("api/comment", body);
}
}
21 changes: 19 additions & 2 deletions src/controls/voteable.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
import type Client from "../client";
import BaseControls from "./base";
import { Data, RedditObject } from "../helper/types";
import Comment from "../objects/comment";
import ReplyableControls from "./replyable";

/** The vote types. 1 = upvote, 0 = no vote, -1 = downvote. */
export type Vote = 1 | 0 | -1;

/** The base controls for all content that you can vote on. */
export default abstract class VoteableControls extends BaseControls {
export default abstract class VoteableControls extends ReplyableControls {
/** @internal */
constructor(client: Client, type: string) {
super(client, `${type}_`);
Expand Down Expand Up @@ -91,6 +93,21 @@ export default abstract class VoteableControls extends BaseControls {
return this.vote(id, -1);
}

/**
* Reply to an item.
*
* @param id The ID of the item to reply to.
* @param text The text content of the reply to post.
*
* @returns A promise that resolves to the comment reply.
*/
async reply(id: string, text: string): Promise<Comment> {
const res: Data = await this.replyImpl(id, text);
const rc: RedditObject = res.things[0];
if (!rc) throw "oh yeah that's definitely not good.";
return this.client.comments.fromRaw(rc);
}

/**
* Save an item.
*
Expand Down
28 changes: 28 additions & 0 deletions src/objects/replyable.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import type { ContentData } from "./content";
import Content from "./content";
import ReplyableControls from "../controls/replyable";

/** The base for all content that you can reply to. */
export default abstract class Replyable extends Content {
protected controls: ReplyableControls;

/** @internal */
constructor(controls: ReplyableControls, data: ContentData) {
super(data);
this.controls = controls;
}

/**
* Report this item to the mods.
*
* The report will be anonymous if you are not a mod of the subreddit. If you
* are a mod the report will be tied to your username.
*
* @param reason The reason you are reporting this item.
*
* @returns A promise that resolves when this item has been reported.
*/
async report(reason?: string): Promise<void> {
await this.controls.report(this.id, reason);
}
}
20 changes: 17 additions & 3 deletions src/objects/voteable.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import type { ContentData } from "./content";
import type { SubredditType } from "../helper/types";
import Content from "./content";
import Comment from "./comment";
import Replyable from "./replyable";
import VoteableControls from "../controls/voteable";

/** A rich text flair containing text. */
Expand Down Expand Up @@ -229,7 +230,9 @@ export interface VoteableData extends ContentData {
}

/** The base for all content that you can vote on. */
export default abstract class Voteable extends Content implements VoteableData {
export default abstract class Voteable
extends Replyable
implements VoteableData {
approved?: boolean;
approvedAtUtc: number | null;
approvedBy: string | null;
Expand Down Expand Up @@ -279,7 +282,7 @@ export default abstract class Voteable extends Content implements VoteableData {

/** @internal */
constructor(controls: VoteableControls, data: VoteableData) {
super(data);
super(controls, data);
this.controls = controls;

this.approved = data.approved;
Expand Down Expand Up @@ -373,6 +376,17 @@ export default abstract class Voteable extends Content implements VoteableData {
return this.controls.downvote(this.id);
}

/**
* Reply to this item.
*
* @param text The text content of the reply to post.
*
* @returns A promise that resolves to the comment reply.
*/
async reply(text: string): Promise<Comment> {
return this.controls.reply(this.id, text);
}

/**
* Save this item.
*
Expand Down

0 comments on commit f5cbf7e

Please sign in to comment.