Phase I¶
Create Lottery Project¶
Create a Lottery project and set-up
~/temp $ smile new Lottery
~/temp $ cd lottery
~/temp/lottery
~/temp/lottery $ sbt
$[Lottery] smile
Load project in IntelliJ(build.sbt) and Eclipse(import k)
Lottery Mongo Module¶
- Open Lottery.ksmile in Eclipse.
- Edit Lottery.ksmile and insert the below content to create a LotteryMongo module
Lottery.ksmile
group lottery {
mongo-module LotteryMongo at com.metastay.lotterymongo
}
- $smile
- In Eclipse refresh to see the LotteryMonogo.kmongo
- Edit LotteryMongo.kmongo to add a collection.
LotteryMongo.kmongo
collection Lottery {
property lotteryName:String
property amount:Int
property participantList:String*
property winner:String?
property open:Boolean
}
- $compile
- Write test cases in LotteryMongoTestSuite.scala
LotteryMongoTestSuite.scala
test("lottery", Tag("lottery")) {
LotteryWriter().drop()
val lotteryName = "KarnatakaLotto"
val row = LotteryRow(lotteryName = lotteryName, amount = 20000, open = true)
LotteryWriter().save(row);
assert(LotteryQuery().count == 1)
//Add Participant
val q = LotteryQuery().lotteryName.is(lotteryName)
val u = LotteryUpdate().participantList.addToSet("John")
LotteryWriter().updateOne(q, u)
assert(q.findOne.get.participantList.size == 1)
//Remove Lottery
//LotteryWriter().remove(q)
//assert(LotteryQuery().count == 0)
}
- import com.metastay.lotterymongo.lottery._
- Run Test
- $project LotteryMongo
- $test-only com.metastay.lotterymongo.LotteryMongoTestSuite – -n lottery
- Show the tables in mongochef/robomongo
Lottery Play Module¶
Building Lottery web-app, to see the list of lotteries, and adding play module to createLottery, addParticipant, runLottery.
Web Reader¶
First add a data module in Lottery.ksmile to hold data to represent Lottery details. LotteryPlay will use LotteryDetails data, so it depends on LotteryData
group Lottery {
data-module LotteryData at com.metastay.lottery
mongo-module LotteryMongo at com.metastay.lotterymongo
play-module LotteryPlay(LotteryData, LotteryMongo) at lotteryplay
}
- $smile
- LotteryData.kdata add a Lottery
data Lottery ( lotteryName:String, amount:Int, participantList:String*, winner:String?, status:String)
- add web-reader to LotteryPlay.kplay
web-reader Lottery {
view lotteryList (GET){
output(lotteryName:String, amount:Int, participantList:String*, winner:String?, status:String)*
}
view lotteryDetails (GET){
input(lotteryName:String)
output(LotteryData::Lottery)
}
}
- $compile
- Implement LotteryWebReaderCode.lotteryList
override def lotteryList: Request[LotteryListView.Input] => List[LotteryListView.Output] = {
import LotteryListView._
request: Request[Input] =>
val input = request.body;
LotteryQuery().find.map(
row =>
LotteryListView.Output(
lotteryName = row.lotteryName,
amount = row.amount,
participantList = row.participantList,
status = if(row.open) "OPEN" else "CLOSED",
winner = row.winner
)
)
}
override def lotteryDetails: Request[LotteryDetailsView.Input] => Lottery = {
import LotteryDetailsView._;
request: Request[Input] => val input = request.body
val row = LotteryQuery().lotteryName.is(input.lotteryName).findOne.get
new Lottery(
lotteryName = row.lotteryName,
amount = row.amount,
participantList = row.participantList,
status = if (row.open) "OPEN" else "CLOSED",
winner = row.winner
)
}
- $run
- Test through url in browser http://localhost:9000/api/lottery/lottery-list
Web Writer¶
- Create lottery passing parameters like name and amount
- Add Participant to a lottery by passing the participantName and lottery name to which the participant will be added to.
- Run lottery which will pick a winner amoung the participant and close the lottery.
- Add the below code in Lottery.ksmile to create a Play Module and depend on LotteryMongo to access LotteryMongo.
Lottery.ksmile
play-module LotteryPlay(LotteryMongo) at lotteryplay
- $smile
- Refresh Eclipse to see the LotteryPlay.kplay
- Adding createLottery, addParticipant, run POST calls with an url “api”
LotteryPlay.kplay
module LotteryPlay (LotteryPlay)
route "api"
web-writer Lottery {
action createLottery(POST) {
input(lotteryName: String, amount: Int)
}
action addParticipant(POST) {
input(lotteryName: String, participantName:String)
}
action run(POST) {
input(lotteryName: String)
}
}
- $compile
- Implement the code to LotteryWebWriterCode.scala
LotteryWebWriterCode.scala
import com.metastay.lotterymongo.lottery._
object LotteryWebWriterCode extends LotteryWebWriterTrait {
override def createLottery: Request[CreateLotteryAction.Input] => Result = {
import CreateLotteryAction._
request: Request[Input] =>
val input = request.body;
LotteryWriter().save(LotteryRow(lotteryName = input.lotteryName, amount = input.amount, open = true))
Ok(s"${input.lotteryName} Lottery Created")
}
override def addParticipant: Request[AddParticipantAction.Input] => Result = {
import AddParticipantAction._;
request: Request[Input] =>
val input = request.body;
val q = LotteryQuery().lotteryName.is(input.lotteryName)
val u = LotteryUpdate().participantList.addToSet(input.participantName)
LotteryWriter().updateOne(q, u)
Ok(s"${input.participantName} has been added to ${input.lotteryName}")
}
override def run: Request[RunAction.Input] => Result = {
import RunAction._
request: Request[Input] =>
val input = request.body;
val q = LotteryQuery().lotteryName.is(input.lotteryName)
val participantList = q.findOne.get.participantList //To find the participantList
val winnerIndex = scala.util.Random.nextInt(participantList.size) //To find a winner Index
val winner = participantList(winnerIndex)
val u = LotteryUpdate().winner.set(Some(winner)).open.set(false)
LotteryWriter().updateOne(q, u)
Ok(s"${winner} has won ${input.lotteryName} Lottery")
}
}
- test through curl
- curl -H “Content-Type: application/json” -X POST -d ‘{“lotteryName”:”Loto”,”amount”:1000}’ http://localhost:9000/api/lottery/create-lottery
- curl -H “Content-Type: application/json” -X POST -d ‘{“lotteryName”:”Loto”,”participantName”:”John”}’ http://localhost:9000/api/lottery/add-participant
- curl -H “Content-Type: application/json” -X POST -d ‘{“lotteryName”:”Loto”,”participantName”:”Jim”}’ http://localhost:9000/api/lottery/add-participant
- curl -H “Content-Type: application/json” -X POST -d ‘{“lotteryName”:”Loto”,”participantName”:”Joe”}’ http://localhost:9000/api/lottery/add-participant
- curl -H “Content-Type: application/json” -X POST -d ‘{“lotteryName”:”Loto”}’ http://localhost:9000/api/lottery/run
- or Test through Postman