Basic authorization: only logged in user can change entities
authorTomas Zeman <tzeman@volny.cz>
Tue, 01 May 2012 23:27:55 +0200
changeset 89 fd364bae9c49
parent 88 777daf9e0026
child 90 39d3fc08414c
Basic authorization: only logged in user can change entities
src/main/scala/fis/aaa/ui/IfLoggedIn.scala
src/main/scala/fis/aaa/ui/UserSnippet.scala
src/main/scala/fis/crm/ui/CompanySnippet.scala
src/main/scala/fis/crm/ui/ContactSnippet.scala
src/main/scala/fis/geo/ui/CitySnipppet.scala
src/main/scala/fis/geo/ui/CountrySnippet.scala
src/main/scala/fis/geo/ui/LocationSnippet.scala
src/main/scala/fis/pm/ui/ProjectSnippet.scala
src/main/scala/fis/pm/ui/TaskSnippet.scala
src/main/webapp/templates-hidden/_resources.html
src/main/webapp/templates-hidden/_resources_cs.html
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/main/scala/fis/aaa/ui/IfLoggedIn.scala	Tue May 01 23:27:55 2012 +0200
@@ -0,0 +1,36 @@
+/*
+ * Copyright 2012 Tomas Zeman <tzeman@volny.cz>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package fis.aaa.ui
+
+import fis.aaa.model.User
+import net.liftweb.common._
+import net.liftweb.http._
+import net.liftweb.sitemap.Loc._
+import net.tz.lift.model._
+
+object IfLoggedIn {
+
+  private def testF: Box[LiftResponse] = User.get match {
+    case Full(_) => Empty
+    case _ => Full(RedirectWithState("/login", RedirectState(Empty,
+      l10n("login.needed") -> NoticeType.Warning)))
+  }
+
+  def test: TestAccess = TestAccess({() => testF})
+  def testVal[T]: TestValueAccess[T] = TestValueAccess({ v: Box[T] => testF })
+}
+
+// vim: set ts=2 sw=2 et:
--- a/src/main/scala/fis/aaa/ui/UserSnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/aaa/ui/UserSnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -41,7 +41,7 @@
     locTpl("entity/list") >> Snippet("list", list)
 
   private val createPre = Menu("user.create", l10n("Create")) / prefix / ADD >>
-    Title(_ => i18n("Create user")) >>
+    Title(_ => i18n("Create user")) >> IfLoggedIn.test >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val viewPre = Menu.param[User]("user.view", l10n("User"), parse,
@@ -52,12 +52,12 @@
 
   private val editPre = Menu.param[User]("user.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(c => i18n("Edit user %s", c.linkName)) >>
+    Title(c => i18n("Edit user %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[User]("user.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(c => i18n("Delete user %s", c.linkName)) >>
+    Title(c => i18n("Delete user %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val listM = listPre >> SecNav(createPre).build
@@ -156,6 +156,7 @@
     private val choosePreM = Menu.param[User]("user.addContact",
       l10n("Add contact"), parse, encode) / prefix / * / "add-contact" >>
       Title(c => i18n("Add contact to %s", c.linkName)) >>
+      IfLoggedIn.testVal >>
       locTpl("entity/add-contact") >> Snippet("panel", chooseContact) >> Hidden
 
     val confirmM = Menu.params[(User, Contact)](
@@ -169,6 +170,7 @@
       { p => List(p._1, p._2) map(_.id.toString) }) / prefix /
         * / "add-contact" / * >>
       Title(p => i18n("Add contact %s to %s", p._2.linkName, p._1.linkName)) >>
+      IfLoggedIn.testVal >>
       locTpl("entity/form") >> Snippet("form", addContact) >> Hidden
 
     val chooseM = choosePreM >> SecNav(viewPre).build
@@ -181,8 +183,9 @@
         }), Empty)
 
     def contacts: CssTr = "*" #> cur.map { u =>
-      FieldTable[Contact]({ c => ContactTable.fields(c).toSeq :+
-        RemoveContactLink(u, c) }, Contact)(UserContacts(u)) }
+      FieldTable[Contact]({ c => ContactTable.fields(c).toSeq ++
+        (User.get.map { _ => RemoveContactLink(u, c) }) }, Contact)(
+        UserContacts(u)) }
 
     private case class AddContactLink(u: User, c: Contact) extends
       EntityLink[Contact](c,
--- a/src/main/scala/fis/crm/ui/CompanySnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/crm/ui/CompanySnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,8 @@
  */
 package fis.crm.ui
 
+import fis.aaa.model.User
+import fis.aaa.ui.IfLoggedIn
 import fis.base.model._
 import fis.base.ui._
 import fis.crm.model._
@@ -40,7 +42,7 @@
     locTpl("entity/list") >> Snippet("list", list)
 
   private val createPre = Menu("company.create", l10n("Create")) / prefix / ADD >>
-    Title(_ => i18n("Create company")) >>
+    Title(_ => i18n("Create company")) >> IfLoggedIn.test >>
     locTpl("company/form") >> Snippet("form", form) >> Hidden
 
   private val viewPre = Menu.param[Company]("company.view", l10n("Company"), parse,
@@ -51,12 +53,12 @@
 
   private val editPre = Menu.param[Company]("company.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(c => i18n("Edit company %s", c.linkName)) >>
+    Title(c => i18n("Edit company %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("company/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[Company]("company.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(c => i18n("Delete company %s", c.linkName)) >>
+    Title(c => i18n("Delete company %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val listM = listPre >> SecNav(createPre).build
@@ -176,6 +178,7 @@
     private val choosePreM = Menu.param[Company]("company.addContact",
       l10n("Add contact"), parse, encode) / prefix / * / "add-contact" >>
       Title(c => i18n("Add contact to %s", c.linkName)) >>
+      IfLoggedIn.testVal >>
       locTpl("company/add-contact") >> Snippet("panel", chooseContact) >> Hidden
 
     val confirmM = Menu.params[(Company, Contact)](
@@ -189,6 +192,7 @@
       { p => List(p._1, p._2) map(_.id.toString) }) / prefix /
         * / "add-contact" / * >>
       Title(p => i18n("Add contact %s to %s", p._2.linkName, p._1.linkName)) >>
+      IfLoggedIn.testVal >>
       locTpl("entity/form") >> Snippet("form", addContact) >> Hidden
 
     val chooseM = choosePreM >> SecNav(viewPre).build
@@ -201,8 +205,9 @@
         }), Empty)
 
     def contacts: CssTr = "*" #> cur.map { c =>
-      FieldTable[Contact]({ cnt => ContactTable.fields(cnt).toSeq :+
-        RemoveContactLink(c, cnt) }, Contact)(CompanyContacts(c)) }
+      FieldTable[Contact]({ cnt => ContactTable.fields(cnt).toSeq ++
+        (User.get.map { _ => RemoveContactLink(c, cnt) }) }, Contact)(
+        CompanyContacts(c)) }
 
     private case class AddContactLink(comp: Company, cnt: Contact) extends
       EntityLink[Contact](cnt,
--- a/src/main/scala/fis/crm/ui/ContactSnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/crm/ui/ContactSnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,7 @@
  */
 package fis.crm.ui
 
+import fis.aaa.ui.IfLoggedIn
 import fis.base.model._
 import fis.base.ui._
 import fis.crm.model._
@@ -37,7 +38,7 @@
     locTpl("entity/list") >> Snippet("list", list)
 
   private val createPre = Menu("contact.create", l10n("Create")) / prefix / ADD >>
-    Title(_ => i18n("Create contact")) >>
+    Title(_ => i18n("Create contact")) >> IfLoggedIn.test >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val viewPre = Menu.param[Contact]("contact.view", l10n("Contact"), parse,
@@ -47,12 +48,12 @@
 
   private val editPre = Menu.param[Contact]("contact.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(c => i18n("Edit contact %s", c.linkName)) >>
+    Title(c => i18n("Edit contact %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[Contact]("contact.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(c => i18n("Delete contact %s", c.linkName)) >>
+    Title(c => i18n("Delete contact %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val listM = listPre >> SecNav(createPre).build
--- a/src/main/scala/fis/geo/ui/CitySnipppet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/geo/ui/CitySnipppet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,7 @@
  */
 package fis.geo.ui
 
+import fis.aaa.ui.IfLoggedIn
 import fis.base.ui._
 import fis.geo.model._
 import net.liftweb.common._
@@ -35,7 +36,7 @@
     locTpl("entity/list") >> Snippet("list", list)
 
   private val createPre = Menu("city.create", l10n("Create")) / prefix / ADD >>
-    Title(_ => i18n("Create city")) >>
+    Title(_ => i18n("Create city")) >> IfLoggedIn.test >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val viewPre = Menu.param[City]("city.view", l10n("City"), parse,
@@ -46,16 +47,17 @@
   private val createLocPre = Menu.param[City]("city.create-loc",
     l10n("Create location"), parse, encode) / prefix / * / "create-location" >>
     Title(c => i18n("Create location in city %s", c.linkName)) >>
+    IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", locationF) >> Hidden
 
   private val editPre = Menu.param[City]("city.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(c => i18n("Edit city %s", c.linkName)) >>
+    Title(c => i18n("Edit city %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[City]("city.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(c => i18n("Delete city %s", c.linkName)) >>
+    Title(c => i18n("Delete city %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val listM = listPre >> SecNav(createPre).build
--- a/src/main/scala/fis/geo/ui/CountrySnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/geo/ui/CountrySnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,7 @@
  */
 package fis.geo.ui
 
+import fis.aaa.ui.IfLoggedIn
 import fis.base.ui._
 import fis.geo.model._
 import net.liftweb.common._
@@ -35,7 +36,7 @@
     locTpl("entity/list") >> Snippet("list", list)
 
   private val createPre = Menu("country.create", l10n("Create")) / prefix / ADD >>
-    Title(_ => i18n("Create country")) >>
+    Title(_ => i18n("Create country")) >> IfLoggedIn.test >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val viewPre = Menu.param[Country]("country.view", l10n("Country"), parse,
@@ -44,12 +45,12 @@
 
   private val editPre = Menu.param[Country]("country.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(c => i18n("Edit country %s", c.linkName)) >>
+    Title(c => i18n("Edit country %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[Country]("country.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(c => i18n("Delete country %s", c.linkName)) >>
+    Title(c => i18n("Delete country %s", c.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val listM = listPre >> SecNav(createPre).build
--- a/src/main/scala/fis/geo/ui/LocationSnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/geo/ui/LocationSnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,7 @@
  */
 package fis.geo.ui
 
+import fis.aaa.ui.IfLoggedIn
 import fis.base.ui._
 import fis.geo.model._
 import net.liftweb.common._
@@ -40,12 +41,12 @@
 
   private val editPre = Menu.param[Location]("location.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(l => i18n("Edit location %s", l.linkName)) >>
+    Title(l => i18n("Edit location %s", l.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[Location]("location.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(l => i18n("Delete location %s", l.linkName)) >>
+    Title(l => i18n("Delete location %s", l.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val viewM = viewPre >> (SecNav(editPre) + deletePre).build
--- a/src/main/scala/fis/pm/ui/ProjectSnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/pm/ui/ProjectSnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,7 @@
  */
 package fis.pm.ui
 
+import fis.aaa.ui.IfLoggedIn
 import fis.base.ui._
 import fis.crm.model._
 import fis.pm.model._
@@ -37,7 +38,7 @@
     locTpl("entity/list") >> Snippet("list", list)
 
   private val createPre = Menu("project.create", l10n("Create")) / prefix / ADD >>
-    Title(_ => i18n("Create project")) >>
+    Title(_ => i18n("Create project")) >> IfLoggedIn.test >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val viewPre = Menu.param[Project]("project.view", l10n("Project"), parse,
@@ -47,17 +48,18 @@
 
   private val editPre = Menu.param[Project]("project.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(p => i18n("Edit project %s", p.linkName)) >>
+    Title(p => i18n("Edit project %s", p.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[Project]("project.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(p => i18n("Delete project %s", p.linkName)) >>
+    Title(p => i18n("Delete project %s", p.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val createTaskPre = Menu.param[Project]("project.create-task",
     l10n("Create task"), parse, encode) / prefix / * / "create-task" >>
     Title(p => i18n("Create task for project %s", p.linkName)) >>
+    IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", taskF) >> Hidden
 
   private val listM = listPre >> SecNav(createPre).build
--- a/src/main/scala/fis/pm/ui/TaskSnippet.scala	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/scala/fis/pm/ui/TaskSnippet.scala	Tue May 01 23:27:55 2012 +0200
@@ -15,6 +15,7 @@
  */
 package fis.pm.ui
 
+import fis.aaa.ui.IfLoggedIn
 import fis.base.ui._
 import fis.pm.model._
 import net.liftweb.common._
@@ -41,17 +42,18 @@
 
   private val editPre = Menu.param[Task]("task.edit", l10n("Edit"), parse,
     encode) / prefix / * / EDIT >>
-    Title(t => i18n("Edit task %s", t.linkName)) >>
+    Title(t => i18n("Edit task %s", t.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/form") >> Snippet("form", form) >> Hidden
 
   private val deletePre = Menu.param[Task]("task.delete", l10n("Delete"),
     parse, encode) / prefix / * / DELETE >>
-    Title(t => i18n("Delete task %s", t.linkName)) >>
+    Title(t => i18n("Delete task %s", t.linkName)) >> IfLoggedIn.testVal >>
     locTpl("entity/delete") >> Snippet("form", deleteF) >> Hidden
 
   private val postCommentPre = Menu.param[Task]("task.post-comment",
     l10n("Post comment"), parse, encode) / prefix / * / "post-comment" >>
     Title(t => i18n("Post comment for task %s", t.linkName)) >>
+    IfLoggedIn.testVal >>
     locTpl("task/view") >> Snippet("panel", postComment) >>
     Snippet("comments", comments) >> Hidden
 
--- a/src/main/webapp/templates-hidden/_resources.html	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/webapp/templates-hidden/_resources.html	Tue May 01 23:27:55 2012 +0200
@@ -22,6 +22,7 @@
   <res name="login.title" lang="en" default="true">Log In</res>
   <res name="logout.title" lang="en" default="true">Log Out</res>
   <res name="login.welcome" lang="en" default="true">Welcome!</res>
+  <res name="login.needed" lang="en" default="true">To proceed, you need to log in.</res>
   <res name="logout.success" lang="en" default="true">You were successfully logged out.</res>
   <res name="logged.as" lang="en" default="true">Logged as </res>
   <res name="btn.login" lang="en" default="true">Log In</res>
--- a/src/main/webapp/templates-hidden/_resources_cs.html	Tue May 01 22:33:38 2012 +0200
+++ b/src/main/webapp/templates-hidden/_resources_cs.html	Tue May 01 23:27:55 2012 +0200
@@ -21,6 +21,7 @@
   <res name="login.title" lang="cs">Log In</res>
   <res name="logout.title" lang="cs">Log Out</res>
   <res name="login.welcome" lang="cs">Vítejte!</res>
+  <res name="login.needed" lang="cs">Pro vykonání akce se musíte přihlásit.</res>
   <res name="logout.success" lang="cs">Byli jste úspěšně odhlášeni.</res>
   <res name="logged.as" lang="cs">Přihlášen jako </res>
   <res name="btn.login" lang="cs">Log In</res>