Skip to content

trigger_error directly in file causes unpredictable system failure #3449

@TPETb

Description

@TPETb
  • Laravel-mongodb Version: 5.5+
  • PHP Version: doesn't matter
  • Database Driver & Version: doesn't matter

Description:

PR #3408 adds trigger_error into the file directly (not inside a method). Since it is quite typical for developers to override error reporting in runtime (e.g., error_reporting(E_ALL & ~E_DEPRECATED & ~E_USER_DEPRECATED), rather than in .ini, the following happens:

On the local env/test server, the app works without caching, and the SoftDeletes class is only included/required after the initial bootstrap, and the error is ignored.

Eventually, the app is deployed to the production environment, which runs on fpm with opcache enabled, which "includes" all files before the app is bootstrapped. The app crashes because error reporting has not yet been configured to exclude deprecation warnings.

You can see that in this scenario, the problem would go unnoticed until the code was deployed into the production environment. To make things worse, developers cannot rely on error reporting tools like Sentry, because the error happens much earlier than the error handler is initialized.

Steps to reproduce

  1. make sure .ini allows deprecation errors reporting
  2. change error reporting in kernel/bootstrap to ignore deprecation warnings
  3. launch the app without opcache enabled (verify, OK)
  4. enable opcache

Expected behaviour

app is functional

Actual behaviour

app crashes

Thoughts: A file with a class definition should not have any side effects, only the class declaration; otherwise, there's a risk of causing problems that will be very hard to spot until too late. In this case, php-fpm and opcache, combined with not relying on .ini for error reporting settings, caused this issue. Side effects could appear for worker-mode-based systems, etc.

I understand the challenge of reporting whole class deprecation (in contrast of particular method deprecation), but there should be a less dangerous way.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions