Skip to content

Instantly share code, notes, and snippets.

@jkyoutsey
Last active October 26, 2023 12:48
Show Gist options
  • Save jkyoutsey/74ee55ecea86fe16ca8b79f99b5a33d5 to your computer and use it in GitHub Desktop.
Save jkyoutsey/74ee55ecea86fe16ca8b79f99b5a33d5 to your computer and use it in GitHub Desktop.
Angular Dynamic Script Execution Directive
<div appDynamicScript>
<!-- most tags work, but Angular strips script tags, so don't try it. -->
<div
src="http://some.script.com/thing.js"
my-custom-attr="some value"
>
Some Text
</div>
</div>
import { DOCUMENT } from '@angular/common';
import { Directive, ElementRef, Inject, AfterViewInit } from '@angular/core';
@Directive({
selector: '[appDynamicScript]',
})
export class DynamicScriptDirective implements AfterViewInit {
constructor(private el: ElementRef, @Inject(DOCUMENT) private document: Document) {}
ngAfterViewInit() {
const templateEl = this.el.nativeElement.firstElementChild as HTMLElement;
if (templateEl) {
this.replaceDivWithScript(templateEl);
}
}
private replaceDivWithScript(templateEl: HTMLElement) {
const script = this.document.createElement('script');
this.copyAttributesFromTemplateToScript(templateEl, script);
this.copyTemplateContentToScript(templateEl, script);
templateEl.remove();
// add the new script element to the host div so the browser will execute it
this.el.nativeElement.appendChild(script);
}
private copyAttributesFromTemplateToScript(templateEl: HTMLElement, script: HTMLScriptElement) {
for (let a = 0; a < templateEl.attributes.length; a++) {
script.attributes.setNamedItem(templateEl.attributes[a].cloneNode() as Attr);
}
}
private copyTemplateContentToScript(templateEl: HTMLElement, script: HTMLScriptElement) {
const scriptContent = this.document.createTextNode(templateEl.textContent);
script.appendChild(scriptContent);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment