Skip to content

🚀 QA/SDET Transition Roadmap (3–6 Months)

A dual-language, step-by-step plan for transitioning into QA Engineer / Automation Tester / SDET roles. Designed for backgrounds in Coding, Technical Writing, and IT Support.


SDET TRANSITION ROADMAP - ULTRA DETAILED ENGLISH VERSION

🎯 FINAL GOALS (3-6 Months)

After 3-6 months, you will have:

  • GitHub Portfolio with at least 1 complete automation project

  • CV clearly presenting: Automation Skills + QA Mindset + Manual Testing

  • Confident interview skills with real case studies

=> Target Position: Junior/Mid Automation Tester, QA Engineer, SDET

🧠 PREPARATION PHASE: BUILDING QA MINDSET (Week 0)

"Automation First" Mindset

 NOT: Writing tests to check
 BUT: Designing a testing system that can run automatically

=> Examples of automation thinking:
- Every new feature  Corresponding automated test
- Every bug fixed  Automated regression test
- Every deployment  Automated smoke test runs first
"Risk-Based Testing" Mindset
NOT: Test everything
BUT: Test the most important things with highest risk
Risk assessment formula:
Risk = Probability (Chance of occurrence) × Impact (Consequences)
Testing priority order:
1. High Probability × High Impact (Example: Payment processing)
2. High Probability × Low Impact (Example: Input validation)
3. Low Probability × High Impact (Example: Security breach)
4. Low Probability × Low Impact (Example: UI cosmetic issues)

🥇 PHASE 1: FOUNDATIONS & TECHNOLOGY CHOICE (Weeks 1-4)

Week 1: Core Theory - Learn Deeply, Understand Essence

Day 1-2: SDLC & STLC

SOFTWARE DEVELOPMENT LIFE CYCLE (SDLC):

Step Describe
1. Planning → Planning, requirement analysis
2. Design → Architecture design, UI/UX
3. Development → Programming
4. Testing → Testing
5. Deployment → Deployment
6. Maintenance → Maintenance

SOFTWARE TESTING LIFE CYCLE (STLC):

Step Describe
1. Requirement Analysis → Analyze requirements
2. Test Planning → Create test plan
3. Test Case Development → Write test cases
4. Test Environment Setup → Prepare test environment
5. Test Execution → Execute tests
6. Test Closure → Close testing, report

Day 3-4: Agile/Scrum for Testers

Daily Standup reports for Testers:

1. What did you test yesterday? Results?
2. What will you test today?
3. Any blockers? (Blocking bugs, environment issues...)

Role in Sprint:

- Sprint Planning: Estimate testing effort
- Sprint Review: Demo test results
- Retrospective: Improve testing process

Day 5-7: Testing Levels - UNDERSTAND DEEPLY

1. UNIT TESTING - Written by Developers

 Goal: Test individual functions, methods
 Framework: JUnit (Java), pytest (Python), Jest (JS)
2. INTEGRATION TESTING - Written by Testers
 Goal: Test multiple modules working together
 Example: API A calls API B, Database + Service
3. SYSTEM TESTING - Written by Testers
 Goal: Test entire system
 Includes: Functional + Non-functional (Performance, Security)
4. ACCEPTANCE TESTING
 Goal: User acceptance of product
 UAT (User Acceptance Test)

Week 2: Testing Types & Bug Reporting

Day 1-2: Functional vs Non-Functional

FUNCTIONAL TESTING - "Does the system do the right thing?"

- Smoke Testing: Check if build is stable
- Sanity Testing: Check if new feature has basic issues
- Regression Testing: Check if new code breaks existing features
- Integration Testing: Do components work together properly

NON-FUNCTIONAL TESTING - "Does the system work WELL?"

- Performance Testing: Load, Stress, Endurance
- Security Testing: Authentication, Authorization, Injection
- Usability Testing: UX/UI, Accessibility
- Compatibility Testing: Cross-browser, Cross-device

Day 3-4: PROFESSIONAL Bug Reporting

HIGH-QUALITY BUG REPORT TEMPLATE

Title

Severity Module/Feature Brief description of issue
Major Checkout User cannot proceed to payment when using gift card

Description

When user applies gift card in checkout process, system doesn't allow proceeding to payment page.

Steps to Reproduce

1. Login with account having gift card balance
2. Add product to cart
3. Navigate to checkout page
4. In Payment section, select "Use Gift Card"
5. Enter gift card code and click "Apply"
6. Click button "Continue to Payment"

Expected Result

=> User is redirected to payment page to complete remaining payment.

Actual Result

Button "Continue to Payment" is disabled, cannot be clicked.

Environment

- Browser: Chrome 98.0.4758.102
- OS: Windows 11
- Device: Desktop
- URL: https://staging.example.com
- User: testuser@email.com / password123

Severity & Priority

- Severity: Major (Feature not working, but workaround exists)
- Priority: High (Affects business revenue)

Attachments

1. Screenshot: checkout_page_bug.png
2. Console Log: [Paste error log here]
3. Network Tab: [Paste failed API call]

Notes

Workaround: Remove gift card to continue checkout.

Day 5-7: Technology Stack Choice - CRITICAL DECISION

DETAILED ANALYSIS OF 3 OPTIONS:

OPTION 1: TypeScript + Playwright (RECOMMENDED)
Advantages:
 - Playwright: Modern, fast, multi-browser support
 - TypeScript: Type-safe, easy to maintain, popular in startups
 - Support: Web, API, Mobile, Visual Testing
 - Community: Rapidly growing
 Suitable for: Wanting to learn modern tech, targeting startups

 OPTION 2: Python + Pytest + Playwright
 Advantages:
 - Python: Easy to learn, simple syntax
 - Pytest: Powerful testing framework
 - Playwright: Has Python binding
 Suitable for: Beginners, want to focus more on logic than syntax

 OPTION 3: Java + Selenium + TestNG
 Advantages:
 - Enterprise: Used by banks, large companies
 - Stable: Has been around for years
 - Selenium: Industry standard
 Suitable for: Targeting enterprise companies, already know Java

 DECISION: Choose Option 1 (TypeScript + Playwright)
 Reason: Modern, many jobs, easy to learn for those with coding background

🥈 PHASE 2: BUILDING AUTOMATION FRAMEWORK (Weeks 5-10)

Week 5: Web Automation Basics with Playwright

Day 1: Installation & Hello World

 1. Install Node.js (>=16)

 2. Create project
mkdir automation-framework
cd automation-framework
npm init -y

 3. Install Playwright
npm init playwright@latest
Choose: TypeScript, create tests folder, install browsers

 4. Basic structure
automation-framework/
├── tests/
   └── example.spec.ts
├── playwright.config.ts
└── package.json

Day 2-3: Locators - MOST IMPORTANT

// DO NOT: Use complex XPath
// await page.locator('//*[@id="app"]/div/div[2]/div/div[1]/form/div[1]/input')

// DO: Use stable locators

// 1. Role-based (BEST)
await page.getByRole('button', { name: 'Submit' }).click();
await page.getByRole('textbox', { name: 'Username' }).fill('user');

// 2. Text-based
await page.getByText('Welcome back').click();
await page.getByLabel('Email Address').fill('test@email.com');

// 3. Test ID (Developer needs to add data-testid)
await page.getByTestId('login-button').click();

// 4. Placeholder
await page.getByPlaceholder('Enter your email').fill('test@email.com');

// 5. Simple CSS Selector
await page.locator('.submit-btn').click();
await page.locator('#username').fill('user');

Day 4-5: Write First Test Case - Login Test

// tests/login.spec.ts
import { test, expect } from '@playwright/test';

// Test Suite
test.describe('Login Functionality', () => {

  // Positive Test Case
  test('Successful login with valid credentials', async ({ page }) => {
    // 1. Navigate
    await page.goto('https://www.saucedemo.com/');

    // 2. Fill credentials
    await page.locator('[data-test="username"]').fill('standard_user');
    await page.locator('[data-test="password"]').fill('secret_sauce');

    // 3. Click login
    await page.locator('[data-test="login-button"]').click();

    // 4. Assertion
    await expect(page).toHaveURL('https://www.saucedemo.com/inventory.html');
    await expect(page.locator('.title')).toContainText('Products');
  });

  // Negative Test Case
  test('Failed login with invalid credentials', async ({ page }) => {
    await page.goto('https://www.saucedemo.com/');

    await page.locator('[data-test="username"]').fill('invalid_user');
    await page.locator('[data-test="password"]').fill('wrong_password');
    await page.locator('[data-test="login-button"]').click();

    // Verify error message
    const errorElement = page.locator('[data-test="error"]');
    await expect(errorElement).toBeVisible();
    await expect(errorElement).toContainText(
      'Username and password do not match'
    );
  });
});

Day 6-7: Hooks & Configuration

// tests/login-hooks.spec.ts
import { test, expect } from '@playwright/test';

// Before Each Test
test.beforeEach(async ({ page }) => {
  console.log('Running before each test');
  await page.goto('https://www.saucedemo.com/');
});

// After Each Test
test.afterEach(async ({ page }) => {
  console.log('Running after each test');
  // Take screenshot on failure
  if (test.info().status === 'failed') {
    const screenshotPath = `screenshots/failure-${test.info().title}.png`;
    await page.screenshot({ path: screenshotPath, fullPage: true });
  }
});

// Before All Tests (Suite Level)
test.beforeAll(async () => {
  console.log('Running once before all tests');
});

test.describe('Login with Hooks', () => {
  test('should login successfully', async ({ page }) => {
    // Test logic here
  });
});

Week 6: Applying Test Case Design Techniques

Day 1-2: Equivalence Partitioning

// Example: Age Field (18-60)
// EP: Divide input into "equivalent" partitions

const testCases = [
  // VALID PARTITION: 18-60 (only need to test 1 representative value)
  { age: 30, expected: 'valid' }, // Representative of valid partition

  // INVALID PARTITIONS:
  { age: 17, expected: 'invalid' }, // < 18
  { age: 61, expected: 'invalid' }, // > 60
  { age: -5, expected: 'invalid' }, // Negative
  { age: 'abc', expected: 'invalid' }, // Non-numeric
  { age: '', expected: 'invalid' }, // Empty
];

// Implement in test
test.describe('Age Validation - Equivalence Partitioning', () => {
  testCases.forEach(({ age, expected }) => {
    test(`Age ${age} should be ${expected}`, async ({ page }) => {
      // Test logic here
    });
  });
});

Day 3-4: Boundary Value Analysis

// Example: Age Field (18-60)
// BVA: Test boundary values

const boundaryTestCases = [
  // VALID BOUNDARIES
  { age: 18, expected: 'valid' },  // Lower boundary
  { age: 60, expected: 'valid' },  // Upper boundary

  // INVALID BOUNDARIES
  { age: 17, expected: 'invalid' }, // Just below lower boundary
  { age: 61, expected: 'invalid' }, // Just above upper boundary

  // TYPICAL VALID VALUES
  { age: 30, expected: 'valid' },   // Typical valid
  { age: 50, expected: 'valid' },   // Typical valid
];

// Negative Testing Scenarios
const negativeScenarios = [
  { scenario: 'Empty username', username: '', password: 'validpass', expectedError: 'Username is required' },
  { scenario: 'Short password', username: 'validuser', password: '123', expectedError: 'Password must be at least 8 characters' },
  { scenario: 'Invalid email format', username: 'not-an-email', password: 'validpass', expectedError: 'Invalid email format' },
  { scenario: 'SQL Injection attempt', username: "admin' --", password: 'any', expectedError: 'Invalid credentials' },
  { scenario: 'XSS attempt', username: '<script>alert(1)</script>', password: 'any', expectedError: 'Invalid input detected' },
];

Day 5-7: Data-Driven Testing

// tests/data-driven/login.data.ts
export const loginTestData = [
  {
    testName: 'Valid standard user',
    username: 'standard_user',
    password: 'secret_sauce',
    expected: 'success',
    expectedURL: '/inventory.html'
  },
  {
    testName: 'Locked out user',
    username: 'locked_out_user',
    password: 'secret_sauce',
    expected: 'error',
    expectedError: 'Sorry, this user has been locked out'
  },
  {
    testName: 'Invalid username',
    username: 'invalid_user',
    password: 'secret_sauce',
    expected: 'error',
    expectedError: 'Username and password do not match'
  },
  // Add more test cases...
];

// tests/login-ddt.spec.ts
import { test, expect } from '@playwright/test';
import { loginTestData } from './data/login.data';

loginTestData.forEach((data) => {
  test(`Login: ${data.testName}`, async ({ page }) => {
    await page.goto('https://www.saucedemo.com/');

    await page.locator('[data-test="username"]').fill(data.username);
    await page.locator('[data-test="password"]').fill(data.password);
    await page.locator('[data-test="login-button"]').click();

    if (data.expected === 'success') {
      await expect(page).toHaveURL(`https://www.saucedemo.com${data.expectedURL}`);
    } else {
      const errorElement = page.locator('[data-test="error"]');
      await expect(errorElement).toBeVisible();
      await expect(errorElement).toContainText(data.expectedError);
    }
  });
});

Week 7-8: Building Professional Framework with POM

Day 1-2: Page Object Model (POM) Structure

automation-framework/
├── src/
│   ├── pages/           # Page Objects
│   │   ├── LoginPage.ts
│   │   ├── ProductsPage.ts
│   │   └── CartPage.ts
│   ├── tests/           # Test Cases
│   │   ├── login.spec.ts
│   │   ├── products.spec.ts
│   │   └── cart.spec.ts
│   ├── data/            # Test Data
│   │   └── test-data.ts
│   ├── utils/           # Helper Functions
│   │   ├── api-client.ts
│   │   ├── test-utils.ts
│   │   └── reporting.ts
│   └── fixtures/        # Custom Fixtures
│       └── custom-fixtures.ts
├── playwright.config.ts
├── package.json
└── README.md

Day 3-4: Implement Page Objects

// src/pages/LoginPage.ts
import { Page, Locator } from '@playwright/test';

export class LoginPage {
  // Page Elements
  private readonly usernameInput: Locator;
  private readonly passwordInput: Locator;
  private readonly loginButton: Locator;
  private readonly errorMessage: Locator;

  constructor(private readonly page: Page) {
    this.usernameInput = page.locator('[data-test="username"]');
    this.passwordInput = page.locator('[data-test="password"]');
    this.loginButton = page.locator('[data-test="login-button"]');
    this.errorMessage = page.locator('[data-test="error"]');
  }

  // Page Actions
  async navigate(): Promise<void> {
    await this.page.goto('https://www.saucedemo.com/');
  }

  async login(username: string, password: string): Promise<void> {
    await this.usernameInput.fill(username);
    await this.passwordInput.fill(password);
    await this.loginButton.click();
  }

  async getErrorMessage(): Promise<string> {
    return await this.errorMessage.textContent() || '';
  }

  async isErrorMessageVisible(): Promise<boolean> {
    return await this.errorMessage.isVisible();
  }

  async clearForm(): Promise<void> {
    await this.usernameInput.clear();
    await this.passwordInput.clear();
  }
}

// src/pages/ProductsPage.ts
export class ProductsPage {
  private readonly pageTitle: Locator;
  private readonly inventoryList: Locator;

  constructor(private readonly page: Page) {
    this.pageTitle = page.locator('.title');
    this.inventoryList = page.locator('.inventory_list');
  }

  async getPageTitle(): Promise<string> {
    return await this.pageTitle.textContent() || '';
  }

  async addProductToCart(productName: string): Promise<void> {
    const productItem = this.page.locator(
      `.inventory_item:has-text("${productName}")`
    );
    const addToCartButton = productItem.locator('button');
    await addToCartButton.click();
  }

  async getCartItemCount(): Promise<number> {
    const cartBadge = this.page.locator('.shopping_cart_badge');
    if (await cartBadge.isVisible()) {
      const countText = await cartBadge.textContent();
      return parseInt(countText || '0');
    }
    return 0;
  }
}

Day 5-6: Test Cases Using POM

// src/tests/login-pom.spec.ts
import { test, expect } from '@playwright/test';
import { LoginPage } from '../pages/LoginPage';
import { ProductsPage } from '../pages/ProductsPage';

test.describe('Login with POM', () => {
  let loginPage: LoginPage;
  let productsPage: ProductsPage;

  test.beforeEach(async ({ page }) => {
    loginPage = new LoginPage(page);
    productsPage = new ProductsPage(page);
    await loginPage.navigate();
  });

  test('Successful login redirects to products page', async ({ page }) => {
    // Act
    await loginPage.login('standard_user', 'secret_sauce');

    // Assert
    await expect(page).toHaveURL(/.*inventory.html/);
    const title = await productsPage.getPageTitle();
    expect(title).toBe('Products');
  });

  test('Login with invalid credentials shows error', async () => {
    // Act
    await loginPage.login('invalid_user', 'wrong_password');

    // Assert
    const isErrorVisible = await loginPage.isErrorMessageVisible();
    expect(isErrorVisible).toBe(true);

    const errorMessage = await loginPage.getErrorMessage();
    expect(errorMessage).toContain('Username and password do not match');
  });

  test('Login with locked out user shows specific error', async () => {
    // Act
    await loginPage.login('locked_out_user', 'secret_sauce');

    // Assert
    const errorMessage = await loginPage.getErrorMessage();
    expect(errorMessage).toContain('Sorry, this user has been locked out');
  });
});

Day 7: API Testing with Playwright

// src/tests/api/auth-api.spec.ts
import { test, expect } from '@playwright/test';

test.describe('Auth API Tests', () => {
  const baseURL = 'https://restful-api.dev';

  test('POST /login with valid credentials', async ({ request }) => {
    // Arrange
    const loginData = {
      username: 'standard_user',
      password: 'secret_sauce'
    };

    // Act
    const response = await request.post(`${baseURL}/login`, {
      data: loginData
    });

    // Assert
    expect(response.status()).toBe(200);

    const responseBody = await response.json();
    expect(responseBody).toHaveProperty('token');
    expect(typeof responseBody.token).toBe('string');
    expect(responseBody.token.length).toBeGreaterThan(0);
  });

  test('POST /login with invalid credentials', async ({ request }) => {
    const response = await request.post(`${baseURL}/login`, {
      data: {
        username: 'invalid',
        password: 'wrong'
      }
    });

    expect(response.status()).toBe(401);

    const responseBody = await response.json();
    expect(responseBody).toHaveProperty('error');
    expect(responseBody.error).toBe('Invalid credentials');
  });

  test('GET /products returns list of products', async ({ request }) => {
    const response = await request.get(`${baseURL}/products`);

    expect(response.status()).toBe(200);

    const products = await response.json();
    expect(Array.isArray(products)).toBe(true);
    expect(products.length).toBeGreaterThan(0);

    // Verify product structure
    const firstProduct = products[0];
    expect(firstProduct).toHaveProperty('id');
    expect(firstProduct).toHaveProperty('name');
    expect(firstProduct).toHaveProperty('price');
  });
});

Week 9-10: Reporting, CI/CD & Finalization

Day 1-2: Advanced Playwright Configuration

// playwright.config.ts
import { defineConfig, devices } from '@playwright/test';

export default defineConfig({
  // Test directory
  testDir: './src/tests',

  // Timeout
  timeout: 30 * 1000, // 30 seconds
  expect: {
    timeout: 5000
  },

  // Parallel execution
  fullyParallel: true,
  workers: process.env.CI ? 2 : undefined,

  // Reporter configuration
  reporter: [
    ['html', { outputFolder: 'playwright-report', open: 'never' }],
    ['junit', { outputFile: 'test-results/junit.xml' }],
    ['list'] // Console reporter
  ],

  // Global setup/teardown
  // globalSetup: require.resolve('./src/global-setup'),
  // globalTeardown: require.resolve('./src/global-teardown'),

  // Use custom fixtures
  // projects: [
  //   {
  //     name: 'chromium',
  //     use: { ...devices['Desktop Chrome'] },
  //   },
  // ],

  // Web server for local testing
  // webServer: {
  //   command: 'npm run start',
  //   url: 'http://localhost:3000',
  //   reuseExistingServer: !process.env.CI,
  // },
});

Day 3-4: Allure Reporting

# Install Allure
npm install -D allure-playwright allure-commandline

# Configuration
// playwright.config.ts
reporter: [
  ['html'],
  ['allure-playwright']
],

# Generate report
npx playwright test --reporter=allure-playwright
npx allure generate allure-results --clean
npx allure open
typescript
// Example with Allure annotations
import { test, expect } from '@playwright/test';
import { allure } from 'allure-playwright';

test.describe('Checkout Process', () => {
  test('Complete purchase with credit card', async ({ page }) => {
    // Allure annotations
    await allure.epic('Checkout');
    await allure.feature('Payment Processing');
    await allure.story('Credit Card Payment');
    await allure.severity(allure.severityLevel.CRITICAL);

    await allure.step('Navigate to checkout', async () => {
      await page.goto('/checkout');
    });

    await allure.step('Fill payment details', async () => {
      await page.fill('#card-number', '4111111111111111');
      await page.fill('#expiry-date', '12/25');
      await page.fill('#cvv', '123');
    });

    await allure.step('Complete purchase', async () => {
      await page.click('#complete-purchase');
    });

    await allure.step('Verify success', async () => {
      await expect(page.locator('.success-message')).toBeVisible();
    });
  });
});

Day 5-6: GitHub Actions CI/CD

# .github/workflows/playwright.yml
name: Playwright Tests

on:
  push:
    branches: [ main, develop ]
  pull_request:
    branches: [ main ]
  workflow_dispatch: # Manual trigger

jobs:
  test:
    timeout-minutes: 60
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v3

    - uses: actions/setup-node@v3
      with:
        node-version: '18'

    - name: Install dependencies
      run: npm ci

    - name: Install Playwright Browsers
      run: npx playwright install --with-deps

    - name: Run Playwright tests
      run: npx playwright test
      env:
        BASE_URL: ${{ secrets.BASE_URL }}
        TEST_USER: ${{ secrets.TEST_USER }}
        TEST_PASSWORD: ${{ secrets.TEST_PASSWORD }}

    - name: Upload test results
      if: always()
      uses: actions/upload-artifact@v3
      with:
        name: playwright-report
        path: playwright-report/
        retention-days: 30

    - name: Upload Allure results
      if: always()
      uses: actions/upload-artifact@v3
      with:
        name: allure-results
        path: allure-results/
        retention-days: 30

Day 7: Custom Fixtures & Utilities

// src/fixtures/custom-fixtures.ts
import { test as base, expect } from '@playwright/test';
import { LoginPage } from '../pages/LoginPage';
import { ProductsPage } from '../pages/ProductsPage';

// Extend base test with custom fixtures
export const test = base.extend<{
  loginPage: LoginPage;
  productsPage: ProductsPage;
  authenticatedPage: any;
}>({
  // Custom fixture: LoginPage
  loginPage: async ({ page }, use) => {
    const loginPage = new LoginPage(page);
    await use(loginPage);
  },

  // Custom fixture: ProductsPage
  productsPage: async ({ page }, use) => {
    const productsPage = new ProductsPage(page);
    await use(productsPage);
  },

  // Custom fixture: Pre-authenticated page
  authenticatedPage: async ({ browser }, use) => {
    // Create new context with storage state
    const context = await browser.newContext({
      storageState: 'auth.json'
    });
    const page = await context.newPage();

    // Use the authenticated page
    await use(page);

    // Cleanup
    await page.close();
    await context.close();
  },
});

export { expect };

🥉PHASE 3: MANUAL TESTING & DOCUMENTATION (Weeks 11-12)

Week 11: Professional Manual Test Cases

Day 1-2: Standard Test Case Template

TEST CASE TEMPLATE - INDUSTRY STANDARD

Test Case Information Title Module Feature Created By Created Date Last Modified Version
ID TC_CHECKOUT_001 Complete checkout with credit card payment Checkout Payment Processin [Your Name] 2024-01-15 2024-01-15 1.0

Test Objective

Verify that a registered user can complete checkout process using credit card payment method.
Preconditions
1. User is registered and logged in
2. User has items in shopping cart
3. Credit card payment method is enabled
4. User has valid shipping address saved
5. Test credit card credentials are available
Test Data

User Credit Card Expiry CVV Shipping Address
testuser@example.com / Password123! 4111 1111 1111 1111 12/2025 123 [Valid US address]

Test Steps & Expected Results

Step Action Expected Result Status Notes
1 Navigate to cart page Cart page loads with items displayed
2 Click "Checkout" button Redirected to checkout page
3 Verify shipping address Pre-saved address is displayed
4 Select shipping method Standard shipping ($5.99) is selected by default
5 Click "Continue to Payment" Payment section expands
6 Select "Credit Card" payment Credit card form displays
7 Enter card number: 4111111111111111 Field accepts input, no errors
8 Enter expiry: 12/25 Field accepts input
9 Enter CVV: 123 Field accepts input
10 Click "Review Order" Order summary page displays
11 Verify order details All items, prices, tax, shipping are correct
12 Click "Place Order" Order confirmation page displays
13 Verify confirmation Order number is generated
14 Check email Order confirmation email is received

Post Conditions

1. Order is created in system
2. Inventory is updated
3. User cart is empty
4. Order appears in user's order history
Test Evidence
- Screenshot: checkout_process.png
- Screenshot: order_confirmation.png
- Email: order_confirmation_email.png

Risk Level Priority Automation
High P1 Yes (Automated in checkout.spec.ts)

Day 3-4: Complex Feature Test Cases

COMPLEX TEST CASE: MULTI-STEP CHECKOUT WITH PROMO CODE

Scenario: Apply expired promo code during checkout

Test Case ID Test Type Test Technique
TC_CHECKOUT_005 Negative Testing Boundary Value Analysis

Test Steps:

1. Add 3 items totaling $150 to cart
2. Apply promo code "SUMMER2023" (expired 2023-12-31)
3. Verify error message: "Promo code has expired"
4. Apply valid promo code "WINTER2024"
5. Verify discount applied (20% off)
6. Proceed with payment
7. Verify final amount = ($150 - $30) + tax + shipping

Edge Cases Covered:

- Expired promo code
- Valid promo code after expired one
- Discount calculation with tax
- Order confirmation with promo details

Day 5-7: Test Plan Template

TEST PLAN TEMPLATE

1. Introduction

  1.1 Purpose
    - This document outlines the test strategy for [Feature Name] release.

  1.2 Scope
    - In Scope: Checkout process, payment integration, order confirmation
    - Out of Scope: User registration, product search, recommendation engine
2. Test Objectives
  - Verify all payment methods work correctly
  - Ensure order calculations are accurate
  - Validate email notifications
  - Confirm database updates

3. Test Strategy

  3.1 Test Levels
    - Unit Testing: Developer responsibility
    - Integration Testing: API testing between services
    - System Testing: End-to-end workflows
    - UAT: Business user validation

  3.2 Test Types
    - Functional Testing: All payment scenarios
    - Regression Testing: Existing features
    - Security Testing: PCI compliance
    - Performance Testing: Load during peak

4. Test Deliverables

  - Test Cases
  - Test Data
  - Bug Reports
  - Test Summary Report
  - Automation Scripts

5. Resource & Schedule

  - Test Lead: [Name]
  - Testers: 2
  - Start Date: 2024-01-15
  - End Date: 2024-01-30
  - Total Effort: 40 person-hours

6. Risks & Mitigation

Risk Probability Impact Mitigation
Payment gateway downtime Medium High Mock service for testing
Test data corruption Low Medium Daily backups
Schedule slippage High Medium Agile iterations, MVP first

7. Exit Criteria

  - All critical test cases executed
  - No P1/P2 bugs open
  - Automation coverage > 70%
  - UAT sign-off received

Week 12: Bug Reporting & Documentation Portfolio

Day 1-2: Real Bug Examples from Production

REAL BUG REPORT EXAMPLE

Title
- [Critical] [Checkout] Race condition causes double charging when rapidly clicking "Place Order"

Bug ID
- BUG-2024-001

Environment
- Environment: Production
- Browser: Chrome 120.0.6099.110
- OS: macOS Sonoma 14.2
- Device: MacBook Pro M2
- User Role: Registered Customer
- Timestamp: 2024-01-15 14:30:22 UTC

Description
- When user rapidly clicks (3+ times) the "Place Order" button within 500ms, system processes multiple payments resulting in duplicate charges to credit card.

Impact
- Business Impact: Customer charged multiple times, requires refunds
- Customer Impact: Financial loss, trust erosion
- Support Impact: Increased support tickets, manual refund processing

Steps to Reproduce
1. Login to account with valid credit card
2. Add any product to cart
3. Navigate to checkout
4. Fill all required fields
5. On "Place Order" page, quickly click button 5 times (within 500ms)
6. Observe network requests

Expected Result
- Only one payment transaction processed
- One order created
- One charge on credit card
- Button becomes disabled after first click

Actual Result
- Multiple payment API calls (/api/v1/payments)
- Multiple orders created (Order #1001, #1002, #1003)
- Multiple charges on credit card ($49.99 × 3)
- Button remains enabled during processing

Evidence
1. Screenshot: duplicate_orders.png
2. Network Log:
- POST /api/v1/payments - 200 OK (14:30:22.100)
- POST /api/v1/payments - 200 OK (14:30:22.300)
- POST /api/v1/payments - 200 OK (14:30:22.450)
3. Console Error: 
- None
4. Database State:
- 3 orders with same cart items

Root Cause Analysis
- Payment button lacks debouncing mechanism. Frontend sends request without waiting for response or disabling button.

Severity: 
- Critical
=> Why: Causes direct financial loss, violates PCI compliance principles.

Priority: 
- P0 (Immediate Fix)
=> Why: Actively affecting customers, high support volume.

Workaround
- Educate support team to process refunds. Add banner warning users not to click multiple times.

Suggested Fix
// Frontend: Add debouncing and disable button
const placeOrder = debounce(async () => {
  placeOrderButton.disabled = true;
  try {
    await processPayment();
  } finally {
    placeOrderButton.disabled = false;
  }
}, 1000);

//Backend: Add idempotency key
POST /api/v1/payments
Headers: { "Idempotency-Key": "cart_123_session_456" }
Status: 
Assigned To: [Backend Lead]
Due Date: 2024-01-17
Current Status: In Progress

Day 3-4: Bug Triage & Prioritization Matrix

BUG PRIORITIZATION MATRIX

Severity vs Priority

Severity (Technical Impact)
- Critical: System crash, data loss, security breach
- Major: Feature broken, workaround exists
- Minor: Feature partially works, cosmetic issues
- Trivial: Typos, minor UI misalignment
Priority (Business Impact)
- P0: Fix immediately (blocking release/production)
- P1: Fix in current sprint
- P2: Fix in next sprint
- P3: Fix when resources available

Decision Matrix

Severity ↓ Priority → P0 P1 P2 P3
Critical Always P0
Major Depends on:
• # of users affected
• Workaround exists
• Business critical feature
Minor Usually P2
Trivial Usually P3
Real Examples:
1. Login not working for all users → Critical, P0
2. Checkout fails for PayPal only → Major, P1
3. Mobile menu alignment issue → Minor, P2
4. Typo in help text → Trivial, P3

Day 5-7: Portfolio Documentation

QA PORTFOLIO - [YOUR NAME]

1. Automation Framework Project

  • GitHub: https://github.com/yourusername/automation-framework

  • Tech Stack: TypeScript, Playwright, POM, Allure, GitHub Actions

Features:

  • ✅ 50+ automated test cases
  • ✅ Page Object Model architecture
  • ✅ Data-driven testing
  • ✅ API testing integration
  • ✅ Cross-browser testing
  • ✅ CI/CD with GitHub Actions
  • ✅ Allure reporting
  • ✅ Visual testing

Sample Test Coverage:

├── Authentication (Login/Logout)
│ ├── Successful login
│ ├── Invalid credentials
│ ├── Locked out user
│ └── Session management
├── Products
│ ├── Product listing
│ ├── Filtering & sorting
│ ├── Product details
│ └── Add to cart
├── Checkout
│ ├── Cart management
│ ├── Shipping address
│ ├── Payment processing
│ └── Order confirmation
└── API Tests
├── Auth endpoints
├── Product endpoints
├── Order endpoints
└── Health checks

2. Manual Testing Artifacts

Test Case Examples:
1. [TC-LOGIN-001] Comprehensive login test cases
2. [TC-CHECKOUT-001] Complete checkout flow
3. [TC-PAYMENT-001] Multiple payment methods

Bug Report Examples:
1. [BUG-001] Critical: Race condition in checkout
2. [BUG-002] Major: Memory leak in product gallery
3. [BUG-003] Minor: Accessibility issue in forms

Test Plan Examples:
1. E-commerce Checkout Test Plan
2. User Registration Test Plan
3. Mobile App Test Plan

3. Technical Skills Matrix

Automation:
- Expert: Playwright, TypeScript, POM
- Advanced: API Testing, CI/CD, Reporting
- Intermediate: Performance Testing, Security Testing

Manual Testing:
- Expert: Test Case Design, Bug Reporting
- Advanced: Test Planning, Risk Analysis
- Intermediate: UAT Coordination, Documentation

Tools:
- Test Management:* Jira, TestRail, Zephyr
- CI/CD: GitHub Actions, Jenkins
- Monitoring: Datadog, New Relic
- API Tools: Postman, Swagger

4. Certifications & Courses

1. ISTQB Foundation Level (In Progress)
2. Test Automation University Courses
3. Playwright Official Certification

🧭 PHASE 4: CAREER POSITIONING & INTERVIEWS (Weeks 13-16)

Week 13: Portfolio & CV Optimization

Day 1-2: CV for Automation Tester/SDET

[YOUR NAME]
- QA Automation Engineer / SDET

Contact
- 📧 email@example.com
- 📱 +84 123 456 789
- 🔗 linkedin.com/in/yourprofile
- 💻 github.com/yourusername

Summary
- QA Engineer with 3+ years experience in IT Support and Technical Writing, 
transitioning to Automation Testing. Specialized in building automation frameworks 
using TypeScript/Playwright, reducing regression testing time by 70%. 
- Combines developer mindset with QA perspective to build sustainable testing systems.

Technical Skills
  1. Automation
   - Languages: TypeScript, Python, JavaScript
   - Frameworks: Playwright, Cypress, Selenium, Pytest
   - Tools: GitHub Actions, Jenkins, Docker, Allure Report
   - Architecture: Page Object Model, Data-Driven Testing

  2. Manual Testing
   - Test Case Design (EP, BVA, Decision Table)
   - Bug Tracking & Triage (Jira, Bugzilla)
   - Test Planning & Strategy
   - API Testing (REST, GraphQL)

Projects
- E-commerce Automation Framework
- Tech: TypeScript, Playwright, POM, GitHub Actions, Allure
- GitHub: github.com/yourusername/ecommerce-automation
- Built framework from scratch with 60+ test cases
- Implemented Page Object Model for maintainability
- Integrated CI/CD running automatically on each commit
- Created custom reports with Allure
- Result* Reduced manual testing time by 70%

API Testing Suite
- Tech: Python, Pytest, Requests, Postman
- Tested 20+ API endpoints of RESTful service
- Implemented data-driven testing with JSON/YAML
- Created performance tests with Locust
- Coverage: 95% of API endpoints automated

Professional Experience
- Technical Support Specialist | ABC Company | 2020-2023
- Troubleshot and fixed 500+ technical issues
- Wrote documentation for internal tools
- Trained 20+ staff members on software usage
- Transferable Skills: Debugging, Documentation, User Perspective

Education
- Bachelor of Computer Science** | University XYZ | 2016-2020

Certifications
- ISTQB Foundation Level (Expected: March 2024)
- Playwright Test Automation Certification
- Test Automation University Courses

Day 3-4: Optimized GitHub Portfolio

🚀 E-commerce Automation Framework

Playwright Tests

https://github.com/yourusername/automation-framework/actions/workflows/playwright.yml/badge.svg

https://github.com/yourusername/automation-framework/actions/workflows/playwright.yml)

License: MIT Professional automation framework for e-commerce testing using Playwright and TypeScript.

📋 Features - ✅ Modern Stack: TypeScript + Playwright + POM - ✅ Cross-browser: Chrome, Firefox, Safari, Edge - ✅ Multi-environment: Dev, Staging, Production - ✅ CI/CD Ready: GitHub Actions integration - ✅ Beautiful Reports: Allure + HTML reports - ✅ API Testing: Integrated REST API tests - ✅ Visual Testing: Screenshot comparisons

🏗️ Architecture

src/
├── pages/ # Page Objects (POM)
├── tests/ # Test Specifications
├── utils/ # Helper Functions
├── data/ # Test Data (JSON/TS)
└── fixtures/ # Custom Playwright Fixtures

🚀 Quick Start

Prerequisites

- Node.js 16+
- npm or yarn

Installation

# Clone repository
git clone https://github.com/yourusername/automation-framework.git
cd automation-framework

Install dependencies

npm install

Install Playwright browsers

npx playwright install
Running Tests
# Run all tests
npm test

Run specific test file

npm test -- tests/login.spec.ts
Run tests in UI mode

npm run test:ui
Run tests with Allure report
npm run test:allure

📊 Test Coverage

Authentication: Login, Logout, Registration
Products: Listing, Filtering, Details
Cart: Add/Remove items, Quantity update
Checkout: Shipping, Payment, Order confirmation
API: REST endpoints testing

📈 CI/CD Pipeline

Automated testing pipeline using GitHub Actions:
On push: Run all tests
On PR: Run smoke tests
Schedule: Daily full regression
Report: Upload Allure report
🎯 Sample Test Case
test('Complete checkout with credit card', async ({ page }) => {
  const loginPage = new LoginPage(page);
  const productsPage = new ProductsPage(page);
  const cartPage = new CartPage(page);

  await loginPage.login('standard_user', 'secret_sauce');
  await productsPage.addProductToCart('Sauce Labs Backpack');
  await cartPage.checkout();
  // ... more steps
});
📝 Test Reports
https://docs/images/allure-report.png
Interactive test reports with steps, screenshots, and videos

🤝 Contributing

Fork the project
Create your feature branch
Add tests for new functionality
Ensure all tests pass
Submit a pull request
📄 License
MIT License - see LICENSE file for details

Week 14: Technical Interviews

Day 1-2: QA Theory Questions

What is SDLC vs STLC? How are they different?
→ SDLC (Software Development Life Cycle): Software development lifecycle
→ STLC (Software Testing Life Cycle): Software testing lifecycle
→ Relationship: STLC is a subset of SDLC, focused on testing activities

How are Severity and Priority different?
→ Severity: Technical impact of bug
→ Priority: Business priority to fix bug
→ Example: Typo on homepage (High Priority, Low Severity)
Memory leak (High Severity, Medium Priority)

What is Regression Testing? When is it needed?
→ Regression: Testing new code doesn't break existing functionality
→ When: After bug fixes, new features, code refactoring
→ Automation is crucial for regression to save time

What Test Case Design Techniques do you know?
→ Equivalence Partitioning: Divide input into partitions
→ Boundary Value Analysis: Test boundary values
→ Decision Table Testing: Test combinations of conditions
→ State Transition Testing: Test system states

How do you estimate testing effort?
→ Based on: Number of test cases, complexity, test environment
→ Formula: (Number of test cases × Average time per test) + Buffer
→ Buffer for: Bug fixing, retesting, environment issues

Day 3-4: Automation Questions

Why choose Playwright over Selenium?
→ Playwright: Modern, faster, built-in wait mechanisms
→ Selenium: Legacy, slower, needs explicit waits
→ Playwright supports: Multi-browser, mobile, API, network mocking

What is Page Object Model? Benefits?
→ POM: Design pattern separating UI locators from test logic
→ Benefits: Easy maintenance, code reuse, reduced duplication
→ When UI changes, only update Page Object

How do you handle dynamic elements?
→ Use: Custom wait, retry mechanisms
→ Locator strategies: Text-based, role-based, test-id
→ Playwright auto-wait: No need for explicit sleep

How do you implement Data-Driven Testing?
→ Separate test data into files (JSON, CSV, TS)
→ Read data in tests
→ Run tests with multiple data sets
→ Benefits: Easy to add test cases, maintainable

How do you debug failed tests?
→ Screenshots on failure
→ Video recording
→ Trace viewer (Playwright)
→ Console logs, network logs

Day 5-7: Practical Questions & Case Study

CASE STUDY: You're assigned to test "Forgot Password" feature

How would you analyze it?
→ Understand requirements: Input email → send reset link → reset password
→ Identify test scope: UI, API, Email, Security, Performance
→ Identify risks: Security (token expiry), Email deliverability

How would you design test cases?
→ Positive: Valid email, check email received
→ Negative: Invalid email, non-existent email
→ Security: Token expiry, token reuse, brute force protection
→ Performance: Load test for mass password reset requests

What would you automate?
→ API tests: /forgot-password endpoint
→ UI tests: Form validation, success/error messages
→ Integration: Check email delivery (using test email service)

What metrics would you track?
→ Test coverage: % scenarios automated
→ Defect density: Bugs found per test case
→ Automation ROI: Time saved vs time invested

Week 15-16: Mock Interviews & Salary Negotiation

Day 1-2: Behavioral Questions

"Why are you transitioning from Developer/IT Support to Tester?"
→ "I discovered passion in ensuring product quality
Coding experience helps me understand systems deeply, write effective tests
I enjoy the feeling of 'breaking things' to find bugs before users"

"Describe the most complex bug you've found?"
→ "I discovered a race condition in checkout process
When users clicked rapidly, system created multiple orders
I reproduced with scripts, captured network requests
Suggested fix: Add debouncing and idempotency keys"

"How do you work with developers when finding bugs?"
→ "First, ensure bug is reproducible with clear steps
Write quality bug report with evidence
Communicate respectfully, focus on problem not person
Collaborate on root cause analysis and solution"

"When do you say 'NO' to a release?"
→ "When there are Critical bugs affecting core functionality
When there's no test coverage for high-risk areas
When performance/security requirements aren't met
But always provide risk assessment and alternatives"

Day 3-4: Technical Assignment Practice

// ASSIGNMENT: Test login page of any website

// Requirements:
// 1. Write manual test cases (10+ scenarios)
// 2. Automate 5 most important test cases
// 3. Implement Page Object Model
// 4. Add reporting
// 5. Write README with setup instructions

// Solution structure:
src/
├── pages/
   └── LoginPage.ts
├── tests/
   └── login.spec.ts
├── data/
   └── users.ts
└── README.md

// Test cases to cover:
// - Successful login
// - Invalid credentials
// - Empty fields
// - SQL injection attempt
// - Password show/hide
// - Remember me functionality
// - Error message validation
// - Session timeout
// - Concurrent login
// - Accessibility testing

Day 5-7: Salary Negotiation & Offer Evaluation

EVALUATE JOB OFFER - CHECKLIST:

1. Compensation Package
✅ Base salary: $X (market range: $Y-$Z)
✅ Bonus structure: Performance, annual
✅ Stock options/RSUs: Vesting schedule
✅ Benefits: Health insurance, 401k match

2. Role & Growth
✅ Title: QA Engineer vs SDET vs Automation Engineer
✅ Career path: Promotion track, skill development
✅ Learning budget: Conferences, courses
✅ Mentorship: Senior engineers available

3. Technical Stack
✅ Modern tools: Playwright/Cypress vs Legacy Selenium
✅ CI/CD: GitHub Actions/Jenkins
✅ Cloud: AWS/Azure/GCP exposure
✅ Development practices: Agile, code reviews

4. Work Culture
✅ Work-life balance: Flexible hours, remote options
✅ Testing culture: QA involved early in SDLC
✅ Engineering quality: Code coverage requirements
✅ Innovation: Time for learning, hackathons

NEGOTIATION SCRIPTS:

When salary is too low:
"Thank you for the offer. Based on my research for [Role] in [Location] with [X] years experience, the market range is [Y-Z]. Given my [specific skills], I was hoping for [desired range]. Is there flexibility?"

When evaluating multiple offers:
"I'm excited about this opportunity. I have another offer at [Company] for [salary]. While I prefer your company because [reasons], the compensation difference is significant. Can we bridge this gap?"

Asking for growth opportunities:
"Beyond compensation, I'm excited about growing into [next role]. Can we discuss the typical timeline for promotion to Senior Engineer and what metrics are used for evaluation?"
==========================================================================

📅 16-WEEK TIMELINE OVERVIEW

Month 1: Foundation (Weeks 1-4)

Weeks 1-2: QA Theory Mastery

- SDLC/STLC, Agile/Scrum
- Test levels & types
- Bug reporting fundamentals

Weeks 3-4: Tech Stack Decision

- Choose: TypeScript + Playwright
- Setup environment
- Basic scripting

Month 2: Automation Framework (Weeks 5-10)

Weeks 5-6: Web Automation Basics

- Locators, basic tests
- Test design techniques
- Data-driven testing

Weeks 7-8: Professional Framework

- Page Object Model
- API testing integration
- Test organization

Weeks 9-10: CI/CD & Reporting

- GitHub Actions
- Allure reports
- Advanced configurations

Month 3: Manual & Documentation (Weeks 11-12)

Week 11: Manual Test Cases

- Professional test case writing
- Test planning
- Complex scenarios

Week 12: Bug Reporting Portfolio

- Real bug examples
- Bug triage process
- Documentation artifacts

Month 4: Career Preparation (Weeks 13-16)

Week 13: Portfolio & CV

- GitHub optimization
- CV tailoring
- LinkedIn profile

Week 14: Technical Interviews

- Theory questions
- Automation questions
- Case studies

Weeks 15-16: Mock Interviews & Offers

- Behavioral questions
- Technical assignments
- Salary negotiation

🎯 SUCCESS METRICS - PROGRESS MEASUREMENT

After 4 weeks:
✅ Clear understanding of SDLC/STLC
✅ Able to write basic automation scripts
✅ Know how to report bugs professionally
✅ Chose suitable tech stack
After 8 weeks:
✅ Have automation project on GitHub
✅ Implemented Page Object Model
✅ Can write data-driven tests
✅ Have 20+ automated test cases
After 12 weeks:
✅ CI/CD pipeline working
✅ Have professional test reports
✅ Portfolio with manual test cases
✅ Quality bug reporting examples

After 16 weeks:

✅ CV optimized for QA/SDET roles
✅ Ready for technical interviews
✅ Have salary negotiation strategy
✅ Can apply for Junior/Mid positions

🚨 COMMON PITFALLS & SOLUTIONS

1. "I'm learning multiple technologies at once"

PROBLEM: Learning Selenium, Cypress, Playwright simultaneously
SOLUTION: Choose 1 framework, master it first

2. "I only focus on automation, ignoring manual"

PROBLEM: Don't know how to design test cases, only know coding
SOLUTION: Spend at least 20% time on manual testing skills

3. "My GitHub only has code, no documentation"

PROBLEM: Repository hard to understand, don't know how to run
SOLUTION: Invest in quality README, screenshots, videos

4. "I apply to every job, don't tailor CV"

PROBLEM: Same CV for every company
SOLUTION: Customize CV for each job description

💼 JOB SEARCH STRATEGY

Target Companies:

Startups (Seed-Series B): Like modern tech stack, wearing multiple hats
Tech Companies: Have engineering culture, value automation highly
E-commerce: Many testing challenges, clear revenue impact
FinTech/HealthTech: High quality standards, security focus
Application Strategy:
Week 13: Research phase
- Identify 50 target companies
- Update LinkedIn with keywords
- Follow engineering blogs

Week 14: Application phase
- Apply 5-10 jobs/day
- Customize cover letters
- Track applications in spreadsheet

Week 15: Interview phase
- Schedule 2-3 interviews/week
- Practice mock interviews
- Collect feedback

Week 16: Decision phase
- Evaluate offers
- Negotiate terms
- Plan onboarding
Networking Strategy:
1. LinkedIn Connections:
   - Connect with QA managers
   - Join QA groups
   - Share learning journey

2. GitHub Presence:
   - Contribute to open source
   - Star similar projects
   - Follow industry leaders

3. Local Meetups:
   - Testing meetups
   - Tech conferences
   - Hackathons

REMEMBER:

This roadmap is just a map. What matters most is ACTION and PERSISTENCE. Study at least 2 hours daily, code at least 1 hour daily. After 4 months, you'll have enough skills to successfully transition to a QA/SDET role.