Ich verstehe JSON, aber nicht JSONP. Das Wikipedia-Dokument zu JSON ist (war) das Top-Suchergebnis für JSONP. Es sagt dies:
JSONP oder "JSON mit Auffüllung" ist eine JSON-Erweiterung, bei der ein Präfix als Eingabeargument des Aufrufs selbst angegeben wird.
Huh? Welcher Anruf? Das ergibt für mich keinen Sinn. JSON ist ein Datenformat. Es gibt keinen Anruf.
Das zweite Suchergebnis stammt von einem Typen namens Remy , der dies über JSONP schreibt:
JSONP ist eine Skript-Tag-Injektion, bei der die Antwort vom Server an eine benutzerdefinierte Funktion übergeben wird.
Ich kann das irgendwie verstehen, aber es macht immer noch keinen Sinn.
Was ist JSONP? Warum wurde es erstellt (welches Problem löst es)? Und warum sollte ich es benutzen?
Nachtrag : Ich habe gerade eine neue Seite für JSONP auf Wikipedia erstellt. Es enthält jetzt eine klare und gründliche Beschreibung von JSONP, basierend auf der Antwort von jvenema .
quelle
Antworten:
Es ist eigentlich nicht zu kompliziert ...
Angenommen, Sie befinden sich in einer Domain
example.com
und möchten eine Anfrage an die Domain stellenexample.net
. Dazu müssen Sie Domänengrenzen überschreiten, ein No-No in den meisten Browserlandschaften.Das einzige Element, das diese Einschränkung umgeht, sind
<script>
Tags. Wenn Sie ein Skript-Tag verwenden, wird die Domänenbeschränkung ignoriert. Unter normalen Umständen können Sie mit den Ergebnissen jedoch nichts anfangen. Das Skript wird nur ausgewertet.Geben Sie ein
JSONP
. Wenn Sie Ihre Anfrage an einen Server richten, der JSONP-fähig ist, übergeben Sie einen speziellen Parameter, der dem Server ein wenig über Ihre Seite erzählt. Auf diese Weise kann der Server seine Antwort auf eine Weise zusammenfassen, die Ihre Seite verarbeiten kann.Angenommen, der Server erwartet einen Parameter, der aufgerufen wird
callback
, um seine JSONP-Funktionen zu aktivieren. Dann würde Ihre Anfrage so aussehen:Ohne JSONP kann dies ein grundlegendes JavaScript-Objekt zurückgeben, wie folgt:
Wenn der Server bei JSONP den Parameter "Rückruf" empfängt, wird das Ergebnis jedoch etwas anders zusammengefasst, und es wird etwa Folgendes zurückgegeben:
Wie Sie sehen, wird jetzt die von Ihnen angegebene Methode aufgerufen. Auf Ihrer Seite definieren Sie also die Rückruffunktion:
Und jetzt, wenn das Skript geladen ist, wird es ausgewertet und Ihre Funktion wird ausgeführt. Voila, domänenübergreifende Anfragen!
Beachten Sie auch das Hauptproblem bei JSONP: Sie verlieren viel Kontrolle über die Anforderung. Zum Beispiel gibt es keinen "guten" Weg, um die richtigen Fehlercodes zurückzubekommen. Infolgedessen verwenden Sie am Ende Timer, um die Anforderung usw. zu überwachen, was immer etwas verdächtig ist. Der Vorschlag für JSONRequest ist eine großartige Lösung, um domänenübergreifendes Scripting zu ermöglichen, die Sicherheit aufrechtzuerhalten und die Anforderung ordnungsgemäß zu steuern.
In diesen Tagen (2015) ist CORS der empfohlene Ansatz gegenüber JSONRequest. JSONP ist immer noch nützlich für die Unterstützung älterer Browser, aber angesichts der Auswirkungen auf die Sicherheit ist CORS die bessere Wahl, es sei denn, Sie haben keine andere Wahl.
quelle
JSONP ist wirklich ein einfacher Trick, um die gleiche Domain-Richtlinie XMLHttpRequest zu überwinden . (Wie Sie wissen, kann eine AJAX- Anfrage (XMLHttpRequest) nicht an eine andere Domain gesendet werden.)
Anstatt XMLHttpRequest zu verwenden, müssen wir Skript- HTML-Tags verwenden, die Sie normalerweise zum Laden von JS-Dateien verwenden, damit JS Daten von einer anderen Domäne abruft. Klingt komisch?
Es stellt sich heraus, dass Skript- Tags ähnlich wie XMLHttpRequest verwendet werden können ! Überprüfen Sie dies heraus:
Sie erhalten ein Skriptsegment , das nach dem Laden der Daten folgendermaßen aussieht:
Dies ist jedoch etwas unpraktisch, da wir dieses Array vom Skript- Tag abrufen müssen. Daher haben die JSONP- Entwickler entschieden, dass dies besser funktioniert (und das ist es auch):
Beachten Sie die my_callback- Funktion dort drüben? Wenn der JSONP- Server Ihre Anfrage empfängt und den Rückrufparameter findet, wird anstelle des einfachen js-Arrays Folgendes zurückgegeben:
Sehen Sie, wo der Gewinn ist: Jetzt erhalten wir einen automatischen Rückruf (my_callback), der ausgelöst wird, sobald wir die Daten erhalten.
Das ist alles, was Sie über JSONP wissen müssen : Es handelt sich um einen Rückruf und Skript-Tags.
HINWEIS: Dies sind einfache Beispiele für die Verwendung von JSONP. Hierbei handelt es sich nicht um produktionsbereite Skripts.
Grundlegendes JavaScript-Beispiel (einfacher Twitter-Feed mit JSONP)
Grundlegendes jQuery-Beispiel (einfacher Twitter-Feed mit JSONP)
JSONP steht für JSON with Padding . (Sehr schlecht benannte Technik, da sie wirklich nichts mit dem zu tun hat, was die meisten Leute als „Polsterung“ betrachten würden.)
quelle
JSONP erstellt ein Skriptelement (entweder im HTML-Markup oder über JavaScript in das DOM eingefügt), das einen Remote-Datendienststandort anfordert. Die Antwort ist ein in Ihren Browser geladenes Javascript mit dem Namen der vordefinierten Funktion und dem übergebenen Parameter, dh den angeforderten JSON-Daten. Wenn das Skript ausgeführt wird, wird die Funktion zusammen mit JSON-Daten aufgerufen, sodass die anfordernde Seite die Daten empfangen und verarbeiten kann.
Weitere Informationen finden Sie unter: https://blogs.sap.com/2013/07/15/secret-behind-jsonp/
clientseitiger Codeausschnitt
Serverseitiger Teil des PHP-Codes
quelle
Weil Sie den Server bitten können, dem zurückgegebenen JSON-Objekt ein Präfix voranzustellen. Z.B
function_prefix(json_object);
Damit der Browser
eval
die JSON-Zeichenfolge als Ausdruck "inline" macht. Dieser Trick ermöglicht es dem Server, Javascript-Code direkt in den Client-Browser zu "injizieren", und dies unter Umgehung der Einschränkungen "gleichen Ursprungs".Mit anderen Worten, Sie können einen domänenübergreifenden Datenaustausch erreichen .
Erlaubt normalerweise
XMLHttpRequest
keinen domänenübergreifenden Datenaustausch direkt (man muss über einen Server in derselben Domäne gehen), wohingegen:<script src="some_other_domain/some_data.js&prefix=function_prefix
> `Man kann auf Daten aus einer anderen Domäne als dem Ursprung zugreifen.Ebenfalls erwähnenswert: Auch wenn der Server vor dem Versuch eines solchen "Tricks" als "vertrauenswürdig" eingestuft werden sollte, können die Nebenwirkungen einer möglichen Änderung des Objektformats usw. enthalten sein. Wenn a
function_prefix
(dh eine richtige js-Funktion) zum Empfangen des JSON-Objekts verwendet wird, kann diese Funktion Überprüfungen durchführen, bevor die zurückgegebenen Daten akzeptiert / weiterverarbeitet werden.quelle
JSONP ist ein guter Weg, um domänenübergreifende Skriptfehler zu umgehen. Sie können einen JSONP-Dienst nur mit JS nutzen, ohne einen AJAX-Proxy auf der Serverseite implementieren zu müssen.
Sie können den Dienst b1t.co verwenden , um zu sehen, wie es funktioniert. Dies ist ein kostenloser JSONP-Dienst, mit dem Sie Ihre URLs minimieren können. Hier ist die URL, die für den Dienst verwendet werden soll:
http://b1t.co/Site/api/External/MakeUrlWithGet?callback=[resultsCallBack‹&url=[escapedUrlToMinify]
Zum Beispiel der Aufruf http://b1t.co/Site/api/External/MakeUrlWithGet?callback=whateverJavascriptName&url=google.com
würde zurückkehren
Und wenn dies als src in Ihr js geladen wird, wird automatisch der JavaScript-Name ausgeführt, den Sie als Rückruffunktion implementieren sollten:
Um den JSONP-Aufruf tatsächlich durchzuführen, können Sie dies auf verschiedene Arten tun (einschließlich der Verwendung von jQuery). Hier ist jedoch ein reines JS-Beispiel:
Ein schrittweises Beispiel und ein jsonp-Webdienst zum Üben finden Sie unter: diesem Beitrag
quelle
Ein einfaches Beispiel für die Verwendung von JSONP.
client.html
server.php
quelle
Bevor Sie JSONP verstehen, müssen Sie das JSON-Format und XML kennen. Derzeit ist XML das am häufigsten verwendete Datenformat im Web, XML ist jedoch sehr kompliziert. Es macht Benutzer unpraktisch, in Webseiten eingebettete Prozesse zu verarbeiten.
Damit JavaScript auch als Datenverarbeitungsprogramm problemlos Daten austauschen kann, verwenden wir den Wortlaut gemäß JavaScript-Objekten und haben ein einfaches Datenaustauschformat entwickelt, das JSON ist. JSON kann als Daten oder als JavaScript-Programm verwendet werden.
JSON kann direkt in JavaScript eingebettet werden. Mit ihnen können Sie bestimmte JSON-Programme direkt ausführen. Aus Sicherheitsgründen deaktiviert der Sandbox-Mechanismus des Browsers jedoch die domänenübergreifende Ausführung von JSON-Code.
Damit JSON nach der Ausführung übergeben werden kann, haben wir ein JSONP entwickelt. JSONP umgeht die Sicherheitsgrenzen des Browsers mit der JavaScript-Rückruffunktion und dem <script> -Tag.
Kurz gesagt, es erklärt, was JSONP ist, welches Problem es löst (wann es verwendet werden soll).
quelle
TL; DR
JSONP ist ein alter Trick, der erfunden wurde, um die Sicherheitsbeschränkung zu umgehen, die es uns verbietet, JSON-Daten von einem anderen Server (einem anderen Ursprung * ) abzurufen.
Der Trick funktioniert mit einem
<script>
Tag, das an dieser Stelle nach dem JSON fragt, z. B.:{ "user":"Smith" }
Aber in eine Funktion eingeschlossen, das eigentliche JSONP ("JSON with Padding"):Wenn wir es in dieser Form erhalten, können wir die Daten innerhalb unserer
peopleDataJSONP
Funktion verwenden. JSONP ist eine schlechte Praxis , verwenden Sie es nicht (siehe unten)Das Problem
Angenommen, wir navigieren weiter
ourweb.com
und möchten JSON-Daten (oder wirklich alle Rohdaten) abrufenanotherweb.com
. Wenn wir eine GET-Anfrage verwenden würden (z. B.XMLHttpRequest
einenfetch
Anruf$.ajax
usw.), würde unser Browser uns mitteilen, dass dieser hässliche Fehler nicht zulässig ist:Wie bekomme ich die gewünschten Daten? Nun,
<script>
Tags unterliegen nicht dieser gesamten Serverbeschränkung (Ursprung *)! Aus diesem Grund können wir eine Bibliothek wie jQuery oder Google Maps fehlerfrei von jedem Server wie einem CDN laden.Wichtiger Punkt : Wenn Sie darüber nachdenken, handelt es sich bei diesen Bibliotheken um tatsächlichen, ausführbaren JS-Code (normalerweise eine umfangreiche Funktion mit der gesamten Logik). Aber Rohdaten? JSON-Daten sind kein Code . Es gibt nichts zu rennen; Es sind nur einfache Daten.
Daher gibt es keine Möglichkeit, mit unseren wertvollen Daten umzugehen oder sie zu manipulieren. Der Browser lädt die Daten herunter, auf die unser
<script>
Tag zeigt, und beschwert sich bei der Verarbeitung zu Recht:Der JSONP-Hack
Der alte / hackige Weg, diese Daten zu nutzen? Wir brauchen diesen Server, um ihn mit einer gewissen Logik zu senden. Wenn er geladen ist, kann Ihr Code im Browser diese Daten verwenden. Der fremde Server sendet uns also die JSON-Daten innerhalb einer JS-Funktion. Die Daten selbst werden als Eingabe dieser Funktion eingerichtet. Es sieht aus wie das:
Das macht es zu JS-Code, den unser Browser analysiert, ohne sich zu beschweren! Genau wie bei der jQuery-Bibliothek. Um dies zu erreichen, "fragt" der Client den JSONP-freundlichen Server danach, normalerweise wie folgt:
Unser Browser empfängt das JSONP mit diesem Funktionsnamen, daher benötigen wir eine Funktion mit demselben Namen in unserem Code wie folgt:
Oder so, das gleiche Ergebnis:
Der Browser lädt das JSONP herunter und führt es aus, wodurch unsere Funktion aufgerufen
data
wird , wobei das Argument unser JSON ist. Wir können jetzt mit unseren Daten machen, was wir wollen.Verwenden Sie nicht JSONP, sondern CORS
JSONP ist ein Cross-Site-Hack mit einigen Nachteilen:
Das Mitnehmen ist, dass es heutzutage nicht nötig ist, es zu benutzen .
JSONP ist der Trick, um JSON-Daten von einem anderen Server abzurufen. Wir verstoßen jedoch gegen dasselbe Sicherheitsprinzip (Same-Origin), wenn wir andere Arten von standortübergreifendem Material benötigen.
Sie sollten hier über CORS lesen , aber das Wesentliche ist:
* Der Ursprung wird durch drei Dinge definiert: Protokoll , Port und Host . So ist zum Beispiel
https://web.com
ein anderer Ursprung alshttp://web.com
(anderes Protokoll) undhttps://web.com:8081
(anderer Port) und offensichtlichhttps://thatotherweb.net
(anderer Host)quelle
Die großartigen Antworten wurden bereits gegeben, ich muss mein Stück nur in Form von Codeblöcken in Javascript geben (ich werde auch eine modernere und bessere Lösung für originensübergreifende Anfragen einschließen: CORS mit HTTP-Headern):
JSONP:
1.client_jsonp.js
2.server_jsonp.js
CORS :
3.client_cors.js
4.server_cors.js
quelle
Hier ist der Ort, mit großen Beispielen , mit der Erklärung , von der einfachstenen Anwendung dieser Technik zu den modernsten in der Ebene JavaScript:
w3schools.com / JSONP
Eine meiner bevorzugten Techniken, die oben beschrieben wurden, ist das dynamische JSON-Ergebnis , mit dem JSON im URL-Parameter an die PHP-Datei gesendet werden kann und die PHP-Datei auch ein JSON-Objekt basierend auf den erhaltenen Informationen zurückgeben kann .
Tools wie jQuery bieten auch Funktionen zur Verwendung von JSONP :
quelle