Con la quantità di eccezioni e mancanza di portabilità utilizzando php://input
Si consiglia di leggere lo stream e salvarlo su un altro stream per evitare comportamenti imprevisti.
È possibile utilizzare php://memory
al fine di creare un wrapper di file-stream-like, che vi darà tutte le stesse funzionalità che php://input
dovrebbe hanno senza tutto il comportamento fastidioso.
Esempio:
<?php
$inputHandle = fopen('php://memory', 'r+');
fwrite($inputHandle, file_get_contents('php://input'));
fseek($inputHandle, 0);
Inoltre è possibile creare la propria classe per fare riferimento a questo oggetto in modo coerente:
<?php
class InputReader {
private static $instance;
/**
* Factory for InputReader
*
* @param string $inputContents
*
* @return InputReader
*/
public static function instance($inputContents = null) {
if (self::$instance === null) {
self::$instance = new InputReader($inputContents);
}
return self::$instance;
}
protected $handle;
/**
* InputReader constructor.
*
* @param string $inputContents
*/
public function __construct($inputContents = null) {
// Open up a new memory handle
$this->handle = fopen('php://memory', 'r+');
// If we haven't specified the input contents (in case you're reading it from somewhere else like a framework), then we'll read it again
if ($inputContents === null) {
$inputContents = file_get_contents('php://input');
}
// Write all the contents of php://input to our memory handle
fwrite($this->handle, $inputContents);
// Seek back to the start if we're reading anything
fseek($this->handle, 0);
}
public function getHandle() {
return $this->handle;
}
/**
* Wrapper for fseek
*
* @param int $offset
* @param int $whence
*
* @return InputReader
*
* @throws \Exception
*/
public function seek($offset, $whence = SEEK_SET) {
if (fseek($this->handle, $offset, $whence) !== 0) {
throw new \Exception('Could not use fseek on memory handle');
}
return $this;
}
public function read($length) {
$read = fread($this->handle, $length);
if ($read === false) {
throw new \Exception('Could not use fread on memory handle');
}
return $read;
}
public function readAll($buffer = 8192) {
$reader = '';
$this->seek(0); // make sure we start by seeking to offset 0
while (!$this->eof()) {
$reader .= $this->read($buffer);
}
return $reader;
}
public function eof() {
return feof($this->handle);
}
}
Usage:
$first1024Bytes = InputReader::instance()->seek(0)->read(1024);
$next1024Bytes = InputReader::instance()->read(1024);
Usage (leggi tutto):
$phpInput = InputReader::instance()->readAll();
Con la quantità di eccezioni nel manuale e la mancanza di portabilità, vi consiglio semplicemente salvando il risultato dopo aver letto la prima volta. Dopo questo puoi cercare quanto vuoi con il risultato (e non devi salvarlo su un file - php: // memory' dovrebbe farlo.) – h2ooooooo
@ h2ooooooo grazie, ho rinunciato a "riparare "questo problema e si è concluso con un piano per evitare di leggere l'input più di una volta in tutti i miei progetti futuri, come suggerivi tu. Se convertirai il tuo commento in una risposta, lo accetterò. – gseric
Prego, dammi un secondo e avrò una risposta. – h2ooooooo