Zaawansowane Schematy i Metody w Mongoose

W tej lekcji przyjrzymy się bardziej zaawansowanym możliwościom schematów Mongoose. Nauczysz się, jak dodawać złożone struktury danych, jak korzystać z domyślnych wartości oraz jak tworzyć metody w modelach, które pozwalają na dodanie własnej logiki aplikacji. Wykorzystamy także wbudowane i niestandardowe walidacje, aby zapewnić integralność danych w naszej bazie MongoDB.

 Zaawansowane Schematy i Metody

Stwórz nowy plik o nazwie mongoose_advanced.js i wklej poniższy kod. Wprowadza on różne aspekty zaawansowanej pracy ze schematami i modelami w Mongoose.

Implementacja

// Importujemy Mongoose do naszego projektu
const mongoose = require('mongoose');

// Ustawiamy URL połączenia z lokalną bazą danych MongoDB
const url = 'mongodb://localhost:27017/myAdvancedMongooseDatabase';

// Funkcja główna, w której będziemy wykonywać wszystkie operacje
async function main() {
  try {
    // Nawiązujemy połączenie z MongoDB za pomocą Mongoose
    await mongoose.connect(url, {
      useNewUrlParser: true,
      useUnifiedTopology: true,
    });
    console.log('Połączono z MongoDB za pomocą Mongoose!');

    // --- Definiowanie zaawansowanego schematu i modelu ---

    // Definiujemy schemat dla kolekcji "products"
    const productSchema = new mongoose.Schema({
      name: {
        type: String,
        required: true,
        trim: true,
        minlength: [3, 'Nazwa produktu musi mieć przynajmniej 3 znaki'], // Wbudowana walidacja długości
      },
      price: {
        type: Number,
        required: true,
        min: [0, 'Cena nie może być ujemna'], // Wbudowana walidacja minimalnej wartości
      },
      category: {
        type: String,
        enum: ['electronics', 'books', 'home_appliances'], // Akceptujemy tylko określone wartości
        default: 'electronics', // Domyślna wartość
      },
      stock: {
        type: Number,
        default: 0, // Domyślnie ustawia stan magazynowy na 0
        validate: {
          validator: Number.isInteger, // Niestandardowa walidacja - pole musi być liczbą całkowitą
          message: 'Stan magazynowy musi być liczbą całkowitą',
        },
      },
      createdAt: {
        type: Date,
        default: Date.now, // Ustawiamy bieżącą datę jako domyślną wartość
      },
      tags: [String], // Tablica ciągów znaków do przechowywania tagów produktu
    });

    // --- Dodawanie metod do schematu ---

    // Definiujemy metodę na poziomie instancji modelu (każdego dokumentu)
    productSchema.methods.applyDiscount = function (percentage) {
      // Obniża cenę produktu o określony procent
      this.price = this.price - (this.price * (percentage / 100));
      return this.price;
    };

    // Definiujemy statyczną metodę na poziomie modelu (dla całej kolekcji)
    productSchema.statics.findByCategory = function (category) {
      // Wyszukuje produkty w określonej kategorii
      return this.find({ category: category });
    };

    // Tworzymy model "Product" na podstawie zdefiniowanego schematu
    const Product = mongoose.model('Product', productSchema);

    // --- CREATE: Dodawanie nowego produktu ---

    // Tworzymy nową instancję produktu
    const newProduct = new Product({
      name: 'Blender',
      price: 250,
      category: 'home_appliances',
      stock: 30,
      tags: ['kitchen', 'appliances'],
    });

    // Zapisujemy nowy produkt w bazie danych
    await newProduct.save();
    console.log('Nowy produkt zapisany:', newProduct);

    // --- READ: Wyszukiwanie produktów przy użyciu metod ---

    // Znajdujemy wszystkie produkty w kategorii "home_appliances"
    const homeAppliances = await Product.findByCategory('home_appliances');
    console.log('Produkty z kategorii "home_appliances":', homeAppliances);

    // --- UPDATE: Aktualizowanie produktu za pomocą metody instancji ---

    // Obniżamy cenę produktu o 20% za pomocą metody instancji
    newProduct.applyDiscount(20);
    await newProduct.save(); // Zapisujemy zaktualizowaną cenę w bazie danych
    console.log('Zaktualizowana cena po obniżce:', newProduct.price);

    // --- Walidacja niestandardowa ---

    try {
      // Tworzymy produkt z nieprawidłowym stanem magazynowym (ułamek)
      const invalidProduct = new Product({
        name: 'Invalid Product',
        price: 100,
        category: 'electronics',
        stock: 5.5, // Nieprawidłowa wartość - powinna być liczbą całkowitą
      });
      await invalidProduct.save(); // Próbujemy zapisać produkt
    } catch (validationError) {
      console.error('Błąd walidacji produktu:', validationError.message);
    }

  } catch (error) {
    console.error('Błąd podczas operacji na bazie danych:', error); // Obsługa błędów
  } finally {
    // Zawsze zamykamy połączenie z bazą danych, nawet w przypadku błędu
    await mongoose.connection.close();
    console.log('Połączenie z MongoDB zamknięte.');
  }
}

// Wywołujemy główną funkcję
main()

 

Jeżeli chcesz przyśpieszyć swoją naukę tworzenia stron chciałbym polecić mój kurs video JavaScript w którym nauczysz się tego języka od podstaw do zaawansowanych jego aspektów.

 

Scroll to Top