Initial
This commit is contained in:
263
listify-api/test/app.e2e-spec.ts
Normal file
263
listify-api/test/app.e2e-spec.ts
Normal file
@@ -0,0 +1,263 @@
|
||||
import { Test, TestingModule } from '@nestjs/testing';
|
||||
import { INestApplication } from '@nestjs/common';
|
||||
import request from 'supertest';
|
||||
import { App } from 'supertest/types';
|
||||
import { AppModule } from './../src/app.module';
|
||||
import { MailService } from './../src/mail/mail.service';
|
||||
|
||||
interface AuthResponseBody {
|
||||
accessToken?: string;
|
||||
refreshToken?: string;
|
||||
user: {
|
||||
id?: string;
|
||||
email: string;
|
||||
verified: boolean;
|
||||
};
|
||||
}
|
||||
|
||||
interface ListTemplateResponseBody {
|
||||
id: string;
|
||||
name: string;
|
||||
kind: string;
|
||||
items: {
|
||||
id: string;
|
||||
title: string;
|
||||
checked?: boolean;
|
||||
}[];
|
||||
}
|
||||
|
||||
describe('AppController (e2e)', () => {
|
||||
let app: INestApplication<App>;
|
||||
let mailService: MailService;
|
||||
|
||||
beforeEach(async () => {
|
||||
const moduleFixture: TestingModule = await Test.createTestingModule({
|
||||
imports: [AppModule],
|
||||
}).compile();
|
||||
|
||||
mailService = moduleFixture.get<MailService>(MailService);
|
||||
app = moduleFixture.createNestApplication();
|
||||
await app.init();
|
||||
});
|
||||
|
||||
it('/ (GET)', () => {
|
||||
return request(app.getHttpServer())
|
||||
.get('/')
|
||||
.expect(200)
|
||||
.expect('Hello World!');
|
||||
});
|
||||
|
||||
it('/auth register, verify and login', async () => {
|
||||
const registerResponse = await request(app.getHttpServer())
|
||||
.post('/auth/register')
|
||||
.send({
|
||||
email: 'user@example.com',
|
||||
password: 'password123',
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const registerBody = registerResponse.body as unknown as AuthResponseBody;
|
||||
expect(registerBody.user.email).toBe('user@example.com');
|
||||
expect(registerBody.user.verified).toBe(false);
|
||||
|
||||
await request(app.getHttpServer())
|
||||
.post('/auth/login')
|
||||
.send({
|
||||
email: 'user@example.com',
|
||||
password: 'password123',
|
||||
})
|
||||
.expect(401);
|
||||
|
||||
const verificationUrl = mailService.getSentEmails()[0].verificationUrl;
|
||||
const token = new URL(verificationUrl).searchParams.get('token');
|
||||
|
||||
const verifyResponse = await request(app.getHttpServer())
|
||||
.get('/auth/verify-email')
|
||||
.query({ token })
|
||||
.expect(200);
|
||||
|
||||
const verifyBody = verifyResponse.body as unknown as AuthResponseBody;
|
||||
expect(verifyBody.user.verified).toBe(true);
|
||||
|
||||
const loginResponse = await request(app.getHttpServer())
|
||||
.post('/auth/login')
|
||||
.send({
|
||||
email: 'user@example.com',
|
||||
password: 'password123',
|
||||
})
|
||||
.expect(200);
|
||||
|
||||
const loginBody = loginResponse.body as unknown as AuthResponseBody;
|
||||
expect(loginBody.accessToken).toBeDefined();
|
||||
expect(loginBody.refreshToken).toBeDefined();
|
||||
expect(loginBody.user.email).toBe('user@example.com');
|
||||
|
||||
const refreshResponse = await request(app.getHttpServer())
|
||||
.post('/auth/refresh')
|
||||
.send({
|
||||
refreshToken: loginBody.refreshToken,
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const refreshBody = refreshResponse.body as unknown as AuthResponseBody;
|
||||
expect(refreshBody.accessToken).toBeDefined();
|
||||
expect(refreshBody.refreshToken).toBeDefined();
|
||||
expect(refreshBody.refreshToken).not.toBe(loginBody.refreshToken);
|
||||
|
||||
await request(app.getHttpServer())
|
||||
.post('/auth/refresh')
|
||||
.send({
|
||||
refreshToken: loginBody.refreshToken,
|
||||
})
|
||||
.expect(401);
|
||||
});
|
||||
|
||||
it('/list-templates creates, updates and uses a template', async () => {
|
||||
const accessToken = await registerVerifiedUserAndGetAccessToken(
|
||||
'template-user@example.com',
|
||||
);
|
||||
|
||||
const initialTemplatesResponse = await request(app.getHttpServer())
|
||||
.get('/list-templates')
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.expect(200);
|
||||
const initialTemplates =
|
||||
initialTemplatesResponse.body as unknown as ListTemplateResponseBody[];
|
||||
|
||||
expect(initialTemplates).toHaveLength(3);
|
||||
expect(initialTemplates.map((template) => template.name)).toContain(
|
||||
'Urlaub',
|
||||
);
|
||||
|
||||
const createTemplateResponse = await request(app.getHttpServer())
|
||||
.post('/list-templates')
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.send({
|
||||
name: 'Urlaub',
|
||||
kind: 'packing',
|
||||
items: [{ title: 'Pass' }, { title: 'Tickets' }],
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const createdTemplate =
|
||||
createTemplateResponse.body as unknown as ListTemplateResponseBody;
|
||||
expect(createdTemplate.name).toBe('Urlaub');
|
||||
expect(createdTemplate.items).toHaveLength(2);
|
||||
|
||||
const updateTemplateResponse = await request(app.getHttpServer())
|
||||
.patch(`/list-templates/${createdTemplate.id}`)
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.send({
|
||||
name: 'Sommerurlaub',
|
||||
})
|
||||
.expect(200);
|
||||
|
||||
const updatedTemplate =
|
||||
updateTemplateResponse.body as unknown as ListTemplateResponseBody;
|
||||
expect(updatedTemplate.name).toBe('Sommerurlaub');
|
||||
|
||||
const createListResponse = await request(app.getHttpServer())
|
||||
.post(`/list-templates/${createdTemplate.id}/lists`)
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.send({
|
||||
name: 'Sommerurlaub 2026',
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const createdList =
|
||||
createListResponse.body as unknown as ListTemplateResponseBody;
|
||||
expect(createdList.name).toBe('Sommerurlaub 2026');
|
||||
expect(createdList.items[0].title).toBe('Pass');
|
||||
expect(createdList.items[0].checked).toBe(false);
|
||||
});
|
||||
|
||||
it('/lists creates, updates and reads a concrete list', async () => {
|
||||
const accessToken = await registerVerifiedUserAndGetAccessToken(
|
||||
'list-user@example.com',
|
||||
);
|
||||
|
||||
const createListResponse = await request(app.getHttpServer())
|
||||
.post('/lists')
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.send({
|
||||
name: 'Wocheneinkauf',
|
||||
kind: 'shopping',
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const createdList =
|
||||
createListResponse.body as unknown as ListTemplateResponseBody;
|
||||
expect(createdList.name).toBe('Wocheneinkauf');
|
||||
expect(createdList.items).toHaveLength(0);
|
||||
|
||||
const addItemResponse = await request(app.getHttpServer())
|
||||
.post(`/lists/${createdList.id}/items`)
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.send({
|
||||
title: 'Milch',
|
||||
quantity: 2,
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const listWithItem =
|
||||
addItemResponse.body as unknown as ListTemplateResponseBody;
|
||||
expect(listWithItem.items).toHaveLength(1);
|
||||
expect(listWithItem.items[0].title).toBe('Milch');
|
||||
|
||||
await request(app.getHttpServer())
|
||||
.patch(`/lists/${createdList.id}/items/${listWithItem.items[0].id}`)
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.send({
|
||||
checked: true,
|
||||
})
|
||||
.expect(200);
|
||||
|
||||
const getListResponse = await request(app.getHttpServer())
|
||||
.get(`/lists/${createdList.id}`)
|
||||
.set('Authorization', `Bearer ${accessToken}`)
|
||||
.expect(200);
|
||||
|
||||
const fetchedList =
|
||||
getListResponse.body as unknown as ListTemplateResponseBody;
|
||||
expect(fetchedList.items[0].checked).toBe(true);
|
||||
});
|
||||
|
||||
async function registerVerifiedUserAndGetAccessToken(
|
||||
email: string,
|
||||
): Promise<string> {
|
||||
await request(app.getHttpServer())
|
||||
.post('/auth/register')
|
||||
.send({
|
||||
email,
|
||||
password: 'password123',
|
||||
})
|
||||
.expect(201);
|
||||
|
||||
const verificationUrl =
|
||||
mailService.getSentEmails()[mailService.getSentEmails().length - 1]
|
||||
.verificationUrl;
|
||||
const token = new URL(verificationUrl).searchParams.get('token');
|
||||
|
||||
await request(app.getHttpServer())
|
||||
.get('/auth/verify-email')
|
||||
.query({ token })
|
||||
.expect(200);
|
||||
|
||||
const loginResponse = await request(app.getHttpServer())
|
||||
.post('/auth/login')
|
||||
.send({
|
||||
email,
|
||||
password: 'password123',
|
||||
})
|
||||
.expect(200);
|
||||
|
||||
const loginBody = loginResponse.body as unknown as AuthResponseBody;
|
||||
expect(loginBody.accessToken).toBeDefined();
|
||||
|
||||
return loginBody.accessToken ?? '';
|
||||
}
|
||||
|
||||
afterEach(async () => {
|
||||
await app.close();
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user