I'm working on a new project with a sizeable PHP codebase. The application uses quite a few PHP constants ( define('FOO', 'bar')
), particularly for things like database connection parameters. These constants are all defined in a single configuration file that is require_once()
'd directly by basically every class in the application.
A few years ago this would have made perfect sense, but since then I've gotten the Unit Testing bug and this tight coupling between classes is really bothering me. These constants smell like global variables, and they're referenced directly throughout the application code.
Is this still a good idea? Would it be reasonable to copy these values into an object and use this object (i.e. a Bean - there, I said it) to convey them via dependency injection to the the classes that interact with the database? Am I defeating any of the benefits of PHP constants (say speed or something) by doing this?
Another approach I'm considering would be be to create a separate configuration PHP script for testing. I'll still need to figure a way to get the classes under test to use the sandbox configuration script instead of the global configuration script. This still feels brittle, but it might require less outright modification to the entire application.
Although you should try to avoid the use of global variables, it is generally permissible to use global constants in a program. A global constant is a named constant that is available to every function in a program.
PHP constants are said to have global scope. This basically means that once you have defined a constant it is accessible from any function or object in your script. In addition, PHP provides a number of built-in constants that are available for use to make life easier for the PHP developer.
const "global" constants are ok - but put them in their own namespace.
Q 3 - Which of the following is correct about constants vs variables in PHP? A - Constants may be defined and accessed anywhere without regard to variable scoping rules.
In my opinion, constants should be used only in two circumstances:
SECONDS_PER_HOUR
).Even then, I'd reconsider whether class constants would be more appropriate so as not to pollute the constants space.
In your situation, I'd say constants are not a good solution because you will want to provide alternative values depending on where they're used.
These constants smell like global variables, and they're referenced directly […]. Would it be reasonable to copy these values into an object and […] convey them via dependency injection?
Absolutely! I would go even further and say even class constants should be avoided. Because they are public, they expose internals and they are API, so you cannot change them easily without risking breaking existing applications due to the tight coupling. A configuration object makes much more sense (just dont make it a Singleton).
Also see:
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With