1 |
53740
|
argiro.kok
|
import { Injectable, Inject } from '@angular/core';
|
2 |
|
|
import { DOCUMENT } from '@angular/common';
|
3 |
54748
|
argiro.kok
|
import { Optional, RendererFactory2, ViewEncapsulation } from '@angular/core';
|
4 |
53740
|
argiro.kok
|
|
5 |
|
|
@Injectable()
|
6 |
|
|
export class SEOService {
|
7 |
54748
|
argiro.kok
|
constructor( @Inject(DOCUMENT) private doc,
|
8 |
|
|
private rendererFactory: RendererFactory2,
|
9 |
|
|
@Inject(DOCUMENT) private document) {
|
10 |
53740
|
argiro.kok
|
}
|
11 |
|
|
|
12 |
54748
|
argiro.kok
|
createLinkForCanonicalURL(url:string, addParameters:boolean=true) {
|
13 |
|
|
if(this.doc && (typeof this.doc.getElementById === "function" || typeof this.doc.createElement === "function") ){
|
14 |
55949
|
argiro.kok
|
if(!addParameters && url && url.indexOf("?") != -1){
|
15 |
|
|
url = url.substring(0,url.indexOf("?"));
|
16 |
53740
|
argiro.kok
|
}
|
17 |
|
|
if (typeof this.doc.getElementById === "function") {
|
18 |
|
|
let currentLink: HTMLLinkElement = this.doc.getElementById("relcan");
|
19 |
|
|
if(currentLink ){
|
20 |
|
|
currentLink.setAttribute('href', url);
|
21 |
|
|
return ;
|
22 |
|
|
}
|
23 |
|
|
}
|
24 |
|
|
if (typeof this.doc.createElement === "function") {
|
25 |
|
|
let link: HTMLLinkElement = this.doc.createElement('link');
|
26 |
|
|
link.setAttribute('id', 'relcan');
|
27 |
|
|
link.setAttribute('rel', 'canonical');
|
28 |
|
|
this.doc.head.appendChild(link);
|
29 |
|
|
link.setAttribute('href', url);
|
30 |
|
|
}
|
31 |
|
|
|
32 |
54748
|
argiro.kok
|
}else{
|
33 |
|
|
try {
|
34 |
|
|
const renderer = this.rendererFactory.createRenderer(this.document, {
|
35 |
|
|
id: '-1',
|
36 |
|
|
encapsulation: ViewEncapsulation.None,
|
37 |
|
|
styles: [],
|
38 |
|
|
data: {}
|
39 |
|
|
});
|
40 |
|
|
|
41 |
|
|
const link = renderer.createElement('link');
|
42 |
|
|
const head = this.document.head;
|
43 |
|
|
|
44 |
|
|
if (head === null) {
|
45 |
|
|
throw new Error('<head> not found within DOCUMENT.');
|
46 |
|
|
}
|
47 |
|
|
renderer.setAttribute(link, "rel", "canonical");
|
48 |
54829
|
argiro.kok
|
renderer.setAttribute(link, "href", (addParameters)?url:url.split("?")[0]);
|
49 |
54748
|
argiro.kok
|
renderer.setAttribute(link, "id", "relcan");
|
50 |
|
|
// [TODO]: get them to update the existing one (if it exists) ?
|
51 |
|
|
renderer.appendChild(head, link);
|
52 |
|
|
} catch (e) {
|
53 |
|
|
console.error('Error within linkService : ', e);
|
54 |
|
|
}
|
55 |
|
|
}
|
56 |
|
|
|
57 |
53740
|
argiro.kok
|
}
|
58 |
|
|
|
59 |
|
|
}
|
60 |
54748
|
argiro.kok
|
|
61 |
|
|
/*
|
62 |
|
|
* -- LinkService -- [Temporary]
|
63 |
|
|
* @MarkPieszak
|
64 |
|
|
*
|
65 |
|
|
* Similar to Meta service but made to handle <link> creation for SEO purposes
|
66 |
|
|
* -- NOTE: Soon there will be an overall DocumentService within Angular that handles Meta/Link everything
|
67 |
|
|
*/
|
68 |
|
|
//
|
69 |
|
|
// import { Injectable, Optional, RendererFactory2, ViewEncapsulation, Inject } from '@angular/core';
|
70 |
|
|
// import { DOCUMENT } from '@angular/platform-browser';
|
71 |
|
|
//
|
72 |
|
|
// @Injectable()
|
73 |
|
|
// export class LinkService {
|
74 |
|
|
//
|
75 |
|
|
// constructor(
|
76 |
|
|
// private rendererFactory: RendererFactory2,
|
77 |
|
|
// @Inject(DOCUMENT) private document
|
78 |
|
|
// ) {
|
79 |
|
|
// }
|
80 |
|
|
|
81 |
|
|
/**
|
82 |
|
|
* Inject the State into the bottom of the <head>
|
83 |
|
|
*/
|
84 |
|
|
// addTag(tag: LinkDefinition, forceCreation?: boolean) {
|
85 |
|
|
//
|
86 |
|
|
// try {
|
87 |
|
|
// const renderer = this.rendererFactory.createRenderer(this.document, {
|
88 |
|
|
// id: '-1',
|
89 |
|
|
// encapsulation: ViewEncapsulation.None,
|
90 |
|
|
// styles: [],
|
91 |
|
|
// data: {}
|
92 |
|
|
// });
|
93 |
|
|
//
|
94 |
|
|
// const link = renderer.createElement('link');
|
95 |
|
|
// const head = this.document.head;
|
96 |
|
|
// const selector = this._parseSelector(tag);
|
97 |
|
|
//
|
98 |
|
|
// if (head === null) {
|
99 |
|
|
// throw new Error('<head> not found within DOCUMENT.');
|
100 |
|
|
// }
|
101 |
|
|
//
|
102 |
|
|
// Object.keys(tag).forEach((prop: string) => {
|
103 |
|
|
// return renderer.setAttribute(link, prop, tag[prop]);
|
104 |
|
|
// });
|
105 |
|
|
//
|
106 |
|
|
// // [TODO]: get them to update the existing one (if it exists) ?
|
107 |
|
|
// renderer.appendChild(head, link);
|
108 |
|
|
//
|
109 |
|
|
// } catch (e) {
|
110 |
|
|
// console.error('Error within linkService : ', e);
|
111 |
|
|
// }
|
112 |
|
|
// }
|
113 |
|
|
//
|
114 |
|
|
// private _parseSelector(tag: LinkDefinition): string {
|
115 |
|
|
// // Possibly re-work this
|
116 |
|
|
// const attr: string = tag.rel ? 'rel' : 'hreflang';
|
117 |
|
|
// return `${attr}="${tag[attr]}"`;
|
118 |
|
|
// }
|
119 |
|
|
// }
|
120 |
|
|
|
121 |
|
|
export declare type LinkDefinition = {
|
122 |
|
|
charset?: string;
|
123 |
|
|
crossorigin?: string;
|
124 |
|
|
href?: string;
|
125 |
|
|
hreflang?: string;
|
126 |
|
|
media?: string;
|
127 |
|
|
rel?: string;
|
128 |
|
|
rev?: string;
|
129 |
|
|
sizes?: string;
|
130 |
|
|
target?: string;
|
131 |
|
|
type?: string;
|
132 |
|
|
} & {
|
133 |
|
|
[prop: string]: string;
|
134 |
|
|
};
|