View Full Version : Scaffold: Overriding show breaks the view
ThomasBecker
Feb 7th, 2011, 08:34 AM
Hi all,
am still evaluating grails for a new project. Grails appeared to be very promising in the beginning (and it still does), but I'm having problems with things that should be really simple.
I'm trying to use scaffolding, but to override single methods in the controller like this:
class BookController {
def scaffold = true
def show = {
[ book : Book.get( params.id ) ]
}
}
If I remove the show method, all is fine. If I have it in, I'm getting the property names shown in the table, but not the values.
So I rewrote the method to:
def show = {
def book = Book.get(params.id)
log.error(book)
[ book : book ]
}
Which is basically the same thing, but gives a log message with the object found: server.BookController some.package.Book : 1
So it finds the object. It should be in the model for the gsp view. And the gsp should just display it, right?
What might be wrong here? That's a very simple use case and actually instead of trying it with my model, I tried it with the Book example from the documentation. Tried to remove scaffolding, but am still not getting any values back.
Any idea is appreciated. As I'm trying to get this running for a long while now and am starting to torn out my hair.
Cheers,
Thomas
deuseks
Feb 7th, 2011, 07:09 PM
Hey Thomas
Your problem might be the handle you are passing to the show.gsp that is used by the scaffolding.
this is what the scaffolding show method might look like
def show = {
def bookInstance = Book.get(params.id)
if (!bookInstance) {
flash.message = "${message(code: 'default.not.found.message', args: [message(code: 'book.label', default: 'Book'), params.id])}"
redirect(action: "list")
}
else {
[bookInstance: bookInstance]
}
}
so.. try renaming your handle from
[book:book]
to
[bookInstance: book]
where bookInstance is what the gsp uses as a reference to the book object you are returning
Let us know if that works
Deuseks
ThomasBecker
Feb 8th, 2011, 02:44 AM
Deuseks,
i can't believe that it works when using bookInstance as the name. But it does!
This is an excerpt from the reference doc. Chapter 6.3.1 Models and Views:
def show = {
[ book : Book.get( params.id ) ]
}
This is an excerpt from the scaffolding template Controller.groovy:
def show = {
def ${propertyName} = ${className}.get(params.id)
if (!${propertyName}) {
flash.message = "\${message(code: 'default.not.found.message', args: [message(code: '${domainClass.propertyName}.label', default: '${className}'), params.id])}"
redirect(action: "list")
}
else {
[${propertyName}: ${propertyName}]
}
}
It's using ${propertyName}: ${propertyName}] which should be resolved to [ book : book ], I thought. That's why I was really certain that it should somehow work that way. I spent more than 3hrs on this. First with my Domain objects. Then I tried the book example. Even tried to setup several fresh grails projects and googled, etc.
So in fact ${propertyName} gets resolved to "bookInstance". Good to know.
Without your hint I'm sure it would have taken me more time and I would have probably given up on grails and went on with known technologies. So thanks for your hint! Much appreciated.
Still this throws a bad light at grails. It's supposed to save me lots of time for custom development and in fact up to this point it did and it's really amazing how much I got for a few lines of code.
Can somebody please elaborate why it has to be named bookInstance and why it seems to be different in the reference doc and so many HowTos/Tutorials? Is it me being stupid and getting something wrong?
Thanks a lot again! You saved my day.
Thomas
deuseks
Feb 8th, 2011, 07:41 AM
Thomas
Actually you might not be right.. you would need to follow the entire trail used by the scaffold and see it indeed it would the same property name you are thinking of.
In my experience, generated template files always used propertyInstance as the name. In any case.. it does not detract from what grails can do for you.... it will take some getting used to but believe me ... this is THE framework to use if you plan to build web applications in Java quickly.
pledbrook
Feb 8th, 2011, 08:32 AM
Thomas, this was changed at some point, I think to avoid name clashes. Unfortunately, section 6.3.1 is about models and views in general, not the scaffolding. And the template Controller.groovy is a little confusing because it looks like 'propertyName' should be 'book', since that's the name of the property on the domain class.
I think the appropriate solution here is to expand the section on scaffolding in the user guide so that it covers this particular use case.
ThomasBecker
Feb 8th, 2011, 11:12 AM
Ok, got the difference now. I thought that what works in Model and Views in general should more or less also apply in scaffolding. I understood now why it doesn't (anymore).
A hint in the reference guide would be great as this might confuse more people than just me.
Thanks to you both for sorting this out. This works like a charm now. :)
pledbrook
Feb 8th, 2011, 11:39 AM
If you have a suggestion as to where the hint should be in the docs, let me know. I do think we should consider moving the scaffolding section to earlier in the guide, but I'm open to other ideas as well.
And here (https://github.com/grails/grails-doc/commit/3b74ddb0db6b4417f2501f029fc0fa1fdf362b54) are the changes I made to the scaffolding section.
ThomasBecker
Feb 8th, 2011, 11:55 AM
Good change. Would have saved me a couple of torned out hairs.
I'd put a yellow box below the example of the show method in the beginning of 6.1.3 that the name has to be different when scaffolding. The yellow box + your change should definetly prevent more users to do the same mistake as I did. Makes sense?
pledbrook
Feb 9th, 2011, 08:08 AM
I added a note (https://github.com/grails/grails-doc/commit/2adbb06be5f183592730e3e689390680216f576c) to 6.1.3 as you suggested. Hopefully it won't be too confusing.
I also raised a JIRA issue (http://jira.codehaus.org/browse/GRAILS-7238) asking that the error message you got from your domain constraints be improved. Until that's in place, users can find out about the gotcha from a new section (https://github.com/grails/grails-doc/commit/5501dd43223a87623fb99022eb9849f93131d99e) in the docs.
Thanks for your feedback.
ThomasBecker
Feb 9th, 2011, 10:49 AM
Peter, looks good. Hope it'll help others.
Powered by vBulletin® Version 4.2.1 Copyright © 2013 vBulletin Solutions, Inc. All rights reserved.