serving error pages in mvc: the control or the view? - model-view-controller

Let's start by getting on the same page about MVC on the web. The control receives requests, selects a view, sends a response that it gets from the view. (Maybe the control gets data from the model, maybe the views do it themselves, I don't care.) Errors can occur, so we want to handle the errors and display a message or error page to the browser.
I'm trying to decide if these error messages/pages are part of the control or come from the view. Perhaps it is different for different kinds of errors.
some examples:
The request path is meaningless, so we want to respond with a custom "not found" page.
The control selects the "not found" view and uses its response
The control builds the "not found" page itself
.
The controller selects a view successfully, but the view throws an exception.
The view returns an error status. The controller checks the status and then selects a new view and uses its response
The view returns an error status. The controller build the error response itself.
The view handles the exception and returns a valid error page or message to the controller. The controller blindly sends it as the response.
Now, the difference between the first two options in both cases is technical/organizational, and there is probably no difference to the user. Is there a standard opinion on this (perhaps across MVC frameworks) or is the choice just arbitrary? What is the preferred method?

The controller selects a view successfully, but the view throws an exception.
If the MVC design pattern is followed, this should never happen. The only logic that should be contained in a view is solely display logic (formatting, localizing etc).
Errors should be trapped either at the model or controller level, but it's up to the controller to decide what to do with the user (redirect/404/etc).
Edit:
Of course it's not the only way.. I'm sure that you can find hacked up, bastardized code all over the place that does different things. As far as I'm concerned, yes - your views should be engineered in such a way that errors will not need to be trapped (other than ajax/javascript errors, but that's where they belong anyway).
I usually set it up so that I have a different view for each HTTP error code I want to handle, and a generic one for a catch-all. The controller will be responsible in this case to pass the error data to the view for rendering (usually as an array). Of course, this could also be done using an ErrorModel (which would be the 'correct' way of implementing it - I'm just lazy ;))

The approach I take is to allow the controller to handle your first case (route based errors). Any request made that is either unauthorized or poorly formed gets managed by a "static content" controller that renders the appropriate error view.
For your second class of errors - I'm not sure how/if the view can communicate back to the controller that it's thrown an error. I'm actually interested to see other's opinions, because as far as I know if a view encounters an error, it's up to the view to deal with it.

Related

What is the difference between "render a view" and send the response using the Response's method "sendResponse()"?

I've asked a question about what is "rendering a view". Got some answers:
Rendering a view means showing up a View eg html part to user or
browser.
and
So by rendering a view, the MVC framework has handled the data in the
controller and done the backend work in the model, and then sends that
data to the View to be output to the user.
and
render just means to emit. To print. To echo. To write to some source
(probably stdout).
but don't understand then the difference between rendering a view and using the Response class to send the output to the user using its sendResponse() method. If render a view means to echo the output to the user then why sendResponse() exists and vise versa? sendResponse() exactly sends headers and after headers outputs the body. They solve the same tasks but differently? What is the difference?
In ZF, rendering a view doesn't actually output any content. Instead the rendering process returns the content as a string to the caller. Zend_Application automatically takes care of taking the rendered view and inserting it into your layout (assuming you use layouts) through a placeholder, and putting that data into the Zend_Controller_Response_Http object which is ultimately responsible for delivering the content to the user. The reason for the Response object is so it can encapsulate your HTML output, and also manage any additional HTTP headers or redirects you want to send.
You can also manipulate further the contents of the response in the Response object prior ot sending the data to the client if you wish.
sendResponse() takes care of sending any headers (including the HTTP response code), checking for any exceptions that may have occurred (due to not being able to send headers or other reasons) and then sends the HTML which could include your layout and one or more rendered view scripts.
Hope that helps.
They are two very different things.
Rendering a view provides another layer in which you can template your data. This will allow you to easily dynamically populate HTML/templates keeping logic seperate from presentation.
Echoing data directly skips this step, and is usally reserved for reterning json/xml (data) responses to user instead of html response.
You didn't post which framework you are talking about but both should allow you to specify response headers.
Please don't oversimplify. Every server's purpose is to render resource but that doesn't mean they are all the same.

How to force Wicket "onchange" AJAX events to be triggered if fields fail validation conditions

The specific case I've got in mind is as follows: an AjaxFormComponentUpdatingBehavior("onchange") is added to a TextField in a form. The behavior verifies the text for certain conditions (either the model object or the form component model, doesn't matter), based on which it might display a message (or hide it, if it has already been shown).
The problem is, there are also validators added to the TextField. One of the possible (and likely) scenarios consists of the user typing in, first, a value that causes the message to be displayed by the AJAX request. If, then, he/she types in a value that doesn't pass validation, the message should disappear, but it does not.
Apparently, either the onUpdate() method for the AJAX behavior is not called at all, or I am failing in my attempts to insert a check for non-validated entries (I have tried to test for both null values and empty strings, to no avail; I have no idea what exactly Wicket's validators do to models when data is invalid).
I am wondering if someone who actually understands validators (or AJAX, actually) has any ideas on where the problem could be.
I can post edit and post code if someone tells me this is not a general issue tying validators and AJAX, but most likely a programming mistake. I still believe the former and thus I'll refrain from posting code sections, in order to keep the discussion on an API/theoretical frame.
Thanks.
When using an AjaxFormComponentUpdatingBehavior, if any of the IValidators fail their validation, onError() will be called instead of onUpdate(). Wicket will effectively prevent invalid user input from reaching the IModels in your components, so the component's ModelObject will not be changed at all. The invalid input will probably remain available by means of getInput()/getConvertedInput() (not sure if it will in an AJAX scenario, it sure is in a traditional form submission).
However, take into account that IFormValidators are not executed when using this mechanism. If you've got any, you might be interested in overriding getUpdateModel() so that AjaxFormComponentUpdatingBehavior will not bring maybe-invalid user input into your IModels, and set modelobjects manually when you're certain user input is valid.
Regarding your specific case, you could perform all the required logic in onError() (or rely on Models that will grab data from somewhere else), and just add the components that need refreshing to the AjaxRequestTarget. This is probably what's missing in your scenario.

How do I use continuations in FubuMVC

https://github.com/adymitruk/fubumvc/commit/083e1d593d4e797ac04fb493acd1e29a332cd303?w=1
It seems returning a continuation breaks the binding to the view. It used to work before I added the continuation. Now I get a blank page for the default view.
You're using the same input model for your get and your post, so when you transfer, you get into an endless loop. I'm surprised you don't get a stackoverflow. There must be some checking in FubuContinuation that breaks the loop.
You're using the input model as the view model which you (generally) shouldn't do.
Your form tag needs to be a
Also, it looks like due to the naming of your models and the folders, the default view conventions weren't matching up views to your actions. To get things working, I threw them all in the same folder (bad, I know).
You'll want to sort out the folders and namespaces before doing anything serious with this.
Here's the pull request which I was able to get working and posting and such:
https://github.com/adymitruk/fubumvc/pull/1

How to get error messages from model

Say you have a User model. The controller is attempting to create a new User. Should the controller check that the username is valid, and the password is long enough, and the first and last name are filled out, etc? Or should you pass all that data straight to the User model via a Create method? The Create method would then return a true on success, or false on failure?
If it's the latter (and I think it is), how do the error messages get sent back to the controller (so they can be displayed in a view)? Should you pass an errors array to the Create method which the model augments? Or should the model keep an internal store of errors, with appropriate accessors? I don't like either method...is there a better way?
These errors don't seem exceptional, so I don't think exception handling is appropriate.
Edit: I'm using PHP for this project, but I use Python too.
For the first question, the model should do the verifications (and use some form of error handling to notify the controller and view that errors did or did not occur). For the second, it depends on what programming language / framework you are using... What are you using?

In a MVC-model, whose responsibility is it to sanitize input?

A simple question: I have a Model-View-Controller setup, with Models accessing a SQL database. In which part should I sanitize/check for malformed incoming data?
It's important to keep error handling as low as possible in the stack, but supplemental in other parts. If you keep the sanitizing in the controller, you could break the model by swapping out the controller with a looser one, but you can never break the model by being strict higher up in the stack. Keep the sanitizing low in the stack for consistency, and high in the stack for user feedback.
I'd say the Controller should sanitize input.
The model should at most decline to store invalid data.
I would say it is the responsibility of the controller to validate the input and make sure the data is valid before passing on the data to the model.
If invalid data is found, the controller should redirect back to the view and display the relevant error messages.
Having validation in the view only could be bypassed if the user doesn't have javascript enabled or posts to the url directly, however some validation in the view is better from a user experience point of view since the user does not need to wait for a return from the server in a web application.
The model will validate business logic rules, i.e. password length requirements, if a user is allowed to perform an action or not.
The model should obviously also make sure interaction with the database is done in a safe way so that SQL Injection is not possible.
The controller should handle relaying business logic errors back to the view, but can also do some basic sanity checks, i.e. a field is not empty.
I would say output sanitization should also go in the Controller before being passed to the View.
I use two levels of checking. My controller will check what is supposed to be a date is a date, an int an int and so forth. Basically ensuring they can be used to set the values on my objects.
Then my domain has validation for things such as valid values and other business rules. These are ALWAYS checked before saving or interacting with an edited object.
All errors from either level get returned to the user so they can take remedial action as necessary.
I tend to:
Put syntactic validation in the view ("this field is numeric", "that field is a date"). This is often very easy or even implicit in your choice of view design (eg: using a date picker for date fields).
Put semantic violation in a separate validator class ("this date field has to be after that date field", "this can be null if that is greater than zero") and call the validator from the controller, passing errors back to the view for display.
(for my own pseudo-correct definitions of syntax and semantics...)

Resources