I just upgraded my server’s PHP version to PHP 7.4.1 and now getting this error:
Notice: Trying to access array offset on value of type bool in
public static function read($id)
{
$Row = MySQL::query("SELECT `Data` FROM `cb_sessions` WHERE `SessionID` = '$id'", TRUE);
# http://php.net/manual/en/function.session-start.php#120589
//check to see if $session_data is null before returning (CRITICAL)
if(is_null($Row['Data']))
{
$session_data = '';
}
else
{
$session_data = $Row['Data'];
}
return $session_data;
}
What is the fix for PHP 7.4 ?
Dharman♦
30.3k22 gold badges84 silver badges132 bronze badges
asked Jan 10, 2020 at 2:48
7
Easy with PHP ??
null coalescing operator
return $Row['Data'] ?? 'default value';
Or you can use as such
$Row['Data'] ??= 'default value';
return $Row['Data'];
Dharman♦
30.3k22 gold badges84 silver badges132 bronze badges
answered Jan 10, 2020 at 19:19
dılo sürücüdılo sürücü
3,6771 gold badge25 silver badges28 bronze badges
2
If your query does not return a row, then your variable $Row will be filled with false,
so you can test if the variable has a value before try to access any index inside it:
if($Row){
if(is_null($Row['Data']))
{
$session_data = '';
}...
answered Jan 10, 2020 at 18:45
Здравствуйте.
На одном из проектов встретил нотис:
Notice: Trying to access array offset on value of type bool in …
Погуглив понял, что это новшество в 7.4, но вот не могу понять как его исправить.
Участок кода где появился нотис
$init = $_POST['external_url'] ?? null;
$preparedLink = prepareExternalLink($init);
$sth = db_query("SELECT external_url, created_short_id FROM result WHERE external_url='" . $preparedLink . "'")->fetch();
if ($sth) {
$_COOKIE['unique_url'] = false;
} elseif (isset($_COOKIE['url_empty'])) {
$_COOKIE['unique_url'] = false;
} elseif (isset($_COOKIE['url_incorrect'])) {
$_COOKIE['unique_url'] = false;
} else {
$_COOKIE['unique_url'] = true;
}
$short_url = "{$_SERVER['HTTP_HOST']}/r_{$sth['created_short_id']}";
if ($sth !== false) {
$sth = array_merge($sth, ['short_link' => $short_url]);
$sth = changeKeyExistArray($sth,
['external_url', 'created_short_id', 'short_link', 0],
['External_url', 'ID_short_url', 'Result_url', 'Unique_url']);
}
Нотис указывает на эту строчку:
$short_url = "{$_SERVER['HTTP_HOST']}/r_{$sth['created_short_id']}";
не подскажите как исправить?
-
Вопрос заданболее трёх лет назад
-
7115 просмотров
Судя по всему, в $sth у вас записано булево значение (предположительно, false). Попасть в переменную это значение могло только при вызове функции db_query()->fetch(). Вот там и ищите проблему. Функция db_query к стандартным не относится, значит смотрите в своём коде, что она возвращает и почему.
Пригласить эксперта
-
Показать ещё
Загружается…
25 мая 2023, в 09:23
1000 руб./в час
25 мая 2023, в 09:14
3000 руб./за проект
25 мая 2023, в 08:33
2000 руб./за проект
Минуточку внимания
При установке Opencart на новые версии PHP>=7.4 вы можете получить эту ошибку:
Trying to access array offset on value of type bool in catalog/controller/startup/startup.php on line 172
Вот строка 172 из этого файла, где возникает ошибка:
$this->tax->setPaymentAddress($this->session->data[‘payment_address’][‘country_id’], $this->session->data[‘payment_address’][‘zone_id’]);
Если в сессии отсутствует country_id или zone_id — получаем эту ошибку.
В новых версиях PHP нужно обязательно проверять наличие элементов массива перед работой с ними.
Решение.
В файле catalog/controller/startup/startup.php найдите строку 171:
if (isset($this->session->data[‘shipping_address’])) {
замените ее на
if (isset($this->session->data[‘shipping_address’][‘country_id’]) && isset($this->session->data[‘shipping_address’][‘zone_id’])) {
Сохраните файл, обновите кэш модификаторов в админке.
Автор: | Дата: 10.12.2020
Популярные модули Opencart 3.0
Модуль Блог для Opencart 3.0
С выходом новой версии Opencart 3.x так и ничего не изменилось в плане встроенных статей — их нет, к..
Всего 637 руб.
Рекомендуем
Миграция с PHP5 на PHP7 и PHP8: что чаще всего приходится править в исходниках
Если не считать необходимого теперь перехода с MySQL на MySQLi и борьбы с Warning: A non-numeric value encountered, есть ещё несколько типовых проблем при миграции скриптов с PHP 5.X (особенно если исходная версия ниже 5.3) на PHP 7.3 — 7.4, а позднее и на PHP 8. Попробую приспособить для описания решений эту заметку, если ещё всплывёт подобное.
Для проверки фрагментов кода предполагалось, что в его начале указана директива
error_reporting (E_ALL);
Уведомление Trying to access array offset on value of type null/bool/int
Часто возникает при использовании синтаксиса обращения к элементу массива на других типах данных. Пример:
$a = false; var_dump($a['somekey']); // PHP 7.3: // NULL // // PHP 7.4: // Notice: Trying to access array offset on value of type bool in Command line code on line ...
Так бывает, например, если функция может возвращать массив в нормальном случае и false/null в случае ошибки, а дальше вверх по стеку информация о false/null теряется и этот случай не обрабатывается отдельно.
Решение — проверять с помощью is_array, является ли объект массивом.
Применение функции mysql_real_escape_string
…которой традиционно «обезопасивали» хранимые в базе данных строки от SQL-инъекций.
было: mysql_real_escape_string($s)
надо: mysqli_real_escape_string ($id,$s)
, где $id
— идентификатор соединения MySQLi. Или хотя бы addslashes($s)
— если нужно только экранировать «опасные» для SQL-запроса кавычки.
Перебор массива с помощью list и each
было: while (list(,$var) = each($params)) {
надо: foreach ($params as $var) {
или же: while (list($num,$var) = each($params)) {
а теперь: foreach ($params as $num=>$var) {
— если массив перебирается как ассоциативный и/или нужны ключи его элементов.
Модификатор /e функции preg_replace
было:
$text = preg_replace('~([0-9]+)^([0-9]+)~e', 'pow("\1", "\2")', $text); //вычислить a^b
надо:
$text = preg_replace_callback('~([0-9]+)^([0-9]+)~',
function ($m) { return pow($m[1], $m[2]); }, $text); //вычислить a^b
— то есть, через callback-функцию.
Проблема с подключаемыми графическими шрифтами GD
было:
$bbox=imagettfbbox ($f,0,'arial.ttf','String');
надо:
$font = dirname(__FILE__) . '/arial.ttf';
$bbox=imagettfbbox ($f,0,$font,'String');
— если фонт лежит в папке скрипта, как обычно и бывает.
То же самое с imageTtfText
, например:
$font = dirname(__FILE__) . '/Roboto-Bold.ttf'; imageTtfText($myimg, $size, $angle, $j, 30, $c, $font, $z);
error_reporting(0) и подобное
Многие разработчики привыкли решать проблему с предупреждениями и даже сообщениями об ошибках просто выключая сообщения о них. При миграции скриптов это приводит к «загадочным белым экранам» вместо содержимого. Лучше всего вообще не трогать включённое в новых версиях протоколирование ошибок по умолчанию, а все вызовы функции error_reporting
приводить к виду, указанному в начале статьи.
Строковые функции
Начиная с версии PHP 5.6 кодировкой по умолчанию стала кодировка Юникода UTF-8, соответственно, вместо прежних «си-подобных» строковых функций теперь лучше использовать их многобайтовые аналоги.
Наиболее часто приходится менять:
- вместо
strlen($s)
писатьmb_strlen($s,'UTF-8')
; - вместо
strpos ($haystack,$needle,0)
писатьmb_strpos ($haystack,$needle,0,'UTF-8')
; - вместо
strstr ($haystack,$needle,false)
писатьmb_strstr ($haystack,$needle,false,'UTF-8')
; - вместо
substr ($string,$start,$length)
писатьmb_substr ($string,$start,$length,'UTF-8')
…и т.д., принцип, думаю, понятен. Будьте внимательны, проверяя, есть ли для функции многобайтовый аналог.
Для «бинарно безопасных» функций strcmp
/ strcasecmp
, к примеру, таковых нет, а сравнение всё равно не работает:
<?php $s1="Привет"; $s2="привет"; echo strcasecmp($s1,$s2); //-32 ?>
и нужно делать так:
<?php function mb_strcasecmp($str1, $str2, $encoding = null) { if (null === $encoding) { $encoding = mb_internal_encoding(); } return strcmp(mb_strtoupper($str1, $encoding), mb_strtoupper($str2, $encoding)); } $s1="Привет"; $s2="привет"; echo mb_strcasecmp($s1,$s2,'UTF-8'); //0 ?>
С другой стороны, как видно из примера, для strtoupper
и strtolower
эти аналоги есть.
Применение array_key_exists к объекту, а не к массиву
Теперь нельзя применять array_key_exists
к объектам классов (а можно только к массивам). Неправильно:
class foo { public $a, $b; }; $bar = new foo(); echo (array_key_exists('a',$bar) ? 'yes' : 'no'); //deprecated
Правильно:
echo (property_exists($bar,'a') ? 'yes' : 'no'); //yes
Итак, 8-я версия, вышедшая в ноябре-2020, теперь есть и в составе XAMPP, ниже, вероятнее всего, будут добавляться исправления для PHP8, хотя и для версии 7 всё написанное выше остаётся в силе.
Отмечу, что в сборке PHP 8.0.0 с сайта XAMPP в файле
php.ini
(диск:xamppphpphp.ini
) была по умолчанию отключена библиотека gd:;extension=gdСоответственно, все функции imagecreatetruecolor,
imagecreatefromgif,
imagecreatefromjpeg,
imagecreatefrompng и т.д. «вдруг перестали работать».Решение — убрать точку с запятой из первой позиции указанной выше строки,
сохранить изменённыйphp.ini
, перезагрузиться.
Функция get_magic_quotes_gpc удалена (PHP8)
Любые упоминания о функции get_magic_quotes_gpc теперь придётся исключить из кода, она просто удалена. При этом нужно учесть, что начиная с версии 5.4 она всё равно всегда возвращала 0.
Почему нельзя было оставить в реализации пустое имя функции, а надо заставлять людей переделывать кучу кода — совершенно неясно.
И так у них всё
Функция each удалена (PHP8)
Удалена в PHP8 и функция each. В общем случае можно попытаться заменить на next
или array_shift, но однозначного рецепта нет из-за возможности использования функции не только в цикле, как показано выше, но и, например, в рекурсивных построениях.
Фигурные скобки и литералы без кавычек для индексов массива (PHP8)
В PHP8 больше нельзя писать $a{$i}
вместо $a[$i]
или $foo[bar]
вместо $foo['bar']
. Просто исправьте это.
Разумеется, если ключ является числовой константой или берётся из переменной, заключать его в апострофы не нужно, $i = 1; $a[$i]
или $a[1]
— это верный синтаксис.
13.02.2020, 17:35 [17598 просмотров]
Code: Select all
SyntaxError: JSON.parse: unexpected character at line 1 column 1 of the JSON data
OK
<b>Notice</b>: Trying to access array offset on value of type bool in <b>/var/www/site/html/catalog/controller/startup/startup.php</b> on line <b>166</b><b>Notice</b>: Trying to access array offset on value of type bool in <b>/var/www/site/html/catalog/controller/startup/startup.php</b> on line <b>166</b>{"country_id":"2","name":"Albania","iso_code_2":"AL","iso_code_3":"ALB","address_format":"","postcode_required":"0","zone":[{"zone_id":"33","country_id":"2","name":"Berat","code":"BR","status":"1"},{"zone_id":"34","country_id":"2","name":"Bulqize","code":"BU","status":"1"},{"zone_id":"35","country_id":"2","name":"Delvine","code":"DL","status":"1"},{"zone_id":"36","country_id":"2","name":"Devoll","code":"DV","status":"1"},{"zone_id":"37","country_id":"2","name":"Diber","code":"DI","status":"1"},{"zone_id":"38","country_id":"2","name":"Durres","code":"DR","status":"1"},{"zone_id":"39","country_id":"2","name":"Elbasan","code":"EL","status":"1"},{"zone_id":"41","country_id":"2","name":"Fier","code":"FR","status":"1"},{"zone_id":"42","country_id":"2","name":"Gjirokaster","code":"GJ","status":"1"},{"zone_id":"43","country_id":"2","name":"Gramsh","code":"GR","status":"1"},{"zone_id":"44","country_id":"2","name":"Has","code":"HA","status":"1"},{"zone_id":"45","country_id":"2","name":"Kavaje","code":"KA","status":"1"},{"zone_id":"40","country_id":"2","name":"Kolonje","code":"ER","status":"1"},{"zone_id":"48","country_id":"2","name":"Korce","code":"KO","status":"1"},{"zone_id":"49","country_id":"2","name":"Kruje","code":"KR","status":"1"},{"zone_id":"47","country_id":"2","name":"Kucove","code":"KC","status":"1"},{"zone_id":"50","country_id":"2","name":"Kukes","code":"KU","status":"1"},{"zone_id":"46","country_id":"2","name":"Kurbin","code":"KB","status":"1"},{"zone_id":"52","country_id":"2","name":"Lezhe","code":"LE","status":"1"},{"zone_id":"51","country_id":"2","name":"Librazhd","code":"LB","status":"1"},{"zone_id":"53","country_id":"2","name":"Lushnje","code":"LU","status":"1"},{"zone_id":"54","country_id":"2","name":"Malesi e Madhe","code":"MM","status":"1"},{"zone_id":"55","country_id":"2","name":"Mallakaster","code":"MK","status":"1"},{"zone_id":"56","country_id":"2","name":"Mat","code":"MT","status":"1"},{"zone_id":"57","country_id":"2","name":"Mirdite","code":"MR","status":"1"},{"zone_id":"58","country_id":"2","name":"Peqin","code":"PQ","status":"1"},{"zone_id":"59","country_id":"2","name":"Permet","code":"PR","status":"1"},{"zone_id":"60","country_id":"2","name":"Pogradec","code":"PG","status":"1"},{"zone_id":"61","country_id":"2","name":"Puke","code":"PU","status":"1"},{"zone_id":"64","country_id":"2","name":"Sarande","code":"SR","status":"1"},{"zone_id":"62","country_id":"2","name":"Shkoder","code":"SH","status":"1"},{"zone_id":"63","country_id":"2","name":"Skrapar","code":"SK","status":"1"},{"zone_id":"65","country_id":"2","name":"Tepelene","code":"TE","status":"1"},{"zone_id":"67","country_id":"2","name":"Tirane","code":"TR","status":"1"},{"zone_id":"66","country_id":"2","name":"Tropoje","code":"TP","status":"1"},{"zone_id":"68","country_id":"2","name":"Vlore","code":"VL","status":"1"}],"status":"1"}