Maksim Fedorov

Golang Software Developer.

Help for developers  •  Posts on Habr

Ctrl + ↑ Позднее

Роутинг для PSR 7 Response/Request. Часть 1: Обзор

Сухая выжимка из видео Дмитрия Елисеева PSR-7 фреймворк 2/6: Контроллеры и маршрутизация.

Вводные данные

У нас уже есть входная точка для нашего приложения и подключена библиотека для работы с HTTP PSR 7  — в примерах будет Zend Diactoros.

В итоге наш index.php выглядит так:


<\?php

use Zend\Diactoros\Response\HtmlResponse;
use Zend\Diactoros\Response\SapiEmitter;
use Zend\Diactoros\ServerRequestFactory;

chdir(dirname(__DIR__));
require 'vendor/autoload.php';

### Initialization
$request = ServerRequestFactory::fromGlobals();

### Action
$name = $request->getQueryParams()['name'] ?? 'Guest';
$response = new HtmlResponse('Hello, ' . $name . '!');

### Postprocessing
$response = $response->withHeader('X-Developer', 'maksfedorov.ru');

### Sending
$emitter = new SapiEmitter();
$emitter->emit($response);


По коду:

  1. Подключаем фабрику Zend Diactoros, которая конвертирует глобальные переменные в объекты Request и Response
  2. Создаем объект Response и передаем в него значение GET параметра name или строку ’Guest’
  3. Добавляем свой пользовательский заголовок к объекту Response
  4. Отправляем на вывод, добавляя код ответа и тип контента

Первый роутинг

Получим наш пользовательский путь (после исполняющего скрипта, до параметров). На основе этого пути зададим свой объект Response и передадим в каждый соответствующий контент.

Помимо простых путей, мы можем добавить сюда более гибкие пути, например для блога в виде JSON:


<\?php

### Action
$path = $request->getUri()->getPath();

if ($path === '/') {
    $name = $request->getQueryParams()['name'] ?? 'Guest';
    $response = new HtmlResponse('Hello, ' . $name . '!');
} elseif ($path === '/about') {
    $response = new HtmlResponse('I am a simple site');
} else {
    $response = new HtmlResponse('Undefined page', 404);
}

# ...


и его отдельных статей, проверяя путь каждой статьи через регулярное выражение:


<\?php



Это и есть простейший роутинг, но как понимаете — если контент будет сколь заметным или путей будет много — работать с таким кодом будет крайне не удобно.

В самом конце мы разнесем по разным файлам, но пока мы будет делать это постепенно, шаг за шагом показывая, как это будет происходить.

Оптимизация

Чтобы в условиях для каждого роута наши переменные не зассоряли наш эфир и глобальные переменные — поместим этот код в анонимные функции, присвоим их результат переменной $action и после условия выведем результат подходящей условию переменной:

Но у нас появляются неудобства для адресов, которые мы проверяем через регулярку и у нас появляются произвольные параметры. Мы можем передать результат регулярки в качестве параметра в анонимную функцию, но мы не можем точно знать, какие переменные мы можем ожидать.

Но мы можем воспользоваться методом withAttribute() объекта Request, тем самым изменяя сам объект Request, который мы и передаем в анонимную функцию, в итоге выглядет это так:


<\?php



ADR (Action Domain Response)

Action Domain Response — частный и упрощенный случай MVC.

Суть этого подхода для нас — нам нужно сделать систему маршрутизации, при которой в зависимости от разных адресов мы возвращаем нужную анонимную функцию.

Простейший вариант:


<\?php



Но для учета HTTP методов (например для REST API) это будет иметь такой вид:


<\?php



Теперь мы получили представление о том, что нам нужно получить и как это должно работать, в следующей части разберем принцип построения системы маршрутизации перейти к созданию маршрутизации→

Общий принцип оплаты в интернет-магазине через платежную систему (HTTP)

Черновик — есть неточности

Если вам нужно будет организовать оплату на своем сайте и под ваш фреймворк или ЦМС нет готовых решений — его не сложно написать самому.

Общий принцип работы

Все платежные системы работают примерно по одной схеме — у них есть API, который работает в частности через HTTP. При оплате товара магазин отправляет запрос на нужный URL платежки с параметрами заказа.

Нужно несколько параметров, например некий ID заказа, стоимость (price), вспомогательные параметры (например lang(язык), currency (валюта) и т. д...)

Наша цель — редиректить наш заказ на этот адрес, например в контроллере при оплате:

return $this->redirect('https://merchant.ru/payment.aspx?' . http_puild_query([
    'id' => $order->id,
    'price' => $order->price,
]))

Когда сервер платежки получает запрос и пользователь оплачивает — происходят два варианта события: Success или  Fail

Success — значит все отлично и происходит простой редирект назад в магазин.

При регистрации в системе своего проекта мы укзаываем successUrl — именно на него платежка и редиректит, например http://shop.dev/payment/success

Fail — происходит аналогично

URL для проверки заказа

Но при этом есть самый главный URL для взаимодействия — processUrl, этот URL интернет-магазина запрашивается «тайком» платежной системой тогда, когда осуществляется платеж.

Порядок работы:

  1. Оплата → (redirect) → merchant.ru/payment.aspx?id=123&price=1000
  2. Пользователь оплачивает
  3. Когда он нажимает оплатить, платежная система идет с запросом на processUrl, например на /payment/process (GET или POST), передавая параметры — чтобы проверить заказ.
  4. Наш сайт отвечает OK или не OK
  5. Если ОК → платежка списывает с человека деньги, и выводит примерно текст «Перейи на сайт магазина» (которая ведет на successUrl)

Сигнатура

Но если бы такая схема работала, то человек мог подменить к примеру цену, занизив ее, потому передают секретный ключ в параметре signature

https://merchant.ru/payment.aspx?id=123&price=1000&signature=dfg7fh6f54jhfgjh8ол65рро6

Например это мог бы быть некий хэш параметров:

md5($id . ':' . $price);

Но такой можно подменить или разгадать, потому делается чуть сложнее.

Платежки выдают пару ключей:

$password1= 'gfg5fh7677hjf';
$password2= '454545';

Почему нельзя обойтись одним — первый используется при кодировании нашых параметров, то есть
вместо md5($id . ’:’ . $price);
делают md5($id . ’:’ . $price . ’:’ . $password1);

После того как платеж оплачен во время редиректа платежка отправляет в запросе параметр сигнатуры на основе второго пароля, а мы проверяем.

Грубо говоря, через password1 мы подписываем запрос, а на сервере платежки идет проверка, когда платежка отправляет ответ — она подписывает его через password2. Так как данные ключи есть и у клиента и у платежки — это происходит безопасно и удобно.

Как я искал работу на vc.ru и в соцсетях

С самого начала этого года мне пришлось искать работу. Небольшая история, которая может подсказать несколько интересных ходов.

Нетрадиционный поиск — через vc.ru

Сразу после НГ праздников разместил свое резюме на vc.ru, результаты:

  • 6 предложений — 3 из Москвы, 2 из Питера, 1 из Казани и 1 из Новосибирска, еще пару предложений было через месяц и через два,
  • 400 человек смотрели резюме, в среднем смотрели 2,1 страницы и провели 2,28 минуты на сайте — внимательно изучали портфолио и читали некоторые статьи,
  • Просмотры в основном из Москвы (105) и Питера (40)

Скрин на 20 января


На самом деле это успех — такой результат только с одной площадки. В резюме не стал раздувать свой опыт и навыки, зарплата была обоснована и не надута, а еще указал недостатки, что повлияло на ожидания соискателей — не было мусора и пустых вопросов.

Без остроты рассказываю про недостатки

Нетрадиционный поиск — через соцсети

Тут было проще — открыл 2ГИС и пошел по всем веб-студиям и диджитал-агентствам в центре Новосибирска. В основном старался найти руководителей в ВКонтакте или Фейсбуке и списаться с ними для встречи. Писал и звонил очень много, в итоге встретился раз 5, с некоторыми компаниями переписывался долго и в ходе переписке определялись, чем подходим друг другу.

Сообщения старался писать под потребности компании и их вакансии

Вывод:

Соцсети и тематические СМИ — комфортный и удобный канал для поиска работы

Традиционные каналы

Тем не менее, нашел работу через «Зарплата.ру» — это местный агрегатор вакансий, типа «Хедхантера». Еще искал работу по горячим вакансиям. В итоге предложили работу по размещенному резюме, на поднятие которого потратил в районе 400 рублей :)

2017   Работа

Как подписаться на меня

После страшного события в Питере (мои соболезнования родственникам) ожидаю:

  • витка затягивания гаек в интернете
  • затягивания гаек после митингов
  • до этого всего курс был однозначный

Может кто-то и заметил, вчера меня заблокировали в ВК за репост митингов https://maksfedorov.ru/blog/all/vk-zablokiroval-menya-za-repost/
не регулярных, а за одно видео, выложу его и снова заблочат.

Давно намеревался переходить на другие каналы, либо в Фейсбук (друзей мало), либо в блог (тут наоборот больше читателей). Также нужно переползти в сервисы Гугла, либо какие-нибудь немецкие сервисы.

Безопасность одобряю, но прослушку россиян «по умолчанию» со стороны ведомств — считаю как раз дико не безопасным и чреветым утечками данных. Наши дебилы в Госдуме вечно путают причину со следствием.

Я на связи

Связаться со мной можно любым способом, везде читаю и отвечаю — например задать вопрос или предложить работу над проектом:

РСС блога:
https://maksfedorov.ru/blog/rss/

Телеграмм:
https://t.me/@maksfedorov

Фейсбук:
https://www.facebook.com/maksfedorovru

Почта:
hello@maksfedorov.ru

ВК заблокировал за репост видео

UPD: Поддержка ответил, причина — описание на странице видео

Заблокировали за попытку вставить видео на страницу — видео о митинге 26 марта от старика, который не понимает, за что загребли столько молодых людей.

Как было все:

  1. Вставил видео на стену
  2. Меня попросил подтвердить аккаунт и сменить пароль -> обновил и снова добавил видео
  3. Слету прилетел бан на сутки

И даже не скрыли за что:

Написал, чтобы разбанили с возможностью зарепостить видео из Ютуба.

Хочу обратить внимание на «Вы» с большой буквы. Прямо испытываю оргазм от такого Не уважения.

Живые индивидуальные уроки по разработке на PHP

Запускаю живые уроки по программированию на PHP. Объясняю, показываю и тщательно разжевываю реальные практики и все моменты, которые необходимы современному разработчику. Разработка с объяснением, с необходимым именно для вас повторением.

Кому

  • Начинающим разработчикам, которые уже разобрались с синтаксисом, прошли пару курсов, но не могут разобраться без реального кода куда и что делать дальше
  • Тестировщикам, которые хотят подтянуть автоматическое тестирование или программирование
  • Верстальщикам/веб-мастерам, которые хотят повысить свои навыки и уже что-то знают о PHP
  • Почти джуниорам, которым не хватает воедино собрать картину и не хватает практики, чтобы все дособрать для своего портфеля навыков


Формат

Москва

В кафе или у вас дома в вечернее время.

Цена: 800 рублей/час

Сперва (перед какими-либо занятиями) мы встречаемся с вами, собеседуем друг друга. Если для вас нужны специфичные вещи — я подготавливаюсь и мы начинаем работу.

Если для вас дорого — вы можете, например, объединиться с кем-нибудь — вдвоем-втроем, и я буду заниматься с вами разом, но для эффективности нужно будет времени побольше.


Список тем

Индивидуально может корректироваться под вас

  • Локальная взрослая настройка проекта — настройка на Линуксе/Маке с виртуальной машиной или Докером, с максимально приближенной к боевому окружению. Со свежей версией языка PHP
  • Система контроля версий (GIT) — как работают в командах, как работать одному, зачем это нужно и основные практики работы, отточим командную работу
  • Работа с VPS сервером — автоматический деплой на боевой сервер, настройка софта и прочее
  • Работа с пакетным менеджером Composer, автозагрузкой, фишки
  • Изучение библиотек и фреймворков — зачем и почему нужны, какие задачи решают, современные тенденции и практики, подходы
  • Архитектура приложений (не самых сложных по своей схеме, но боевых и распространенных)
  • Базы данных — как работать с данными, как их организовывать, как хранить, как доставать и обслуживать. Как работать со сложными ORM (Doctrine)
  • Как работать с сетью — как отправлять формы, как их проверять, как делать это по-взрослому (как это делают в командах разработчиков)
  • Как сделать свое API и как работать с чужим
  • Объектно-ориентированное программирование — объяснение зачем, на что влияет. Почему появились паттерны, почему выбираются те или иные подходы, и практическое изучение примеров использования
  • В целом будет акцент не на изучение синтаксиса, но по ходу работы если будут запинки — будем дополнительно проходить и разбирать
  • Дебаг и отладка, работа в IDE со сложными проектами
  • Тестирование своего кода / Автоматическое тестирование через браузерные тесты
  • Код ревью и требования к разработке (типизация, инспекции, строгие правила)


Обо мне

Что умею, что смогу донести

  • Сейчас работаю в команде разработчиков в издательстве Conde Nast (журналы Vogue, GQ, Glamour, Tatler) — платформа, состоящая из множества сервисов на языке PHP на фреймворке Symfony.
  • Активно помогаю на Тостере: https://toster.ru/user/Maksclub и еще на паре форумов
  • Руководил интернет-магазином
  • В прошлом предприниматель — один из проектов был успешный нишевой магазинчик

Связаться со мной

Telegram
ВКонтактик

2017  

Поиск налоговой по адресу, версия 2

Сервис поиска налоговой по адресу — будет полезным для юристов и предпринимателей. Помогает быстро найти контакты и реквизиты ИФНС, например для регистрации юрлица, узнать где регистрировать кассовый аппарат... узнать телефон и график работы.

Старый сервис работал только по Москве и Питеру.

О сервисе

  • Ищет налоговую для адреса по всей России (спасибо Dadata.ru) — ищет по всем городам, поселкам и улицам
  • Ищет по почтовому индексу
  • Использует открытые данные ФНС
  • Помогает подсказками при введении адреса

Планы

  • Доработать дизайн (сейчас его просто нет :)
    Прикрутить карты Яндекса, сейчас выводится на карте не налоговая, а введнный адрес — исправлю до 15 апреля
  • Прикрутить MongoDB
  • Сделать легенькое АПИ
  • Исправить тонну ошибок и почистить от мусора
  • Пересадить на React и Express (для опыта ради, сейчас на PHP и JQuery)
  • Сделать новости по налогам и блог

Найдите налоговую по нужному адресу

Прототипы сайтов на Pingendo вместо Axure

Пару дней назад на собеседовании в веб-студии Новосибирска на должность менеджера проектов я получил вопрос:

Как ты делаешь прототипы?

Ответил, что сразу в коде ХТМЛ — мне начали советовать Axure, а я даже и не понял, что было не так — проблем с прототипами и набрасывании эскизов в ХТМЛ у меня никогда не было. Сразу и не сориентировался, ведь использую Pingendo — эта штука позволяет набросать адаптивную страницу за 3-4 минуты и выплевывает чистый кода на Бутстрапе, а я это даже не рассматривал как инструмент для прототипа → сразу делал готовые сверстанные шаблоны для сайта и потом уже допиливал.

Конструктор адаптивных страниц — Pingendo

Pingendo — отдельный браузер, сделанный для ускорения (дикого ускорения) верстки на Бутстрапе, в панели этой программы предусмотрены все компоненты и блоки — просто перетаскиваешь и собираешь из них страницу.

Чувак за 8 минут собирает готовую страницу

Особенности Pingendo

+ Выплевывает готовый ХТМЛ-код, чистый
+ Если проект на Бутстрапе — сразу готовы исходники
+ Все компоненты, блоки, кнопки (да все есть) Бутстрапа в коробке
+ Адаптив — сразу можно просмотреть отображение на мобильном, планшете или ноутбуке
+ Можно добавлять свои классы и внизу в коде писать стили CSS
+ Поддерживает все ОС — я работаю под Линуксом и мне все нравится, под Мак тоже есть
+ Поддерживает LESS — инструмент не просто для прототипов, а для полноценной разработки
+ Уже есть версия с бетой Бутстрапа 4 — разрабы не сидят на месте
+ Обнаружил веб-версию, идет с версией под новый Бутстрап


— Немного мусорит — добавляет лишние блоки для обертки: .section и .container, ставит лишние переносы, устраняется секундами
— Дизайн подчинен сетке Бутстрапа — не подойдет для прототипов мобильных приложений, кабинетов (если не планируется Бутстрап) и специфичных интерфейсов

В общем я остался непонятым на собеседовании, не умеющим делать прототипы, но, сука, классным :)

UPD1: Если есть вопросы по работе с Пингендо — пишите мне в ВК
заметил, что много людей с поиска заходит узнать по работе, а заметку писал чисто дял себя...

Sitemap.xml для блога на Эгее

##UPD (от 11.08.2017):Чуть позже сделаю по лучше

Читал у Ильи Бирмана, что он не понимает зачем его блогу Сайтмап.хмл и в Эгее его никогда не будет. А мне нужен → Гугл и Яндекс указывают на ошибку.

Сайтмап — карта сайта в формате ХМЛ, позволяет поисковым роботам видеть страницы сайта, этакий алфавит.

Использовал возможность Эгеи выводить весь список статей по адресу /all/, сделал скрипт, который парсит все ссылки с этой странице и выводит их в нужном формате.
Итог можно посмотреть по адресу: maksfedorov.ru/sitemap.xml

Инструкция установки

  • Скачайте файл sitemap.php и залейте его в корневую директорию блога
  • Если блог лежит в папке (например blog или notes) — установите значение для переменной $BLOG_URI на 5 строке файла, например если блог лежит в папке blog, то это будет выглядеть так:
$BLOG_URI = 'blog';
  • Если ваш блог не в папке, а открывается как полноценный сайт, то оставьте строку пустой
  • Отредактируйте файл .htaccess в корне блога — вставьте сразу на следующей строке после RewriteEngine On эти строки:
# Google sitemap
RewriteRule sitemap.xml?$	sitemap.php  [L,QSA]

Теперь ваша карта сайта доступна по адресу:
ваш_сайт_точка_ру/sitemap.xml

Красивый репост статьи на Эгее

Запилил доработку для Эгеи, которая генерирует для Фейсбука, ВКонтакте и Твиттера картинку с заголовком поста, а-ля Meduza. Стандартный вывод работает уныло, если в посте нет картинок, то выводит юзерпик — вашу фотку возле названия блога.

Скрипт очень сырой, выкатил пока для теста. Можно настроить:
— фон — можно самому сделать свой шаблон
— шрифт, задать размер, цвет и положение
— свой заголовок (по умолчанию берет название блога) и юзерпик (лого)

Пример в стиле Медузы:

В планах:
— возможность управлять шрифтами (сейчас задается один для названия и заголовка поста)
— сделать генерацию изображений из поста с логотипом и надписью заголовка
— сделать веб-морду
— запилить что-то вроде базы данных, чтобы можно было в будущем менять изображения
— на основе пункта выше сделать возможность в редактирвоании поста выбирать шаблоны изображения и сохранять

Ctrl + ↓ Ранее