Project

General

Profile

1
import { Injectable, Inject } from '@angular/core';
2
import { DOCUMENT } from '@angular/common';
3
import {  Optional, RendererFactory2, ViewEncapsulation } from '@angular/core';
4

    
5
@Injectable()
6
export class SEOService {
7
   constructor( @Inject(DOCUMENT) private doc,
8
   private rendererFactory: RendererFactory2,
9
   @Inject(DOCUMENT) private document) {
10
   }
11

    
12
   createLinkForCanonicalURL(url:string, addParameters:boolean=true) {
13
       if(this.doc && (typeof this.doc.getElementById === "function" || typeof this.doc.createElement === "function") ){
14
         if(!addParameters && url && url.indexOf("?") != -1){
15
           url = url.substring(0,url.indexOf("?"));
16
         }
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
      }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
            renderer.setAttribute(link, "href", (addParameters)?url:url.split("?")[0]);
49
            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
   }
58

    
59
}
60

    
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
    };
(1-1/2)