
Zkracování odkazů ve 13 letech není ostudné, že? Nováček, a nejen on, by měl zkusit napsat svého Ovladače Odkazů, přitom studovat nějaký nový framework. A tím jsem se zabýval. Co říct — pátý bootstrap, odlehčený framework a kousek duše.
Tady , a to je . Pro takové čtenáře, jako jsem já 😉
Framework, že?
Samozřejmě ne Laravel a podobné — dnes se obejdeme s 65 kilobajty. . Pokud znáte Python Flask, budete mít pocit, že tohle už jste někde viděli:
#роутинг во Фласке
@app.route('/')
def hello_world():
return 'Hello, World!'
//роутинг в Обезжиренном
$f3->route('GET /',
function() {
echo 'Hello, world!';
}
);Dobře, zapomeňte. Stahujeme , rozbalíme do složky, která se v ten samý okamžik otevře ve vašem Oblíbeném Editoru Kódu. Vymažte index.php a odstraňte všechno z /ui.
Zde je všechno maximálně jednoduché — ve složce ui máme všechny pohledy, a pokud to zjednodušíme — vylepšené HTML šablony, které ukážeme uživateli při návštěvě určitého URL.
Tady je kostra naší "aplikace":
set('DEBUG', 1);
if ((float)PCRE_VERSIONconfig('config.ini');
// VŠECHEN OSTATNÍ KÓD BUDEME PSÁT ZDE
$f3->run();A to je vše, co potřebujete vědět na začátek. Začněme s programováním!
[pro vývoj jsem použil místní na Windows a VS Code, ]
Homepage
Začneme s hlavní stránkou. Logické, že?
//Файл: index.php
$f3->route('GET /',
function($f3) { //чтобы использовать функции F3 передаем его в роут
$view = new View; // создаем вьюшку
echo $view->render('home.htm'); //рендерим шаблон
}
);Teď je potřeba napsat tuto šablonu. Pro zjednodušení jsem použil
Nezapomeňte vytvářet všechny šablony ve složce ui, jinak nebudou viditelné pro framework. Tady je to — už máme funkční hlavní stránku. Formulář odesílá POST požadavek na odkaz, který je třeba zkrátit.
<!-- Файл: 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>Píšeme (kód), zkracujeme (linky)!</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="#">Hlavní stránka</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Článek na Habr</a>
</li>
<li class="nav-item">
<a class="nav-link" href="https://nikonovs.ru">Tvůrce</a>
</li>
</ul>
</nav>
<div class="container">
<h1>Krátké odkazy jsou již zde.</h1>
<!-- Будем отправлять данные POST-запросом на /newLink -->
<form class="mt-5 mb-3" action="/cs/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">Zadej odkaz:</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">Zkrátit!</button>
</div>
</div>
<input type="hidden" name="trp-form-language" value="cs"/></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">Vyrobeno s <img width="20" height="20" src="https://image.flaticon.com/icons/svg/833/833472.svg" alt="láskou">, <a href="https://v5.getbootstrap.com/">pátým Bootstrapem</a> a <a href="https://fatfreeframework.com/">bez tuku</a></footer>
</div>
</body>
</html>Nyní je na řadě to nejzajímavější (ne).
Práce s DB
Práce s DB
Vytvořme DB — MySQL. Pokud máte nainstalovaný PhpMyAdmin, vytvořte novou DB "linker", a pak proveďte tento SQL:
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`);Každý odkaz bude mít 3 pole:
- Code — to jsou náhodné 4 znaky za doménou, podle kterých bude probíhat přesměrování, typu example.com/ABC1
- Link — Nezkrácený odkaz.
- Hits — počet přechodů po zkráceném odkazu.
Krátce vám povím o principu práce s DB, bez zbytečného balastu.
set('result', $db->exec('SELECT * FROM wherever'));
// budou dostupné v šablonách, jako
// A můžete využít vestavěný SQL Mapper:
$row = new DBSQLMapper($db, 'links');
$row->load(array('link="https://habrahabr.ru"')); // nyní jsou z tohoto objektu dostupné všechny sloupce řádku, kde je odkaz na Habr:
$row_value = $row->somerow; // Takto
// Samozřejmě, že můžete měnit hodnoty:
$row->link = 'https://habr.com';
$row->save(); // změny je potřeba uložit, co jste mysleli
// více informací o práci s DB je k dispozici zde: https://a.nikonovs.ru/MPHR Důrazně doporučuji přečíst, alespoň s pomocí překladače, který je zabudován v prohlížeči.
?>Přejděme k zkracování.
Zpracování nového odkazu
Vytváříme nový pohled v indexu, který bude zpracovávat dotaz z formuláře na hlavní stránce.
Nejprve vytvoříme nový, ale velmi podobný prvnímu (home.htm) šablonu — "newLink.htm".
Tam budeme zobrazovat již zkrácený odkaz a počet přístupů k němu (abyste mohli znovu vidět tuto "statistiku", musíte znovu zkrátit stejný odkaz — adresa zůstane stejná).
Pro zobrazení využijeme trik s "přenosem proměnných":
set('link', $shorted_link);
$view = new View;
echo $view->render('newLink.htm');
// nyní v šabloně můžete použít:A tady je výpis 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>Píšeme (kód), zkracujeme (linky)!</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="/cs/">Hlavní stránka</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Článek na Habr</a>
</li>
<li class="nav-item">
<a class="nav-link" href="https://nikonovs.ru">Tvůrce</a>
</li>
</ul>
</nav>
<div class="container">
<h1>Krátké odkazy jsou již zde.</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">Zkrátili:</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">Přes tento odkaz přešli: ``</p>
<input type="hidden" name="trp-form-language" value="cs"/></form>
<a href="/cs/" class="mt-3 mb-5 btn btn-primary btn-lg">VRÁTIT SE NA HLAVNÍ STRÁNKU</a>
<footer class="m-2">Vyrobeno s <img width="20" height="20" src="https://image.flaticon.com/icons/svg/833/833472.svg" alt="láskou">, <a href="https://v5.getbootstrap.com/">pátým Bootstrapem</a> a <a href="https://fatfreeframework.com/">bez tuku</a></footer>
</div>
</body>
</html>Píšeme samotnou trasu.
$f3->route('GET|POST /newLink', // budeme zpracovávat jak POST, tak GET
function($f3) {
$db = new DBSQL( // Připojení k DB nové v každém Routu
'mysql:host=localhost;port=3306;dbname=linker',
'root',
''
);
// skvělá funkce pro generaci náhodných symbolů:
$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; // pokud se odkaz opakuje, ukážeme starý kód
}
$short_link = 'https://'. $_SERVER['HTTP_HOST'] . '/' . $g_code; // skládáme konečný odkaz
// parametry z $_POST lze získat pomocí $f3->get('POST'), podporována je tečková notace (opravte mě, pokud to nazývám špatně): parametr "link" lze získat takto:
$link = $f3->get('POST.link');
if ( !empty($f3->get('POST')) ) { // Vydáváme HTML, pouze pokud není POST prázdný.
$f3->set('link', $short_link);
$f3->set('hits', $check->hits);
$view = new View;
echo $view->render('newLink.htm');
} else { // jinak - přesměrování na hlavní stránku
$f3->$f3->reroute('/');
}
}
);Hotovo! Opravdu to bylo jednoduché.
Přesměrování
Zbytek práce je jednoduchý:
- Získat parametr z URL
- Zkontrolovat jeho přítomnost v DB
- Získat odpovídající odkaz z DB
- Přesměrovat uživatele
- Zisk!
Pokračujeme ve psaní kódu po posledním Routu.
$f3->route('GET \/@code', \/\/určujeme parametr po "@", on se dostane do PARAMS
function($f3) {
\/\/znovu definujeme $db
$db = new DBSQL(
'mysql:host=localhost;port=3306;dbname=linker',
'root',
''
);
$code = $f3->get('PARAMS.code'); \/\/dostaneme parametr
$link = new DBSQLMapper($db,'links');
\/\/pokud se podaří získat odkaz z DB - získáme, zvýšíme počet přístupů a přesměrujeme
if ($link->load(array('code="'.$code.'"', 'link=?'))) {
$link->hits++;
$link->save();
$f3->reroute($link->link);
} else {
$f3->reroute('\/'); \/\/a pokud takový odkaz neexistuje - srdečně vás zveme na hlavní stránku
}
}
);Měli jste možnost si všimnout, že v a v routě newLink, a v předchozí routě se definuje stejné - vždyť může se shodnout s "newLink" (nemůže, v generátoru jsou pouze písmena velkého písmene), ale protože je nejprve definován on, tak se vykoná jako první.
$f3→run()!
Děkujeme za přečtení!
Budu rád, pokud napíšete komentář a opravíte mě, pokud je něco špatně.
A jako domácí úkol nebo důkaz lenosti autora (mě) zanechávám seznam, co lze udělat. Vždyť je lepší se učit na praxi!
- To je samozřejmě málo pravděpodobné, ale při generaci $g_code se může opakovat, takže navrhuji napsat funkci, která to zkontroluje.
- Ještě lze udělat pořádnou statistiku a zobrazit ji při přístupu na /@code/stats
- Zakázat vytvářet odkazy na samotnou službu zkracování odkazů, vytvořit seznam "chráněných" zdrojů před zkracováním
Důrazně doporučuji i v tak malé záležitosti provádět validaci vstupu i na straně serveru, s výstupem odpovídajících chyb, není dobré spoléhat se na přidání atributu required a typu type="url" k poli vstupu
Navrhněte v komentářích…
Na spojení)
Zdroj: habr.com
