I am in the early stages of creating a small-medium sized web application by myself. I read "PHP Objects, Patterns, and Practice," and I decided to use page controllers because quick production is a high priority. Page controllers were also appealing because I am unfamiliar with PHP frameworks and creating an elaborate front controller seems to currently outweigh the project. My plan is to release the page controller version of the website ASAP and see if the audience likes it before committing to more complex software designs.
That said, I might decide to add more 'modules' and developers down the road...at which point I really should switch to a front controller. The above mentioned book describes that "it is not impossible to start with page controller and move toward the front controller pattern," but the wording of "not impossible" has me worried that it may be fairly difficult.
My questions are:
How 'hard' is it to make the transition from page controller to front controller design? While working on my page controller-based app, what should I be careful with to create code that allows a smooth transition to front controller design? The ideal situation would be to rewrite/restructure the code as little as possible and tack on the front controller with related classes/objects. Right now I'm only cautious about maintaining MVC, so any advice from experienced developers would be great. Thank you.
I think your main concerns should be to put "business logic" into properly designed model classes. In other words, don't put such logic in your page controllers directly. Instead, use your page controllers to parse input, such as GET and POST, instanciate the correct business logic objects, and call the correct methods on those to do the actual data crunching.
The page controllers should also be responsible for choosing a view to display - don't output things in the business objects, simply return data for the controller.
By using this approach, you should have most of your code in the model classes, and if/when you want to rewrite to using front controller, you will only need to change the page controllers to work with a front controller, hopefully not having to modify anything else.
I read the book you mentioned about 3 or 4 years ago as a first introduction to object oriented programming and I found it a great book, but I have to say that I only really got to grips with the whole thing once I started to use CakePHP and root around in its code to see how things are done in practice. The examples in the book can be a little confusing at times.
I recommend having a second look at some of the frameworks out there, Cake is good, Yii is meant to be even better. It doesn't long to get a system set up with them, and as long as you're prepared to have a good look under the hood, they can be an invaluable learning tool.
Related
** simplified question **
I am learning oop patterns and I am looking to build my own simple mvc framework. I would like this to have a front controller but I am finding it difficult to find any credible information for implementing a front controller with MVC.
In particular I am confused about whether the front controller should initiate the entire triad or whether the front controller simply calls the controller and the other parts do the rest.
I have noticed classes like route, router and bootstrap and I am wondering what these particular classes do and whether they are dependent on the front controller itself.
Actually that's not a question, you're just trying to get suggestions on how to proceed while building your own MVC framework.
So I'll try to provide an answer / consideration as generic as your question.
1) "I'm learning OOP Patterns": patterns are as much powerful as dangerous in the wrong hands. What I'm trying to say is that you should start building your fw without trying to use every patterns you come across the net just because it is used or talked about by the big ones. You can refactor you code later providing each step an higher level of abstraction: this will naturally involve using the patterns you'll be reading about and a better understanding of them.
2) "confused about whether the front controller should initiate the entire triad": that's up to which level of coupling you're aiming to have in your mvc.
You can have your Front Controller handling everything like:
bootstrap: load config and instantiate database connection and so on
request: get the needed data describing what was asked
route: handle the request
response: return what was asked
But what if the configuration is needed somewhere else? Maybe in a CLI running script? You'll be naturally detaching the bootstrap component from the router to use it anywhere else is needed. And the same is for the other components.
3) "classes like route, router and bootstrap".
Imagine to have your big class handling everything. How will you be testing your methods? Will you manually call the script with different inputs? Will every testing method have to check for the input, the routing and the output at once?
Providing an abstraction level upon every component involved in your Front Controller encapsulating it in a proper class/object/module, will give you far better testing capabilities.
I'm talking because I've been down that road before creating exactly what you're talking about: https://github.com/OverKiller/PHP-Router
But I had to face hard testing capabilities and deep coupling.
I'll be rewriting it soon, abstracting the request, the route and the response component.
But I had my experience and I'm proud of it!
You should do the same.
What I'm trying to say is: do not try to build the next Ultimate SymZendCakeIgniter PHP Framework all at once.
Take your time, take your time to read and take your time to learn.
And for god sake: *even before reading anything about design patterns get a nice book about T-E-S-T-I-N-G
I hope I was useful.
This is more or less a framework-centric version of a past Stack Overflow question, which is about how most introductory material on MVC applications tends to present a tight coupling between models, views, and controllers. For example, you'll have a User table that is modified by a User controller which in turn pushes filtered data to a User view. It's my impression that a lot of MVC frameworks tend to reflect this pattern as well. This is all fine and well for what it is, but it never really leads me to anything beyond building and displaying monotonous lists of things with an HTML form.
The MVC framework that looking at right now is Lithium, which seems quite interesting as a case study of clever PHP5.3 coding techniques. On one end, Lithium has a Model class that offers wrapper objects around a individual tables, and abstracts away some simple queries. On the other end, it's got a nifty convention of routing URLs to method calls on controller objects, which then render to display templates.
But in the midst of this, I find myself at a loss as to where to place all of the interesting logic that relates data in table A to data in tables B through Z. Or at least, I'm not sure where to place such logic in a manner that's consistent with the design of the framework. To my understanding, Lithium's Model abstraction doesn't do much more than eliminate some row-level insert/update/delete boilerplate, and the controller/view architecture seems mostly about user interface. I wouldn't want to put a lot of business logic in the same Controller class that is receiving routed function calls from URL requests.
My instinct would be to fill the gap with a bunch of my own code that exists more or less entirely outside of the framework. I'm not sure if I ought to expect more than that, but given how rigidly structured everything else is in Lithium, it feels somehow unsatisfying, like I could have just rolled my own boilerplate-reduction code without the overhead of grokking the source of a big framework.
What am I missing here? Is there a recommended architecture or philosophy to using this type of framework?
One thing you have to remember with Lithium is that theres no production ready release yet (although some sites are using it in production).
The main missing feature right now is model relations. With relations in place i assume your question would be partially answered as that is an important brick in the big picture of creating more complex applications.
You could check out the x-data branch where the work on relations should be ongoing.
For the second part of writing domain logic the simple answer is "in the model".
See this (rather useless) example of extending model functionality for example.
Another example to look at is the open source mini application Analogue that is one of the few working open examples of Lithium in use. The Analogue model class shows a slightly more meaty model.
And finally its a matter of connecting the dots between M, V and C.
A Lithium controller should mainly delegate jobs over to models, and perhaps restructure the input data if needed.
The simple examples of having a Post model, PostsController and views/posts/add,index,etc doesn't mean that you have to merely have Post::all() in there.
PostsController::view need to load a set of Comment models probably.
So you will toss a lot of your own code in there, of course! Else it would not be much of an application. But keep the domain logic tied to the model where it is natural.
Need to verify that blog post has a
unique title? Write a validator.
Need to ensure the user has write access to the post? Override the save method and verify it, or filter it.
But I think we need to wait for relations to land and a 1.0 release before we can fully judge how structuring applications in Lithium can be solved best.
The web-based application I’m currently working on is growing arms and legs! It’s basically an administration system that helps users to keep track of bookings, user accounts, invoicing, etc. It can also be accessed via a couple of different websites using a fairly crude API.
The fat-client design loosely follows the MVC pattern (or perhaps MVP) with a PHP/MySQL backend, Front Controller, several dissimilar Page Controllers, a liberal smattering of object-oriented and procedural Models, a confusing bunch of Views and templates, some JavaScripts, CSS files and Flash objects.
The programmer in me is a big fan of the principle of “Separation of Concerns” and on that note, I’m currently trying to figure out the best way to separate and combine the various concerns as the project grows and more people contribute to it.
The problem we’re facing is that although JavaScript (or Flash with ActionScript) is normally written with the template, hence part of the View and decoupled from the Controller and Model, we find that it actually encompasses the entire MVC pattern... Swap an image with an onmouseover event - that’s Behaviour. Render a datagrid - we’re manipulating the View. Send the result of reordering a list via AJAX - now we’re in Control. Check a form field to see if an email address is in a valid format - we’re consulting the Model.
Is it wise to let the database people write up the validation Model with jQuery? Can the php programmers write the necessary Control structures in JavaScript? Can the web designers really write a functional AJAX form for their View? Should there be a JavaScript overlord for every project?
If the MVC pattern could be applied to the people instead of the code, we would end up with this:
Model - the database boffins - “SELECT * FROM mind WHERE interested IS NULL”
Control - pesky programmers - “class Something extends NothingAbstractClass{…}”
View - traditionally the domain of the graphic/web designer - “”
…and a new layer:
Behaviour - interaction and feedback designer - “CSS3 is the new black…”
So, we’re refactoring and I’d like to stick to best practice design, but I’m not sure how to proceed. I don’t want to reinvent the wheel, so would anyone have any hints or tips as to what pattern I should be looking at or any code samples from someone who’s already done the dirty work? As the programmer guy, how can I rewrite the app for the backend and front end whilst keeping the two separate?
And before you ask, yes I’ve looked at Zend, CodeIgnitor, Symfony, etc., and no, they don’t seem to cross the boundary between server logic and client logic!
You and everyone else with a brain is asking this question and it's a sticky one. A really good Information Architect thinks in terms of usability, behaviors and flow, although he/she may not even know how to use design tools or be able to draw or program. If they can get an interface into a sketch, the designers can make it pretty. Let the designers do the looky feely STATIC stuff--that's what they are good at. Provide IA with a library of front-end behaviors that they can specify for screen objects. They don't implement this stuff, they only USE it. This is much easier if you use a front end tool such as JQuery, and it's great if you have a front end guru who understands both design & the back end quite well. Separate your javascripts into their own directory and always link them as external files. All the PHP frameworks have methods to do this dynamically. I have toyed with the idea of a config structure that maps files to all the front end stuff that they load so each individual view only loads what it needs. But you are absolutely right: There is a whole nother sub-MVC for the clientside that lives primarily within the views of the overall MVC. I think you can partition off the Ajax stuff (when the view needs to refer back to the server) I document Ajax controller methods as ajax methods and don't call them otherwise. A lot of it is having everyone on your team buy into the division of labor paradigm. It will just cause them to write more decoupled reusable code whatever framework you ultimately choose to hang it on. And you're right, you can do the front end encapslation with all of them, but NONE of them enforce good front end encapsulation, I think that's still in the realm of DYI. Good luck.
Greetings all!
Looking for some help with MVC in a PHP context. Currently I am building a small, lightweight MVC framework to help expedite application development at work. It's a long hard separation eliminating inline code - at least with numerous projects looming overhead and the temptation to utilize it ever-present.
I understand most of the basic requirements of MVC, and I've already begun porting some of my existing classes that are in Singleton pattern over as utilities in my new framework (these are mostly basic 'handlers' to perform site services - a class for file uploads, authorization, wrapped PDO database queries, error printing etc.)
What I can't seem to grasp moving forward after reading much documentation is the best approach to instantiating views. In my old, inefficient design I would switch off a $_GET variable to switch ouput from within the home view. Just going off intuition, this seems like an extremely bad way of getting the job done.
I've looking into CodeIgniter, and it would seem that there are predefined functions for loading views within that framework. What is the best approach to such an application design? Would it be a class based 'link factory' that utilizes the same variables to fetch content, select the proper view file, and place it in the page flow? Also, how could the new view be included between the header and footer includes in the root index without using switches? This is the only thing really confusing me - I really hope I have worded myself clearly enough.
Thanks all as ever!
I highly recommend "PHP Objects, Patterns, and Practice" by Matt Zandstra. A good bit of the book deals with creating MVC frameworks and would be very, very helpful to you.
It covers these patterns (which you can also research elsewhere):
Front Controller
Application Controller
Page Controller
Template View
View Helper
While I'd suggest going with an established, flexible framework (like Zend), to answer your question, here are the steps involved as I see them (understand I stopped trying to write this kind of stuff a while ago, this is based on my understanding of the existing frameworks I've used).
Some kind of router parses the request and translates to a controller object with an action (or takes the default) and optional parameters. The router then calls the controller object's function matching the action.
The controller object (usually extended from a generic controller object) process the request and determines what data to pass to the view, as well as what view to use. Most frameworks setup a default view based on the action, but ultimately it's up to the controller to decided what view to use.
The view takes the data and displays it.
That is my very simplified take on the process.
Long time lurker, first time poster...
I'm now at the point where I'd almost call myself a professional grade PHP programmer and have a lot of code I re-use in various projects. Also, a lot of Open Source packages I've worked with use the MVC model and as a result I've done a lot of research recently into how it all works so I can better edit them as required.
At this point, I'm considering taking a bare-bones MVC framework (from a tutorial) and extending it as required for my forthcoming programming jobs.
My question is whether the MVC model with pretty much all application logic separated from the presentation layer is considered best practice over a well structured OOP website with coding on the page as necessary e.g setting function variables.
Or will I run into issues when I want coding flexibility e.g.
using something like PHPthumb for a gallery where I want different output
sizes on different pages and currently set parameters in the head
of the page
a contact form with x fields and a feedback form with y fields - will this require 2 differrent models rather than a generic form class again with some parameters set in the head of the page
some pages requiring ob_start() and ob_flush() but not others?
Please don't tell me not to build my own framework - I'd rather know how each little bit works than use a slab of code I know nothing about - I'm really interested in the opinion of people who have gone this route and build sites every day. What are the real pros and cons of this over plain (but well structured) OOP and bunch of pages to a site as opposed to 1 index.php page and separate files.
Cheers,
Niggles
I know you say you don't want this advice, but don't write your own. The first thing I've done at every single job I've ever worked at is picked up some existing code or framework, often commercial but highly modified, and begun maintaining it. You'll seldom get the option to write your own, and doing so is a bad idea. It's hard, expensive, and somebody else has already written a better MVC PHP framework than you're likely to write.
There are literally dozes of mature PHP frameworks, most of which have been around for over a decade. Choose one of them. It doesn't matter which one - they're all maintained by a dozen people at least as smart as you who've been writing MVC frameworks a lot longer, and have spent months or years refining their frameworks and listening to user input.
All that said, if you want to write your own on your own time, as a hobby, so you're not wasting your boss's money, then by all means. There's a huge variety of interpretations of MVC. Some frameworks view views as basically templates. I personally think you can throw as much raw PHP in there as you'd like, so long as it's purpose is display, and you do the usual smart things like distilling out shared code into functions. Some frameworks have virtually no business logic in the models (where it belongs IMO) but have very heavy controllers. The best thing you can do is try other frameworks and see how they work, and which you like best, and decide what you'd like to see changed. Then, set out to change it in your own.
You say you're almost ready to consider yourself a professional? The hardest lesson I had to learn was that professionals don't write their own low-level libraries. They don't reinvent the wheel on the company buck. They use off-the-shelf components and get the job done today, rather than a month from now. You don't want to use a slab of unfamiliar code? That's the biggest part of your life to come as a programmer - get used to it.
Writing your own framework is great for your own edification and for truly understanding the language.
Personally I find its as time consuming using a third party framework as it is to write your own. Yet I have total control of my own code, not something you can claim with any third party framework.
I also think many MVC frameworks are very resource intensive. For high volume sites you need to be prepared to throw hardware at them to get them to run nicely. For low volume sites (the majority) the rapid development of a third party MVC framework is a huge bonus.
So in my opinion if you have the time, roll your own and be proud of it. Just make sure you learn from others especially where security is concerned.
It all depends on what are you project requirements are and how you design your application objects. MVC do not force you to use an specific class or view design, It will only provide you with an architecture that will help you isolate the business logic from the presentation and the data layer making you application more scalable and easy to test.
In MVC you are not tied to one view per controller you can use as many views as you want per controller since every exposed method can call a view itself and control how it looks and behave based on the business logic you define. That said you can have 2 methods to return a full size image and a thumbnail without having to create two pages. You can set everything on the view from the controller, header meta-data, scripts, links, theme, content, etc...
In regard to the models, it again depends on your project requirements but definitely, in any case, if you have several pages with different purposes and they require to modify different data sources there should be a model for each one of them and what you can do after is to create a class that encapsulates the form functionality by calling the model for getting the fields to create form, get and save the data. This is just an idea you can do it in a lot of different ways, that is the beauty of OOP.
In the end it is not a matter of comparing a well structured OOP site against an OOP MVC site, It is more an analysis of the time and effort you spend working on building a site architecture that can succeed in isolating concerns at the same time it still readable and scalable while it meets your project requirements.
If you want to get more ideas about design patterns you can use google MVP design pattern and/or MVVM design pattern.
I have written my own framework. It does not take time to create the architecture and raw code. It's great if someone writes there own framework. But If documentation is not proper than definitely pain in asses. Completely depends upon yourself. I have written mine as well. It took almost 7 days to make framework QA ready :). but the main issue is to get satisfied by the piece of code you write in your framework. You would always like to improvise your framework and wanted it to be best ever. BLAH! BLAH! If you wish to write your own and you are confident enough for sustenance. GO for it.
Any MVC -- homegrown or not -- will allow you flexibility and re-usable code.
ob_start() / ob_* calls are no problem, they go in your model and called from your template, e.g.:
Hello <?php echo $this->getFormattedName(); ?>
where your model is
function getFormattedName() {
ob_start();
echo '' . $this->getName() . '';
$return = ob_end_clean();
return $return;
}
For your form scenario, you would probably want an abstract form class that defines how a field is made and its validation, then each specific form would extend your abstract.
You may want to consider using something like Zend Framework -- while it's an MVC library in its own right, you can pull in single components super easily (for example, you can pull in Zend_Form and Zend_Mail for your contact and feedback forms & validation and use your own models for everything else). This would also give you the extra benefit of having a fallback when/if the time comes when your homebrew MVC framework starts to outgrow its original design. Or, at the very least, speed up your development time so that you're not held up for days because you suddenly realize you need an e-mail model.