Skip to content

Commit

Permalink
chore: merge release/2023.4.7 into main
Browse files Browse the repository at this point in the history
  • Loading branch information
AndrewBastin committed Jun 27, 2023
2 parents e2b668b + 399a238 commit 2ec29c4
Show file tree
Hide file tree
Showing 51 changed files with 603 additions and 171 deletions.
1 change: 1 addition & 0 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ MICROSOFT_CLIENT_ID="************************************************"
MICROSOFT_CLIENT_SECRET="************************************************"
MICROSOFT_CALLBACK_URL="http://localhost:3170/v1/auth/microsoft/callback"
MICROSOFT_SCOPE="user.read"
MICROSOFT_TENANT="common"

# Mailer config
MAILER_SMTP_URL="smtps://[email protected]:[email protected]"
Expand Down
2 changes: 1 addition & 1 deletion packages/hoppscotch-backend/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "hoppscotch-backend",
"version": "2023.4.6",
"version": "2023.4.7",
"description": "",
"author": "",
"private": true,
Expand Down
16 changes: 14 additions & 2 deletions packages/hoppscotch-backend/src/admin/admin.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -236,18 +236,30 @@ export class AdminService {
const user = await this.userService.findUserByEmail(userEmail);
if (O.isNone(user)) return E.left(USER_NOT_FOUND);

const isUserAlreadyMember = await this.teamService.getTeamMemberTE(
const teamMember = await this.teamService.getTeamMemberTE(
teamID,
user.value.uid,
)();
if (E.left(isUserAlreadyMember)) {
if (E.isLeft(teamMember)) {
const addedUser = await this.teamService.addMemberToTeamWithEmail(
teamID,
userEmail,
role,
);
if (E.isLeft(addedUser)) return E.left(addedUser.left);

const userInvitation =
await this.teamInvitationService.getTeamInviteByEmailAndTeamID(
userEmail,
teamID,
);

if (E.isRight(userInvitation)) {
await this.teamInvitationService.revokeInvitation(
userInvitation.right.id,
)();
}

return E.right(addedUser.right);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ export class MicrosoftStrategy extends PassportStrategy(Strategy) {
clientSecret: process.env.MICROSOFT_CLIENT_SECRET,
callbackURL: process.env.MICROSOFT_CALLBACK_URL,
scope: [process.env.MICROSOFT_SCOPE],
passReqToCallback: true,
tenant: process.env.MICROSOFT_TENANT,
store: true,
});
}
Expand Down
10 changes: 5 additions & 5 deletions packages/hoppscotch-backend/src/errors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const AUTH_FAIL = 'auth/fail';
export const JSON_INVALID = 'json_invalid';

/**
* Tried to delete an user data document from fb firestore but failed.
* Tried to delete a user data document from fb firestore but failed.
* (FirebaseService)
*/
export const USER_FB_DOCUMENT_DELETION_FAILED =
Expand Down Expand Up @@ -231,7 +231,7 @@ export const TEAM_COLL_INVALID_JSON = 'team_coll/invalid_json';
export const TEAM_NOT_OWNER = 'team_coll/team_not_owner' as const;

/**
* Tried to perform action on a request that doesn't accept their member role level
* Tried to perform an action on a request that doesn't accept their member role level
* (GqlRequestTeamMemberGuard)
*/
export const TEAM_REQ_NOT_REQUIRED_ROLE = 'team_req/not_required_role';
Expand Down Expand Up @@ -262,7 +262,7 @@ export const TEAM_REQ_REORDERING_FAILED = 'team_req/reordering_failed' as const;
export const SENDER_EMAIL_INVALID = 'mailer/sender_email_invalid' as const;

/**
* Tried to perform action on a request when the user is not even member of the team
* Tried to perform an action on a request when the user is not even a member of the team
* (GqlRequestTeamMemberGuard, GqlCollectionTeamMemberGuard)
*/
export const TEAM_REQ_NOT_MEMBER = 'team_req/not_member';
Expand Down Expand Up @@ -307,7 +307,7 @@ export const SHORTCODE_INVALID_JSON = 'shortcode/invalid_json' as const;
export const SHORTCODE_ALREADY_EXISTS = 'shortcode/already_exists' as const;

/**
* Invalid or non-existent TEAM ENVIRONMMENT ID
* Invalid or non-existent TEAM ENVIRONMENT ID
* (TeamEnvironmentsService)
*/
export const TEAM_ENVIRONMENT_NOT_FOUND = 'team_environment/not_found' as const;
Expand Down Expand Up @@ -340,7 +340,7 @@ export const USER_SETTINGS_NULL_SETTINGS =
'user_settings/null_settings' as const;

/*
* Global environment doesnt exists for the user
* Global environment doesn't exist for the user
* (UserEnvironmentsService)
*/
export const USER_ENVIRONMENT_GLOBAL_ENV_DOES_NOT_EXISTS =
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,15 @@ import * as T from 'fp-ts/Task';
import * as O from 'fp-ts/Option';
import * as TO from 'fp-ts/TaskOption';
import * as TE from 'fp-ts/TaskEither';
import * as E from 'fp-ts/Either';
import { pipe, flow, constVoid } from 'fp-ts/function';
import { PrismaService } from 'src/prisma/prisma.service';
import { Team, TeamMemberRole } from 'src/team/team.model';
import { Email } from 'src/types/Email';
import { User } from 'src/user/user.model';
import { TeamService } from 'src/team/team.service';
import {
INVALID_EMAIL,
TEAM_INVITE_ALREADY_MEMBER,
TEAM_INVITE_EMAIL_DO_NOT_MATCH,
TEAM_INVITE_MEMBER_HAS_INVITE,
Expand All @@ -19,6 +21,7 @@ import { TeamInvitation } from './team-invitation.model';
import { MailerService } from 'src/mailer/mailer.service';
import { UserService } from 'src/user/user.service';
import { PubSubService } from 'src/pubsub/pubsub.service';
import { validateEmail } from '../utils';

@Injectable()
export class TeamInvitationService {
Expand Down Expand Up @@ -63,6 +66,32 @@ export class TeamInvitationService {
);
}

/**
* Get the team invite for an invitee with email and teamID.
* @param inviteeEmail invitee email
* @param teamID team id
* @returns an Either of team invitation for the invitee or error
*/
async getTeamInviteByEmailAndTeamID(inviteeEmail: string, teamID: string) {
const isEmailValid = validateEmail(inviteeEmail);
if (!isEmailValid) return E.left(INVALID_EMAIL);

try {
const teamInvite = await this.prisma.teamInvitation.findUniqueOrThrow({
where: {
teamID_inviteeEmail: {
inviteeEmail: inviteeEmail,
teamID: teamID,
},
},
});

return E.right(teamInvite);
} catch (e) {
return E.left(TEAM_INVITE_NO_INVITE_FOUND);
}
}

createInvitation(
creator: User,
team: Team,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ export class TeamInviteViewerGuard implements CanActivate {
// Get user
TE.bindW('user', ({ gqlCtx }) =>
pipe(
O.fromNullable(gqlCtx.getContext<{ user?: User }>().user),
O.fromNullable(gqlCtx.getContext().req.user),
TE.fromOption(() => BUG_AUTH_NO_USER_CTX),
),
),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ export class TeamInviteeGuard implements CanActivate {
// Get user
TE.bindW('user', ({ gqlCtx }) =>
pipe(
O.fromNullable(gqlCtx.getContext<{ user?: User }>().user),
O.fromNullable(gqlCtx.getContext().req.user),
TE.fromOption(() => BUG_AUTH_NO_USER_CTX),
),
),
Expand Down
2 changes: 1 addition & 1 deletion packages/hoppscotch-backend/src/types/AuthError.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { HttpStatus } from '@nestjs/common';

/**
** Custom interface to handle errors specific to Auth module
** Since its REST we need to return HTTP status code along with error message
** Since its REST we need to return the HTTP status code along with the error message
*/
export type AuthError = {
message: string;
Expand Down
Loading

0 comments on commit 2ec29c4

Please sign in to comment.