A test clicks "View invoice" and then looks for the invoice number. It fails. The invoice opened in a new tab, and Selenium is still pointed at the old one.
This is a rule worth stating plainly: the driver has exactly one window in focus at any time. Opening a tab does not move that focus. You move it yourself.
Selenium identifies windows with handles, which are just opaque id strings.
const original = await driver.getWindowHandle();
await driver.findElement(By.css('[data-testid="view-invoice"]')).click();
// wait for the second window to exist
await driver.wait(async () => (await driver.getAllWindowHandles()).length === 2, 5000);
const handles = await driver.getAllWindowHandles();
const newWindow = handles.find((h) => h !== original);
await driver.switchTo().window(newWindow);
await driver.wait(until.elementLocated(By.css('[data-testid="invoice-number"]')), 5000);
await driver.close(); // close the invoice tab
await driver.switchTo().window(original); // go back
Read it step by step, because every line prevents a specific failure.
Save the original handle first. Without it you cannot reliably get back.
Wait for the count to change. The tab takes a moment to open. Grabbing the handles immediately often returns one, and then find gives you nothing.
Find the handle that is not the original. Do not assume the new one is last in the array. The order is not guaranteed.
close() and quit() are different, and confusing them is a common mistake. close() closes the current window. quit() ends the whole session and closes every window. Calling quit() when you meant close() ends your test early with a confusing error.
Switch back explicitly. After closing a window, the driver is not automatically looking anywhere sensible. Commands issued before you switch back will fail.
Now the practical advice, which matters more than the API.
Ask whether you need to open the tab at all. If you only care that the link points somewhere correct, check the attribute and stop:
const link = await driver.findElement(By.css('[data-testid="terms"]'));
expect(await link.getAttribute('href')).to.equal('/terms');
Faster, steadier, and it tests the thing you cared about.
Be careful about testing pages you do not own. New tabs often lead to a payment provider or a document viewer. Testing someone else's application is not your job, and those pages change without warning and break your suite at random.
Remember this: save the original handle, wait for the new one, switch on purpose, and switch back.
Reference: Working with windows.