FE-1026: Add Yandex Metrika (#181)

This commit is contained in:
Rinat Arsaev 2020-03-26 12:25:49 +03:00 committed by GitHub
parent 8e9f06fe5c
commit d4e6e2cc61
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
15 changed files with 166 additions and 14 deletions

View File

@ -9,9 +9,11 @@
"cSpell.words": [
"CAPI",
"FATCA",
"SNILS",
"Metrika",
"OGRN",
"OKVED",
"SNILS",
"Yandex",
"actionbar",
"anapi",
"anthroponym",
@ -33,6 +35,7 @@
"snils",
"submodule",
"transloco",
"webvisor",
"ЕГРЮЛ",
"СНИЛС",
"бенефициарного",

8
package-lock.json generated
View File

@ -9325,6 +9325,14 @@
"integrity": "sha512-iyam8fBuCUpWeKPGpaNMetEocMt364qkCsfL9JuhjXX6dRnguRVOfk2GZaDpPjcOKiiXCPINZC1GczQ7iTq3Zw==",
"dev": true
},
"ng-yandex-metrika": {
"version": "3.0.2",
"resolved": "https://registry.npmjs.org/ng-yandex-metrika/-/ng-yandex-metrika-3.0.2.tgz",
"integrity": "sha512-qH0JW1dRcvEit0ecom91R8nA+1YN9SKq9PwDQQasWg1/z59aUK6xK7+jQvJr2D07vmURdNkGDQv1bVuLAO/KdQ==",
"requires": {
"tslib": "^1.9.0"
}
},
"ngx-build-plus": {
"version": "9.0.2",
"resolved": "https://registry.npmjs.org/ngx-build-plus/-/ngx-build-plus-9.0.2.tgz",

View File

@ -61,6 +61,7 @@
"lodash.round": "^4.0.4",
"lodash.template": "^4.4.0",
"moment": "^2.24.0",
"ng-yandex-metrika": "^3.0.2",
"rxjs": "~6.5.4",
"saturn-datepicker": "8.0.1",
"ts-keycode-enum": "^1.0.6",

View File

@ -1 +1,5 @@
<dsh-container><dsh-sections></dsh-sections></dsh-container>
<dsh-container>
<dsh-sections></dsh-sections>
</dsh-container>
<dsh-yandex-metrika *ngIf="env.production"></dsh-yandex-metrika>

View File

@ -1,5 +1,6 @@
import { Component, OnInit } from '@angular/core';
import { Component, Inject, OnInit } from '@angular/core';
import { ENV, Env } from '../environments';
import { TestShopService } from './test-shop.service';
@Component({
@ -8,7 +9,7 @@ import { TestShopService } from './test-shop.service';
providers: [TestShopService]
})
export class AppComponent implements OnInit {
constructor(private testShopService: TestShopService) {}
constructor(private testShopService: TestShopService, @Inject(ENV) public env: Env) {}
ngOnInit() {
this.testShopService.createTestShopWhenNoShops();

View File

@ -1,6 +1,6 @@
import { CommonModule } from '@angular/common';
import { HttpClientModule } from '@angular/common/http';
import { APP_INITIALIZER, LOCALE_ID, NgModule } from '@angular/core';
import { APP_INITIALIZER, LOCALE_ID, NgModule, PLATFORM_ID } from '@angular/core';
import { MatIconRegistry } from '@angular/material';
import {
MAT_MOMENT_DATE_ADAPTER_OPTIONS,
@ -13,7 +13,7 @@ import { BrowserModule, DomSanitizer } from '@angular/platform-browser';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { TRANSLOCO_CONFIG, TranslocoConfig, TranslocoModule } from '@ngneat/transloco';
import { environment } from '../environments/environment';
import { ENV, environment } from '../environments';
import { APICodegenModule } from './api-codegen';
import { AppComponent } from './app.component';
import { AuthModule, KeycloakAngularModule, KeycloakService } from './auth';
@ -26,6 +26,7 @@ import { SectionsModule } from './sections';
import { SettingsModule } from './settings';
import { ThemeManagerModule } from './theme-manager';
import { translocoLoader } from './transloco.loader';
import { YandexMetrikaConfigService, YandexMetrikaModule } from './yandex-metrika';
@NgModule({
declarations: [AppComponent],
@ -42,14 +43,15 @@ import { translocoLoader } from './transloco.loader';
SettingsModule,
KeycloakAngularModule,
HttpClientModule,
TranslocoModule
TranslocoModule,
YandexMetrikaModule
],
providers: [
LanguageService,
{
provide: APP_INITIALIZER,
useFactory: initializer,
deps: [ConfigService, KeycloakService, LanguageService],
deps: [ConfigService, KeycloakService, LanguageService, YandexMetrikaConfigService, PLATFORM_ID],
multi: true
},
{
@ -77,7 +79,8 @@ import { translocoLoader } from './transloco.loader';
scopeStrategy: 'shared'
} as TranslocoConfig
},
translocoLoader
translocoLoader,
{ provide: ENV, useValue: environment }
],
bootstrap: [AppComponent]
})

View File

@ -1,14 +1,24 @@
import { KeycloakService } from './auth/keycloak';
import { ConfigService } from './config';
import { LanguageService } from './language';
import { YandexMetrikaConfigService } from './yandex-metrika';
export const initializer = (
configService: ConfigService,
keycloakService: KeycloakService,
languageService: LanguageService
) => async () => {
await Promise.all([
configService.init({ configUrl: '/appConfig.json' }),
languageService: LanguageService,
yandexMetrikaService: YandexMetrikaConfigService,
platformId: Object
) => () =>
Promise.all([
configService.init({ configUrl: '/appConfig.json' }).then(() =>
yandexMetrikaService.init(
{
id: configService.yandexMetrika.id
},
platformId
)
),
keycloakService.init({
config: '/authConfig.json',
initOptions: {
@ -21,4 +31,3 @@ export const initializer = (
}),
languageService.init()
]);
};

View File

@ -0,0 +1,3 @@
export * from './yandex-metrika.module';
export * from './yandex-metrika.component';
export * from './yandex-metrika-config.service';

View File

@ -0,0 +1,15 @@
import { Injectable } from '@angular/core';
import { appInitializerFactory as yandexMetrikaInitializer, countersFactory } from 'ng-yandex-metrika';
import { CounterConfig, YandexCounterConfig } from 'ng-yandex-metrika/lib/ng-yandex-metrika.config';
@Injectable()
export class YandexMetrikaConfigService {
config: YandexCounterConfig & CounterConfig;
init(config: CounterConfig, platformId: Object) {
this.config = countersFactory(config)[0];
if (config.id) {
yandexMetrikaInitializer([this.config], platformId)();
}
}
}

View File

@ -0,0 +1,5 @@
<noscript>
<div>
<img src="https://mc.yandex.ru/watch/{{ id }}" style="position:absolute; left:-9999px;" alt="" />
</div>
</noscript>

View File

@ -0,0 +1,19 @@
import { ChangeDetectionStrategy, Component } from '@angular/core';
import { YandexMetrikaConfigService } from './yandex-metrika-config.service';
import { YandexMetrikaService } from './yandex-metrika.service';
@Component({
selector: 'dsh-yandex-metrika',
templateUrl: 'yandex-metrika.component.html',
changeDetection: ChangeDetectionStrategy.OnPush,
providers: [YandexMetrikaService]
})
export class YandexMetrikaComponent {
id = this.yandexMetrikaConfigService.config.id;
constructor(
private yandexMetrikaConfigService: YandexMetrikaConfigService,
_yandexMetrikaService: YandexMetrikaService
) {}
}

View File

@ -0,0 +1,32 @@
import { CommonModule } from '@angular/common';
import { Injector, NgModule, PLATFORM_ID } from '@angular/core';
import { RouterModule } from '@angular/router';
import { Metrika, ɵb as DEFAULT_COUNTER_ID, ɵd as YANDEX_COUNTERS_CONFIGS } from 'ng-yandex-metrika';
import { YandexMetrikaConfigService } from './yandex-metrika-config.service';
import { YandexMetrikaComponent } from './yandex-metrika.component';
@NgModule({
imports: [RouterModule, CommonModule],
providers: [
YandexMetrikaConfigService,
{
provide: DEFAULT_COUNTER_ID,
useFactory: (yandexMetrikaService: YandexMetrikaConfigService) => yandexMetrikaService.config.id,
deps: [YandexMetrikaConfigService]
},
{
provide: YANDEX_COUNTERS_CONFIGS,
useFactory: (yandexMetrikaService: YandexMetrikaConfigService) => [yandexMetrikaService.config],
deps: [YandexMetrikaConfigService]
},
{
provide: Metrika,
useClass: Metrika,
deps: [Injector, PLATFORM_ID]
}
],
declarations: [YandexMetrikaComponent],
exports: [YandexMetrikaComponent]
})
export class YandexMetrikaModule {}

View File

@ -0,0 +1,39 @@
import { Location } from '@angular/common';
import { Injectable, OnDestroy } from '@angular/core';
import { NavigationEnd, Router } from '@angular/router';
import { Metrika } from 'ng-yandex-metrika';
import { Subscription } from 'rxjs';
import { filter, map, pairwise, startWith, tap } from 'rxjs/operators';
@Injectable()
export class YandexMetrikaService implements OnDestroy {
private subscription: Subscription;
constructor(private router: Router, private location: Location, private metrika: Metrika) {
this.subscription = this.hitRouterEvents().subscribe();
}
ngOnDestroy() {
this.subscription.unsubscribe();
}
hitRouterEvents() {
return this.router.events.pipe(
filter(event => event instanceof NavigationEnd),
map(() => this.location.path()),
startWith(null),
map(path => (path === '' ? '/' : path)),
pairwise(),
tap(([prevPath, newPath]) => {
this.metrika.hit(
newPath,
prevPath !== null
? {
referer: prevPath
}
: undefined
);
})
);
}
}

View File

@ -4,5 +4,8 @@
"docsEndpoint": "https://rbkmoney.github.io/docs",
"supportEmail": "support@rbkmoney.com",
"oldDashboardEndpoint": "https://dashboard.rbk.money"
},
"yandexMetrika": {
"id": null
}
}

View File

@ -0,0 +1,7 @@
import { InjectionToken } from '@angular/core';
import { environment } from '../environments/environment';
export type Env = typeof environment;
export const ENV = new InjectionToken<Env>('Env');
export { environment };