✅ Nowości, motywy, wtyczki WEB i WordPress. Tutaj dzielimy się wskazówkami i najlepszymi rozwiązaniami dla stron internetowych.

Staraj się dzielić programy na mniejsze komponenty

19

Jedną z rzeczy, o których często mówią programiści, jest chęć podzielenia programów na mniejsze komponenty lub funkcje, aby ułatwić ich śledzenie, czytanie i debugowanie.

Ale nie jest niczym niezwykłym zobaczyć monolityczne funkcje z wieloma komentarzami do kodu, które pomagają wyjaśnić, co się dzieje w programie.

Naprawdę tego nie pukam, bo nie znam ograniczeń, pod jakimi pracował programista. To znaczy:

  • Jaki był jego/jej budżet budując program?
  • Ile czasu poświęcono na wykonanie projektu?
  • Czy nad projektem pracowało wiele osób?
  • Czy programista miał czas na napisanie kodu, aby mógł go przetestować jednostkowo, zrefaktoryzować lub po prostu ułatwić czytanie?

Krótko mówiąc, istnieje wiele powodów – wierzę – że możemy czytać „zły kod" i nie zawsze musi to być wina programisty (to po prostu najbardziej naturalna rzecz, którą musimy wyrzucić, kiedy czytamy coś, czego nie lubimy).

Czy to jednak oznacza, że ​​nie powinniśmy dążyć do refaktoryzacji lub pisania kodu w taki sposób, aby był łatwiejszy do zrozumienia? Oczywiście nie. Zakładając, że mamy na to czas, jak możemy to zrobić?

Podziel programy na mniejsze komponenty

Jeśli chodzi o pisanie na taki temat, zwłaszcza w gospodarce, która jest tak aktywna jak eCommerce w WordPressie, może to być wyzwaniem.

„Bądźmy konkretni, Bob”.

Oznacza to, że mogę o tym pisać na bardzo szczegółowym poziomie, korzystając z zestawu wtyczek, patrząc na dane, analizując zapytania i pokazując, jak to zrobić. Albo mogę napisać o tym na nieco wyższym poziomie, a ostatecznym celem jest pokazanie, jak podzielić programy na mniejsze komponenty.

Ponieważ istnieje tak wiele sposobów, aby to pierwsze osiągnąć, wybieram to drugie. Oznacza to, że niekoniecznie będzie to używanie konkretnych wtyczek, ale bezpośrednie zapytania. Będzie jednak używał przykładów wysokiego poziomu, które pomogą Ci przejść przez serię zapytań i pętli oraz podzielić je na mniejsze funkcje.

Ogólny przykład

Załóżmy na przykład, że pracuję nad funkcją wtyczki WordPress, której ostatecznym celem jest pobranie wszystkich różnych metod płatności zapisanych przez użytkownika i powiązanych z jego kontem.

Wyzwanie polega na tym, że informacje te są rozproszone w wielu tabelach bazy danych (z powodu różnych używanych wtyczek), więc istnieje kilka zapytań, które należy wykonać, a następnie pobrać.

Kroki tworzenia takich zapytań mogą wyglądać mniej więcej tak:

  1. uzyskać identyfikator klienta bieżącego użytkownika,
  2. zdobądź wszystkie numery identyfikacyjne zamówienia dla klienta
  3. określić, jakie metody płatności zostały użyte przy każdym zamówieniu
  4. pobrać wspomniane metody płatności, a następnie wysłać informacje do klienta,

W zależności od konfiguracji bazy danych, w zależności od poziomu umiejętności SQL i w zależności od tego, jak różne wtyczki obsługujące wszystkie powyższe dane działają w tandemie, może być łatwo napisać jedno duże zapytanie w celu pobrania tych informacji.

Ale jeśli pracowałeś z eCommerce w WordPressie i różnych wtyczkach, wiesz, że nie zawsze jest to takie proste.

Zamiast tego patrzysz na coś takiego jak:

  1. musimy uzyskać profil klienta z metadanych użytkownika,
  2. musimy znaleźć wszystkie zamówienia złożone przez użytkownika, a to często może być powiązane z postem lub tabelą metadanych posta,
  3. metody płatności mogą być z dużym prawdopodobieństwem przechowywane w ich tabeli powiązanej z użytkownikiem za pomocą pewnego rodzaju tokena,
  4. powyższy token znajduje się w tabeli i jest powiązany z daną informacją w innej tabeli, z której musisz następnie wywnioskować, patrząc na dane istniejące w całej bazie danych.

Ostatecznie musisz utworzyć zestaw zapytań tylko przez zrozumienie, w jaki sposób wykonać zapytanie o dane, których szukasz. To już wystarczająco trudne. Ale kiedy już to zrobisz, powiedzmy, że piszesz zapytania sekwencyjnie, a następnie używasz wyników każdego z nich, aby uzyskać pożądany wynik.

Może to spowodować coś takiego :

<?php

// First, read the user ID and meta value to get authorization information
global $wpdb;
$results = $wpdb->get_results(
    $wpdb->prepare(
        "
        SELECT
            user_id, meta_value
        FROM $wpdb->usermeta
        WHERE meta_key LIKE %s
        AND user_id = %d
        ",
        '%customer_profile_id%',
        filter_input(INPUT_GET, 'customer_id')
    ),
    ARRAY_A
);

$result = isset($results[0])? array_column($results[0], 'meta_value'): [];
if (empty($result)) {
    return $result;
}

// Get the ID of the current customer.
$customers = $wpdb->get_results(
    $wpdb->prepare(
        "", // Your custom query goes here.
        filter_input(INPUT_GET, 'customer_id')
    ),
    ARRAY_A
);

$customer = isset($customers[0])? array_column($customers[0], 'customer_id'): [];
if (empty($customer)) {
    return $customer;
}

// Get all of the order IDs from the set of orders returned from the previous query.
$orderIds = $wpdb->get_results(
    $wpdb->prepare(
        "", // Your custom query goes here.
        $customer
    ),
    ARRAY_A
);

return $orderIds;

// Finally, get all of the payment methods for the orders based on their Ids.
$orders = [];
foreach ($orderIds as $orderId) {
    $results = $wpdb->get_results(
        $wpdb->prepare(
            "" // The query for retrieving various payment method information based on the $orderId
        ),
        ARRAY_A
    );

    if (empty($results)) {
        continue;
    }

    $orders[$orderId] = $results;
}

// Now send the information back to the user.
wp_send_json_success($orders);

Ale nie musi tak być.

Po pierwsze, są to wszystkie niezależne zapytania z niezależnymi zestawami wyników, mimo że muszą być używane w tandemie. Oznacza to, że możemy je rozdzielić i ocenić wyniki każdego z nich, zanim przejdziemy do następnego kroku.

Ponadto pozwala nam pisać mniejsze, bardziej spójne funkcje. Nawet jeśli mogą one od siebie zależeć, możemy ustawić każdą funkcję tak, aby akceptowała argument (lub zestaw argumentów, z którego możemy pobrać wszystkie informacje.

Być może efekt końcowy może wyglądać mniej więcej tak :

<?php

public function getPaymentMethods()
{
  $authInfo = $this->getAuthorizationInformation();
  $currentCustomerId = $this->getCurrentCustomerId($authInfo);
  $orders = $this->getCustomerOrders($currentCustomerId);
  $paymentMethods = $this->getPaymentMethodsFromOrders($orders);
  wp_send_json_success($orders);
}

private function getAuthorizationInformation()
{
  global $wpdb;
  $authInfo = $wpdb->get_results(
      $wpdb->prepare(
          "
          SELECT
              user_id, meta_value
          FROM $wpdb->usermeta
          WHERE meta_key LIKE %s
          AND user_id = %d
          ",
          '%customer_profile_id%',
          filter_input(INPUT_GET, 'customer_id')
      ),
      ARRAY_A
  );

  return isset($authInfo[0])? array_column($authInfo[0], 'meta_value'): [];
}

private function getCurrentCustomerIdFromAuthInfo($authInfo)
{
  global $wpdb;
  $customers = $wpdb->get_results(
      $wpdb->prepare(
          "", // Your custom query goes here.
          $authInfo;
      ),
      ARRAY_A
  );

  return isset($customerId[0])? array_column($customerId[0], 'meta_value'): [];
}

private function getCustomerOrders($customerId)
{
  global $wpdb;
  $orderIds = $wpdb->get_results(
      $wpdb->prepare(
          "", // Your custom query goes here.
          $customerId
      ),
      ARRAY_A
  );

  return empty($orderIds)? []: $orderIds;
}

private function getPaymentMethodsFromOrders($orderIds)
{
  $paymentMethods = [];
  foreach ($orderIds as $orderId) {
      $results = $wpdb->get_results(
          $wpdb->prepare(
              "" // The query for retrieving various payment method information based on the $orderId
          ),
          ARRAY_A
      );

      if (empty($results)) {
          continue;
      }

      $paymentMethods[$orderId] = $results;
  }

  return $paymentMethods;
}

Oczywiście nie mogę pokazać żadnego rzeczywistego SQL – cóż, przynajmniej nie wszędzie – ponieważ nie znam ogólnej konfiguracji ani nie wiem dokładnie, z jakimi wtyczkami lub schematami pracujesz.

Ale to nigdy nie było celem tego postu.

Zamiast tego, ostateczną kwestią, którą staram się przekazać, jest to, że nawet jeśli pracujemy pod bardzo ograniczonymi ograniczeniami, nadal możemy dzielić programy na mniejsze komponenty, które pomagają nam opisać, co się dzieje, zrozumieć, jak to się robi, a następnie wysyłać dane tam iz powrotem między różnymi funkcjami oraz do i od użytkownika.

Źródło nagrywania: tommcfarlin.com

Ta strona korzysta z plików cookie, aby poprawić Twoje wrażenia. Zakładamy, że nie masz nic przeciwko, ale możesz zrezygnować, jeśli chcesz. Akceptuję Więcej szczegółów