When is it reasonable to use getInstance/new class()? (PHP) - php

I've got a basic question:
When I'm developing PHP I often wonder, when is it reasonable to use exampleclass::getInstance()
and when to use new exampleclass()
When should I use which one? and what is the big difference between them?
I just want to get out the "best practice" out of that issue.
Thanks for your help!

A class that implements a getInstance() method is usually a singleton. In this case, you should basically never use new exampleclass(). (Actually, calling the constructor directly should be forbidden after all.)
A singleton assumes that one instance of its class at most exists during the program's lifetime. If there were more instances, they could conflict with each other which would cause some ugly problems. (For example, the singleton could access some globally available functions or methods or open some connection to another module or another network location. If two instances write to the same variables without knowning about each other, the system could get into a state where it does not know how to continue working.)

Typically, getInstance() is used in the case of a Singleton pattern, that is when you need to always use the same instance of object. In this case, the getInstance calls a usually private constructor only on the first call.
A new ExampleClass() will create a new instance of this class on each call.

Related

Is the Template Method Pattern the best solution for shared Soap methods?

I have a number of Soap Server classes most of which will need to implement 3 methods:
ping() // something to bounce a signal off to prove it has been reached
getCredentials($creds) // credentials to check sets session value
getCaller() // for logging, uses session value
As they form part of the WSDL defn they need to be public.
I am fairly sure this (I have christened it a Soaplogin) would need to be an abstract class (because it must never be instantiated on its own)
The concrete classes which extend then this core then have their own methods, none of which are shared.
I am searching for the best type of Pattern to use and am getting a bit confused, though I think a Template Method just about fits the bill - but I could just plain extend the SoapLogin class.
What advice can you give me on the best pattern to use, and maybe a preferred name for this class.
(while this uses ZF1 components it does not use full blown MVC - in case that was of importance)
Prefer composition over inheritance.
What you really do is you create completely independent interfaces that only by chance happen to have the same methods.
Fine. Generic methods that always do the same - that should be in a class of it's own. But not ONE class for all these methods! One class per method!
You can then add all these method classes to your server classes, and also add all the special functions the same way.
That way you can combine any of the generic functions in any way, and add another only to one API if needed.
This pattern could be a good solution if you just want to create several soap connect.
An other one could be to use interface. It will tell your program that every class that implements SoapItf (for example, rename it if you want) are able to perform soap method.
If you look for an evolutive application, maybe you'll need to connect with Rest webservice after so you can create an abstract class Werbservice, two class Soap and Rest that extends it and this two class implements interface SoapItf ans RestItf respectively.
This method helps using polymorphism, an important concept in OOP.
In this case I can add method to Soap or Rest without changing both.
After that if you have specificity with Soap like in your example, you could extends Soap class. It will be easier to evolve the application and using package architecture (interesting if you work with namespaces)
In my opinion, you can use template pattern to manage a common resource that is spreadable in sub-classes. For instance, you have a soaplogin common abstract class and that might have some resource that can be used by most of the sub-classes. Then it's better to manage that resource in super-class and pass the callback in subclass to use the resource of the super-class. Advantage is that you are managing resource at a single place.
For example, I have a common resource in my super-class. I can create a callback passing resource as a parameter.
interface ResourceCallback {
T call(Resource resource);
}
Then can define a abstract method in super-class like as doWithResource(ResourceCallback callback) and all the subclass can now use the resource with their own implementation of their methods.

Why people use singletons in their PHP framework

Ok guys I am struggling to understand why there is a need of singleton.
Let's make a real example: I have a framework for a my CMS
I need to have a class that logs some information (let's stick on PHP).
Example:
class Logger{
private $logs = array();
public function add($log) {
$this->logs[]=$log;
}
}
Now of course this helper object must be unique for the entry life of a page request of my CMS.
And to solve this we would make it a singleton (declaring private the constructor etc.)
But Why in the hell a class like that isn't entirerly static? This would solve the need of the singleton pattern (that's considered bad pratice) Example:
class Logger {
private static $logs = array();
public static function add($log) {
self::$logs[]=$log;
}
}
By making this helper entirely static, when we need to add a log somewhere in our application we just need to call it statically like: Logger::add('log 1'); vs a singleton call like: Logger::getInstance()->add('log 1');
Hope someone makes it easy to understand for me why use singleton over static class in PHP.
Edit
This is a pretty nice lecture on the singleton vs static class for who is interested, thanks to #James. (Note it doesn't address my question)
Many reasons.
Static methods are basically global functions that can be called from any scope, which lends itself to hard to track bugs. You might as well not use a class at all.
Since you cannot have a __construct method, you may have to put an init static method somewhere. Now people in their code are unsure if the init method has been called previously. Do they call it again? Do they have to search the codebase for this call? What if init was somewhere, but then gets removed, or breaks? Many places in your code now rely on the place that calls the init method.
Static methods are notoriously hard to unit test with many unit testing frameworks.
There are many more reasons, but it's hard to list them all.
Singletons aren't really needed either if you are using DI.
A side note. DI allows for your classes not to rely on each other, but rather on interfaces. Since their relationships are not cemented, it is easier to change your application at a later time, and one class breaking will not break both classes.
There are some instances where single state classes are viable, for instance if none of your methods rely on other methods (basically none of the methods change the state of the class).
I use singletons, so I can tell you exactly why I do it instead of a static function.
The defining characteristic of a singleton is that it is a class that has just one instance. It is easy to see the "just one instance" clause and forget to see the "it is a class" clause. It is, after all, a normal class object with all the advantages that that brings. Principly, it has its own state and it can have private functions (methods). Static functions have to do both of these in more limited or awkward ways.
That said, the two complement each other: a static function can be leveraged to return a singleton on the same class. That's what I do in the singleton I use the most often: a database handler.
Now, many programmers are taught that "singletons are bad, mm'kay?" but overlook the rider that things like are usually only bad when overused. Just like a master carver, an experienced programmer has a lot of tools at his disposal and many will not get a lot of use. My database handler is ideal as a singleton, but it's the only one I routinely use. For a logging class, I usually use static methods.
Singletons allow you to override behavior. Logger::add('1') for example can log to different devices only if the Logger class knows how. Logger::getLogger()->add('1') can do different things depending on what subtype of Logger getLogger() returns.
Sure you can do everything within the logger class, but often you then end up implementing the singleton inside the static class.
If you have a static method that opens a file, writes out and closes it, you may end up with two calls trying to open the same file at the same time, as a static method doesn't guarantee there is one instance.
But, if you use a singleton, then all calls use the same file handler, so you are always only having one write at a time to this file.
You may end up wanting to queue up the write requests, in case there are several, if you don't want them to fail, or you have to synchronize in other ways, but all calls will use the same instance.
UPDATE:
This may be helpful, a comparison on static versus singleton, in PHP.
http://moisadoru.wordpress.com/2010/03/02/static-call-versus-singleton-call-in-php/
As leblonk mentioned, you can't override static classes, which makes unit testing very difficult. With a singleton, you can instantiate a "mock" object instead of the actual class. No code changes needed.
Static classes can have namespace conflicts. You can't load 2 static classes of the same name, but you can load 2 different versions of a singleton and instantiate them under the same name. I've done this when I needed to test new versions of classes. I instantiate a different version of the class, but don't need to change the code that references that class.
I often mix singletons and static. For example, I use a database class that ensures there is only 1 connection to each master (static) and slave (singleton). Each instance of the db class can connect to a different slave, if a connection to the same slave is requested, the singleton object is returned. The master connection is a static object instantiated inside each slave singleton, so only 1 master connection exists across all db instantiated objects.

correct use of 'construct' when designing classes

I am new to object oriented programming and writing some of my first classes for a PHP application.
In some of the simpler classes, I declare a function __construct(), and inside of that function, call certain class methods. In some cases, I find myself instantiating the class in my app, and not needing to do anything with the resultant object because the class's __construct() called the methods, which did their job, leaving me nothing left to do with the class.
This just doesn't feel right to me. Seems goofy that I have a new object that I never do anything with.
Again, I'll stress this is only the case for some of my more simple classes. In the more complicated ones, I do use class methods via the object and outside of __construct().
Do I need to rethink the way I coding things, or am I ok?
Well, the constructor is used to create a new instance of a class, and to do any necessary setup on that class. If you're just creating the class and leaving it, that does seem a bit of a waste. Why not, for instance, use static functions in the class as an organizational tool and just call them(or a function that calls them) instead of constructing a new instance that you'll never use?
This just doesn't feel right to me. Seems goofy that I have a new object that I never do anything with.
Yes, that should raise a red flag.
In general, you should not let constructors have any side effects; They are meant for initialising the state of the object - not for anything else. There are of course exceptions to this rule, but in general it's a good guide line. You should also abstain from doing any heavy calculations in the constructor. Move that to a method instead.
Side effects are many things - Changes to global variables or static (class) variables; output to the environment (For example calls to print(), header() or exit()); calls to a database or other external service and even changes to the state of other objects.
A side effect free function is also called a "pure" function - as opposed to a procedure, which is a function that has side effects. It's a good practise to explicitly separate pure functions from procedures (and perhaps even label them as such).

What things are best not done in a constructor?

I started off by drafting a question: "What is the best way to perform unit testing on a constructor (e.g., __construct() in PHP5)", but when reading through the related questions, I saw several comments that seemed to suggest that setting member variables or performing any complicated operations in the constructor are no-nos.
The constructor for the class in question here takes a param, performs some operations on it (making sure it passes a sniff test, and transforming it if necessary), and then stashes it away in a member variable.
I thought the benefits of doing it this way were:
1) that client code would always be
certain to have a value for this
member variable whenever an object
of this class is instantiated, and
2) it saves a step in client code
(one of which could conceivably be
missed), e.g.,
$Thing = new Thing;
$Thing->initialize($var);
when we could just do this
$Thing = new Thing($var);
and be done with it.
Is this a no-no? If so why?
My rule of thumb is that an object should be ready for use after the constructor has finished. But there are often a number of options that can be tweaked afterwards.
My list of do's and donts:
Constructors should set up basic options for the object.
They should maybe create instances of helper objects.
They should not aqquire resources(files, sockets, ...), unless the object clearly is a wrapper around some resource.
Of course, no rules without exceptions. The important thing is that you think about your design and your choises. Make object usage natural - and that includes error reporting.
This comes up quite a lot in C++ discussions, and the general conclusion I've come to there has been this:
If an object does not acquire any external resources, members must be initialized in the constructor. This involves doing all work in the constructor.
(x, y) coordinate (or really any other structure that's just a glorified tuple)
US state abbreviation lookup table
If an object acquires resources that it can control, they may be allocated in the constructor:
open file descriptor
allocated memory
handle/pointer into an external library
If the object acquires resources that it can't entirely control, they must be allocated outside of the constructor:
TCP connection
DB connection
weak reference
There are always exceptions, but this covers most cases.
Constructors are for initializing the object, so
$Thing = new Thing($var);
is perfectly acceptable.
The job of a constructor is to establish an instance's invariants.
Anything that doesn't contribute to that is best kept out of the constructor.
To improve the testability of a class it is generally a good thing to keep it's constructor as simple as possible and to have it ask only for things it absolutely needs. There's an excellent presentation available on YouTube as part of Google's "Clean Code Talks" series explaining this in detail.
You should definitely avoid making the client have to call
$thing->initialize($var)
That sort of stuff absolutely belongs in the constructor. It's just unfriendly to the client programmer to make them call this. There is a (slightly controversial) school of thought that says you should write classes so that objects are never in an invalid state -- and 'uninitialized' is an invalid state.
However for testability and performance reasons, sometimes it's good to defer certain initializations until later in the object's life. In cases like these, lazy evaluation is the solution.
Apologies for putting Java syntax in a Python answer but:
// Constructor
public MyObject(MyType initVar) {
this.initVar = initVar;
}
private void lazyInitialize() {
if(initialized) {
return
}
// initialization code goes here, uses initVar
}
public SomeType doSomething(SomeOtherType x) {
lazyInitialize();
// doing something code goes here
}
You can segment your lazy initialization so that only the parts that need it get initialized. It's common, for example, to do this in getters, just for what affects the value that's being got.
Depends on what type of system you're trying to architect, but in general I believe constructors are best used for only initializing the "state" of the object, but not perform any state transitions themselves. Best to just have it set the defaults.
I then write a "handle" method into my objects for handling things like user input, database calls, exceptions, collation, whatever. The idea is that this will handle whatever state the object finds itself in based on external forces (user input, time, etc.) Basically, all the things that may change the state of the object and require additional action are discovered and represented in the object.
Finally, I put a render method into the class to show the user something meaningful. This only represents the state of the object to the user (whatever that may be.)
__construct($arguments)
handle()
render(Exception $ex = null)
The __construct magic method is fine to use. The reason you see initialize in a lot of frameworks and applications is because that object is being programmed to an interface or it is trying to enact a singleton/getInstance pattern.
These objects are generally pulled into context or a controller and then have the common interface functionality called on them by other higher level objects.
If $var is absolutely necessary for $Thing to work, then it is a DO
You should not put things in a constructor that is only supposed to run once when the class is created.
To explain.
If i had a database class. Where the constructor is the connection to the database
So
$db = new dbclass;
And now i am connected to the database.
Then we have a class that uses some methods within the database class.
class users extends dbclass
{
// some methods
}
$users = new users
// by doing this, we have called the dbclass's constructor again

Possible circular dependency issue with PHP application

I'm experiencing what I believe is a circular dependency issue with my PHP application. Please let me know if this is incorrect. Here is the situation:
Two classes, LogManager and DBSession.
DBSession is used to interact with the database, and LogManager is used to log to files. Both are widely used in my application. When you create an instance of DBSession, you must give it an instance of LogManager via a constructor parameter. This because DBSession will sometimes log information to a file, and will use the LogManager instance to do this.
Now, I wanted to extend LogManager so that it could also log to a database table, rather than a text file. Naturally, my preference is to re-use existing classes, but I soon realized this brought about an interesting situation.
DBSession already requires an instance of LogManager for construction. If I want to re-use the DBSession class in LogManager, it will now require an instance of DBSession. How can I satisfy both demands? Clearly, something must be wrong with my approach.
How would you suggest I fix this?
Thanks in advance, guys.
Don't extend LogManager, let it be an aggregate type. And delay the choice of where you want to log, i.e.:
$logManager = new LogManager();
$dbSession = new DbSession($logManager);
$logManager->add(new FileLog($filename) );
$logManager->add(new DBLog($dbSession) );
Where of course FileLog and DBLog share a common interface.
This is an application of the Observer pattern, where add() is the "subscribe" operation, and FileLog/DBLog are the observers of logging events.
(In this way you could also save logs in many places.)
Owen edit: adjusted to php syntax.
One of these objects doesn't actually need the other: you guessed it, it's the DBSession. Modify that object so that the logger can be attached to it after construction.
Why demand a LogManager object for the creation of a DbSession object, if it only sometimes writes to files? lazy load it instead only when you need it. Also, in my opinion both should be independent from each other. Each could instance the other when needed.
Maybe you can apply some pattern, like the Singleton Pattern to ensure that you only have one instance of your LogManager class for example.

Categories