{"id":19033446,"date":"2026-09-30T18:55:24","date_gmt":"2026-09-30T18:55:24","guid":{"rendered":"https:\/\/wordpress.org\/support\/topic\/fatal-valueerror-max-on-empty-sessions-in-concurrentlogin-php-8\/"},"modified":"2026-09-30T18:55:24","modified_gmt":"2026-09-30T18:55:24","slug":"fatal-valueerror-max-on-empty-sessions-in-concurrentlogin-php-8","status":"publish","type":"topic","link":"https:\/\/wordpress.org\/support\/topic\/fatal-valueerror-max-on-empty-sessions-in-concurrentlogin-php-8\/","title":{"rendered":"Fatal ValueError: max() on empty sessions in ConcurrentLogin (PHP 8)"},"content":{"rendered":"\n<pre class=\"wp-block-code\"><code>Hi,<br \/><br \/>We run Inactive Logout on about a dozen sites (PHP 8.4 and 8.5) with concurrent-login limiting on. <strong>**3.6.3**<\/strong> (current trunk) can throw a hard fatal in <code>core\/ConcurrentLogin.php<\/code>, <code>concurrent_logins()<\/code>:<br \/><br \/><code>&lt;br&gt;&lt;br&gt;PHP Fatal error: Uncaught ValueError: max(): Argument #1 ($value) must contain at least one element in ...\/inactive-logout\/core\/ConcurrentLogin.php:80&lt;br&gt;&lt;br&gt;<\/code><br \/><br \/><strong>**Lines 79-82:**<\/strong><br \/><br \/><code>php&lt;br&gt;&lt;br&gt;$sessions = wp_get_all_sessions();&lt;br&gt;&lt;br&gt;$newest \u00a0 = max( wp_list_pluck( $sessions, &#039;login&#039; ) );&lt;br&gt;&lt;br&gt;$session \u00a0= $this-&gt;get_current_session();&lt;br&gt;&lt;br&gt;if ( $session&amp;#091;&#039;login&#039;] === $newest ) {&lt;br&gt;&lt;br&gt;<\/code><br \/><br \/>Two things can go wrong here:<br \/><br \/>1. <strong>**Line 80:**<\/strong> <code>wp_get_all_sessions()<\/code> can return an empty array if the tokens expire or are destroyed (for example by <code>wp_destroy_all_sessions()<\/code> from another plugin) between the <code>user_has_multiple_sessions()<\/code> check on line 53 and this call. On PHP 7, <code>max()<\/code> on an empty array was only a warning. On PHP 8+ it throws a <code>ValueError<\/code>, which white-screens the request.<br \/><br \/>2. <strong>**Line 82:**<\/strong> <code>get_current_session()<\/code> returns <code>WP_Session_Tokens::get()<\/code>, which is <code>null<\/code> when the current token no longer exists. <code>$session&amp;#091;&#039;login&#039;]<\/code> then logs \"Trying to access array offset on value of type null\".<br \/><br \/><strong>**Suggested fix:**<\/strong> two guards, no change in behaviour when sessions exist:<br \/><br \/><code>php&lt;br&gt;&lt;br&gt;$sessions = wp_get_all_sessions();&lt;br&gt;&lt;br&gt;if ( empty( $sessions ) ) return;&lt;br&gt;&lt;br&gt;$newest \u00a0 = max( wp_list_pluck( $sessions, &#039;login&#039; ) );&lt;br&gt;&lt;br&gt;$session \u00a0= $this-&gt;get_current_session();&lt;br&gt;&lt;br&gt;if ( ! is_array( $session ) ) return;&lt;br&gt;&lt;br&gt;if ( $session&amp;#091;&#039;login&#039;] === $newest ) {&lt;br&gt;&lt;br&gt;<\/code><br \/><br \/><strong>**To reproduce:**<\/strong> a logged-in user with 2+ sessions whose session store empties, or whose current token is destroyed, between the multiple-sessions check and these lines.<br \/><br \/><strong>**Expected:**<\/strong> the function returns quietly, with no fatal and no warning.<br \/><br \/><strong>**Environment:**<\/strong> WordPress 7.2-alpha (nightly), PHP 8.4.25 and 8.5.11, Inactive Logout 3.6.3.<br \/><br \/>We carry these two guards as a local patch and re-apply them after each update. It would be great to have them upstream. Thanks!<\/code><\/pre>\n","protected":false},"template":"","class_list":["post-19033446","topic","type-topic","status-publish","hentry","topic-tag-fatal-error","topic-tag-php-8"],"jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/wordpress.org\/support\/wp-json\/wp\/v2\/topic\/19033446","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/wordpress.org\/support\/wp-json\/wp\/v2\/topic"}],"about":[{"href":"https:\/\/wordpress.org\/support\/wp-json\/wp\/v2\/types\/topic"}],"version-history":[{"count":0,"href":"https:\/\/wordpress.org\/support\/wp-json\/wp\/v2\/topic\/19033446\/revisions"}],"wp:attachment":[{"href":"https:\/\/wordpress.org\/support\/wp-json\/wp\/v2\/media?parent=19033446"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}