Wie kann ich ein PHP-Array in eine externe JS-Datei übergeben?

2 Antworten

Vom Fragesteller als hilfreich ausgezeichnet

In jedem Fall würde ich das Array zu einen JSON-String konvertieren und dann weitergeben. Mit JavaScript lässt sich der String gut parsen und das ermittelte Objekt/Array somit auch leicht weiterverarbeiten.

Anschließend könntest du einen dieser Transportwege wählen:

a) Du schreibst mit PHP den JavaScript-Code.

<?php
  $someArray = array('sky', 'cloud', 'blue', 'sun');
  $json = json_encode($someArray);
?>
<script>
  const data = <?= $json ?>;
</script>

Das gerenderte Ergebnis wäre:

<script>
  const data = ["sky","cloud","blue","sun"];
</script>

Mit JavaScript hättest du in nachfolgenden script-Tags problemlos Zugriff auf data.

b) Statt den JavaScript-Code zusammenzuwurschteln, könnte man die Variable $json auch in einem data-Attribut eines HTML-Elements ablegen.

<?php
  $someArray = array('sky', 'cloud', 'blue', 'sun');
  $json = htmlspecialchars(json_encode($someArray), ENT_QUOTES, 'UTF-8');
?>
<div data-json="<?= $json ?>"></div>

Beachte, dass diesmal ein Encoding notwendig wäre. JSON-Objekte sind nur mit doppelten Anführungszeichen valid, daher konvertiert json_encode die einfachen Anführungszeichen zu doppelten. Da HTML-Attribute aber ebenso doppelte Anführungszeichen für die Gruppierung ihrer Werte nutzen, gäbe es hier einen Konflikt, wenn die Anführungszeichen in $json nicht maskiert werden würden.

Das Rendering-Ergebnis wäre dieses:

<div data-json="[\"sky\", \"cloud\", \"blue\", \"sun\"]"></div>

Mit JavaScript und der vom Browser zur Verfügung gestellten DOM-API ließe sich dieser Wert leicht einlesen:

<script>
  const dataContainer = document.querySelector("[data-json]");

  if (dataContainer) {
    const data = JSON.parse(dataContainer.dataset.json);
    // do something with data (Array of strings) ...
  }
</script>

c) Du holst dir die Daten mit JavaScript via HTTP (oder WS)-Request.

Ein separates PHP-Skript generiert die Daten und gibst die bei Aufruf aus. Im Response Header kann man ruhig gleich noch mit angeben, dass das Skript Daten im JSON-Format schickt.

<?php
  header('Content-Type: application/json');
  $someArray = array('sky', 'cloud', 'blue', 'sun');
  print json_encode($someArray);

Auf deiner Seite, auf der du die Daten weiterverarbeiten möchtest, führst du den Request an dieses PHP-Skript aus.

<script>
  fetch("url/to/your/php/script")
    .then(response => response.json())
    .then(data => {
      // do something with data (Array of strings) ...
    });
</script>

Beachte hierbei, dass der Programmverlauf stets asynchron ist. Das heißt, wann (und ob) der Response ankommt, ist unbestimmt. Du kannst die Daten, die (bei Erfolg) übermittelt werden nur im Callback verarbeiten (oder müsstest mittels async/await auf sie warten).

Weiteres zur Fetch API kannst du auf MDN nachlesen (Using Fetch). Alternativ zu dieser könntest du auch noch das XMLHttpRequest-Objekt verwenden (lies dazu hier). Fetch ist allerdings kürzer und ebenso die modernere Technologie.

Zu guter Letzt ein kleines Review zu den vorgestellten Methoden:

Der erstgenannte Lösungsweg trennt nicht wirklich zwischen View- und Model/Logik. Das Zusammenstückeln von JavaScript-Code mittels PHP kann leicht Fehler bergen und der Code ist nicht gut lesbar. Daher würde ich diese Option den anderen beiden Vorschlägen nicht vorziehen.

Ein genereller Nachteil der ersten beiden Vorschläge ist, dass die zu transportierenden Daten schon beim ersten Request mit geliefert werden müssen. Bei einem sehr großen Array hättest du also auch viele Daten auf einen Schlag.

Der dritte Weg bietet dir da mehr Flexibilität. Zum einen hast du (im Gegensatz zu Vorschlag 1) eine klare Trennung zwischen Model und View und kannst die einzelnen Programmmodule leicht / gut separat voneinander testen.

Des Weiteren lassen sich Verfahren wie lazy loading besser umsetzen.

Um das an einem Beispiel zu verdeutlichen: Bei einer Fotogalerie könntest du beim ersten Request erst einmal nur die ersten 50 Bilder anfordern. Wenn der Nutzer mehr Bilder laden lassen möchte, können weitere Requests (z.B. vom Nutzer durch Buttonklicks ausgelöst) weitere Bilder anfragen, indem sie der URL Parameter mitstecken, die im PHP-Skript ausgewertet werden.

Request-URL:

https://somewebsite.com/getimages.php?start=51

PHP:

<?php
  header('Content-Type: application/json');
  
  if (!isset($_GET['start'] || !is_numeric($_GET['start'])) {
    die('[]');
  }

  $start = intval($_GET['start']);

  // get images from start to start + 50 ...
  // generate json string ...

  print $json;