From 3fea748c4ecea30e42712f3e59c26377ea5bfa25 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marko=20Mili=C4=87?= Date: Thu, 20 Jan 2022 15:13:42 +0100 Subject: [PATCH] feature/User Attributes; Add mapper model --- .../main/scala/bootstrap/liftweb/Boot.scala | 4 +- .../code/remotedata/RemotedataActors.scala | 3 +- .../remotedata/RemotedataUserAttribute.scala | 29 ++++++++++ .../RemotedataUserAttributeActor.scala | 31 ++++++++++ .../code/users/MappedUserAttribute.scala | 40 +++++++++++++ .../code/users/UserAttributeProvider.scala | 58 +++++++++++++++++++ .../commons/model/CommonModelTrait.scala | 7 +++ .../commons/model/enums/Enumerations.scala | 9 +++ 8 files changed, 179 insertions(+), 2 deletions(-) create mode 100644 obp-api/src/main/scala/code/remotedata/RemotedataUserAttribute.scala create mode 100644 obp-api/src/main/scala/code/remotedata/RemotedataUserAttributeActor.scala create mode 100644 obp-api/src/main/scala/code/users/MappedUserAttribute.scala create mode 100644 obp-api/src/main/scala/code/users/UserAttributeProvider.scala diff --git a/obp-api/src/main/scala/bootstrap/liftweb/Boot.scala b/obp-api/src/main/scala/bootstrap/liftweb/Boot.scala index 59f4292ec..764450abc 100644 --- a/obp-api/src/main/scala/bootstrap/liftweb/Boot.scala +++ b/obp-api/src/main/scala/bootstrap/liftweb/Boot.scala @@ -29,6 +29,7 @@ package bootstrap.liftweb import java.io.{File, FileInputStream} import java.util.stream.Collectors import java.util.{Locale, TimeZone} + import code.CustomerDependants.MappedCustomerDependant import code.DynamicData.DynamicData import code.DynamicEndpoint.DynamicEndpoint @@ -120,7 +121,7 @@ import code.transactionattribute.MappedTransactionAttribute import code.transactionrequests.{MappedTransactionRequest, MappedTransactionRequestTypeCharge, TransactionRequestReasons} import code.usercustomerlinks.MappedUserCustomerLink import code.userlocks.UserLocks -import code.users.{UserAgreement, UserInitAction, UserInvitation} +import code.users.{UserAgreement, UserAttribute, UserInitAction, UserInvitation} import code.util.Helper.MdcLoggable import code.util.{Helper, HydraUtil} import code.validation.JsonSchemaValidation @@ -865,6 +866,7 @@ object ToSchemify { ResourceUser, UserInvitation, UserAgreement, + UserAttribute, MappedComment, MappedTag, MappedWhereTag, diff --git a/obp-api/src/main/scala/code/remotedata/RemotedataActors.scala b/obp-api/src/main/scala/code/remotedata/RemotedataActors.scala index f56583e8a..c7b701211 100644 --- a/obp-api/src/main/scala/code/remotedata/RemotedataActors.scala +++ b/obp-api/src/main/scala/code/remotedata/RemotedataActors.scala @@ -67,7 +67,8 @@ object RemotedataActors extends MdcLoggable { ActorProps[RemotedataConsentAuthContextActor] -> RemotedataConsentAuthContext.actorName, ActorProps[RemotedataTransactionRequestAttributeActor] -> RemotedataTransactionRequestAttribute.actorName, ActorProps[RemotedataUserAgreementActor] -> RemotedataUserAgreement.actorName, - ActorProps[RemotedataBankAttributeActor] -> RemotedataBankAttribute.actorName + ActorProps[RemotedataBankAttributeActor] -> RemotedataBankAttribute.actorName, + ActorProps[RemotedataUserAttributeActor] -> RemotedataUserAttribute.actorName ) actorsRemotedata.foreach { a => logger.info(actorSystem.actorOf(a._1, name = a._2)) } diff --git a/obp-api/src/main/scala/code/remotedata/RemotedataUserAttribute.scala b/obp-api/src/main/scala/code/remotedata/RemotedataUserAttribute.scala new file mode 100644 index 000000000..02eefe4c8 --- /dev/null +++ b/obp-api/src/main/scala/code/remotedata/RemotedataUserAttribute.scala @@ -0,0 +1,29 @@ +package code.remotedata + +import akka.pattern.ask +import code.accountattribute.{AccountAttributeProvider, RemotedataAccountAttributeCaseClasses} +import code.actorsystem.ObpActorInit +import code.users.{RemotedataUserAttributeCaseClasses, UserAttribute, UserAttributeProvider} +import com.openbankproject.commons.model._ +import com.openbankproject.commons.model.enums.{AccountAttributeType, UserAttributeType} +import net.liftweb.common.Box + +import scala.collection.immutable.List +import scala.concurrent.Future + + +object RemotedataUserAttribute extends ObpActorInit with UserAttributeProvider { + + val cc = RemotedataUserAttributeCaseClasses + + override def getAccountAttributesByUser(userId: String): Future[Box[List[UserAttribute]]] = + (actor ? cc.getAccountAttributesByUser(userId)).mapTo[Box[List[UserAttribute]]] + + override def createOrUpdateUserAttribute(userId: String, + userAttributeId: Option[String], + name: String, + attributeType: UserAttributeType.Value, + value: String): Future[Box[UserAttribute]] = + (actor ? cc.createOrUpdateUserAttribute(userId, userAttributeId, name, attributeType, value )).mapTo[Box[UserAttribute]] + +} diff --git a/obp-api/src/main/scala/code/remotedata/RemotedataUserAttributeActor.scala b/obp-api/src/main/scala/code/remotedata/RemotedataUserAttributeActor.scala new file mode 100644 index 000000000..84b0e3670 --- /dev/null +++ b/obp-api/src/main/scala/code/remotedata/RemotedataUserAttributeActor.scala @@ -0,0 +1,31 @@ +package code.remotedata + +import akka.actor.Actor +import akka.pattern.pipe +import code.actorsystem.ObpActorHelper +import code.users.{MappedUserAttributeProvider, RemotedataUserAttributeCaseClasses} +import code.util.Helper.MdcLoggable +import com.openbankproject.commons.ExecutionContext.Implicits.global +import com.openbankproject.commons.model.enums.UserAttributeType + +class RemotedataUserAttributeActor extends Actor with ObpActorHelper with MdcLoggable { + + val mapper = MappedUserAttributeProvider + val cc = RemotedataUserAttributeCaseClasses + + def receive: PartialFunction[Any, Unit] = { + + case cc.getAccountAttributesByUser(userId: String) => + logger.debug(s"getAccountAttributesByUser(${userId})") + mapper.getAccountAttributesByUser(userId) pipeTo sender + + case cc.createOrUpdateUserAttribute(userId: String, userAttributeId: Option[String], name: String, attributeType: UserAttributeType.Value, value: String) => + logger.debug(s"createOrUpdateUserAttribute(${userId}, ${userAttributeId}, ${name}, ${attributeType}, ${value})") + mapper.createOrUpdateUserAttribute(userId, userAttributeId, name, attributeType, value) pipeTo sender + + case message => logger.warn("[AKKA ACTOR ERROR - REQUEST NOT RECOGNIZED] " + message) + } + +} + + diff --git a/obp-api/src/main/scala/code/users/MappedUserAttribute.scala b/obp-api/src/main/scala/code/users/MappedUserAttribute.scala new file mode 100644 index 000000000..ceb067148 --- /dev/null +++ b/obp-api/src/main/scala/code/users/MappedUserAttribute.scala @@ -0,0 +1,40 @@ +package code.users + +import code.util.MappedUUID +import com.openbankproject.commons.model.enums.{AccountAttributeType, UserAttributeType} +import com.openbankproject.commons.model.{AccountAttribute, UserAttributeTrait} +import net.liftweb.common.Box +import net.liftweb.mapper._ + +import scala.collection.immutable.List +import scala.concurrent.Future + + +object MappedUserAttributeProvider extends UserAttributeProvider { + override def getAccountAttributesByUser(userId: String): Future[Box[List[UserAttribute]]] = ??? + + override def createOrUpdateUserAttribute(userId: String, + userAttributeId: Option[String], + name: String, + attributeType: UserAttributeType.Value, + value: String): Future[Box[UserAttribute]] = ??? +} + +class UserAttribute extends UserAttributeTrait with LongKeyedMapper[UserAttribute] with IdPK { + + override def getSingleton = UserAttribute + object UserAttributeId extends MappedUUID(this) + object Name extends MappedString(this, 50) + object Type extends MappedString(this, 50) + object Value extends MappedString(this, 255) + + override def userAttributeId: String = UserAttributeId.get + override def name: String = Name.get + override def attributeType: UserAttributeType.Value = UserAttributeType.withName(Type.get) + override def value: String = Value.get +} + +object UserAttribute extends UserAttribute with LongKeyedMetaMapper[UserAttribute] { + override def dbIndexes: List[BaseIndex[UserAttribute]] = Index(UserAttributeId) :: super.dbIndexes +} + diff --git a/obp-api/src/main/scala/code/users/UserAttributeProvider.scala b/obp-api/src/main/scala/code/users/UserAttributeProvider.scala new file mode 100644 index 000000000..e58087815 --- /dev/null +++ b/obp-api/src/main/scala/code/users/UserAttributeProvider.scala @@ -0,0 +1,58 @@ +package code.users + + +import code.api.util.APIUtil +import code.remotedata.RemotedataUserAttribute +import com.openbankproject.commons.model.AccountAttribute +import com.openbankproject.commons.model.enums.{AccountAttributeType, UserAttributeType} +import net.liftweb.common.{Box, Logger} +import net.liftweb.util.SimpleInjector + +import scala.collection.immutable.List +import scala.concurrent.Future + +object UserAttributeProvider extends SimpleInjector { + + val userAttributeProvider = new Inject(buildOne _) {} + + def buildOne: UserAttributeProvider = + APIUtil.getPropsAsBoolValue("use_akka", false) match { + case false => MappedUserAttributeProvider + case true => RemotedataUserAttribute // We will use Akka as a middleware + } + + // Helper to get the count out of an option + def countOfUserAttribute(listOpt: Option[List[UserAttribute]]): Int = { + val count = listOpt match { + case Some(list) => list.size + case None => 0 + } + count + } + + +} + +trait UserAttributeProvider { + + private val logger = Logger(classOf[UserAttributeProvider]) + + def getAccountAttributesByUser(userId: String): Future[Box[List[UserAttribute]]] + def createOrUpdateUserAttribute(userId: String, + userAttributeId: Option[String], + name: String, + attributeType: UserAttributeType.Value, + value: String): Future[Box[UserAttribute]] + // End of Trait +} + +class RemotedataUserAttributeCaseClasses { + case class getAccountAttributesByUser(userId: String) + case class createOrUpdateUserAttribute(userId: String, + userAttributeId: Option[String], + name: String, + attributeType: UserAttributeType.Value, + value: String) +} + +object RemotedataUserAttributeCaseClasses extends RemotedataUserAttributeCaseClasses diff --git a/obp-commons/src/main/scala/com/openbankproject/commons/model/CommonModelTrait.scala b/obp-commons/src/main/scala/com/openbankproject/commons/model/CommonModelTrait.scala index 38d81929d..80bd1f5ef 100644 --- a/obp-commons/src/main/scala/com/openbankproject/commons/model/CommonModelTrait.scala +++ b/obp-commons/src/main/scala/com/openbankproject/commons/model/CommonModelTrait.scala @@ -95,6 +95,13 @@ trait AccountApplication { def status: String } +trait UserAttributeTrait { + def userAttributeId: String + def name: String + def attributeType: UserAttributeType.Value + def value: String +} + trait AccountAttribute { def bankId: BankId def accountId: AccountId diff --git a/obp-commons/src/main/scala/com/openbankproject/commons/model/enums/Enumerations.scala b/obp-commons/src/main/scala/com/openbankproject/commons/model/enums/Enumerations.scala index 860587c48..6846d014d 100644 --- a/obp-commons/src/main/scala/com/openbankproject/commons/model/enums/Enumerations.scala +++ b/obp-commons/src/main/scala/com/openbankproject/commons/model/enums/Enumerations.scala @@ -7,6 +7,15 @@ import net.liftweb.common.Box import net.liftweb.json.JsonAST.{JNothing, JString} import net.liftweb.json.{Formats, JBool, JDouble, JInt, JValue} + +sealed trait UserAttributeType extends EnumValue +object UserAttributeType extends OBPEnumeration[UserAttributeType]{ + object STRING extends Value + object INTEGER extends Value + object DOUBLE extends Value + object DATE_WITH_DAY extends Value +} + sealed trait BankAttributeType extends EnumValue object BankAttributeType extends OBPEnumeration[BankAttributeType]{ object STRING extends Value