Skip to content

Commit

Permalink
fix(icon): server-side error when registering icons (#8492)
Browse files Browse the repository at this point in the history
Fixes an error that is thrown by the `IconRegistry` when registering icons on the server side.

Fixes #6787.
  • Loading branch information
crisbeto authored and jelbourn committed Jan 5, 2018
1 parent d85c44b commit b6da765
Showing 1 changed file with 32 additions and 11 deletions.
43 changes: 32 additions & 11 deletions src/lib/icon/icon-registry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,21 @@ import {tap} from 'rxjs/operators/tap';
import {finalize} from 'rxjs/operators/finalize';
import {map} from 'rxjs/operators/map';
import {share} from 'rxjs/operators/share';
import {Injectable, Optional, SecurityContext, SkipSelf} from '@angular/core';
import {
Injectable,
Inject,
InjectionToken,
Optional,
SecurityContext,
SkipSelf,
} from '@angular/core';
import {HttpClient} from '@angular/common/http';
import {DomSanitizer, SafeResourceUrl} from '@angular/platform-browser';
import {Observable} from 'rxjs/Observable';
import {forkJoin} from 'rxjs/observable/forkJoin';
import {of as observableOf} from 'rxjs/observable/of';
import {_throw as observableThrow} from 'rxjs/observable/throw';
import {DOCUMENT} from '@angular/common';


/**
Expand Down Expand Up @@ -97,7 +105,12 @@ export class MatIconRegistry {
*/
private _defaultFontSetClass = 'material-icons';

constructor(@Optional() private _httpClient: HttpClient, private _sanitizer: DomSanitizer) {}
constructor(
@Optional() private _httpClient: HttpClient,
private _sanitizer: DomSanitizer,
@Optional() @Inject(DOCUMENT) private _document?: any) {
// TODO(crisbeto): make _document required next major release.
}

/**
* Registers an icon by URL in the default namespace.
Expand Down Expand Up @@ -405,13 +418,17 @@ export class MatIconRegistry {
* Creates a DOM element from the given SVG string.
*/
private _svgElementFromString(str: string): SVGElement {
const div = document.createElement('DIV');
div.innerHTML = str;
const svg = div.querySelector('svg') as SVGElement;
if (!svg) {
throw Error('<svg> tag not found');
if (this._document || typeof document !== 'undefined') {
const div = (this._document || document).createElement('DIV');
div.innerHTML = str;
const svg = div.querySelector('svg') as SVGElement;
if (!svg) {
throw Error('<svg> tag not found');
}
return svg;
}
return svg;

throw new Error('MatIconRegistry could not resolve document.');
}

/**
Expand Down Expand Up @@ -483,8 +500,11 @@ export class MatIconRegistry {

/** @docs-private */
export function ICON_REGISTRY_PROVIDER_FACTORY(
parentRegistry: MatIconRegistry, httpClient: HttpClient, sanitizer: DomSanitizer) {
return parentRegistry || new MatIconRegistry(httpClient, sanitizer);
parentRegistry: MatIconRegistry,
httpClient: HttpClient,
sanitizer: DomSanitizer,
document?: any) {
return parentRegistry || new MatIconRegistry(httpClient, sanitizer, document);
}

/** @docs-private */
Expand All @@ -494,7 +514,8 @@ export const ICON_REGISTRY_PROVIDER = {
deps: [
[new Optional(), new SkipSelf(), MatIconRegistry],
[new Optional(), HttpClient],
DomSanitizer
DomSanitizer,
[new Optional(), DOCUMENT as InjectionToken<any>]
],
useFactory: ICON_REGISTRY_PROVIDER_FACTORY
};
Expand Down

0 comments on commit b6da765

Please sign in to comment.