TGViewer
Channel Public Channel
Red Collar | DEV

Red Collar | DEV

@rdclr_dev

Про разработку от команды Red Collar
redcollar.ru

Основной канал Red Collar @rdclr_home
Subscribers
962
Photos
234
Videos
11
Links
129

Showing posts older than #54 · Back to latest

Older Posts 19 shown
Post #53 267
Сервис, где методы будут помечены созданными аннотациями LogSomething и CheckFileAccess

#rdclr_backend #java
Post #52 290
Аспект для логирования сигнатуры метода. Связан через аннотацию CheckFileAccess (написана вручную, в ней тоже нет ничего особенного)

#rdclr_backend #java
Post #51 261
Аспект для логирования сигнатуры метода. Связан через аннотацию LogSomething (написана вручную, в ней нет ничего особенного)

#rdclr_backend #java
Post #50 280
АОП. Аспектно-ориентированное программирование

Всем привет! С вами снова Андрей, java-разработчик. Мы продолжим говорить об экосистеме java и смежных вещах. Сегодня затронем АОП. Тема очень обширная, поэтому в этой мини-статье заденем минимальные основы.

В рамках Spring-фреймворка АОП является некой сквозной логикой, которую мы можем использовать в любом месте приложения, всего навсего повесив аннотацию (или с помощью xml-разметки). Также этот механизм используется почти во всех модулях фреймворка Spring, являясь фундаментом для построения более сложных механизмов.

Пару недель назад мы уже краем касались этой темы, когда рассматривали self-inject’ы и Transactional-аннотацию. Под этой аннотацией, как и под многими другими, как раз таки и скрывается механизм аспектно-ориентированного программирования.

Зачем нам нужно АОП? Данный функционал хорошо себя показывает в задачах, связанных с логированием или предоставлением доступов к каким-либо ресурсам. Чтобы не дублировать код наших логов по всему проекту, мы можем вынести это в одно место и вызывать (с помощью аспектов) перед выполнением метода или после. В случае предоставления доступов бывают ситуации, когда нам нужно проверить доступ к ресурсам исходя не только из токена (или любого другого ключа) пользователя, а из данных, которые находятся, например, в базе данных. Есть ли у пользователя X доступ к скачиванию этой фотографии или архива с документами?

Давайте попробуем разобраться на простом примере (примеры будут сразу в следующих постах). Для начала, в pom.xml, вы должны иметь следующие зависимости: spring-boot-starter-web, spring-boot-starter-aop. Это минимальный набор, чтобы начать изучать spring aop. Рассмотрим самописные аспекты по логированию какой-то информации сигнатуре метода и по доступу к файлу.

#rdclr_backend #java
Telegram RDCLR.DEV Ловушка @Transactional или использование Self-inject’ов В бине имеется 2 метода: a() и b(), помеченных аннотацией @Transactional. Если мы из метода а() вызовем метод b() — как поведет себя транзакция метода b()? Правильный ответ — транзакция метода b() не…
Post #49 274
Всем привет! Наступил декабрь, а это значит, что скоро Новый год. В преддверии этого праздника на просторах интернета часто появляются различные мини-игры, акции, забавные дудлы и тому подобное.

К счастью для нас, сфера разработки не исключение. Уже не первый год энтузиаст Eric Wastl разрабатывает адвент-календарь, суть которого в решении серии небольших программных головоломок различного уровня сложности. Каждый день, начиная с 1 декабря и заканчивая Новым годом, вам предоставляется новая задача, которую вы можете решить на вашем любимом языке программирования. Само собой начальные задачи не представляют какой-либо сложности и решаются довольно просто, но чем ближе 31 декабря, тем всё больше усилий от вас будет требовать этот мини-квест.

Предлагаю вам проверить свои силы и присоединиться к этому чиловому соревнованию!
Ссылка на календарь: https://adventofcode.com/

#read
Post #48 332
Генерация клиента из OpenAPI

Если ваш бэкенд использует Swagger (OpenApi 3.0) для генерации документации, то вы можете знатно упростить себе жизнь на крупном проекте.
Однако это упрощение идет дальше типичного чтения документации. Прямо сейчас вы можете генерировать Клиент, Сервер и Типы данных для TypeScript из файла openapi schema.

🎁 Пакет для генерации Клиента: https://github.com/OpenAPITools/openapi-generator-cli

Установка:
yarn add @openapitools/openapi-generator-cli
либо
npm install @openapitools/openapi-generator-cli

1️⃣ Предварительно создайте папку для результатов генерации и файл конфигурации.

2️⃣ После установки вам нужно создать файл конфигурации openapitools.json для генератора и папку для хранения результатов
openapitools.json:
{
"$schema": "node_modules/@openapitools/openapi-generator-cli/config.schema.json",
"spaces": 2,
"generator-cli": {
"version": "5.1.1",
"generators": {
"v1": {
"generatorName": "typescript-fetch",
"inputSpec": "link_or_path_to_yours_openapi_schema",
"output": "path_to_yours_output",
"additionalProperties": {
"supportsES6": true,
"sagasAndRecords": true,
"typescriptThreePlus": true,
"withInterfaces": true,
"withoutRuntimeChecks": false
}
}
}
}
}


```3️⃣ Затем запустите процесс генерации командой:
```yarn openapi-generator-cli generate

4️⃣ В результате мы получим:
generated-api/models — здесь хранятся типы данных и функции для трансформации данных бэк->фронт фронт->бэк
generated-api/apis — здесь вы найдете сгрупированные по эндпоинтам классы для запросов к API

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

🦷 Если вам необходимы только типы для TypeScript, может подойти пакет: https://github.com/drwpow/openapi-typescript

Полный список генераторов вы найдёте здесь: https://openapi-generator.tech/docs/generators

#rdclr_frontend #React #product #read #library
Post #47 283
#meme
Post #46 284
Суть в том, что существует «старый добрый» способ описания хранилища состояний при помощи обычного react-redux.
Проблема старого способа в том, что приходилось писать очень много шаблонного кода (на жаргоне — бойлерплейта).
За это его постоянно ругали разработчики всех мастей.

Но затем вышел Redux Toolkit, который создан специально для решения данной проблемы.
Мы можем создавать все те же хранилища состояний, но при этом писать гораздо меньше кода, по сравнению с react-redux.

Однако реалии таковы, что это все же новый инструмент со своими нюансами, поэтому редко кто-то перепрыгивает
с react-redux на ReduxToolKit прямо на ходу.

#rdclr_frontend #React #product #read #library #redux
Post #45 274
Redux Toolkit createSlice — функция, которая помогает писать редьюсеры проще

Предлагаю взглянуть на демо крохотного приложения с использованием createSlice:
https://codesandbox.io/s/todo-list-logger-jwzwb?file=/src/index.tsx

Слева мы можем добавлять/удалять записи.
Справа отображается лог наших действий.

Вся логика реализована через 2 слайса:
contactsSlice https://codesandbox.io/s/todo-list-logger-jwzwb?file=/src/store/features/contactsSlice.ts
loggerSlice https://codesandbox.io/s/todo-list-logger-jwzwb?file=/src/store/features/loggerSlice.ts

Для создания слайса мы указываем название, начальное состояние и редьюсеры:
export const someSlice = createSlice({
name,
initialState,
reducers,
});

Кроме того, мы можем указать extraReducers, что бы «ловить» действия от других слайсов. см. loggerSlice

Как вы могли заметить, при описании редьюсеров мы «мутируем состояние». Но на самом деле это не так.
Redux Toolkit использует под капотом Immer (https://immerjs.github.io/immer/).
Который в свою очередь отслеживает все мутации, а затем возвращает новое (не мутированное) состояние.

Например, вот редьюсер без Immer:
function handwrittenReducer(state, action) {
return {
...state,
first: {
...state.first,
second: {
...state.first.second,
[action.someId]: {
...state.first.second[action.someId],
fourth: action.someValue
}
}
}
}
}


А вот с использованием Immer:
function reducerWithImmer(state, action) {
state.first.second[action.someId].fourth = action.someValue
}


Как я и сказал, это позволяет писать редьюсеры проще.

Любые вопросы и критика приветствуется.
Как вы реализовали бы функцию отмены конкретного действия в логгере (см. демо)?

#rdclr_frontend #React #product #read #library #redux
CodeSandbox todo-list-logger - CodeSandbox todo-list-logger by gormonn using @reduxjs/toolkit, @types/faker, @types/object-hash, @types/react-redux, @types/styled-components, faker, localforage, object-hash, react
Post #44 258
RTKQuery, как инструмент общения с API

На одном из проектов используем именно его. Плюсы:
- является частью Redux Toolkit — который мы уже используем для хранилища;
- поддержка React Native — хороший задел на будущее;
- генерация React hooks — буквально вчера вышел в релиз кодогенератор v1.0 см документацию (https://redux-toolkit.js.org/rtk-query/usage/code-generation);
- полная поддержка Typescript;
- отслеживание статуса запросов — плюс не нужно писать мидлвары для асинхронных запросов;
- возможность преобразования полученных ответов;
- встроенный кэш: по-умолчанию данные хранятся в памяти, пока на него существует подписка, например, при анмаунте компонента кэш очистится спустя минуту;
- система инвалидации кэша: мы можем связать различные эндпоинты между собой, чтобы при PATCH/POST запросе автоматически происходил refetch (например, постим в список — список обновляется);
- и многое другое.

Почитать обзорный материал можно тут: https://redux-toolkit.js.org/rtk-query/overview

#rdclr_frontend #React #product #read #library
redux-toolkit.js.org Code Generation | Redux Toolkit RTK Query > Usage > Code Generation: automated creation of API code
Post #43 250
Всем привет! Меня зовут Дима, я фронтенд-разработчик. Пишу в основном на React. И на этой неделе хочу поделиться инструментами, которые помогают мне в работе.
Post #42 337
#meme
Post #41 329
Focus trapping при помощи атрибута inert
Post #40 300
Как достичь корректной работы приложения с клавиатуры

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

Пример плохой разметки: кнопка закрытия поп-апа сделана ссылкой, которая никуда не ведет. Нет никаких причин использовать ссылку вместо кнопки, если не осуществляется навигация.

Да, в современных интерфейсах часто встречаются сложные объекты для ввода (дейт-пикеры, мульти-селекты etc.), которые нельзя полностью реализовать нативными средствами. В этом случае вам следует позаботиться о том, чтобы элементы «не проваливались» при работе с клавиатуры.

📸 2. Обрабатывайте состояние focus с помощью css и javascript. Опишите стилистические правила для состояний focus, disabled и проч., как именно это будет реализовано — с помощью outline, box-shadow или иными средствами — не важно. Для простых элементов этого будет достаточно.

В отдельных случаях (например, чтобы показать выпадающее меню) обрабатывайте события focus и blur при помощи javascript.

📇 3. Следите за порядком элементов в DOM или определяйте порядок, в котором элементы будут перебираться при помощи Tab, используя атрибут taborder.

🥅 4. Для фокус-менеджмента применяйте стратегию focus trapping. В общем виде это может выглядеть так: на странице есть поп-ап, фокус на нем должен быть заблокирован. При его открытии делаем наоборот: элементы вне поп-апа должны быть заблокированы для фокуса, а сам поп-ап разблокирован.

Иногда для этого приходится написать много кода, который будет обрабатывать focusable-элементы в поп-апе и за его пределами. Решением этой проблемы может стать атрибут inert, позволяющий выключать видимость элементов для скринридеров и блокировать фокусировку на них. На сегодняшний день это поддерживается не везде, но вы можете использовать Inert Polyfill или реализовать нечто похожее самостоятельно.

#rdclr_frontend
Post #39 259
Focus on me: навигация с клавиатуры

Попробуйте интереса ради зайти на парочку популярных сайтов (особенно в зоне рунета) со своего лэптопа и посёрфить по ним без мыши или тачпада. Уверен, вы не раз окажетесь в затруднительном положении. 😁

🔦 Любой интерактивный элемент в интерфейсе, будь то кнопка, ссылка или поле для ввода, должен реагировать на фокус. То есть, во-первых, он должен так или иначе «подсвечиваться» при получении фокуса (когда вы нажимаете Tab или Shift+Tab).

⌨ Во-вторых, он должен реагировать на нажатие Enter и Space точно так же, как если бы вы кликнули по нему (и не должен, если имеет состояние disabled). А если предусмотрено какое-то поведение при наведении на элемент, то и оно должно воспроизводиться: либо при получении фокуса, либо при нажатии на Enter и Space, когда элемент получил фокус.

📇 В-третьих, важно, чтобы порядок переключения фокуса отражал порядок, в котором мы видим интерактивные элементы на экране. Кроме того, на странице могут быть скрытые слои (temporality offscreen): дропдаун-меню, поп-апы, модальные окна и проч., – и в них часто бывают интерактивные (focusable) элементы. До тех пор, пока элемент скрыт, он не должен получать фокус при навигации с клавиатуры.

📸 В-четвертых, сбрасывайте состояние фокуса в SPA-приложениях после перехода по ссылкам. При навигации по разделам SPA-сайта, предыдущее состояние фокуса может не измениться, если активный элемент не был перерисован. В результате, после перехода в новый раздел, скринридер продолжит воспроизводить контент с того места, на котором остановился. Нужно «перебросить» фокус в начало документа, то есть на первый focusable-элемент на странице.

#rdclr_frontend
Post #36 265
Семантические элементы в доступности интерфейсов

К сожалению, сегодня по-прежнему приходится говорить об очевидных вещах вроде: «Используйте семантическую разметку», «Не забывайте альтернативные тексты для картинок» и все в таком духе. Спецификация HTML5 вышла 7 лет назад, но ряд разработчиков в своем коде до сих пор не применяют или применяют неверно теги header, nav, section, main и т. д.

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

🌳Дерево доступности
Современные браузеры наряду с DOM-моделью создают на ее основе так называемое дерево доступности (accessibility tree, AOM), которое будет содержать информацию о «доступности» элемента: у каждого объекта будет имя, описание, роль и состояние. Затем браузер предоставляет эту модель вспомогательным программам, например, скринридерам.

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

👨‍💻Пример дерева доступности
Продемонстрирую на маленьком сэмпле html-кода, как браузер строит дерево доступности: перед нами обычная группа радио-кнопок в форме (для примера будет форма оплаты), все элементы нативные и имеют текстовые ноды, поэтому браузер может построить дерево в котором будет выделена группа, ее название, члены группы, при этом он видит, что внутри label’ов есть radiobutton’ы, а значит это интерактивные элементы, имеющие свои состояния.

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

#rdclr_frontend
Post #35 282
Инклюзивность и доступность веб-интерфейсов

Даже если ваше приложение не адресовано широкой аудитории, и вы на все сто уверены, что им не будут пользоваться люди с ограниченными возможностями, стоит помнить, что «доступность» не замыкается на понятие «инклюзивность». Если сайтом невозможно пользоваться при помощи клавиатуры, а мобильным приложением одной свободной рукой, то их доступность снижается для всех категорий пользователей.

Кроме того, важно понимать, что ограниченные возможности бывают ситуативными. Представим такие обстоятельства: вы оформляете авиабилет и вдруг у вас сел аккумулятор в мыши. Вы бы хотели продолжить с клавиатуры и все-таки закончить оформление? Или в отпуске вы катались на сноуборде, а домой вернулись с гипсом на руке, и на ближайшие пару месяцев использование мыши будет невозможно или затруднено.

Как добиться повышения доступности интерфейса

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

В результате такого опыта и возникают стереотипы, что для создания доступного интерфейса вам, как разработчику, придется выбирать: реализовать стильный и удобный интерфейс таким, как задумал его дизайнер, или сделать нечто уродливое, не сильно удобное, но при этом отвечающее требованиям доступности. К счастью, это не так, и повышать доступность интерфейса можно, почти не прибегая к изменениям его внешнего вида.

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

#rdclr_frontend
Post #34 271
Привет, меня зовут Артем, я frontend-разработчик компании Red Collar, и на этой неделе предлагаю немного поговорить о концепциях доступности веб-интерфейсов. Расскажу, почему это важно для проекта, а также с чего начать погружение в эту сложную и многогранную тему.

#rdclr_frontend
Older posts →
Threads Profile ViewerView any public Threads profile without an account.Open ThreadLook →Writing with AI? Make it sound human.Metric37 rewrites AI drafts so they read naturally. Free AI detector, 1,500 words free.Try Metric37 →