Search code examples
model-view-controllercoldfusionrailocfwheels

CFWheels - How to have a form self post?


I'm new to wheels and still learning. It seems to me that every post of a form needs to call an action that maps to a method in the particular model. However, is it possible for a form to post to itself?

What I want to avoid is people navigating to an action view directly - which seems to throw an error. I'd also like to do a lot of self-posting because it might mean I won't have to have a lot of empty files laying around in my views folder.

Another advantage I was thinking about was the fact that if a form is self posting, I'd have the benefit of having it used globally. For example, I might have a form in my header that I want my user to fill out anywhere in the website. Or is there a way to detect where the user came from and do a dynamic redirectTo?

Many thanks, Michael.


Solution

  • To avoid errors due to users browsing to post actions, look at Verification: http://cfwheels.org/docs/chapter/verification

    So your create and update actions would be configured like this in the controller's init:

    <cffunction name="init">
        <cfset verifies(only="create,update", post=true, params="comment", paramsTypes="struct")>
    </cffunction>
    

    It is not unreasonable to redirect the user back to the previous page after the form has posted. Look at redirectTo(back=true) for your success action. http://cfwheels.org/docs/1-1/function/redirectto

    <cffunction name="init">
        <cfscript>
            verifies(only="create,update", params="comment", paramsTypes="struct");
            provides("html,json");
        </cfscript>
    </cffunction>
    
    <cffunction name="create">
        <cfscript>
            comment = model("comment").new(params.comment);
            comment.save();
    
            if (isAjax())
            {
                renderWith(comment);
            }
            else
            {
                if (comment.hasErrors())
                    redirectTo(back=true, error="There was an error saving the comment.");
                else
                    redirectTo(back=true, success="The comment was posted successfully.");
            }
        </cfscript>
    </cffunction>
    

    Yes, I like Craig's answer that AJAX is a good solution, but you also need to consider what happens if the AJAX fails and the form is ultimately posted to the URL through a non-AJAX request. Best to provide a fully accessible experience.