So say I have a class, say Store, and it has a method, say place_order() that may differ for different type of order processes - I'm thinking of using a composite approach to build the needed store object at run time with the proper checkout function type loaded in based on a store's configuration in the database.
So would the best thing to do be to add this kind of functionality in a class that extends \Orm\Model? I'd prefer to not tie myself so deeply into the Fuel framework if it can be avoided so that these classes may be more portable and pluggable-ish into any framework.
Also I would have to add the above code that figures out what checkout handler to compose at runtime in either the init function or override the constructor I guess? Any suggestions on best practices here would be great.
And as one more point, I considered also just creating my class and adding the actual model as a protected variable, then if I extend Orm\Model, I considered using some magic methods to test to see if they are inherited methods from Orm\Model and if so call the method on the protected model variable in an effort to make it less dependent on the actual data model. This way I could have an abstract Store class with concrete implementations which I can't seem to figure out how to do if Store is a direct extension of Orm\Model. However, I'm not sure if this suggestion is possible with the Reflection API, or if it would actually decouple the Store concept from the data model in practice.
I would use a layered approach, where Store is your top layer, interfacing with the application. The second layer would be a model layer (a data model, not an ORM model) which would provide the data handling. In your case, you can have more of those. And a third layer of ORM models that interact with the database.
Depending on the functionality of your data model you can either use the driver approach (like your code example), or the Store that creates a data model instance internally.
Assuming that you can place multiple orders on a single store object, and these can have different handlers, I think you should pass the desired handler to the place_order() method, so it can create an instance of the handler and process the order.
I would also suggest to define an interface for these handlers, so you are sure all handlers implement the correct API. Your place_order() can then check if the data model loaded implements this interface before using it.
Thanks for the feedback. For some reason I just saw your response, but your suggestion is the path I ended up taking. I hope to shore it up a little bit and make it available to community over the next month or two.