Commit a038a094 authored by Alexandre Morin's avatar Alexandre Morin

Merge branch 'hotfix/2.6' into 'master'

hotfix/2.6 into master

See merge request !440
parents ac413d57 205a1be9
Pipeline #7174 failed with stages
......@@ -30,7 +30,7 @@ namespace core\Encoding;
class Base64
{
/**
* Encode stream
* Decode stream
*/
public static function decode($value)
{
......@@ -41,10 +41,36 @@ class Base64
if (is_resource($value)) {
$stream = fopen('php://temp', 'w+');
while (!feof($value)) {
$chunk = fread($value, 1024*1024*2);
// Chunk size 1024*1024*2 (2Mo binary)
$chunk = fread($value, 2097152);
fwrite($stream, base64_decode($chunk));
}
rewind($value);
rewind($stream);
return $stream;
}
}
/**
* Encode stream
*/
public static function encode($value)
{
if (is_scalar($value)) {
return base64_encode($value);
}
if (is_resource($value)) {
$stream = fopen('php://temp', 'w+');
while (!feof($value)) {
// Chunk size 48*48*48/2 (2M of base64 6 bytes words)
$chunk = fread($value, 2654208);
fwrite($stream, base64_encode($chunk));
}
rewind($value);
rewind($stream);
return $stream;
......
<?php
class JsonSerializer
{
protected $salt;
protected $resources = [];
public function serialize($data, $options)
{
$data = $this->getRefs($data);
$json = json_encode($data, $options);
$parts = preg_split('/(Resource id #\d+)/', $json, 0, PREG_SPLIT_DELIM_CAPTURE);
$stream = fopen('php://temp', 'w+');
foreach ($parts as $part) {
if (isset($this->resources[$part])) {
stream_copy_to_stream($this->resources[$part], $stream);
} else {
fwrite($stream, $part);
}
}
rewind($stream);
return $stream;
}
/**
* Converts resources to refs "Resource id #i"
*/
protected function getRefs($data)
{
if (is_scalar($data)) {
return $data;
}
if (is_array($data)) {
foreach ($data as $key => $value) {
$data[$key] = $this->getRefs($value);
}
return $data;
}
if (is_object($data)) {
foreach ($data as $key => $value) {
$data->{$key} = $this->getRefs($value);
}
return $data;
}
if (is_resource($data)) {
$ref = (string) $data;
$this->resources[$ref] = $data;
return $ref;
}
}
}
......@@ -213,60 +213,30 @@ class JsonTokenizer
do {
$chunk = fread($this->stream, $this->threshold);
$length = strlen($chunk);
if (preg_match('#^[^"\\\\]*(?:\\\\.[^"\\\\]*)*"#', $chunk, $matches)) {
$tail = substr($matches[0], 0, -1);
if (preg_match('/(?<!\\\\)(?:\\\\{2})*\\K"/', $chunk, $matches, PREG_OFFSET_CAPTURE)) {
$tail = substr($chunk, 0, $matches[0][1]);
$end = strlen($tail);
$size += $end;
fwrite($buffer, $tail);
fwrite($buffer, $this->unescape($tail));
fseek($this->stream, (-$length+$end+1), SEEK_CUR);
rewind($buffer);
$out = $this->unescapeStream($buffer, $this->threshold);
if ($size < $this->threshold) {
return stream_get_contents($buffer);
return stream_get_contents($out);
}
return $buffer;
return $out;
}
fwrite($buffer, $chunk);
fwrite($buffer, $this->unescape($chunk));
$size += $this->threshold;
} while ($chunk);
return $buffer;
}
while (true) {
$char = fread($this->stream, 1);
// Unterminated string (waiting for quotes)
if ($char === false || $char === "") {
throw new Exception("String not terminated correctly " . ftell($this->stream));
}
// Terminated string
if ($quotes == $char && !$escaped) {
if (is_resource($buffer)) {
return $buffer;
} else {
return json_decode($quotes . $buffer . $quotes);
}
}
// Continued
if (is_string($buffer)) {
$buffer .= $char;
$size++;
if (strlen($buffer) == $this->threshold) {
$tmp = fopen('php://temp', 'w+');
fwrite($tmp, $buffer);
$buffer = $tmp;
}
} else {
fwrite($buffer, $char);
}
$escaped = !$escaped && $quotes === "\"" && $char == "\\";
}
}
/**
* @param $char
......@@ -333,4 +303,34 @@ class JsonTokenizer
{
return end($this->context);
}
/**
* Unsescape a stream contents
*/
protected function unescapeStream($stream)
{
$out = fopen('php://temp', 'w+');
do {
// Add 1 to chunk length to prevent end of chunk escape chars
$chunk = fread($stream, $this->threshold+1);
fwrite($out, $this->unescape($chunk));
} while ($chunk);
rewind($out);
rewind($stream);
return $out;
}
/**
* Unescape string or chunk
*/
protected function unescape($string)
{
$escaped = array('\\\\', '\\/', '\\"', "\\n", "\\r", "\\t", "\\f", "\\b");
$unescaped = array('\\', '/', '"', "\n", "\r", "\t", "\x08", "\x0c");
$result = str_replace($escaped, $unescaped, $string);
return $result;
}
}
......@@ -77,7 +77,11 @@ class json
*/
public static function encode($data)
{
$jsonString = \json_encode($data, \JSON_PRETTY_PRINT + \JSON_UNESCAPED_SLASHES + \JSON_UNESCAPED_UNICODE);
require_once __DIR__.'/JsonSerializer.php';
$serializer = new \JsonSerializer();
//$jsonString = \json_encode($data, \JSON_PRETTY_PRINT + \JSON_UNESCAPED_SLASHES + \JSON_UNESCAPED_UNICODE);
$jsonString = $serializer->serialize($data, \JSON_PRETTY_PRINT + \JSON_UNESCAPED_SLASHES + \JSON_UNESCAPED_UNICODE);
if ($jsonString === false) {
return false;
......
......@@ -556,12 +556,12 @@ trait archiveAccessTrait
if (\laabs::isServiceClient()) {
// Returns base64 encoded contents for web service clients
$binaryDataObject->attachment->data = base64_encode($digitalResource->getContents());
$binaryDataObject->attachment->data = \core\Encoding\Base64::encode($digitalResource->getHandler());
} else {
// Let presenter stream the contents
$binaryDataObject->attachment->data = $digitalResource->getHandler();
}
$binaryDataObject->attachment->uri = "";
$binaryDataObject->attachment->filename = $digitalResource->fileName;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment