Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1,013 changes: 580 additions & 433 deletions package-lock.json

Large diffs are not rendered by default.

22 changes: 21 additions & 1 deletion src/__mocks__/discord.js.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
import { Client, ClientOptions, RESTOptions, UserFlagsBitField } from "discord.js";
import { Client, ClientOptions, GuildManager, RESTOptions, UserFlagsBitField } from "discord.js";

const discordJS = jest.requireActual<typeof import("discord.js")>("discord.js");
const mockDiscordJS = jest.createMockFromModule<typeof import("discord.js")>("discord.js");

mockDiscordJS.MessageFlags = discordJS.MessageFlags;
mockDiscordJS.EmbedBuilder = discordJS.EmbedBuilder;
mockDiscordJS.ApplicationCommandOptionType = discordJS.ApplicationCommandOptionType;
mockDiscordJS.GatewayIntentBits = discordJS.GatewayIntentBits;
Expand Down Expand Up @@ -32,12 +33,29 @@ class MockREST extends discordJS.REST {
}
}


class MockGuildManager {
create: jest.Mock;
fetch: jest.Mock;
setIncidentActions: jest.Mock;
widgetImageURL: jest.Mock;

constructor() {
this.create = jest.fn().mockResolvedValue(null);
this.fetch = jest.fn().mockResolvedValue(new mockDiscordJS.Collection());
this.setIncidentActions = jest.fn().mockResolvedValue(null);
this.widgetImageURL = jest.fn().mockResolvedValue(null);
}
}

// @ts-ignore
class MockClient {
_ready: true = true;
on: jest.Mock;
options: ClientOptions;
token: string;
guilds: GuildManager;

constructor(options?: ClientOptions) {
this.on = MockClient.prototype.on;
this.login = MockClient.prototype.login;
Expand All @@ -47,6 +65,7 @@ class MockClient {
} as any
}
this.token = "test-token";
this.guilds = new MockGuildManager() as unknown as GuildManager;
}

public login(token: string): Promise<void> {
Expand Down Expand Up @@ -98,5 +117,6 @@ class MockClientUser {
mockDiscordJS.REST = MockREST;
mockDiscordJS.Client = MockClient as unknown as typeof discordJS.Client;
mockDiscordJS.ClientUser = MockClientUser as unknown as typeof discordJS.ClientUser;
mockDiscordJS.GuildManager = MockGuildManager as unknown as typeof discordJS.GuildManager;

module.exports = mockDiscordJS;
30 changes: 30 additions & 0 deletions src/__mocks__/firebase/database.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
import { DatabaseReference, DataSnapshot } from "firebase/database";

const firebaseDatabase = jest.requireActual<typeof import("firebase/database")>("firebase/database");
const mockFirebaseDatabase = jest.createMockFromModule<typeof import("firebase/database")>("firebase/database");

const mockSnapshot = {
exists: () => true,
val: () => ({ count: 2 }),
forEach: () => true
};

mockFirebaseDatabase.get = jest.fn().mockResolvedValue(mockSnapshot);

mockFirebaseDatabase.child = jest.fn((_, path): DatabaseReference => {
return `${path}` as unknown as DatabaseReference;
});
mockFirebaseDatabase.ref = jest.fn().mockReturnValue('mock-ref');
mockFirebaseDatabase.set = jest.fn().mockResolvedValue(undefined);
mockFirebaseDatabase.remove = jest.fn().mockResolvedValue(undefined);

class mockDataSnapshot {
forEach: jest.Mock;
constructor() {
this.forEach = jest.fn().mockReturnValue(true);
}
}

mockFirebaseDatabase.DataSnapshot = mockDataSnapshot as unknown as typeof DataSnapshot;

module.exports = mockFirebaseDatabase;
7 changes: 7 additions & 0 deletions src/__mocks__/helpers.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
const helpers = jest.requireActual<typeof import("../helpers")>("../helpers");
const mockHelpers = jest.createMockFromModule<typeof import("../helpers")>("../helpers");

module.exports = {
...helpers,
MINIMUM_MOOD_LIFESPAN: 0
};
11 changes: 10 additions & 1 deletion src/discordApp.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import "dotenv/config";
import { Client, GatewayIntentBits, Events } from "discord.js";
import { clarify, embed, ping, tone, requestAnonymousClarification, mood } from "./interactions"
import { cleanupMoods } from "./helpers";

export async function launchBot(): Promise<Client> {
// the client has to declare the features it uses up front so discord.js kno9ws if it can
Expand All @@ -9,7 +10,8 @@ export async function launchBot(): Promise<Client> {
// discord API: https://discord.com/developers/docs/topics/gateway#list-of-intents
const client = new Client({
intents: [
GatewayIntentBits.GuildEmojisAndStickers,
GatewayIntentBits.GuildExpressions,
GatewayIntentBits.GuildMembers,
GatewayIntentBits.GuildVoiceStates,
GatewayIntentBits.Guilds,
GatewayIntentBits.GuildMessages,
Expand All @@ -25,6 +27,13 @@ export async function launchBot(): Promise<Client> {
client.on(Events.ClientReady, () => {
if (client.user) {
console.log(`client "ready": Logged in as ${client.user.tag}!`);

client.guilds.fetch().then(guilds => {
guilds.map((_, id) => {
console.log(`cleaning up roles in guild with id ${id}`);
cleanupMoods(client, id);
})
});
} else {
console.error(`client "ready": client.user is null!`);
}
Expand Down
2 changes: 1 addition & 1 deletion src/gptRequests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ export async function analyzeMoodColor(mood: string): Promise<string> {
"text": `
This text is supposed to show a text messaging app user's mood. The text might be an emotion, or a symbol for an emotion (such as a smiley)
or it could be something arbitrary. Try to come up with a color hexcode that depicts the mood, and return that as hexcode without the pound (#) symbol
(example, 000000) Only return the 6 character hexcode that is appropriate for the mood, and nothing else.
(example, 000000) Only return the 6 character hexcode that is appropriate for the mood, and nothing else. Use saturated colors.
`
}
]
Expand Down
Loading