---
title: "What are the risks of not completing a transaction and how do you handle failed writes?"  
description: "What are the risks of not completing a transaction and how do you handle failed writes?"  
author: "Ponu Maurya"  
published: 2025-07-06  
updated: 2025-07-06  
canonical: https://www.mindstick.com/interview/34323/what-are-the-risks-of-not-completing-a-transaction-and-how-do-you-handle-failed-writes  
category: "database"  
tags: ["database", "indexeddb"]  
reading_time: 5 minutes  

---

# What are the risks of not completing a transaction and how do you handle failed writes?

If a transaction in [**IndexedDB**](https://www.mindstick.com/interview/34289/what-is-indexeddb) **is not completed successfully**, it has **significant consequences**, including **data loss**, **inconsistent state**, or **silent failures** that may be hard to debug.

## Risks of Not Completing a Transaction

| Risk | What Happens |
| --- | --- |
| **No** `oncomplete` | Changes might not be written; browser may roll back |
| **Uncaught error** | Entire transaction rolls back (nothing is saved) |
| **Async delay or** `await` **inside transaction** | Transaction auto-closes before write — results in `TransactionInactiveError` |
| **Not handling** `onerror` **or** `onabort` | You lose track of failures — app silently breaks |

## Example of a Failed Write

```plaintext
const tx = db.transaction("notes", "readwrite");
const store = tx.objectStore("notes");

store.put({ id: 1, content: "Note" });

// No error handling:
setTimeout(() => {
  // This fails because the transaction auto-closed
  store.put({ id: 2, content: "Late Note" }); // ❌ TransactionInactiveError
}, 100);
```

## How to [Handle Failed](https://www.mindstick.com/interview/34314/how-do-you-handle-errors-in-indexeddb-operations#:~:text=Use%20onerror%20Events%20on%20Each,.)%20has%20an%20onerror%20event.) Writes Properly

### 1. Use `try/catch` with Promises

```javascript
try {
  const tx = db.transaction(["users", "notes"], "readwrite");
  tx.objectStore("users").put({ id: "u1", name: "Alice" });
  tx.objectStore("notes").put({ id: "n1", userId: "u1", content: "Welcome!" });

  await new Promise((resolve, reject) => {
    tx.oncomplete = resolve;
    tx.onerror = () => reject(tx.error);
    tx.onabort = () => reject(tx.error);
  });

  console.log("Transaction successful.");
} catch (err) {
  console.error("Transaction failed and rolled back:", err);
}
```

### 2. [Handle Transaction Events](https://www.mindstick.com/interview/34307/what-are-transactions-in-indexeddb-and-why-are-they-important): `oncomplete`, `onerror`, `onabort`

```javascript
const tx = db.transaction("notes", "readwrite");

tx.oncomplete = () => console.log("Success ✅");
tx.onerror = () => console.error("Error ❌", tx.error);
tx.onabort = () => console.warn("Aborted 🛑", tx.error);
```

### 3. Avoid Delays During a Transaction

Don’t do async work *inside* the transaction, or it may auto-close:

```javascript
// ❌ Bad: async code inside transaction scope
const tx = db.transaction("notes", "readwrite");
await fetch("/api/data"); // this yields the event loop
tx.objectStore("notes").put({ ... }); // ❌ TransactionInactiveError
```

✅ Instead:

```javascript
const data = await fetch("/api/data").then(res => res.json());
const tx = db.transaction("notes", "readwrite");
tx.objectStore("notes").put(data);
```

### 4. Recover from Failures

If a write fails:

- Log the error or show a user notification
- Optionally retry the transaction
- Store in a local queue for background sync

```javascript
if (tx.error?.name === "QuotaExceededError") {
  alert("Storage is full. Please clear space.");
}
```

## Summary: Preventing Transaction Failure

| Best Practice | Benefit |
| --- | --- |
| Handle `onerror`, `onabort`, `oncomplete` | Know exactly what happened |
| Wrap in `try/catch` if using async | Catch errors in one place |
| Avoid async delays in transaction | Prevent `TransactionInactiveError` |
| Confirm success via `oncomplete` | Ensure all writes finished |
| Log and retry failed writes | Improve user experience |

## Answers

### Answer by Ponu Maurya

If a transaction in [**IndexedDB**](https://www.mindstick.com/interview/34289/what-is-indexeddb) **is not completed successfully**, it has **significant consequences**, including **data loss**, **inconsistent state**, or **silent failures** that may be hard to debug.

## Risks of Not Completing a Transaction

| Risk | What Happens |
| --- | --- |
| **No** `oncomplete` | Changes might not be written; browser may roll back |
| **Uncaught error** | Entire transaction rolls back (nothing is saved) |
| **Async delay or** `await` **inside transaction** | Transaction auto-closes before write — results in `TransactionInactiveError` |
| **Not handling** `onerror` **or** `onabort` | You lose track of failures — app silently breaks |

## Example of a Failed Write

```plaintext
const tx = db.transaction("notes", "readwrite");
const store = tx.objectStore("notes");

store.put({ id: 1, content: "Note" });

// No error handling:
setTimeout(() => {
  // This fails because the transaction auto-closed
  store.put({ id: 2, content: "Late Note" }); // ❌ TransactionInactiveError
}, 100);
```

## How to [Handle Failed](https://www.mindstick.com/interview/34314/how-do-you-handle-errors-in-indexeddb-operations#:~:text=Use%20onerror%20Events%20on%20Each,.)%20has%20an%20onerror%20event.) Writes Properly

### 1. Use `try/catch` with Promises

```javascript
try {
  const tx = db.transaction(["users", "notes"], "readwrite");
  tx.objectStore("users").put({ id: "u1", name: "Alice" });
  tx.objectStore("notes").put({ id: "n1", userId: "u1", content: "Welcome!" });

  await new Promise((resolve, reject) => {
    tx.oncomplete = resolve;
    tx.onerror = () => reject(tx.error);
    tx.onabort = () => reject(tx.error);
  });

  console.log("Transaction successful.");
} catch (err) {
  console.error("Transaction failed and rolled back:", err);
}
```

### 2. [Handle Transaction Events](https://www.mindstick.com/interview/34307/what-are-transactions-in-indexeddb-and-why-are-they-important): `oncomplete`, `onerror`, `onabort`

```javascript
const tx = db.transaction("notes", "readwrite");

tx.oncomplete = () => console.log("Success ✅");
tx.onerror = () => console.error("Error ❌", tx.error);
tx.onabort = () => console.warn("Aborted 🛑", tx.error);
```

### 3. Avoid Delays During a Transaction

Don’t do async work *inside* the transaction, or it may auto-close:

```javascript
// ❌ Bad: async code inside transaction scope
const tx = db.transaction("notes", "readwrite");
await fetch("/api/data"); // this yields the event loop
tx.objectStore("notes").put({ ... }); // ❌ TransactionInactiveError
```

✅ Instead:

```javascript
const data = await fetch("/api/data").then(res => res.json());
const tx = db.transaction("notes", "readwrite");
tx.objectStore("notes").put(data);
```

### 4. Recover from Failures

If a write fails:

- Log the error or show a user notification
- Optionally retry the transaction
- Store in a local queue for background sync

```javascript
if (tx.error?.name === "QuotaExceededError") {
  alert("Storage is full. Please clear space.");
}
```

## Summary: Preventing Transaction Failure

| Best Practice | Benefit |
| --- | --- |
| Handle `onerror`, `onabort`, `oncomplete` | Know exactly what happened |
| Wrap in `try/catch` if using async | Catch errors in one place |
| Avoid async delays in transaction | Prevent `TransactionInactiveError` |
| Confirm success via `oncomplete` | Ensure all writes finished |
| Log and retry failed writes | Improve user experience |


---

Original Source: https://www.mindstick.com/interview/34323/what-are-the-risks-of-not-completing-a-transaction-and-how-do-you-handle-failed-writes

Copyright © MindStick Software Pvt. Ltd. This Markdown version is provided for developers, AI systems, and offline reading.
