Prejsť na obsah

Príklad DotBridge

Otvoriť živú ukážku na adrese /documentation/examples/run/bridge (dostupná aj na /documentation/examples/run/forms3).

Úvod

Tento príklad je živá stránka Examples:Forms@index3! / @submit3!. Značky šablóny volajú PHP cez šifrovaný AJAX POST na URL aktuálnej stránky. Vstupy môžete filtrovať, šifrovať, obmedzovať limitom požiadaviek a viazať na konkrétnu URL.

Predpoklady

Začnite od príkladu pomenovaných formulárov, aby modul Examples a kontrolér Forms už existovali.

Vytvorenie view

Živá ukážka používa samostatný view v /app/modules/Examples/views/bridge.view.php. Súbor je kompletný HTML dokument.

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1" />
  <title>{{ var: $title }} — DotApp PHP Framework 2.0</title>
  <link rel="stylesheet" href="/assets/modules/Examples/css/examples.css" />
</head>
<body class="ex-body">
  <header class="ex-top">
    <a href="{{ var: $docsUrl }}">Documentation</a>
    <span>DotBridge</span>
  </header>
  <main class="ex-main">
    <h1>DotBridge</h1>
    <p class="ex-lead">Each button calls PHP over the current page URL.</p>
    <form method="post" class="ex-card" data-dotapp-nojs>
      <label for="email">Email</label>
      <input type="text" id="email" {{ dotbridge:input="email.address(email, 6, email_ok, email_bad)" }} placeholder="Enter your email" />
      <label for="category">Category</label>
      <select id="category" {{ dotbridge:input="category" }}>
        <option value="" disabled selected>Select a category</option>
        <option value="{{ enc(additionalKey): "AdminVal" }}">Admin</option>
        <option value="{{ enc(additionalKey): "EditorVal" }}">Editor</option>
        <option value="{{ enc(additionalKey): "OtherVal" }}">Other</option>
      </select>
      <div class="ex-bridge-actions">
        <div class="ex-btn" {{ dotbridge:on(click)="example.showEmailCategory(email.address, category)" oneTimeUse }}>Submit only once</div>
        <div class="ex-btn" {{ dotbridge:on(click)="example.showEmailCategory2(email.address, category)" regenerateId rateLimit(60,2) rateLimit(3600,5) url(/documentation/examples/run/forms3/) }}>Submit 2× per minute</div>
        <div class="ex-btn" {{ dotbridge:on(click)="example.showEmailCategory3(email.address, category)" regenerateId }}>Submit no limit</div>
      </div>
    </form>
    <div class="output" id="output1">Submit with the first button to see the result</div>
    <div class="output" id="output2">Submit with the second button to see the result</div>
    <div class="output" id="output3">Submit with the third button to see the result</div>
  </main>
  <script src="/assets/dotapp/dotapp.js"></script>
  <script src="/assets/modules/Examples/js/bridge.js"></script>
</body>
</html>

Pridanie štýlov

Zdieľaný vzhľad príkladov je v /app/modules/Examples/assets/css/examples.css a je dostupný ako /assets/modules/Examples/css/examples.css.

Vytvorenie layoutu

setView('bridge') vykreslí celý HTML dokument. Moduly môžu view obaliť aj pomocou {{ layout:name }}. Táto ukážka ponecháva view samostatný.

Vstupy DotBridge

Polia označte značkou {{ dotbridge:input="name" }} alebo skráteným tvarom dotbridge="name". Vnorené názvy, napríklad email.address, prídu do PHP ako $request->data(true)['data']['email.address'].

Vstavané filtre zahŕňajú email, url, phone, password, date, time, creditcard, username a ipv4. Ďalšie zaregistrujte pomocou Bridge::addFilter($name, $callback).

Filtre DotBridge

Pole e-mailu používa email.address(email, 6, email_ok, email_bad): filter email, minimálnu dĺžku 6 a voliteľné callbacky úspechu/zlyhania. Možnosti kategórie sú v šablóne šifrované pomocou {{ enc(additionalKey): "AdminVal" }} a v PHP dešifrované tým istým extra kľúčom.

Udalosti DotBridge

Kliknutie (alebo inú udalosť) naviažete značkou {{ dotbridge:on(click)="functionName(arg1, arg2)" }}. Modifikátory na tej istej značke riadia opätovné použitie a limity:

  • oneTimeUse — kľúč sa po jednom úspešnom volaní spotrebuje.
  • regenerateId — po volaní sa vydá nové id.
  • rateLimit(seconds,count) — môžete stohovať viaceré okná, napr. rateLimit(60,2) rateLimit(3600,5).
  • url(/path) — cieľ POST pre dané volanie. Neplatná viazaná URL vráti HTTP 403 s error_code 6.

JavaScript funkcie DotBridge

Každý názov funkcie v šablóne spárujte s $dotapp().bridge(name, event). Hooky: before, onValueError, after a onResponseCode. Ak sa knižnica ešte načítava, počkajte na udalosť dotapp.

Konfigurácia trás

V initialize($dotApp) zaregistrujte GET stránky a každú funkciu Bridge naviažte na tie isté URL:

$bridgePages = array_merge($pair($p . '/forms3'), $pair($p . '/bridge'));
Router::get($bridgePages, 'Examples:Forms@index3!', Router::STATIC_ROUTE);
foreach (['example.showEmailCategory', 'example.showEmailCategory2', 'example.showEmailCategory3'] as $fn) {
    Router::bridge($bridgePages, $fn, 'Examples:Forms@submit3!', Router::STATIC_ROUTE);
}

Router::bridge($urls, $functionName, $handler, Router::STATIC_ROUTE) obmedzí handler na tieto URL stránky. Closures používajú Bridge::listen() s rovnakým poradím argumentov.

Úprava kontroléra

Metódy sú public static a prijímajú $request. Akcia GET vykreslí view. Akcia Bridge prečíta payload a vráti reťazec (alebo pole), ktorý sa stane JSON body.

public static function index3($request)
{
    return self::view('bridge', [
        'title' => 'DotBridge demo',
        'docsUrl' => '/documentation/examples/dotbridge',
    ]);
}

public static function submit3($request)
{
    $payload = $request->data(true)['data'] ?? [];
    $email = (string) ($payload['email.address'] ?? '');
    $category = Crypto::decrypt((string) ($payload['category'] ?? ''), 'additionalKey');
    if ($category === false) {
        $category = '(invalid category)';
    }
    return 'This is reply from submit3() function. Email: ' . $email . ', category: ' . $category;
}

Neúspešné dešifrovanie vráti false — porovnávajte s === false.

Implementácia JavaScriptu

Súbor živej ukážky: /app/modules/Examples/assets/js/bridge.js. Klientské API je $dotapp.

(function () {
  var runMe = function ($dotapp) {
    function before(selector) {
      var categoryInput = $dotapp('[dotbridge-input="category"]').val();
      if (categoryInput === null || categoryInput === "") {
        alert("Select a category.");
        return $dotapp().halt();
      }
      $dotapp(selector).html("Loading...").removeClass("error").removeClass("success").addClass("loading");
    }

    function after(selector, body) {
      var text = "";
      if (typeof body === "string") text = body;
      else if (body && body.body) text = body.body;
      else if (body) text = String(body);
      if (text) {
        $dotapp(selector).html(text).removeClass("error").removeClass("loading").addClass("success");
      }
    }

    function onResponse(selector, data) {
      var reply = $dotapp().parseReply(data);
      var text = (reply && reply.status_txt) ? reply.status_txt : "Request failed.";
      $dotapp(selector).html(text).addClass("error").removeClass("loading").removeClass("success");
    }

    $dotapp()
      .bridge("example.showEmailCategory", "click")
      .before(function () { return before("#output1"); })
      .onValueError(function (inputname) {
        if (inputname == "email.address") alert("Enter a valid email address.");
      })
      .after(function (body) { after("#output1", body); })
      .onResponseCode(function (status, text) { onResponse("#output1", text); }, 429);
  };
  if (window.$dotapp) runMe(window.$dotapp);
  else window.addEventListener("dotapp", function () { runMe(window.$dotapp); }, { once: true });
})();

Rovnaký reťazec .bridge() zopakujte pre example.showEmailCategory2 a example.showEmailCategory3 s ich selektormi výstupu.

Chybové kódy

Úspech je HTTP 200 s JSON { status: 1, body: <your return> } a hlavičkou X-Answered-By: dotbridge.

  • HTTP 400, error_code 1: kontrola CRC zlyhala.
  • HTTP 403, error_code 2: nesúlad kľúča Bridge.
  • HTTP 404, error_code 3: funkcia nie je zaregistrovaná alebo nie je volateľná.
  • HTTP 429, error_code 4: limit požiadaviek, neplatné id alebo chýbajúci platný kľúč.
  • HTTP 403, error_code 5: nesúlad CSRF referera.
  • HTTP 403, error_code 6: neplatná dotbridge-url.

Živá ukážka

/documentation/examples/run/bridge a /documentation/examples/run/forms3 vykresľujú tú istú stránku.