Skip to content

Commit

Permalink
add assigning role when user lists his first item
Browse files Browse the repository at this point in the history
  • Loading branch information
radekm2000 committed Jun 2, 2024
1 parent a24b0ec commit cabfc27
Show file tree
Hide file tree
Showing 12 changed files with 122 additions and 12 deletions.
18 changes: 18 additions & 0 deletions server/ecommerce/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions server/ecommerce/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
"@aws-sdk/s3-request-presigner": "^3.485.0",
"@nestjs/common": "^10.0.0",
"@nestjs/core": "^10.0.0",
"@nestjs/event-emitter": "^2.0.4",
"@nestjs/jwt": "^10.2.0",
"@nestjs/passport": "^10.0.3",
"@nestjs/platform-express": "^10.0.0",
Expand Down
2 changes: 2 additions & 0 deletions server/ecommerce/src/app.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import { DiscordBotModule } from './discord-bot/discord-bot.module';
import { DiscordNotificationsModule } from './discord-notifications/discord-notifications.module';
import { ItemNotifierModule } from './discord-bot/src/commands/notifiers/item-notifier.module';
import { DiscordGuildModule } from './discord-guild/discord-guild.module';
import { EventEmitterModule } from '@nestjs/event-emitter';

@Module({
imports: [
Expand All @@ -43,6 +44,7 @@ import { DiscordGuildModule } from './discord-guild/discord-guild.module';
DiscordNotificationsModule,
ItemNotifierModule,
DiscordGuildModule,
EventEmitterModule.forRoot(),
],
controllers: [AppController],
providers: [AppService],
Expand Down
10 changes: 10 additions & 0 deletions server/ecommerce/src/discord-bot/discord-bot.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,17 @@ import { DiscordGuildService } from 'src/discord-guild/discord-guild.service';
FollowersService,
ItemNotifierService,
DiscordNotificationsService,
{
provide: DiscordGuildService,
useFactory: (botService: DiscordBotService, usersService: UsersService) =>
new DiscordGuildService({
botClient: botService.bot,
usersService: usersService,
}),
inject: [DiscordBotService, UsersService],
},
],

imports: [
TypeOrmModule.forFeature([
Follow,
Expand Down
10 changes: 6 additions & 4 deletions server/ecommerce/src/discord-guild/discord-guild.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,6 @@ import { DiscordNotificationsService } from 'src/discord-notifications/discord-n
]),
],
providers: [
DiscordBotService,
UsersService,
ProductNotificationService,
ItemNotifierService,
Expand All @@ -39,15 +38,18 @@ import { DiscordNotificationsService } from 'src/discord-notifications/discord-n
provide: IProductsService,
useClass: ProductsService,
},
FollowersService,
{
provide: DiscordGuildService,
useFactory: (botService: DiscordBotService) =>
useFactory: (botService: DiscordBotService, usersService: UsersService) =>
new DiscordGuildService({
botClient: botService.bot,
usersService: usersService,
}),
inject: [DiscordBotService],
inject: [DiscordBotService, UsersService],
},
DiscordBotService,

FollowersService,
],
exports: [DiscordGuildService],
})
Expand Down
46 changes: 42 additions & 4 deletions server/ecommerce/src/discord-guild/discord-guild.service.ts
Original file line number Diff line number Diff line change
@@ -1,40 +1,78 @@
import { Injectable, Logger, OnApplicationBootstrap } from '@nestjs/common';
import { EventEmitter2, OnEvent } from '@nestjs/event-emitter';
import { Client, MessageCreateOptions } from 'discord.js';
import 'dotenv/config';
import { UsersService } from 'src/users/users.service';

type AssignDiscordRoleEvent = {
userId: number;
VENDOR_ROLE_ID: string;
};

type Config = {
botClient: Client;
usersService: UsersService;
};

@Injectable()
export class DiscordGuildService {
private readonly botClient: Client;
private readonly guildId: string;
private readonly logger: Logger;
private readonly usersService: UsersService;

constructor(config: Config) {
this.usersService = config.usersService;
this.botClient = config.botClient;
this.logger = new Logger(DiscordGuildService.name);
this.guildId = process.env.GUILD_ID ?? '';
}

public assignRoles = async (userId: string, roleIds: string[]) => {
if (roleIds.length === 0) {
@OnEvent('assignDiscordRole', { async: true })
public async handleAssignDiscordRoleEvent(payload: AssignDiscordRoleEvent) {
const user = await this.getUser(payload.userId);
if (!user.discordId) {
return;
}

roleIds = roleIds.filter((roleId) => !this.hasRole(userId, roleId));
if (user.products.length < 1) {
return;
}
return this.assignRoles(user.discordId, payload.VENDOR_ROLE_ID);
}

public assignRoles = async (userId: string, roleId: string) => {
if (!roleId) {
return;
}

const member = await this.getGuildMember(userId);
try {
await member.roles.add(roleIds);
if (member && !(await this.hasRole(userId, roleId)))
await member.roles.add(roleId);
this.logger.log(`User ${userId} has been granted a new role`);
} catch (error) {
console.log(error);
this.logger.error(
`Error while trying to assign roles for user ${userId}`,
);
}
};

private checkUserRoles = async (userId: string, roleId: string) => {
const member = await this.getGuildMember(userId);
if (member.roles.cache.some((role) => role.id === roleId)) {
console.log('user has that role');
} else {
console.log('user doesnt have that role');
}
};

private getUser = async (userId: number) => {
const user = await this.usersService.findUserById(userId);
return user;
};

private hasRole = async (userId: string, roleId: string) => {
try {
const member = await this.getGuildMember(userId);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,9 @@ import { DiscordNotificationsService } from 'src/discord-notifications/discord-n
import { IProductsService } from 'src/spi/products';
import { DiscordGuildService } from 'src/discord-guild/discord-guild.service';
import { DiscordGuildModule } from 'src/discord-guild/discord-guild.module';
import { IDiscordGuildService } from 'src/spi/discord-guild';
import { DiscordBotService } from 'src/discord-bot/discord-bot.service';
import { FollowersService } from 'src/followers/followers.service';

@Module({
imports: [
Expand All @@ -37,6 +40,17 @@ import { DiscordGuildModule } from 'src/discord-guild/discord-guild.module';
{ provide: IProductsService, useClass: ProductsService },
ItemNotifierService,
DiscordNotificationsService,
{
provide: DiscordGuildService,
useFactory: (botService: DiscordBotService, usersService: UsersService) =>
new DiscordGuildService({
botClient: botService.bot,
usersService: usersService,
}),
inject: [DiscordBotService, UsersService],
},
DiscordBotService,
FollowersService,
],
exports: [ProductNotificationService],
})
Expand Down
15 changes: 14 additions & 1 deletion server/ecommerce/src/products/products.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,19 @@ import { Response } from 'express';
import { StripeService } from 'src/stripe/stripe.service';
import { ParseAndValidateProductPipe } from 'src/utils/pipes/ParseAndValidateProductPipe';
import { IProductsService } from 'src/spi/products';
import { DiscordGuildService } from 'src/discord-guild/discord-guild.service';
import { IDiscordGuildService } from 'src/spi/discord-guild';
import 'dotenv/config';
import { EventEmitter2 } from '@nestjs/event-emitter';

const VENDOR_ROLE_ID = process.env.VENDOR_ROLE_ID ?? '';

@Controller('products')
export class ProductsController {
constructor(
@Inject(IProductsService) private productsService: IProductsService,
private eventEmitter: EventEmitter2,

private stripeService: StripeService,
) {}

Expand Down Expand Up @@ -117,6 +125,11 @@ export class ProductsController {
@UploadedFile() file: Express.Multer.File,
@AuthUser() authUser: AuthUser,
) {
return await this.productsService.uploadProduct(body, file, authUser.sub);
const userId = authUser.sub;
await this.productsService.uploadProduct(body, file, authUser.sub);
return this.eventEmitter.emit('assignDiscordRole', {
userId,
VENDOR_ROLE_ID,
});
}
}
4 changes: 1 addition & 3 deletions server/ecommerce/src/products/products.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,16 @@ import { ProductNotificationService } from 'src/product-notification/product-not
import { ProductNotification } from 'src/utils/entities/product-notification.entity';
import { StripeService } from 'src/stripe/stripe.service';
import { NodemailerService } from 'src/nodemailer/nodemailer.service';
import { ItemNotifier } from 'src/discord-bot/src/commands/notifiers/item-notifier';
import { DiscordNotificationsService } from 'src/discord-notifications/discord-notifications.service';
import { ItemNotifierService } from 'src/discord-bot/src/commands/notifiers/item-notifier.service';
import { IProductsService } from 'src/spi/products';
import { DiscordGuildService } from 'src/discord-guild/discord-guild.service';
import { DiscordGuildModule } from 'src/discord-guild/discord-guild.module';

@Module({
controllers: [ProductsController],
providers: [
{ provide: IProductsService, useClass: ProductsService },
UsersService,

ProductNotificationService,
StripeService,
NodemailerService,
Expand Down
2 changes: 2 additions & 0 deletions server/ecommerce/src/products/products.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ export class ProductsService implements IProductsService {
@InjectRepository(Image)
private readonly imageRepository: Repository<Image>,
private usersService: UsersService,

private itemNotifierService: ItemNotifierService,
) {
this.logger = new Logger(ProductsService.name);
Expand Down Expand Up @@ -238,6 +239,7 @@ export class ProductsService implements IProductsService {
this.logger.log(
`User ${existingUser.username} added product with id ${newProduct.id}`,
);

return;
}

Expand Down
11 changes: 11 additions & 0 deletions server/ecommerce/src/spi/discord-guild.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { MessageCreateOptions } from 'discord.js';

export const IDiscordGuildService = Symbol('DiscordGuildService');

export interface IDiscordGuildService {
assignRoles(userId: string, roleIds: string[]): Promise<void>;
sendMessageToMember(
userId: string,
message: MessageCreateOptions,
): Promise<void>;
}
1 change: 1 addition & 0 deletions server/ecommerce/src/users/users.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,7 @@ export class UsersService {
where: {
id: userId,
},
relations: ['products'],
});

return user;
Expand Down

0 comments on commit cabfc27

Please sign in to comment.