diff --git a/.github/workflows/newrelic-release-tracking.yml b/.github/workflows/newrelic-release-tracking.yml index f6bc59ae..a18d21ba 100644 --- a/.github/workflows/newrelic-release-tracking.yml +++ b/.github/workflows/newrelic-release-tracking.yml @@ -17,7 +17,7 @@ jobs: uses: newrelic/deployment-marker-action@v2.2.0 with: apiKey: ${{ secrets.NEW_RELIC_API_KEY }} - region: 'EU' + region: 'US' guid: ${{ secrets.NEW_RELIC_DEPLOYMENT_ENTITY_GUID }} version: '${{ env.COMMIT_REF }}' user: '${{ github.actor }}' diff --git a/src/auth/auth.service.ts b/src/auth/auth.service.ts index 6ad64833..9535e1e5 100644 --- a/src/auth/auth.service.ts +++ b/src/auth/auth.service.ts @@ -6,6 +6,7 @@ import { UnauthorizedException, } from '@nestjs/common'; import { DecodedIdToken } from 'firebase-admin/lib/auth/token-verifier'; +import { Logger } from 'src/logger/logger'; import { FIREBASE } from '../firebase/firebase-factory'; import { FirebaseServices } from '../firebase/firebase.types'; import { UserAuthDto } from './dto/user-auth.dto'; @@ -13,6 +14,7 @@ import { UserAuthDto } from './dto/user-auth.dto'; @Injectable() export class AuthService { constructor(@Inject(FIREBASE) private firebase: FirebaseServices) {} + private readonly logger = new Logger('AuthService'); public async loginFirebaseUser({ email, password }: UserAuthDto) { return await this.firebase.auth.signInWithEmailAndPassword(email, password); @@ -63,4 +65,45 @@ export class AuthService { throw new HttpException(error.message, HttpStatus.BAD_REQUEST); } } + + public async deleteCypressFirebaseUsers() { + const allUsers = []; + + try { + this.firebase.admin + .auth() + .listUsers(1000) + .then((listUsersResult) => { + listUsersResult.users.forEach((userRecord) => { + if (userRecord.email.includes('cypresstestemail')) { + allUsers.push(userRecord.uid); + } + }); + this.firebase.admin + .auth() + .deleteUsers(allUsers) + .then((deleteUsersResult) => { + if (deleteUsersResult.successCount > 0) { + this.logger.log( + `Successfully deleted ${deleteUsersResult.successCount} cypress firebase users`, + ); + } + + if (deleteUsersResult.failureCount > 0) { + this.logger.error( + `Failed to delete ${deleteUsersResult.failureCount} cypress firebase users`, + ); + } + if (deleteUsersResult.errors.length > 0) { + this.logger.error( + `Errors deleting cypress firebase users - ${deleteUsersResult.errors}`, + ); + } + }); + }); + return 'ok'; + } catch (error) { + throw new HttpException(error.message, HttpStatus.BAD_REQUEST); + } + } } diff --git a/src/user/user.service.ts b/src/user/user.service.ts index 17f23cb3..cbff29fb 100644 --- a/src/user/user.service.ts +++ b/src/user/user.service.ts @@ -358,23 +358,24 @@ export class UserService { const queryResult = await this.userRepository .createQueryBuilder('user') .select() - .where('user.name LIKE :searchTerm', { searchTerm: `%Cypress test user%` }) + .where('user.name LIKE :searchTerm', { searchTerm: `%Cypress test%` }) .getMany(); const deletedUsers = await Promise.all( queryResult.map(async (user) => { try { await this.authService.deleteFirebaseUser(user.firebaseUid); - await this.userRepository.delete(user.id); + await this.userRepository.delete(user); return user; } catch (error) { - this.logger.error(`Unable to delete cypress user: ${user.email} ${error}`); - this.logger.error( - `deleteCypressTestAccessCodes - Unable to delete cypress user: ${user.email} ${error}`, - ); + await this.userRepository.delete(user); } }), ); + + // Delete all remaining cypress firebase users (e.g. from failed user creations) + this.authService.deleteCypressFirebaseUsers(); + return deletedUsers; } catch (error) { // If this fails we don't want to break cypress tests diff --git a/src/webhooks/webhooks.service.ts b/src/webhooks/webhooks.service.ts index dc1292d0..643c6028 100644 --- a/src/webhooks/webhooks.service.ts +++ b/src/webhooks/webhooks.service.ts @@ -462,6 +462,8 @@ export class WebhooksService { const action = data.action; const story_id = data.story_id; + this.logger.log('Storyblok action', action); + if (action === STORYBLOK_STORY_STATUS_ENUM.PUBLISHED) { let story;