Angular2 - SEO - как манипулировать мета-описанием

Результаты поиска в google отображаются через TitleTag и тег <meta name="description"..."/>. <title> -Tag может быть изменен с помощью Angular2 как изменить название страницы в маршрутизаторе Angular2

Осталось описание.

Можно ли написать директиву в angular2, которая манипулирует метатегами в части <head> моей страницы.
Поэтому в зависимости от выбранного маршрута мета-описание изменяется следующим образом:

<meta name="description" content="**my description for this route**"/>

Ответы

Ответ 1

С помощью Angular4 вы можете использовать Angular Meta service.   

import { Meta } from '@angular/platform-browser';

// [...]

constructor(private meta: Meta) {}

// [...]

this.meta.addTag({ name: 'robots', content: 'noindex' });

Ответ 2

Я нашел решение для службы SEO Angular2 в этом блоге.

http://blog.devcross.net/2016/03/20/angular-2-seo/

Своя хорошая вспомогательная служба для изменения <title>, мета-описания и роботов-текста.

Ответ 3

Это возможно. Я реализовал его в своем приложении, а ниже я даю описание, как оно сделано.

Основная идея - использовать Meta из @angular/platform-browser

Для динамического изменения определенного метатега вам необходимо:

  • Удалите старый, используя removeTag(attrSelector: string) : void Метод.
  • Добавить новый с помощью метода addTag(tag: MetaDefinition, forceCreation?: boolean) : HTMLMetaElement.

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

Примечание: на самом деле также необходимо иметь значения по умолчанию <title>...</title> и <meta name="description"..." content="..."/> в заголовке index.html, поэтому перед тем, как он будет установлен динамически, уже есть некоторый статический контент.

Мой app-routing.module.ts контент:

import 'rxjs/add/operator/filter';
import 'rxjs/add/operator/map';
import 'rxjs/add/operator/mergeMap';

import { NgModule } from '@angular/core';
import { RouterModule, Routes, Router, NavigationEnd, ActivatedRoute } from '@angular/router';

import { StringComparisonComponent }  from '../module-string-comparison/string-comparison.component';
import { ClockCalculatorComponent }  from '../module-clock-calculator/clock-calculator.component';

import { Title, Meta } from '@angular/platform-browser';

const routes: Routes = [
  {
    path: '', redirectTo: '/string-comparison', pathMatch: 'full',
    data: { title: 'String comparison title', metaDescription: 'String comparison meta description content' }
  },
  {
    path: 'string-comparison',  component: StringComparisonComponent,
    data: { title: 'String comparison title', metaDescription: 'String comparison meta description content' }
  },
  {
    path: 'clock-time-calculator',  component: ClockCalculatorComponent,
    data: { title: 'Clock time calculator title', metaDescription: 'Clock time calculator meta description content' }
  }
];

@NgModule({
  imports: [ RouterModule.forRoot(routes) ],
  exports: [ RouterModule ]
})

export class AppRoutingModule {

  constructor(
    private router: Router,
    private activatedRoute: ActivatedRoute,
    private titleService: Title,
    private metaService: Meta
  ){
    //Boilerplate code to filter out only important router events and to pull out data object field from each route
    this.router.events
    .filter(event => event instanceof NavigationEnd)
    .map(() => this.activatedRoute)
    .map(route => {
        while (route.firstChild) route = route.firstChild;
        return route;
    })
    .filter(route => route.outlet === 'primary')
    //Data fields are merged so we can use them directly to take title and metaDescription for each route from them
    .mergeMap(route => route.data)
    //Real action starts there
    .subscribe((event) => {
        //Changing title
        this.titleService.setTitle(event['title']);

        //Changing meta with name="description"
        var tag = { name: 'description', content: event['metaDescription'] };
        let attributeSelector : string = 'name="description"';
        this.metaService.removeTag(attributeSelector);
        this.metaService.addTag(tag, false);
    });
  }

}
  • Как можно видеть, есть дополнительное поле объекта data для каждый маршрут. Он содержит строки title и metaDescription который будет использоваться в качестве содержимого заголовка и метатега.
  • В конструкторе мы отфильтровываем события маршрутизатора и подписываемся на фильтрацию событие маршрутизатора. Rxjs используется там, но на самом деле его не нужно использовать. Обычные if statements и loops могут использоваться в потоке, фильтре и карте.
  • Мы также объединяем наше поле объекта данных с нашим событием, чтобы мы могли легко используйте информацию типа title и metaDescription.
  • Мы динамически меняем теги <title>...</title> и <meta name="description"..." content="..."/>.

Эффекты:

Первый компонент Заголовок сравнения строк и теги метаописания

Второй компонент Название калькулятора часов и метатеги описания

Фактически я использую в настоящее время немного более сложную версию этого решения, которая также использует ngx-translate, чтобы показать другое название и мета-описание для разные языки.
Полный код доступен в angular2-bootstrap-translate-website-starter проекте.
Файл app-routing.module.ts с решением ngx-translate находится именно там: app-routing.module.ts.

Существует также производственное приложение, в котором используется такое же решение: http://www.online-utils.net.

Конечно, это не единственный способ, и могут быть лучшие способы сделать это. Но я тестировал это решение, и оно работает.

На самом деле решение очень похоже на это из соответствующего сообщения об изменении заголовка: Как изменить заголовок страницы в маршрутизаторе angular2.

Angular Метаданные: https://angular.io/docs/ts/latest/api/platform-browser/index/Meta-class.html. На самом деле они не очень информативны, и мне пришлось экспериментировать и смотреть в настоящий .js-код, чтобы сделать это динамическое изменение метаданных.

Ответ 4

Я разработал и только что выпустил плагин @ngx-meta/core, который манипулирует метатегами на уровне маршрута и позволяет устанавливать метатеги программным способом в конструкторе компонента.

Подробные инструкции можно найти в @ngx-meta/core репозиторий github. Кроме того, исходные файлы могут быть полезны для введения пользовательской логики.

Ответ 5

В настоящее время нет готового решения только для открытой проблемы, чтобы реализовать его https://github.com/angular/angular/issues/7438.

Вы можете, конечно, реализовать что-то вроде службы заголовка самостоятельно, просто используйте TitleService в качестве шаблона

Служба

A Meta, аналогичная службе Title, находится в работе (в настоящее время только запрос на перенос).