
Если вы регулярно пишете приложения на Angular и потратили на это не одну сотню часов, вы, скорее всего, знаете об этих функциях. Но, всё же, чтобы убедиться — прочтите :)
Прежде чем мы перейдем к функциям Angular, стоит упомянуть один очень полезный инструмент. Bit (Github) позволяет с легкостью работать над Angular-компонентами вместе и делиться ими. От души рекомендую его для поддержания консистентного интерфейса, ускорения разработки и минимизации количества ошибок в коде.

Пример: Круговые загрузчики для Angular с bit.dev
1. Title
Тег title — это HTML-элемент, определяющий заголовок веб-страницы. Заголовки отображаются на странице результатов поиска (SERP) в виде кликабельного заглавия результата. Они очень важны для юзабилити, SEO и продвижения в соц. сетях.
Приложения на Angular берут заголовок из тега ... в index.html. По умолчанию, переход между компонентами в Angular этот заголовок не меняет.
Знаете ли вы, что заголовок можно задать отдельно из каждого компонента?
В Angular есть сервис Title в angular/platform-browser. Можно легко внедрить его в другие компоненты и использовать метод setTitle, чтобы переопределить заголовок.
import { Title } from "@angular/platform-browser"@Component({ ... }) export class LoginComponent implements OnInit { constructor(private title: Title) {} ngOnInit() { title.setTitle("Login") } }
При переходе к LoginComponent в приложении, заголовок окна браузера изменится на “Login”.
То же самое можно сделать в любом компоненте и, соответственно, по мере навигации внутри приложения заголовок будет меняться, реагируя на действия пользователя.
2. Meta
Метатеги Angular-приложения тоже берут из файла index.html. А чтобы задавать их из компонентов, пригодится сервис Meta из angular/platform-browser.
И снова: применение метатегов полезно с точки зрения SEO и продвижения страницы в соц. сетях, они содержат информацию о веб-странице, которая используется поисковыми системами для правильного ранжирования и корректного отображения в результатах поиска.
Чтобы использовать компонент метатегов, импортируйте Meta из angular/platform-browser и внедрите в нужный компонент.
import { Meta } from "@angular/platform-browser"@Component({ ... }) export class BlogComponent implements OnInit { constructor(private meta: Meta) {} ngOnInit() { meta.updateTag({name: "title", content: ""}) meta.updateTag({name: "description", content: "Lorem ipsum dolor"}) meta.updateTag({name: "image", content: "./assets/blog-image.jpg"}) meta.updateTag({name: "site", content: "My Site"}) } }
Теперь BlogComponent сможет корректно отображаться в Twitter, Facebook и т.д. При этом выводя описания, заголовки и изображения в правильном, читабельном виде.
Об это тоже слышали? Тогда вот кое-что поинтереснее.
3. Переопределение интерполяции шаблонов
Стандартный интерполятор в шаблонах — {{}}. Если вписать переменную между {{ и }}, её значение отобразится в итоговом DOM.
Знаете ли вы, что есть возможность переопределить стандартные разделители инкапсуляции на какие угодно символы? Это просто. Необходимо лишь указать новые значения в свойстве интерполяции в декораторе Component.
@Component({ interpolation: ["((","))"] }) export class AppComponent {}
Интерполяция используемая в шаблоне AppComponent изменилась на (()), а {{}} больше не работает.
@Component({ template: ` <div> ((data)) </div> `, interpolation: ["((","))"] }) export class AppComponent { data: any = "dataVar" }
В браузере вы увидите, что строка «dataVar» будет отображена на месте ((data)).
4. Location
Мы можем получить текущий URL страницы, открытой в браузере, используя сервис Location. В зависимости от того, какой LocationStrategy используется, Location будет сохраняться либо по пути в URL (/example/page/), либо по части URL после решётки (#test/page/).
С помощью Location мы можем перейти к URL-адресу, перейти вперед в истории, вернуться назад, изменить текущий URL-адрес, или заменить верхний элемент в истории.
Здесь поможет сервис Location из CommonModule.
import { Location } from "@angular/common"@Component({ ... }) export class AppComponent { constructor(private location: Location) {} navigateTo(url) { this.location.go(url) } goBack() { location.back() } goForward() { location.forward() } }
5. Document
Иногда необходимо получить модель документа, чтобы производить операции с DOM прямо из Angular приложения.
DOCUMENT как раз и служит этой цели. DOCUMENT — это DI-токен, представляющий основной контекст рендеринга. В браузере это DOM Document. Он обеспечивает операции с DOM независимо от среды выполнения.
Примечание: Document может быть недоступен в Application Context, если контексты Application и Rendering не совпадают (например, при запуске приложения в Web Worker).
Допустим, у нас есть какой-то HTML элемент:
<canvas id="canvas"></canvas>
Чтобы получить canvas HTMLElement внедряем DOCUMENT:
@Component({}) export class CanvasElement { constructor(@Inject(DOCUMENT) _doc: Document) {} }
Получаем HTMLElement canvas используя getElementById()
@Component({}) export class CanvasElement { constructor(@Inject(DOCUMENT) _doc: Document) {} renderCanvas() { this._doc.getElementById("canvas") } }
Предупреждение: используйте DOCUMENT осторожно! Взаимодействие с DOM напрямую опасно и увеличивает риск XSS.
6. Декоратор @Attribute
В основном, в Angular приложении, используют декораторы Component, Module и Directive.
Однако, ещё есть декоратор Attribute, позволяющий передавать статическую строку без лишних затрат производительности, минуя проверку изменений.
Значения декоратора Attribute проверяются только один раз. Используется аналогично декоратору Input:
@Component({ ... }) export class BlogComponent { constructor(@Attribute("type") private type: string ) {} }
7. HttpInterceptor
HttpInterceptor — очень мощная функция в Angular, позволяющая перехватывать запросы HttpRequest и обрабатывать их.
Большинство перехватчиков преобразуют исходящий запрос, прежде чем передать его следующему перехватчику в цепочке, вызывая next.handle(transformedReq).
В редких случаях, перехватчики могут полностью обработать запрос самостоятельно, а не делегировать оставшуюся часть цепочки дальше. Такое поведение разрешено.
HttpInterceptor чаще всего используется в:
- Аутентификации
- Кэшировании
- Fake backend
- Трансформации URL
- Подмене заголовков
Для использования этого перехватчика, необходимо создать сервис и реализовать интерфейс HttpInterceptor.
@Injectable() export class MockBackendInterceptor implements HttpInterceptor { constructor() {} intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> { ... } }
Вставляем его в основной модуль:
@NgModule({ ... providers: [ { provide: HTTP_INTERCEPTORS, useClass: MockBackendInterceptor, multi: true } ] ... }) export class AppModule {}
8. AppInitializer
Иногда, при запуске Angular-приложения, необходимо инициализировать какой-либо конкретный фрагмент кода. Например, загрузить настройки, загрузить кэш, загрузить какие-либо конфигурации или произвести проверки. Токен AppInitialzer создан специально для этого.
APP_INITIALIZER: функция, исполняемая сразу же по факту запуска приложения.
Допустим, нам нужно запускать некую функцию runSettings при старте Angular-приложения:
function runSettingsOnInit() { ... }
Для этого перейдем к основному модулю AppModule и добавим её в раздел провайдеров декоратора NgModule:
@NgModule({ providers: [ { provide: APP_INITIALIZER, useFactory: runSettingsOnInit } ] })
9. Bootstrap Listener
По аналогии с AppInitialzer, в Angular есть функция позволяющая отслеживать загрузку какого-либо компонента. Это APP_BOOTSTRAP_LISTENER.
Все коллбеки, возвращаемые этим токеном, будут вызываться для каждого загружаемого компонента.
Применить эту функцию отслеживания начальной загрузки компонентов можно во многих случаях. Например, модуль Router использует её для уничтожения и создания компонентов на основе навигации по маршруту.
Для использования APP_BOOTSTRAP_LISTENER, необходимо добавить его в раздел провайдеров в AppModule с функцией обратного вызова:
@NgModule({ { provide: APP_BOOTSTRAP_LISTENER, multi: true, useExisting: runOnBootstrap } ... }) export class AppModule {}
10. NgPlural
Плюрализация — головная боль программистов. Задача грамматической корректировки словоформ в зависимости от употребления единственного / множественного числа возникает постоянно. Некоторые сайты просто используют для этого окончание (s). Например:
1 component(s) removed 3 component(s) removed
То есть читатель сам должен понять, какое число подразумевается :)
Angular предлагает решить эту проблему более цивилизованно, с помощью директивы NgPlural.
NgPlural добавляет или удаляет подветви DOM на основании числового значения. Для плюрализации — то, что нужно.
Чтобы использовать эту директиву необходимо задать атрибут [ngPlural] контейнеру элемента в виде выражения-переключателя. Внутренние элементы с атрибутом [ngPluralCase] отобразятся в зависимости от заданных условий:
<p [ngPlural]="components"> <ng-template ngPluralCase="=1">1 component removed</ng-template> <ng-template ngPluralCase=">1">{{components}} components removed </ng-template> </p>
Теперь можно выбросить “(s)”. Директива NgPlural поможет вывести правильную словоформу в зависимости от значения. Итог:
// if 1 component 1 component removed // if 5 components 5 components removed

