Transaktionen und Migrationen
Implementieren Sie Datenbanktransaktionen für atomare Operationen und verwalten Sie Schemaänderungen effizient mit TypeORM-Migrationen.
Transaktionen und Migrationen ist eine kostenlose NestJS Enterprise Backend APIs-Lektion auf CoddyKit. Dies ist Lektion 2 von 3. Du kannst die komplette Lektion unten kostenlos lesen – dann übst du sie direkt im Browser mit einem integrierten Code-Editor und einem KI-Tutor rund um die Uhr. Sie ist Teil des NestJS Enterprise Backend APIs-Lernpfads, und dein Fortschritt wird über Web und CoddyKit-App synchronisiert. Der NestJS Enterprise Backend APIs-Kurs umfasst insgesamt 3 Lektionen.
Teile dieser Lektion wurden noch nicht übersetzt und werden auf Englisch angezeigt.
Atomic Operations: Transactions
Imagine transferring money between two bank accounts. If the deduction from one account succeeds but the addition to the other fails, your data is inconsistent!
Database transactions solve this by grouping multiple database operations into a single, atomic unit. Either all operations succeed (commit), or none of them do (rollback).
Understanding ACID Properties
Transactions ensure data reliability by adhering to ACID properties:
- Atomicity: All or nothing.
- Consistency: Database state remains valid.
- Isolation: Concurrent transactions don't interfere.
- Durability: Committed changes are permanent.
These properties are vital for maintaining data integrity in complex applications.
TypeORM Manual Transactions
TypeORM allows you to manage transactions manually using the DataSource or EntityManager. This gives you fine-grained control over when to commit or rollback.
You typically use dataSource.transaction(async manager => { ... }), where manager is a transactional entity manager.
Manual Transaction Example
Here's a simplified example of transferring funds within a transaction. If any step fails, the entire operation is rolled back.
import { DataSource, Entity, PrimaryGeneratedColumn, Column, Repository } from 'typeorm';
@Entity()
export class Account {
@PrimaryGeneratedColumn() id: number;
@Column({ type: 'decimal', precision: 10, scale: 2 }) balance: number;
}
async function runTransaction() {
const AppDataSource = new DataSource({
type: 'sqlite',
database: ':memory:',
entities: [Account],
synchronize: true,
});
await AppDataSource.initialize();
const accountRepo = AppDataSource.getRepository(Account);
await AppDataSource.transaction(async manager => {
const sender = await manager.save(accountRepo.create({ balance: 100 }));
const receiver = await manager.save(accountRepo.create({ balance: 50 }));
console.log(`Initial: Sender ${sender.balance}, Receiver ${receiver.balance}`);
sender.balance -= 20;
receiver.balance += 20;
await manager.save(sender);
// Simulate an error here to trigger rollback:
// throw new Error('Failed to update receiver!');
await manager.save(receiver);
console.log(`Final: Sender ${sender.balance}, Receiver ${receiver.balance}`);
});
await AppDataSource.destroy();
}
// To run this in a Node.js context:
// runTransaction().catch(console.error);
// For CoddyKit, we just show the code.Decorators for Transactions
NestJS and TypeORM often work together. For convenience, TypeORM provides the @Transaction() and @TransactionManager() decorators.
You can apply @Transaction() to a service method, and TypeORM will automatically wrap the method's execution in a transaction.
Decorator Transaction Example
Using the @Transaction() decorator makes your service code cleaner, as you don't need to manually handle transaction commits or rollbacks.
import { Injectable } from '@nestjs/common';
import { Repository, EntityManager } from 'typeorm';
import { InjectRepository } from '@nestjs/typeorm';
import { Transaction } from 'typeorm'; // Import Transaction decorator
// Assume Account Entity is defined elsewhere
class Account {
id: number;
balance: number;
}
@Injectable()
export class BankService {
constructor(
@InjectRepository(Account) private accountRepository: Repository<Account>,
) {}
@Transaction()
async transferFunds(
senderId: number,
receiverId: number,
amount: number,
@TransactionManager() manager?: EntityManager, // Manager is injected
): Promise<boolean> {
const accountManager = manager || this.accountRepository.manager; // Use injected manager
const sender = await accountManager.findOneBy(Account, { id: senderId });
const receiver = await accountManager.findOneBy(Account, { id: receiverId });
if (!sender || !receiver || sender.balance < amount) {
throw new Error('Transfer failed: Invalid accounts or insufficient funds');
}
sender.balance -= amount;
receiver.balance += amount;
await accountManager.save(sender);
await accountManager.save(receiver);
console.log(`Transferred ${amount}. Sender: ${sender.balance}, Receiver: ${receiver.balance}`);
return true;
}
}
// Note: This code is illustrative within a NestJS service context.
// It's not runnable as a standalone script without a full NestJS setup.Managing Schema Changes: Migrations
As your application evolves, your database schema will change (e.g., adding new columns, tables). Directly modifying the database can be risky and hard to track.
Database migrations provide a structured, version-controlled way to apply changes to your database schema, ensuring consistency across environments.
Generating TypeORM Migrations
TypeORM has a powerful CLI to generate migration files. It compares your entities with the current database schema and creates a script to bridge the differences.
First, ensure your ormconfig.json or DataSource is set up correctly. Then, run the command:
npx typeorm migration:generate src/migration/MyNewMigration
This creates a timestamped .ts file in the specified folder.
Migration File Structure
Each migration file contains two key methods:
up(queryRunner: QueryRunner): Promise: Defines changes to apply to the database (e.g., create table, add column).down(queryRunner: QueryRunner): Promise: Defines how to revert the changes made byup(e.g., drop table, remove column).
This allows you to easily roll forward and backward through schema versions.
import { MigrationInterface, QueryRunner, Table } from 'typeorm';
export class MyNewMigration1678886400000 implements MigrationInterface {
public async up(queryRunner: QueryRunner): Promise<void> {
await queryRunner.createTable(
new Table({
name: 'products',
columns: [
{ name: 'id', type: 'int', isPrimary: true, isGenerated: true, generationStrategy: 'increment' },
{ name: 'name', type: 'varchar' },
{ name: 'price', type: 'decimal', precision: 10, scale: 2, default: 0 },
],
}),
true,
);
}
public async down(queryRunner: QueryRunner): Promise<void> {
await queryRunner.dropTable('products');
}
}Applying and Reverting Migrations
Once you've written or generated your migration files, you need to apply them to your database:
- Apply all pending migrations:
npx typeorm migration:run - Revert the last applied migration:
npx typeorm migration:revert
Always run migrations in your development and production environments to keep schemas synchronized.
Check Your Knowledge
Which of the following statements about database transactions and migrations in TypeORM is FALSE?
Recap: Transactions & Migrations
You've learned about two critical concepts for robust database management:
- Transactions: Ensure data integrity through atomic operations following ACID principles, using TypeORM's manual methods or the
@Transaction()decorator. - Migrations: Provide a structured way to evolve your database schema, using TypeORM CLI to generate and apply changes via
up()anddown()methods.
Mastering these will help you build more reliable and maintainable backend APIs.
Lerne TypeScript mit einem KI-Tutor — kostenlos
Schreibe und führe echten Code in deinem Browser aus, bekomme sofortige Hilfe von einem 24/7 KI-Tutor und setze dein Lernen im Web oder in der App fort.
- Kurse
- 20
- Lektionen
- 76
Häufig gestellte Fragen
Ist die Lektion „Transaktionen und Migrationen“ kostenlos?
Ja — der vollständige Text von „Transaktionen und Migrationen“ ist hier im Web kostenlos zu lesen. Um sie interaktiv zu üben (integrierter Code-Editor und 24/7 KI-Tutor) und den Rest des NestJS Enterprise Backend APIs-Kurses freizuschalten, upgrade auf CoddyKit PRO. Der NestJS Enterprise Backend APIs-Kurs umfasst insgesamt 3 Lektionen.
Was lerne ich in „Transaktionen und Migrationen“?
Implementieren Sie Datenbanktransaktionen für atomare Operationen und verwalten Sie Schemaänderungen effizient mit TypeORM-Migrationen. Du übst NestJS Enterprise Backend APIs mit praktischem Code, den du direkt im Browser ausführst, und ein 24/7 KI-Tutor beantwortet deine Fragen während du die Lektion bearbeitest.
Brauche ich Erfahrung, um NestJS Enterprise Backend APIs zu starten?
Keine Vorkenntnisse erforderlich. NestJS Enterprise Backend APIs auf CoddyKit ist für Anfänger bis fortgeschrittene Lernende strukturiert, sodass du hier starten oder von Anfang an beginnen und in deinem eigenen Tempo voranschreiten kannst. Dies ist Lektion 2 von 3.
Wie lange dauert die Lektion „Transaktionen und Migrationen“?
Die meisten CoddyKit-Lektionen dauern etwa 5–10 Minuten. Jede ist kompakt und interaktiv, sodass du stetig Fortschritte machst und genau dort weitermachst, wo du aufgehört hast – im Web und in der App.
Kann ich in dieser NestJS Enterprise Backend APIs-Lektion Code schreiben und ausführen?
Ja. Jede NestJS Enterprise Backend APIs-Lektion enthält einen integrierten Code-Editor, sodass du echten Code direkt in deinem Browser schreibst und ausführst und sofort KI-Feedback erhältst — ohne lokale Einrichtung erforderlich.
Alle Lektionen in diesem Kurs
- Benutzerdefinierte TypeORM-Repositories
- Transaktionen und Migrationen
- Datenbank-Seeding und -Tests