al.
al.

Reputation: 504

Paginate error - grails dynamic scaffolding

On looking for a solution for a two-domain-classes-in-one-view problem, I ran into the scaffolding tutorial for grails where I saw this:

class BookController {
   def scaffold = Book
   // overrides scaffolded action to return both authors and books
   def list = {
     [ "books" : Book.list(), "authors": Author.list() ]
     }
 } 

And it says underneath:

All of this is what is known as "dynamic scaffolding" where the CRUD interface is generated dynamically at runtime.

I'm quite new to the scaffolding concept, and there is something I don't get here. I expect that the list.gsp is dynamically generated based on the controller return parameters, thus enabling me to have both lists in one view. I don't know if this is possible, it's just the thing that I expect to magically happen here. So please, correct me if I'm wrong.

If this should be the case, then something goes wrong in my application and I get:

 org.codehaus.groovy.grails.web.pages.exceptions.GroovyPagesException: Error processing GroovyPageView: Tag [paginate] is missing required attribute [total] at /customer/list:45

So this is something in the view, which I don't have, because I'm expecting it to get scaffolded. Could it be that the error is caused by the fact, that I use the default templates? Should I create a new template specially for my needs? Also, is there some aricle on grails lifecycle, so that I can see what gets passed when?

Thank you all for the help, al

Upvotes: 0

Views: 1771

Answers (3)

ben3000
ben3000

Reputation: 5029

Interestingly, in overriding the index() action so that I could sort the result differently, I found that in Grails 2.3.7, the default values are now bookInstanceList and bookInstanceCount.

The documentation hasn't changed from bookInstanceTotal!

These names are further decided by the following setting in grails-app/conf/Config.groovy:

grails.scaffolding.templates.domainSuffix = 'Instance'

Upvotes: 0

Victor Sergienko
Victor Sergienko

Reputation: 13495

If you're scaffolding Book class, it will only scaffold list of Books.

You can issue a command grails install-templates to see what scaffolding does. You can safely delete the src/template/scaffolding afterwards.

In your case, list.gsp template is expecting two variables: bookInstanceList and bookInstanceTotal. bookInstanceTotal is a value of required total parameter to [paginate][2] tag, so you get the mentioned error.

Upvotes: 1

chrislatimer
chrislatimer

Reputation: 3560

I believe you have misunderstood that section of the Grails documentation. By default, scaffolding provides an index, list, show, edit, save, update, and delete action. However, when they Grails documentation says that you can return both Books and Authors, it doesn't mean that it will automatically scaffold a new view for BOTH books and authors. It is saying that if you want to go and create a new 'list' view, i.e. grails-app/views/book/list.gsp you can make it so that the application will use your list closure and view instead of a scaffolded one.

Now, you've run into a bit of Grails trivia that I have never considered before. What if you override a scaffolded closure without specifying a new view, will Grails give a 404 or will it use the scaffolded view? It appears that it uses the scaffolded view. As such, the default list view uses pagination, and it expects to see an xxxInstanceListTotal variable which the paginate tag then uses for its total attribute. Since there's no value provided, paginate throws the exception seen there.

Scaffolding is pretty basic functionality, it's not smart enough to show a combined list of Books and Authors.

Upvotes: 2

Related Questions