Dolibarr/dolibarr · info
ERROR_NOT_LOGGED
ERROR_NOT_LOGGED
Error message
ERROR_NOT_LOGGED
What it means
When a request reaches a protected page without a logged-in user, Dolibarr normally redirects to the login page. However, if NOREDIRECTBYMAINTOLOGIN is defined (e.g. AJAX components like selectsearchbox.php), main.inc.php instead returns the literal string 'ERROR_NOT_LOGGED' so the including script can handle the unauthenticated state itself; a 401 is optionally sent when the user agent is 'securitytest'.
Solutions
- Log in again or re-establish the session before calling the AJAX endpoint.
- Make the AJAX client handle the ERROR_NOT_LOGGED return by redirecting to the login page.
- In custom scripts, check the return value of the main.inc.php inclusion and handle it.
- For tests, expect the 401 status rather than parsing HTML.
- If a full-page redirect is desired, remove the NOREDIRECTBYMAINTOLOGIN define.
Example fix
// before
@require './main.inc.php';
// after
$res = require './main.inc.php';
if ($res === 'ERROR_NOT_LOGGED') { top_httphead('application/json'); echo '{"error":"not_logged"}'; exit; } Defensive patterns
Strategy: fallback
Validate before calling
if (empty($user->id)) { /* not logged in yet, handle before protected calls */ } Try / catch
$res = require __DIR__.'/main.inc.php';
if ($res === 'ERROR_NOT_LOGGED') { http_response_code(401); exit; } Prevention
- In AJAX clients, treat 401/not-logged responses by reloading the login page
- Keep sessions alive with keep-alive pings for long-running pages
- Check main.inc.php's return value when using NOREDIRECTBYMAINTOLOGIN
When it happens
Trigger: Session expired or no user in session while including main.inc.php in a script that defines NOREDIRECTBYMAINTOLOGIN; AJAX endpoints hit after a session timeout.
Common situations: AJAX search components polling after the session timed out; headless/API-style scripts expecting a return code rather than a redirect; automated tests sending User-Agent 'securitytest' and receiving 401.
Related errors
- You are logged with user
- ErrorConfigParameterNotDefined
- ErrorSessionInvalidatedAfterPasswordChange
- If define NOREQUIREDB or NOREQUIRETRAN are set, you must…
- If define NOREQUIREUSER is set, you must also set…
AI-assisted analysis of Dolibarr/dolibarr@598aa4bdad (2026-09-14).
Data as JSON: /api/errors/150427317a8bb455.
Report an issue: GitHub.
Appendix: source
Thrown at htdocs/main.inc.php:865
$reshook = $hookmanager->executeHooks('afterLoginFailed', $parameters, $user, $action); // Note that $action and $object may have been modified by some hooks
if ($reshook < 0) {
$error++;
}
// Note: exit is done in next chapter
}
}
// End test login / passwords
if (!$login || (in_array('ldap', $authmode) && !in_array('openid_connect', $authmode) && empty($passwordtotest))) { // With LDAP we refused empty password because some LDAP are "opened" for anonymous access so connection is a success.
// No data to test login, so we show the login page.
dol_syslog("--- Access to ".(empty($_SERVER["REQUEST_METHOD"]) ? '' : $_SERVER["REQUEST_METHOD"].' ').$_SERVER["PHP_SELF"]." - action=".GETPOST('action', 'aZ09')." - actionlogin=".GETPOST('actionlogin', 'aZ09')." - showing the login form and exit", LOG_NOTICE);
if (defined('NOREDIRECTBYMAINTOLOGIN')) {
// When used with NOREDIRECTBYMAINTOLOGIN set, the http header must already be set when including the main.
// See example with selectsearchbox.php. This case is reserved for the selectesearchbox.php so we can
// report a message to ask to login when search ajax component is used after a timeout.
//top_httphead();
return 'ERROR_NOT_LOGGED';
} else {
if (!empty($_SERVER["HTTP_USER_AGENT"]) && $_SERVER["HTTP_USER_AGENT"] == 'securitytest') {
http_response_code(401); // It makes easier to understand if session was broken during security tests
}
// Show login form
dol_loginfunction($langs, $conf, (!empty($mysoc) ? $mysoc : '')); // This include http headers
}
exit;
}
$resultFetchUser = $user->fetch(0, $login, '', 1, ($entitytotest > 0 ? $entitytotest : -1)); // value for $login was retrieved previously when checking password.
if ($resultFetchUser <= 0 || $user->isNotIntoValidityDateRange()) {
dol_syslog('User not found or not valid, connection refused');
session_destroy();
session_set_cookie_params(0, '/', null, !empty($dolibarr_main_force_https), true); // Add tag secure and httponly on session cookie
session_name($sessionname);View on GitHub (pinned to 598aa4bdad)