This is a creation in Article, where the information may have evolved or changed.
Since the Revel framework itself does not provide any guidance for the writing of the model layer, there is some hesitation in designing this part, and it is a good practice to reconsider what is best.
I was just beginning to get tangled up when I was doing the hillside net, unsure where the creation and destruction of MongoDB's session should be handled. Until one day I saw the author of the Revmgo in the discussion with the author of the Revel (specific content here), went to study the next Revmgo, then immediately replaced my own implementation.
Let's start with the usage.
1. Add MongoDB connection string in app.conf.
Revmgo.dial = Mongodb://username:password@serverip/database
2. Initialize in the Init method of the controller layer.
Func init () {
Revmgo. Controllerinit ()
Revel. Onappstart (func () {
Revmgo. Appinit ()
}
}
3. Check the Mongocontroller into all controllers that require access to the database.
Type application struct {
*revel. Controller
Revmgo. Mongocontroller
}
Here's a little episode, Revmgo. Mongocontroller has been embedded in the Revel.controller, but it is still not possible to omit *revel here. Controller. The reason is that revel only reflected a layer when determining the active Controller's action, and discussed the problem with the author of Revel, who later persuaded me that the complexity would be higher and the performance penalty would be out of control if the constant recursive reflection. Well, actually this is OO legacy. Looks very uncomfortable, write a line of code, the design is not too comfortable, but carefully think about the performance and overall complexity is good, so, why persist in design perfection? Simplicity is beauty.
4. Modify the implementation of the DAL.
Data Access Layer
Type Dal struct {
Session *mgo. Session
}
Create a new DAL
Func Newdal (Session *mgo. Session) *dal {
if session = = Nil {
Panic ("Session cannot be nil.")
}
Return &dal{session}
}
Now let's look at how to use it in the controller.
Func (c *account) handleregister (user *models. Mockuser) Revel. Result {
Validate parameter here.
DAL: = models. Newdal (c.mongosession)
ERR: = Dal. RegisterUser (user)
Biz logic here
}
Revmgo's internal implementation is very simple, the entire code is 110 lines, the basic can be at a glance.
In general, call Revmgo. Appinit () When reading the configuration in the app.conf, you can see that there are two configuration entries valid, "Revmgo.dial" for the connection string, "Db.spec" to determine the way MongoDB session reuse (the specific meaning of reference here), Then set up the session.
After the Revmgo. Controllerinit registered two Interceptfunc to establish and close the session before and after the Controller's action access.
Func Controllerinit () {
Revel. Interceptmethod ((*mongocontroller). Begin, Revel. Before)
Revel. Interceptmethod ((*mongocontroller). End, Revel. FINALLY)
}
In fact, I have a very bad criticism of this design, the existence of controllerinit is simply a mock-up of the Revel module design mechanism, it is difficult to believe that as a module should also require users to manually invoke the initialization function. This part should not be difficult to handle, in general, should only let the user register to use the module and the order of execution, initialization and deconstruction are responsible for the module manager. With Revel's author also discussed this issue, see he seems to have other design intentions, and so on see Revel 1.0 when the official release will be what kind of son.