38

What does the '@' symbol do in the following code?

@mkdir(ROOT. "cache/");
alex
  • 479,566
  • 201
  • 878
  • 984
Rich Turner
  • 10,800
  • 1
  • 51
  • 68
  • 14
    Sure. Try searching PHP site for "@" or "@ prefix" - gets you a long way. NOT. – Rich Turner Jan 20 '11 at 00:06
  • 3
    "[This operator is affectionately known by veteran phpers as the stfu operator.](http://php.net/manual/en/language.operators.errorcontrol.php#112900)" ;-) – Uwe Keim Dec 22 '14 at 21:18

3 Answers3

42

It suppresses errors from displaying:

PHP supports one error control operator: the at sign (@). When prepended to an expression in PHP, any error messages that might be generated by that expression will be ignored.

If the track_errors feature is enabled, any error message generated by the expression will be saved in the variable $php_errormsg. This variable will be overwritten on each error, so check early if you want to use it.

As noted in the comments, I too cannot imagine a reason to actually use this functionality -- write code that deals appropriately with error states/conditions.

Mark Elliot
  • 75,278
  • 22
  • 140
  • 160
  • 1
    Thanks for the answer. This just makes the disgusting code I've inherited even worse than I thought it was! – Rich Turner Jan 11 '11 at 01:42
  • Because it will be most difficult to debug, try to avoid this feature, especially on critical code. – Xavier Barbosa Jan 11 '11 at 01:45
  • If you plan on suppressing errors, you're better off using `error_reporting(0);` for two reasons: A. it's quicker, B. it's easier to change later. – John M. Jan 11 '11 at 01:52
  • +1 Just like other languages (per example, C), a warning or notice is thrown at you for a reason. They should not be ignored, but dealt with accordingly. – netcoder Jan 11 '11 at 01:52
  • @John: Funny because E_NONE is not actually a defined constant and will actually spit a E_NOTICE error! – netcoder Jan 11 '11 at 01:53
  • 1
    Be careful when using @ in a loop: Each run will trigger `error_reporting()` twice. It's often better to disable errors before the loop and then reset the error level after the loop is done. – xrstf Jan 11 '11 at 02:18
  • @netcoder: I realized that. That's why I corrected myself to 0. – John M. Jan 11 '11 at 17:16
  • It can be useful in isolated cases when you also set an error_handler that throws exceptions (e.g. one that converts error messages into `ErrorException`). Instead of using try/catch you would use the `@` and check the return value for an error case. Of course, if it's all in the same codebase, you would use only one kind of error handling, but it can be the only way possible when several libraries are involved. – Ludovic Chabant Nov 26 '11 at 02:08
  • One instance where error suppression with @ could be useful is in the case where you're looking for a unique file name with `fopen($file, 'x')` which produces an E_WARNING error if a file of that name already exists. – Brian C Mar 24 '14 at 00:12
8

As pointed out, it is the error suppression operator.

But what has not been pointed out, is that it is very bad practice to use - errors should not fail silently.

Check for error returns, and use try/catch blocks where exceptions are being used.

In the specific example...

@mkdir(ROOT. "cache/");

...it ignores any errors from mkdir(). The docs says it returns FALSE on failure, so you should be doing...

if ( ! mkdir(ROOT. "cache/")) {
   // Handle error.
}
alex
  • 479,566
  • 201
  • 878
  • 984
7

People seem to forget that PHP was a quick dirty language for getting things done, only recently has it tried to be mature and sophisticated.

Error suppression is a quick and dirty way of making functions behave the way you need them to, because in web-development you cannot predict what will be thrown at you, and sometimes it is not worth caring!

A classic example is the useful function getimagesize, that allows you to get some information about an image that someone has uploaded. This function chucks a wobbly if the image file is not a standard image file. It is not really the developers role to inspect a file, determine if it can be loaded into getimagesize. There might be elegant ways of doing this, but seriously I don't care!

just do this:

if( !($a = @getimagesize(  $_FILE['file']['tmp_name'] )))
{
   unlink( $_FILE['file']['tmp_name'] );

   //politely tell user that you rejected their image!
}

yes, you could use try and catch statements which are more elegant, but in the end, you have caught the error and suppressed the error message, which is what you wanted without wearing out the tab-key!

Contrary to what above answers say, the @ prefix used carefully does not result in a runaway train wreck. It just allows the developer to accommodate errors in the way they prefer.

Gordon Rouse
  • 301
  • 3
  • 6
  • With PHP notices on, I think the @ suppressor becomes very useful, ie: if( @$_POST['submit'] == 'send' ){} – Gordon Rouse Feb 21 '18 at 05:09
  • "There might be elegant ways of doing this, but seriously I don't care!" I hope I'll never touch your code. – Gabriel Mar 13 '18 at 13:53
  • I really like this answer. I'm quite new to PHP and its quite easy to accidentally generate errors you don't want users to see. This operator seems to be an easy fix. – I_ATE_YOUR_WORK_FILES Jun 07 '18 at 10:10
  • "its quite easy to accidentally generate errors you don't want users to see" – Gordon Rouse Jun 08 '18 at 11:00
  • Sorry, trying to say "its quite easy to accidentally generate errors you don't want users to see" is not the reason to use @. You still need to take responsibility for the condition. – Gordon Rouse Jun 08 '18 at 11:10
  • OK - I am being hypocritical, yes it does suppress the warning, but only use it when you know what you are doing! – Gordon Rouse Jun 08 '18 at 12:08