Links ohne Fett (F3) verkürzen

Links ohne Fett (F3) verkürzen

Es ist nicht peinlich, mit 13 Jahren Links zu kürzen, oder? Einem Neuling, und nicht nur ihm, sollte es in Betracht gezogen werden, seinen eigenen Linkverwalter zu schreiben, während er ein neues Framework lernt. Genau das habe ich gemacht. Was soll ich sagen – das fünfte Bootstrap, ein abgespecktes Framework und ein Stück Seele.

Hier Demo, aber hier ist Code. Für solche Leser wie mich 😉

Ein Framework, nicht wahr?

Natürlich nicht Laravel und Ähnliches – heute kommen wir mit 65 Kilobyte aus. FatFreeFramework. Wenn Sie mit Python Flask vertraut sind, werden Sie das Gefühl haben, dass dies schon mal irgendwo anders war:

#роутинг во Фласке
@app.route('/')
def hello_world():
    return 'Hello, World!'
//роутинг в Обезжиренном
$f3->route('GET /',
    function() {
        echo 'Hello, world!';
    }
);

Gut, vergessen Sie es. Laden wir .zip von der offiziellen Seite herunter, entpacken wir es in den Ordner, der im gleichen Moment in Ihrem Lieblings-Code-Editor geöffnet wird. Reinigen Sie index.php und entfernen Sie alles aus /ui.

Hier ist alles ganz einfach – im Ordner ui haben wir alle Views, oder einfacher gesagt – raffinierte HTML-Vorlagen, die wir dem Benutzer bei Besuch einer bestimmten URL anzeigen werden.

Hier ist das Gerüst unserer "Anwendung":

set('DEBUG', 1);
if ((float)PCRE_VERSIONconfig('config.ini');

// DEN GESAMTEN ÜBRIGEN CODE WERDEN WIR HIER SCHREIBEN

$f3->run();

Das ist alles, was Sie für den Anfang wissen müssen. Lass uns mit dem Codieren beginnen!

[Für die Entwicklung habe ich lokal XAMPP unter Windows und VS Code verwendet, der Artikel wurde in Notion verfasst.]

Homepage

Lass uns mit der Hauptseite beginnen. Ist logisch, oder?

//Файл: index.php

$f3->route('GET /',
    function($f3) { //чтобы использовать функции F3 передаем его в роут
                $view = new View; // создаем вьюшку
        echo $view->render('home.htm'); //рендерим шаблон
    }
);

Jetzt müssen wir diese Vorlage erstellen. Zur Vereinfachung habe ich Bootstrap v5 alpha verwendet.

Vergessen Sie nicht, alle Vorlagen im Ordner ui zu erstellen, sonst werden sie dem Framework nicht angezeigt.

<!-- Файл: ui/home.htm -->

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="<?php echo $ENCODING; ?>" />
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <title>Wir schreiben (Code), wir kürzen (Links)!</title>
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/5.0.0-alpha1/css/bootstrap.min.css" integrity="sha384-r4NyP46KrjDleawBgD5tp8Y7UzmLA05oM1iAEQ17CSuDqnUK2+k9luXQOfXJCJ4I" crossorigin="anonymous">
    </head>
    <body class="text-center bg-dark text-light"> <!-- темная тема ;) -->

        <!-- менюшка -->
        <nav class="m-2">
            <ul class="nav nav-pills justify-content-center">
                <li class="nav-item">
                    <a class="nav-link active" aria-current="page" href="#">Startseite</a>
                </li>
                <li class="nav-item">
                    <a class="nav-link" href="#">Artikel auf Habré</a>
                </li>
                <li class="nav-item">
                    <a class="nav-link" href="https://nikonovs.ru">Ersteller</a>
                </li>
            </ul>
        </nav>

        <div class="container">
        <h1>Kurze Links sind jetzt hier.</h1>

        <!-- Будем отправлять данные POST-запросом на /newLink -->
        <form class="mt-5 mb-3" action="/de/newLink/" method="POST" data-trp-original-action="/newLink/">
            <div class="row justify-content-center">
                <div class="col-auto">
                <label for="inputLink" class="col-form-label">Gib den Link ein:</label>
                </div>
                <div class="col-auto">
                <input required placeholder="https://" type="url" name="link" id="inputLink" class="form-control mb-1" aria-describedby="inputLink">
                </div>
                <div class="col-auto">
                <button type="submit" class="btn btn-outline-primary">Kürzen!</button>
                </div>
            </div>
        <input type="hidden" name="trp-form-language" value="de"/></form>

        <!-- немного -->
        <p class="text-left m-auto mb-5" style="max-width: 30rem;">Lorem ipsum dolor sit, amet consectetur adipisicing elit. Omnis illum molestiae hic fugiat molestias nemo, architecto beatae repellat ullam exercitationem non ab, necessitatibus maxime quod iure ipsa quam quos! Reprehenderit. Lorem ipsum dolor, sit amet consectetur adipisicing elit. Necessitatibus eos sapiente voluptates veniam sequi delectus totam tenetur praesentium obcaecati. Repudiandae quisquam, ipsa ullam corrupti molestiae minima optio nihil est modi?</p>

        <footer class="m-2">Gemacht mit <img width="20" height="20" src="https://image.flaticon.com/icons/svg/833/833472.svg" alt="mit Liebe">, <a href="https://v5.getbootstrap.com/">Bootstrap 5</a>    und <a href="https://fatfreeframework.com/">ohne überflüssige Elemente</a></footer>
        </div>
    </body>
</html>

Das ist alles, unsere Hauptseite funktioniert bereits. Das Formular sendet per POST-Anfrage den Link, der verkürzt werden soll.
Jetzt wird es interessant (nicht).

Arbeiten mit der Datenbank

Erstellen wir eine Datenbank – MySQL. Wenn Sie PhpMyAdmin installiert haben, erstellen Sie eine neue Datenbank "linker", und führen Sie dann dieses SQL aus:

SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
SET time_zone = "+00:00";

CREATE TABLE IF NOT EXISTS `links` (
  `code` varchar(4) NOT NULL,
  `link` varchar(1000) NOT NULL,
  `hits` int(255) NOT NULL DEFAULT '0'
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

ALTER TABLE `links`
  ADD UNIQUE KEY `code` (`code`);

Wir werden für jede Link 3 Felder haben:

  1. Code – das sind zufällige 4 Zeichen nach der Domain, nach denen die Weiterleitung erfolgt, zum Beispiel example.com/ABC1
  2. Link – der nicht verkürzte Link.
  3. Hits – die Anzahl der Klicks auf den verkürzten Link.

Ich werde kurz das Prinzip der Arbeit mit der Datenbank erläutern, ohne Schnickschnack.

set('result', $db->exec('SELECT * FROM wherever')); 
// sie sind in den Vorlagen verfügbar als 

// Oder man kann den eingebauten SQL Mapper verwenden:
$row = new DBSQLMapper($db, 'links');

$row->load(array('link="https://habrahabr.ru"')); // jetzt sind alle Spalten der Zeile, wo der Link auf Habr ist, aus diesem Objekt verfügbar:
$row_value = $row->somerow; // So

// Natürlich kann man die Werte ändern:
$row->link = 'https://habr.com';
$row->save(); // Änderungen müssen gespeichert werden, was habt ihr gedacht?

// Mehr Informationen zur Arbeit mit der Datenbank sind hier verfügbar: https://a.nikonovs.ru/MPHR Ich empfehle dringend, das zu lesen, auch wenn es mit Hilfe eines Übersetzers im Browser ist.
?>

Wir beginnen mit der Verkürzung.

Verarbeitung des neuen Links

Wir erstellen eine neue Ansicht in index., die die Anfrage aus dem Formular auf der Hauptseite bearbeitet.

Zuerst erstellen wir eine neue, aber sehr ähnliche Vorlage wie die erste (home.htm) — "newLink.htm".
Dort werden wir den bereits verkürzten Link und die Anzahl der Klicks darauf anzeigen (um diese "Statistik" erneut zu sehen, muss man denselben Link erneut verkürzen — die Adresse bleibt gleich).
Wir verwenden einen Trick mit "Variable Übetragungen" für die Anzeige:

set('link', $shorted_link);
$view = new View;
echo $view->render('newLink.htm');
// Jetzt kann man in der Vorlage verwenden:

Hier ist der Listing newLink.html:

<!-- Файл: newLink.htm -->

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="<?php echo $ENCODING; ?>" />
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <title>Wir schreiben (Code), wir kürzen (Links)!</title>
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/5.0.0-alpha1/css/bootstrap.min.css" integrity="sha384-r4NyP46KrjDleawBgD5tp8Y7UzmLA05oM1iAEQ17CSuDqnUK2+k9luXQOfXJCJ4I" crossorigin="anonymous">
    </head>
    <body class="text-center bg-dark text-light">
        <nav class="m-2">
            <ul class="nav nav-pills justify-content-center">
                <li class="nav-item">
                    <a class="nav-link" aria-current="page" href="/de/">Startseite</a>
                </li>
                <li class="nav-item">
                    <a class="nav-link" href="#">Artikel auf Habré</a>
                </li>
                <li class="nav-item">
                    <a class="nav-link" href="https://nikonovs.ru">Ersteller</a>
                </li>
            </ul>
        </nav>

        <div class="container">
        <h1>Kurze Links sind jetzt hier.</h1>

        <!-- Убираем из формы функционал формы и выводим переменные -->
        <form class="mt-5 mb-3" action="">
            <div class="row justify-content-center">
                <div class="col-auto">
                    <label for="inputLink" class="col-form-label">Reduziert:</label>
                </div>
                <div class="col-auto">
                    <input disabled required type="url" name="link" id="inputLink" class="form-control disabled" aria-describedby="inputLink" value="<?= $link ?>">
                </div>
            </div>
            <p class="m-2 text-secondary">Über diesen Link erreicht: ``</p>
        <input type="hidden" name="trp-form-language" value="de"/></form>

        <a href="/de/" class="mt-3 mb-5 btn btn-primary btn-lg">ZURÜCK ZUR STARTSEITE</a>

        <footer class="m-2">Gemacht mit <img width="20" height="20" src="https://image.flaticon.com/icons/svg/833/833472.svg" alt="mit Liebe">, <a href="https://v5.getbootstrap.com/">Bootstrap 5</a>    und <a href="https://fatfreeframework.com/">ohne überflüssige Elemente</a></footer>
        </div>
    </body>
</html>

Wir schreiben die Route.

$f3->route('GET|POST /newLink', //Wir werden sowohl POST als auch GET verarbeiten
    function($f3) {

            $db = new DBSQL( //Neue Verbindung zur DB in jeder Route
                'mysql:host=localhost;port=3306;dbname=linker',
                'root',
                ''
            );

            //Tolle Funktion zur Generierung zufälliger Zeichen:
            $permitted_chars = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ';
            function generate_string($input, $strength = 4) {
                $input_length = strlen($input);
                $random_string = '';
                for($i = 0; $i load(array('link="'. $link .'"'));
            if ($check->dry()) {
                $g_code = generate_string($permitted_chars);
                $row = new DBSQLMapper($db,'links');
                $row->reset();
                $row->code = $g_code;
                $row->link = $link;
                $row->save();
            } else {
                $g_code = $check->code; //Wenn der Link mehrfach vorkommt, zeigen wir den alten Code an
            }

            $short_link = 'https://'. $_SERVER['HTTP_HOST'] . '/' . $g_code; //Endgültigen Link zusammenstellen

            //Parameter aus $_POST können mit $f3->get('POST') abgerufen werden, die Punktnotation wird unterstützt (bitte korrigieren, wenn ich es falsch nenne): Parameter "link" kann so abgerufen werden: 
            $link = $f3->get('POST.link');

            if (!empty($f3->get('POST'))) { //Geben Sie HTML nur aus, wenn POST nicht leer ist.

            $f3->set('link', $short_link);
            $f3->set('hits', $check->hits);
            $view = new View;
            echo $view->render('newLink.htm');

            } else { //Ansonsten - Weiterleitung zur Hauptseite
                $f3->$f3->reroute('/');
            }

        }
);

Fertig! Tatsächlich war es einfach.

Weiterleitung

Es bleibt nur noch wenig zu tun:

  1. Parameter aus der URL erhalten
  2. Seine Existenz in der DB überprüfen
  3. Den entsprechenden Link aus der DB abrufen
  4. Den Benutzer weiterleiten
  5. Gewinn!

Wir machen mit dem Codieren nach der letzten Route weiter.

$f3->route('GET \/@code', \/\/ Wir geben den Parameter nach "@" an, dieser wird in PARAMS gelangen
    function($f3) {

        \/\/ Wieder definieren wir $db
        $db = new DBSQL(
            'mysql:host=localhost;port=3306;dbname=linker',
            'root',
            ''
        );

        $code = $f3->get('PARAMS.code'); \/\/ Wir erhalten den Parameter

        $link = new DBSQLMapper($db,'links'); 

        \/\/ Falls es gelingt, den Link aus der DB zu erhalten - erhöhen wir die Anzahl der Zugriffe und leiten weiter
        if ($link->load(array('code="'.$code.'"', 'link=?'))) {
            $link->hits++;
            $link->save();

            $f3->reroute($link->link);
        } else {
            $f3->reroute('\/'); \/\/ Wenn es keinen solchen Link gibt - herzlich willkommen auf der Startseite
        }
    }
);

Sie haben vielleicht bemerkt, dass in der Route newLink, und in der oben genannten Route wird dasselbe definiert - schließlich code kann mit "newLink" übereinstimmen (was nicht möglich ist, im Generator sind nur Buchstaben in Großbuchstaben erlaubt), aber da es zuerst definiert wird, wird es auch zuerst ausgeführt.

$f3→run()!

Danke fürs Lesen!
Ich würde mich freuen, wenn Sie einen Kommentar hinterlassen und mich korrigieren, wenn etwas nicht stimmt.

Als Hausaufgabe oder als Beweis für die Faulheit des Autors (meinerseits) hinterlasse ich eine Liste von Dingen, die man tun könnte. Schließlich lernt man am besten durch Praxis!

  • Es ist zwar eher unwahrscheinlich, aber bei der Generierung $g_code kann sich wiederholen, deshalb schlage ich vor, dass Sie eine Funktion schreiben, die dies überprüft.
  • Man kann auch eine ordentliche Statistik erstellen und diese beim Übergang auf /@code/stats
  • Das Erstellen von Links auf den Service selbst zur URL-Verkürzung verbieten, eine Liste von "geschützten" Ressourcen gegen Verkürzung erstellen
  • Ich empfehle dringend, selbst bei so einer kleinen Sache die Eingabevalidierung auch auf der Serverseite vorzunehmen, mit der Ausgabe entsprechender Fehler, man sollte sich nicht nur auf das Hinzufügen des Attributes required und den Typ type="url" zum Eingabefeld verlassen.
    RedComrade

  • Schlage in den Kommentaren vor…

    Bleiben Sie in Verbindung)

Quelle: habr.com

60GB SSD 8Gb DDR4