Wie kann man <iframe src = "..."> setzen, ohne eine Ausnahme "unsicherer Wert" zu verursachen?

164

Ich arbeite an einem Tutorial, in dem ein iframe srcAttribut festgelegt wird:

<iframe width="100%" height="300" src="{{video.url}}"></iframe>

Dies löst eine Ausnahme aus:

Error: unsafe value used in a resource URL context
at DomSanitizationServiceImpl.sanitize...

Ich habe bereits erfolglos versucht, Bindungen zu verwenden [src].

TJ.
quelle

Antworten:

343

Update v8

Die folgenden Antworten funktionieren, setzen Ihre Anwendung jedoch XSS-Sicherheitsrisiken aus! . Anstelle der Verwendung this.sanitizer.bypassSecurityTrustResourceUrl(url)wird die Verwendung empfohlenthis.sanitizer.sanitize(SecurityContext.URL, url)

Aktualisieren

Für RC.6 ^ Version Verwendung DomSanitizer

Plunker

Und eine gute Option ist die Verwendung von reinen Rohren:

import { Pipe, PipeTransform } from '@angular/core';
import { DomSanitizer} from '@angular/platform-browser';

@Pipe({ name: 'safe' })
export class SafePipe implements PipeTransform {
  constructor(private sanitizer: DomSanitizer) {}
  transform(url) {
    return this.sanitizer.bypassSecurityTrustResourceUrl(url);
  }
} 

Denken Sie daran, Ihr neues SafePipezum declarationsArray des AppModule hinzuzufügen. ( wie in der Dokumentation zu sehen )

@NgModule({
   declarations : [
     ...
     SafePipe
   ],
})

html

<iframe width="100%" height="300" [src]="url | safe"></iframe>

Plunker

Wenn Sie ein embedTag verwenden, könnte dies für Sie interessant sein:


Alte Version RC.5

Sie können Folgendes nutzen DomSanitizationService:

export class YourComponent {
  url: SafeResourceUrl;
  constructor(sanitizer: DomSanitizationService) {
    this.url = sanitizer.bypassSecurityTrustResourceUrl('your url');
  }
}

Und binden Sie dann urlin Ihre Vorlage:

<iframe width="100%" height="300" [src]="url"></iframe>

Vergessen Sie nicht, folgende Importe hinzuzufügen:

import { SafeResourceUrl, DomSanitizationService } from '@angular/platform-browser';

Plunker Probe

Yurzui
quelle
1
@FugueWeb Das liegt daran, dass ionic2 heute eckiges RC4 verwendet. github.com/driftyco/ionic/blob/master/…
yurzui
2
Ich benutze Ionic2. Ich deklariere eine Pipe Pipe({ name: 'safe' }) export class SafePipe implements PipeTransform { constructor(private sanitizer: DomSanitizer) {} transform(url): any { return this.sanitizer.bypassSecurityTrustResourceUrl(url); } } und rufe in der Vorlage an <iframe width="100%" height="315" src="{{url}} | safe" frameborder="0" allowfullscreen></iframe>. Aber es funktioniert nicht mit dem Fehler 'unsicherer Wert'. Bitte helfen Sie
Insane Rose
1
@Insane Rose Ich denke, es sollte sein, [src]="url | safe"entfernen Sie einfach Klammern
Yurzui
7
@yurzui Ich bin Ihrer Empfehlung für die aktualisierte Version 8 gefolgt. Wenn ich jedoch verwende this.sanitizer.sanitize(SecurityContext.URL, url), wird die Fehlermeldung "FEHLER Fehler: Unsicherer Wert, der in einem Ressourcen-URL-Kontext verwendet wird" angezeigt. II Ändern Sie ihn so, dass er this.sanitizer.bypassSecurityTrustResourceUrl(url)einwandfrei funktioniert. Irgendeine Idee, was falsch sein kann?
Kosmonaft
2
this.sanitizer.sanitize(SecurityContext.URL, url)funktioniert nicht und this.sanitizer.bypassSecurityTrustResourceUrl(url)funktioniert, wirft jedoch ein Problem mit hoher Sicherheitslücke in der statischen Code-Analyse auf, das mich daran hindert, dies in die Produktion zu verlagern. Brauchen Sie einen Weg, um dies zu beheben
cjkumaresh
28

Dieser arbeitet für mich.

import { Component,Input,OnInit} from '@angular/core';
import {DomSanitizer,SafeResourceUrl,} from '@angular/platform-browser';

@Component({
    moduleId: module.id,
    selector: 'player',
    templateUrl: './player.component.html',
    styleUrls:['./player.component.scss'],
    
})
export class PlayerComponent implements OnInit{
    @Input()
    id:string; 
    url: SafeResourceUrl;
    constructor (public sanitizer:DomSanitizer) {
    }
    ngOnInit() {
        this.url = this.sanitizer.bypassSecurityTrustResourceUrl(this.id);      
    }
}
vikvincer
quelle
Dieser Ansatz funktioniert bei mir, da ich ihn an einer Stelle verwende. Ansonsten ist der Rohransatz besser.
Narek Tootikian
@Pang Wie funktioniert es? Ich habe das gleiche Problem, ich möchte meinen Parameter in URL hinzufügen Ich verwende diesen Code "@Input () parameterForFB: number = this.selectedStudent.schoolId url: string =" designs.mydeievents.com/jq-3d-flip-book /index.html?id=$ {parameterForFB} "; urlSafe: SafeResourceUrl;" aber kein Problem mit dem Arbeitsgesicht im Parameter.
Arjun Walmiki
15

Das funktioniert bei Angular 5.2.0

sarasa.Component.ts

import { Component, OnInit, Input } from '@angular/core';
import { DomSanitizer, SafeResourceUrl } from '@angular/platform-browser';

@Component({
  selector: 'app-sarasa',
  templateUrl: './sarasa.component.html',
  styleUrls: ['./sarasa.component.scss']
})

export class Sarasa implements OnInit {
  @Input()
  url: string = "https://www.mmlpqtpkasjdashdjahd.com";
  urlSafe: SafeResourceUrl;

  constructor(public sanitizer: DomSanitizer) { }

  ngOnInit() {
    this.urlSafe= this.sanitizer.bypassSecurityTrustResourceUrl(this.url);
  }

}

sarasa.Component.html

<iframe width="100%" height="100%" frameBorder="0" [src]="urlSafe"></iframe>

das war's Leute!!!

Lrodriguez84
quelle
7
constructor(
 public sanitizer: DomSanitizer, ) {

 }

Ich hatte 4 Stunden lang gekämpft. das problem war im img tag. Wenn Sie eine eckige Klammer für 'src' verwenden, z. B.: [Src]. Sie können diesen Winkelausdruck {{}} nicht verwenden. Sie geben nur direkt aus einem Objektbeispiel unten. wenn Sie einen Winkelausdruck {{}} angeben. Sie erhalten einen Interpolationsfehler.

  1. Zuerst habe ich ngFor verwendet, um die Länder zu iterieren

    *ngFor="let country of countries"
    
  2. Zweitens setzen Sie dies in das img-Tag. Das ist es.

    <img [src]="sanitizer.bypassSecurityTrustResourceUrl(country.flag)"
    height="20" width="20" alt=""/>
    
Kumaresan Perumal
quelle
Beachten Sie, dass das Einfügen eines Funktionsaufrufs in HTML eine schlechte Idee ist, da dieser jedes Mal aufgerufen wird, wenn ChangeDetector nach Änderungen sucht.
KaroluS
1

Ich bin auch auf dieses Problem gestoßen, aber um ein sicheres Rohr in meinem Winkelmodul zu verwenden, habe ich das Safe-Pipe-npm-Paket installiert, das Sie hier finden . Zu Ihrer Information, dies hat in Angular 9.1.3 funktioniert. Ich habe dies in keiner anderen Version von Angular versucht. So fügen Sie es Schritt für Schritt hinzu:

  1. Installieren Sie das Paket über npm. Installieren Sie das Safe-Rohr oder fügen Sie das Safe-Rohr hinzu. Dadurch wird ein Verweis darauf in Ihren Abhängigkeiten in der Datei package.json gespeichert, die Sie bereits beim Starten eines neuen Angular-Projekts haben sollten.

  2. Fügen Sie das SafePipeModule-Modul wie folgt zu NgModule.imports in Ihrer Angular-Moduldatei hinzu:

    import { SafePipeModule } from 'safe-pipe';
    
    @NgModule({
        imports: [ SafePipeModule ]
    })
    export class AppModule { }
    
    
  3. Fügen Sie die sichere Pipe einem Element in der Vorlage für die Angular-Komponente hinzu, die Sie auf folgende Weise in Ihr NgModule importieren:

<element [property]="value | safe: sanitizationType"></element>
  1. Hier sind einige spezifische Beispiele für die safePipe in einem HTML-Element:
<div [style.background-image]="'url(' + pictureUrl + ')' | safe: 'style'" class="pic bg-pic"></div>
<img [src]="pictureUrl | safe: 'url'" class="pic" alt="Logo">
<iframe [src]="catVideoEmbed | safe: 'resourceUrl'" width="640" height="390"></iframe>
<pre [innerHTML]="htmlContent | safe: 'html'"></pre>

LRitter
quelle
-1

Normalerweise füge ich eine separate wiederverwendbare sichere Rohrkomponente wie folgt hinzu

# Add Safe Pipe

import { Pipe, PipeTransform } from '@angular/core';
import { DomSanitizer } from '@angular/platform-browser';

@Pipe({name: 'mySafe'})
export class SafePipe implements PipeTransform {
    constructor(private sanitizer: DomSanitizer) {
    }

    public transform(url) {
        return this.sanitizer.bypassSecurityTrustResourceUrl(url);
    }
}
# then create shared pipe module as following 

import { NgModule } from '@angular/core'; 
import { SafePipe } from './safe.pipe';
@NgModule({
    declarations: [
        SafePipe
    ],
    exports: [
        SafePipe
    ]
})
export class SharedPipesModule {
}
# import shared pipe module in your native module

@NgModule({
    declarations: [],
    imports: [
        SharedPipesModule,
    ],
})
export class SupportModule {
}
<!-------------------
call your url (`trustedUrl` for me) and add `mySafe` as defined in Safe Pipe
---------------->
<div class="container-fluid" *ngIf="trustedUrl">
    <iframe [src]="trustedUrl | mySafe" align="middle" width="100%" height="800" frameborder="0"></iframe>
</div>
Janki
quelle
-8

Glückwunsch! ¨ ^^ Ich habe eine einfache und effiziente Lösung für Sie, ja!

<iframe width="100%" height="300" [attr.src]="video.url"></iframe

[attr.src] anstelle von src "video.url" und nicht {{video.url}}

Toll ;)

Smaillns
quelle
5
Für Zeichenfolgenwerte macht das keinen Unterschied.
Günter Zöchbauer
1
es funktioniert nicht Fehlermeldung erhaltenunsafe value used in a resource URL context
Derek Liang
Sie können also das HTML5-Video-Tag verwenden, aber wenn Sie darauf bestehen, iframe zu verwenden (aus vielen Gründen;), sehen Sie sich andere Lösungen an, die DomSanitizationService verwenden.
Smaillns
Wenn Sie also nach dem ' <video> <source [src]=video.url type="video/mp4" /> Browser not supported </video> Video' -Tag suchen, wird es tatsächlich so sein. Sie können es auch verwenden, um Dokumente anzuzeigen. Wenn Sie Probleme bei der Verwendung des Video-Tags haben, bin ich hier;)
Smaillns