created in the spirit of Ruby on Rails.
In this tutorial, we'll be writing a simple application to make sure we have Wheels installed properly and that everything is working properly. Along the way, you'll get to know some basics about how applications built on top of Wheels work.
Watch and learn the basics with the Hello World video tutorial by Peter Amiri.
Let's make sure we're all on the same page. I'm going to assume that you've already downloaded the latest version of Wheels and have it installed on your system. If you haven't done that, stop and read the Installation chapter and get everything setup. It's okay, this web page will wait for you.
Okay, so you have Wheels installed and can see the Wheels congratulations page as shown in Figure 1 below. That wasn't that hard now, was it?

Figure 1: Wheels congratulations screen.
Imagine a football team where everyone tries to be quarterback. Things would get pretty messy rather quickly. On a football team, or any team for that matter, each member should have a specific job and responsibility.
Wheels helps clean up this mess by using a design pattern called Model-View-Controller (MVC). Let's take a brief look at MVC and see how it helps organize your Wheels applications.
At a basic level, a MVC framework like Wheels breaks your application into 3 distinct pieces, each having a well-defined role and responsibility. The 3 pieces are called models, views, and controllers. Pretty intuitive so far, eh?
The model is responsible for the data objects of your application. In general, models interact with your databases and contain any specific business rules that tell your applications how to use that data.
The view is responsible for the user interface, or presentation layer, of your application. Views build and present the web pages and other interface elements that make up your application.
The controller is the central command of your application. Controllers define and know about the functions or actions that your application can handle. These actions are generally the web requests initiated by the users by invoking URLs. A controller's job is to listen for these actions, interact with the model to get any data that is needed by the action, and then finally hand off the data to the view so it can display a page for the user.
Others have written entire volumes describing the MVC pattern and its pros and cons. Some of these books are great reads, but this high level understanding of MVC should be all that you need in order to get starting using Wheels.
The built-in URL-rewriting functionality of Wheels helps you create friendly, search engine safe URLs. No more are the days of URLs polluted with question marks, ampersands, and equals signs!
Consider the URL below:
http://www.example.com/say/hello
Like all URLs that you're familiar with, the http://www.example.com/ portion of the URL defines the domain or server name of your application. This portion is similar to any other URL on the Web. Really not much to see here, so let's move on.
The next portion is where the magic happens.
In other ColdFusion frameworks, we're used to seeing variables separated by ? and &. With Fusebox, for example, we'd probably see a URL like http://www.example.com/index.cfm?fuseaction=say.hello. Yuck.
Wheels, on the other hand, uses URL rewriting. Instead of specifying variables by separating them with ? and &, the different variables are passed to the application as folder names.
Our example URL defines which components and methods within the application get called by the URL. The example URL above tells our application to execute the say controller and call the hello action within that controller. So this is how the URL of a Wheels application maps to the parts of the MVC pattern described above.
Okay, let's get to some example code. We know that you've been dying to get your hands on some code!
To continue with Programming Tutorial Tradition, we'll create the ubiquitous Hello World! application. But to keep things interesting, let's add a little Wheels magic along the way.
Let's create a controller from scratch to illustrate how easy it is to set up a controller and plug it into the Wheels framework.
First, create a file called say.cfc in the controller directory and add the code below to the file.
<cfcomponent extends="controller">
</cfcomponent>
Congratulations, you just created your first Wheels controller! What does this controller do, you might ask? Well, to be honest, not much. It has no functions defined so it doesn't add any new functionality to our Wheels application. But because it extends the base controller component, it inherits quite a bit of powerful functionality and is now tied into our Wheels application.
So what happens if we try to call our new controller right now? Lets take a look! Open your browser and point your browser to the new controller. Because my server is installed on port 80, my URL is http://localhost/say. You may need to enter a different URL, depending on how your web server is configured.
If you did everything right, you will get the Wheels error shown below in Figure 2. (Ironic that getting an error is doing something right, huh? Don't get used to it, buddy!)

Figure 2: Wheels error after setting up your blank say controller.
The error says "There is no action named 'index'." Where did "index" come from? The URL we typed in only specified a controller name but no action. When an action is not specified in the URL, Wheels assumes that we want the default action. Out of the box, the default action in Wheels is set to index. So in our example, Wheels tried to find the index action within the say controller, and it threw an error because it couldn't find it.
But let's jump ahead. Now that we have the controller created, let's add an action to it called hello. Change your say controller so it looks like the code block below:
<cfcomponent extends="controller">
<cffunction name="hello"></cffunction>
</cfcomponent>
As you can see, we created an empty method named hello.
Now let's call our new action in the browser and see what we get. To call the hello action we simply add /hello to the end of the previous URL that we used to call our say controller:
http://localhost/say/hello
Once again, we get a ColdFusion error. Although we have created the controller and added the hello action to it, we haven't created the view.
By default, when an action is called, Wheels will look for a view file with the same name as the action. It then hands off the processing to the view to display the user interface. In our case, Wheels tried to find a view file for our say/hello action and couldn't find one.
Let's remedy the situation and create a view file. View files are simple CFML pages that handle the output of our application. In most cases, views will return HTML code to the brower. By default, the view files will have the same name as our controller actions and will be grouped into a directory under the view directory. This new directory will have the same name as our controller.
Find the view directory in the root of your Wheels installation. There will be a few directories in there already. For now, we need to create a new directory in the view directory called say. This is the same name as the controller that we created above.
Now inside the say directory, create a file called hello.cfm. In the hello.cfm file, add the following line of code:
<h1>Hello!</h1>
Save your hello.cfm file, and let's call our say/hello action once again. You have your first working Wheels page if your browser looks like Figure 3 below.

Figure 3: Your first working Wheels action.
You have just created your first functional Wheels page, albeit it is a very simple one. Pat yourself on the back, go grab a snack, and when you're ready, let's go on and extend the functionality of our Hello World! application a little more.
We will add some simple dynamic content to our hello action and add a second action to the application. We'll then use some Wheels code to tie the 2 actions together. Let's get get to it!
The first thing we are going to do is to add some dynamic content to our say/hello action. Modify your say controller so it looks like the code block below:
<cfcomponent extends="controller">
<cffunction name="hello">
<cfset time = Now()>
</cffunction>
</cfcomponent>
All we are doing here is creating a variable called time and setting its value to the current server time using the basic ColdFusion Now() function. When we do this, the variable becomes immediately available to our view code.
Why not just set up this value directly in the view? If you think about it, maybe the logic behind the value of time may eventually change. What if eventually we want to display its value based on the user's time zone? What if later we decide to pull it from a web service instead? Remember, the controller is supposed to coordinate all of the data and business logic, not the view.
Next, we will modify our say/hello.cfm view file so that it looks like the code block bellow. When we do this, the value will be displayed in the browser.
<h1>Hello!</h1>
<p>Current time: <cfoutput>#time#</cfoutput></p>
Now call your say/hello action again in your browser. Your browser should look like Figure 4 below.

Figure 4: Hello World with the current date and time.
This simple example showed that any dynamic content created in a controller action is available to the corresponding view file. In our application, we created a time variable in the say/hello controller action and display that variable in our say/hello.cfm view file.
Now we will expand the functionality of our application once again by adding a second action to our say controller. If you feel adventurous, go ahead and add a goodbye action to the say controller on your own, then create a goodbye.cfm view file that displays a "Goodbye" message to the user. If you're not feeling that adventurous, we'll quickly go step by step.
First, modify the the say controller file so that it looks like the code block below.
<cfcomponent extends="controller">
<cffunction name="hello">
<cfset time = Now()>
</cffunction>
<cffunction name="goodbye"></cffunction>
</cfcomponent>
Now go to the view/say directory and create a goodbye.cfm page.
Add the following code to the goodbye.cfm page and save it.
<h1>Goodbye!</h1>
If we did everything right, we should be able to call the new say/goodbye action using the following URL:
http://localhost/say/goodbye
Your browser should look like Figure 5 below:

Figure 3: Your new goodbye action.
Now let's link our two actions together. We will do this by adding a link to the bottom of each page so that it calls the other page.
Open the say/hello.cfm view file. We are going to add a line of code to the end of this file so our say/hello.cfm view file looks like the code block below:
<h1>Hello!</h1>
<p>Current time: <cfoutput>#time#</cfoutput></p>
<p>Time to say <cfoutput>#linkTo(text="goodbye", action="goodbye")#?</cfoutput></p>
The linkTo() function is a built-in Wheels function. In this case, we are passing 2 named parameters to it. The first parameter, text, is the text that will be displayed in the hyperlink. The second parameter, action, defines the action to point the link to. By using this built-in function, your application's main URL may change, and even controllers and actions may get shifted around, but you won't suffer from the dreaded dead link. Wheels will always create a valid link for you as long as you configure it correctly when you make infrastructure changes to your application.
Once you have added the additional line of code to the end of the say/hello.cfm view file, save your file and call the say/hello action from your browser. Your browser should look like Figure 6 below.

Figure 6: Your say/hello action with a link to the goodbye action.
You can see that Wheels created a link for us and added an appropriate URL for the say/goodbye action to the link.
Let's complete our little app and add a corresponding link to the bottom of our say/goodbye.cfm view page.
Open your say/goodbye.cfm view page and modify it so it looks like the code block below.
<h1>Goodbye!</h1>
<p>Time to say <cfoutput>#linkTo(text="hello", action="hello")#?</cfoutput></p>
If you now call the say/goodbye action in your browser, your browser should look like Figure 7 below.

Figure 7: Your say/goodbye action with a link to the hello action.
You now know enough to be dangerous with ColdFusion on Wheels. Look out! But there are many more powerful features to cover. You may have noticed that we haven't even talked about the M in MVC.
No worries. We will get there. And we think you will enjoy it.