2016-12-28 8 views
2

Этот вопрос связан с this one, и я жесткая проблема была исправлена, но на удивление нет. Я снова напишу тот же код (я удалил комментарии и фрагменты кода, это всего лишь общий пример), чтобы сделать это сообщение понятным.Что может помешать серверу отправить действительный ответ?

В настоящее время это код, который я имею в Zend Framework 1 контроллер:

public function uploadAction() 
{ 
    $this->_helper->viewRenderer->setNoRender(); 
    $data = $errors = $line_of_text = []; 

    if ($this->getRequest()->isPost()) { 
     $path = '/cronjobs/uploads/charge_type_details'; 

     if ([email protected]($path, 0777, true) && !is_dir($path)) { 
      $data['error'][] = "Not able to create subdirectory: <strong>{$path}</strong>"; 
      echo json_encode($data); 

      die(); 
     } 

     $di = new RecursiveDirectoryIterator($path, FilesystemIterator::SKIP_DOTS); 
     $ri = new RecursiveIteratorIterator($di, RecursiveIteratorIterator::CHILD_FIRST); 
     foreach ($ri as $file) { 
      $file->isDir() ? rmdir($file) : unlink($file); 
     } 

     $adapter = new Zend_File_Transfer_Adapter_Http(); 
     $adapter->setDestination($path); 
     $adapter->addValidator('Extension', false, ['extension' => 'csv', 'case' => true]); 
     $adapter->addValidator('MimeType', false, 'text/plain'); 
     $adapter->addValidator('Size', false, ['max' => ini_get('upload_max_filesize').'B']); 

     if ($adapter->isValid() === false) { 
      foreach ($adapter->getMessages() as $message) { 
       $data['error'][] = $message; 
      } 

      echo json_encode($data); 

      die(); 
     } 

     $file  = $adapter->getFileInfo()['file']; 
     $ext  = pathinfo($file['name'])['extension']; 
     $new_path = $file['tmp_name']; 

     $file_handle = fopen($new_path, 'r'); 

     while (($result = fgetcsv($file_handle)) !== false) { 
      if (array(null) !== $result) { // ignore blank lines 
       $line_of_text[] = $result; 
      } 
     } 

     $unique_rows = array_unique($line_of_text, SORT_REGULAR); 

     if (false === $this->isFileHeadersValid(
       array_map('strtolower', $unique_rows[0]), 
       [ 
        'country', 
        'charge_type', 
        'charge_type_code', 
        'business_sla_description', 
        'service_provider', 
        'sub_menu', 
        'charge_type_group', 
        'transaction_type', 
        'slc_code', 
        'coverage_code', 
        'standard_sla', 

       ] 
      ) 
     ) { 
      $data['error'][] = $this->translate->_('Required file headers are not present. Please check the file and try again.'); 
      echo json_encode($data); 

      die(); 
     } 

     unset($unique_rows[0]); 

     $data['error'] = $errors; 

     $data['file'] = array(
      'name'  => $file['name'], 
      'size'  => $adapter->getFileSize(), 
      'file_ext' => $ext 
     ); 
    } else { 
     $data['error'] = 'Invalid request.'; 
    } 

    echo json_encode($data); 

    die(); 
} 

Эта функция вызывается с помощью JavaScript, как функция AJAX:

$('#fileupload').show().fileupload({ 
    url: '/upload', 
    cache: false, 
    dataType: 'json', 
    done: function (e, data) { 
     if (data.result.error.length > 0) { 
      // process errors here 
     } else { 
      // do something here 
     } 
    } 
}) 

Я загрузив файл с около 1,5 МБ размера и около 9000 строк (это CSV-файл).

Как только я загружаю этот файл, все, кажется, работает, и это означает, что выполнение кода на стороне PHP продолжается до последнего echo json_encode($data); без «ошибки». Я знал это, потому что я использую Xdebug для отладки кода в среде IDE.

По какой-то причине ответ не возвращается в браузер, и я получаю следующее сообщение: «Не удалось загрузить ответ», и я не могу правильно обработать ответ.

enter image description here

enter image description here

enter image description here

Я проверил результат json_encode($data), назначив его на вар и все, кажется, хорошо, как на этом выходе (имена файлов на изображениях и это примеры различны, но это только для показанной надлежащей функциональности):

{ 
    "error": [], 
    "file": { 
    "name": "test1.csv", 
    "size": "1.24kB", 
    "file_path": "/data/tmp/php/uploads/phpSh2tZt", 
    "file_ext": "csv", 
    "delimiter": "", 
    "worksheets": [] 
    } 
} 

Я проверил процесс в Chrome и Firefox и Status на ответ отправлен, как вы могли видеть на изображениях выше. Зачем? Я не знаю, что еще делать, чтобы исправить это, я не знаю, откуда исходит ошибка (это не из PHP-кода, потому что, поскольку я сказал, что все работает правильно на уровне кода, и журналы говорят так), и я застрял в этой точке, может ли кто-нибудь дать мне некоторые идеи или понять об этом?

Мое окружение работает в Docker, если это помогает.

Установка PHP выглядит следующим образом:

memory_limit = 2048M 
post_max_size = 128M 
upload_max_filesize = 128M 
date.timezone = UTC 
max_execution_time = 120 
short_open_tag=On 
serialize_precision=100 
session.gc_maxlifetime=7200 
session.entropy_length=0 

PS: если вам нужен какой-либо информации, дайте мне знать, и я добавлю его в ОП

UPDATE

Я только выяснил, где может быть проблема, и мне любопытно «почему». Имея следующий код:

$adapter = new Zend_File_Transfer_Adapter_Http(); 
$adapter->setDestination($path); 
$adapter->addValidator('Extension', false, ['extension' => 'csv', 'case' => true]); 
$adapter->addValidator('MimeType', false, 'text/plain'); 
$adapter->addValidator('Size', false, ['max' => ini_get('upload_max_filesize').'B']); 

if ($adapter->isValid() === false) { 
    foreach ($adapter->getMessages() as $message) { 
     $data['error'][] = $message; 
    } 

    echo json_encode($data); 

    die(); 
} 

Делает полный код недействительным, получая отклик в браузере.Отказ от проверки заставляет код работать должным образом:

$adapter = new Zend_File_Transfer_Adapter_Http(); 
$adapter->setDestination($path); 

Возможно, что-то не так? Я что-то упустил?

UPDATE 2

Это в настоящее время, как код выглядит следующим образом:

.... 
$adapter = new Zend_File_Transfer_Adapter_Http(); 
$adapter->setDestination($path); 
$adapter->addValidator('Extension', false, ['extension' => 'csv', 'case' => true]); 
$adapter->addValidator('MimeType', false, ['text/plain', 'text/csv']); 
$adapter->addValidator('Size', false, ['max' => $this->SizeToBytes(ini_get('upload_max_filesize'))]); 

if ($adapter->receive() === false || $adapter->isValid() === false) { 
    foreach ($adapter->getMessages() as $message) { 
     $data['error'][] = $message; 
    } 

    echo json_encode($data); 

    return true; 
} 
.... 
private function SizeToBytes($val) 
{ 
    $val = trim($val); 
    $last = strtolower($val[strlen($val) - 1]); 
    switch ($last) { 
     case 'g': 
      $val *= 1024; 
     case 'm': 
      $val *= 1024; 
     case 'k': 
      $val *= 1024; 
    } 

    return $val; 
} 

Это не работает. Единственный способ, которым я получил это работа движется к «ванильным» PHP следующим образом:

// Validate file mimetype 
if (!in_array($adapter->getMimeType(), ['text/plain', 'text/csv'])) { 
    $data['error'][] = $this->translate->_('File is not valid only CSV files are accepted!'); 
    echo json_encode($data); 

    return true; 
} 

// Validate file extension 
if ($ext !== 'csv') { 
    $data['error'][] = $this->translate->_('File extension is not valid only CSV files are accepted!'); 
    echo json_encode($data); 

    return true; 
} 

// Validate file size depending on php.ini upload_max_filesize configuration 
$max = $this->SizeToBytes(ini_get('upload_max_filesize')); 
if ($file['size'] > $max) { 
    $data['error'][] = $this->translate->_e('File size is not valid! The size should be less than: ').ini_get('upload_max_filesize').'B'; 
    echo json_encode($data); 

    return true; 
} 

Таким образом, он работает как шарм.

+0

Если вы используете Xdebug вы не можете пройти через него и посмотреть, в какой момент она перестает в коде проверки? – mickadoo

+0

@ mickadoo Да, у меня Xdebug, но код немного близок к концу исполнения без ошибок, это нечетно – ReynierPM

+0

Хм, но вы сказали, что код проверки он терпит неудачу. Работает ли он на 100% без кода проверки - вы получаете правильный ответ в браузере? – mickadoo

ответ

0

Вы используете гораздо меньший максимальный размер (128 байт), чем вы планировали.

Вы должны преобразовать введенное ini upload_max_filesize в полное целочисленное значение (~ 128000000).

Например:

$adapter->addValidator('Size', false, ['max' => 128000000]); 
+0

Это не сработало – ReynierPM

0

Что касается Status & "почему":

Я думаю, с помощью http_response_code(200) на перерабатывающем странице ответа Ajax может помочь.

+0

Я не думаю, что это хорошее решение, так как запрос может сбой действительно – ReynierPM

0

Разве вы не называете «$ adapter-> receive()» где-то?

https://framework.zend.com/manual/1.11/en/zend.file.transfer.introduction.html

$adapter = new Zend_File_Transfer_Adapter_Http(); 

$adapter->setDestination('C:\temp'); 

if (!$adapter->receive()) { 
    $messages = $adapter->getMessages(); 
    echo implode("\n", $messages); 
} 
+0

Проверить ** ОБНОВЛЕНИЕ 2 ** есть ваш ответ ... Я использую '$ adapter-> receive() === false' ... – ReynierPM

 Смежные вопросы

  • Нет связанных вопросов^_^