* Initial migration * Cleanup and create migration scripts * Introduce test suite * Fix test issues * Correct CORS issue and update paths * Update README
96 lines
No EOL
2.6 KiB
TypeScript
96 lines
No EOL
2.6 KiB
TypeScript
import React from 'react';
|
|
import { render, screen, fireEvent, waitFor, act } from '@testing-library/react';
|
|
import userEvent from '@testing-library/user-event';
|
|
import { BrowserRouter } from 'react-router-dom';
|
|
import Login from '../../components/Login';
|
|
|
|
// Mock fetch
|
|
global.fetch = jest.fn();
|
|
|
|
const renderLogin = () => {
|
|
return render(
|
|
<BrowserRouter>
|
|
<Login />
|
|
</BrowserRouter>
|
|
);
|
|
};
|
|
|
|
describe('Login Component', () => {
|
|
beforeEach(() => {
|
|
(fetch as jest.Mock).mockClear();
|
|
});
|
|
|
|
it('renders login form', () => {
|
|
renderLogin();
|
|
|
|
expect(screen.getByLabelText(/email/i)).toBeInTheDocument();
|
|
expect(screen.getByLabelText(/password/i)).toBeInTheDocument();
|
|
expect(screen.getByRole('button', { name: /login/i })).toBeInTheDocument();
|
|
});
|
|
|
|
it('handles form submission with valid credentials', async () => {
|
|
const user = userEvent.setup();
|
|
(fetch as jest.Mock).mockResolvedValueOnce({
|
|
ok: true,
|
|
json: async () => ({ success: true, user: { email: 'test@example.com' } })
|
|
});
|
|
|
|
renderLogin();
|
|
|
|
await act(async () => {
|
|
await user.type(screen.getByLabelText(/email/i), 'test@example.com');
|
|
await user.type(screen.getByLabelText(/password/i), 'password123');
|
|
});
|
|
|
|
await act(async () => {
|
|
await user.click(screen.getByRole('button', { name: /login/i }));
|
|
});
|
|
|
|
await waitFor(() => {
|
|
expect(fetch).toHaveBeenCalledWith('/api/login', {
|
|
method: 'POST',
|
|
headers: { 'Content-Type': 'application/json' },
|
|
credentials: 'include',
|
|
body: JSON.stringify({
|
|
email: 'test@example.com',
|
|
password: 'password123'
|
|
})
|
|
});
|
|
});
|
|
});
|
|
|
|
it('displays error message on failed login', async () => {
|
|
const user = userEvent.setup();
|
|
(fetch as jest.Mock).mockResolvedValueOnce({
|
|
ok: false,
|
|
json: async () => ({ error: 'Invalid credentials' })
|
|
});
|
|
|
|
renderLogin();
|
|
|
|
await act(async () => {
|
|
await user.type(screen.getByLabelText(/email/i), 'test@example.com');
|
|
await user.type(screen.getByLabelText(/password/i), 'wrongpassword');
|
|
});
|
|
|
|
await act(async () => {
|
|
await user.click(screen.getByRole('button', { name: /login/i }));
|
|
});
|
|
|
|
await waitFor(() => {
|
|
expect(screen.getByText(/an error occurred/i)).toBeInTheDocument();
|
|
});
|
|
});
|
|
|
|
it('validates required fields', async () => {
|
|
const user = userEvent.setup();
|
|
renderLogin();
|
|
|
|
await act(async () => {
|
|
await user.click(screen.getByRole('button', { name: /login/i }));
|
|
});
|
|
|
|
// Should not make API call with empty fields
|
|
expect(fetch).not.toHaveBeenCalled();
|
|
});
|
|
}); |