I'm completely new to Lift. My goal is to make a small application which will let me enter data about scientific articles (studies) into a database.
I haven't gotten around to making a database yet, still playing with getting an entry form to work. So I decided that I will hold a few studies in memory, in a list of a companion object to the Study class. I also created an accumulator variable to dispense unique IDs, as long as I don't have a DBMS managing the IDs.
As a smoke test, I visited the page showing the list of studies (seeded with two studies in code), then visited the form page, entered a new study, and navigated again to the list of studies. I was surprised to see that my new study has the ID of 1 instead of 3, so at some point, my accumulator variable must have been reset. But the ListBuffer collecting studies was not reset, because it showed all three studies. Adding more studies results in the counter incrementing by 1 every time.
The literature I have found on Lift (the two free books on Liftweb, as well as Gilberto Garcia's Lift Application Development Cookbook) are incomplete and are more like a collection of mini-tutorials, they don't explain how Lift works.
So what is the actual lifecycle of my Study object, and why did one mutable variable get reset after re-opening the page but not another?
package org.rumtscho.litsuche
package study
import scala.collection.mutable.ListBuffer
class Study private[study](
val id: Int,
val handmadeAuthorRef: String,
val humanReadableDescription: String )
{
}
object Study {
val seedStudies = List(
new Study(dispenseNextFreeId, "Brooks1975", "Tells us that throwing more programmers at a project makes it run late, not early"),
new Study(dispenseNextFreeId, "Dijkstra1968", "Recognizes that we need structured code")
)
private var studiesList = seedStudies.to[ListBuffer]
private var currentId = 0
private def dispenseNextFreeId: Int = {
currentId = currentId + 1
return currentId
}
def allStudies = studiesList.toList
def addStudy(reference: String, description: String): Unit = {
studiesList += new Study(dispenseNextFreeId, reference, description)
}
}
Here is the representation of the three studies:
update My understanding of what is happening (could be wrong, of course):
I open the page showing the list of studies. This calls
allStudies
.studiesList
is initialized to contain Brooks1975 and Dijkstra1968. During the construction of the studies, currentId is initialized to 0 and then incremented to 2.I open the entry form and add a third study.
addStudy
retrievesallStudies
from memory, without initializing it again. It initializes currentId to 0. I end up with a third study with the ID 1.I display all studies, then return to the entry form page. This time,
addStudy
retrieves bothallStudies
andcurrentId
from memory. I get a fourth study with the ID of 2.
The comments have pointed out that this is probably Scala-specific and not related to Lift. But still, I don't understand why currentId
is initialized two times (in steps 1 and 2), and not either once (as soon as the object itself is created) or every time it is read. I would have expected the first behavior, but even reinitializing every time seems more logical than randomly reinitializing one time only.