Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Profile #388

Merged
merged 27 commits into from
Oct 9, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
e7e53ca
start profile module
fatemeh-i Jul 24, 2023
a3323b5
try to manage permissions
fatemeh-i Jul 24, 2023
5c7e336
try to organize limitations
fatemeh-i Jul 25, 2023
efee99b
try to organize actions history
fatemeh-i Jul 26, 2023
8c2704e
start kyc module
fatemeh-i Jul 29, 2023
9b0952f
init kyc module
fatemeh-i Jul 29, 2023
b63441f
develope diffrent kyc level process
fatemeh-i Jul 30, 2023
2cc24f1
link profile manager to kyc manager
fatemeh-i Jul 31, 2023
d31328d
fix some bugs
fatemeh-i Aug 1, 2023
f3943ee
set storage proxy for kyc module
fatemeh-i Aug 2, 2023
05f3a0f
try to set pointcut for dao.save
fatemeh-i Aug 10, 2023
bd60004
sync kyc and profile module in kycLevelUpdated messages
fatemeh-i Aug 13, 2023
b4f0914
review and tes kyc services
fatemeh-i Aug 14, 2023
b38a8d9
review and test kyc services
fatemeh-i Aug 15, 2023
f0180d4
add related account services
fatemeh-i Aug 20, 2023
ac98a71
check securityContext
fatemeh-i Aug 21, 2023
658ee75
test services and fig some buges
fatemeh-i Aug 22, 2023
28d8038
check and test profile services
fatemeh-i Aug 23, 2023
c3c3696
review security layers
fatemeh-i Aug 26, 2023
1308276
mint kyc level in jwt token
fatemeh-i Sep 4, 2023
81aa7db
manage whitelist in user-management module
fatemeh-i Sep 5, 2023
3260df3
fix a typo
fatemeh-i Sep 10, 2023
490710a
Merge branch 'dev' into profile
Marchosiax Sep 12, 2023
ed2aa07
Fix maven version mismatch
Marchosiax Sep 12, 2023
9acf498
Fix build failure
Marchosiax Sep 12, 2023
e9bed27
rm excessive dependence
fatemeh-i Sep 13, 2023
95288c2
Merge branch 'dev' into profile
Marchosiax Oct 9, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions admin/admin-app/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,10 @@
<groupId>co.nilin.opex.admin</groupId>
<artifactId>admin-service-auth</artifactId>
</dependency>
<dependency>
<groupId>co.nilin.opex.admin</groupId>
<artifactId>admin-service-profile</artifactId>
</dependency>
<dependency>
<groupId>co.nilin.opex.admin</groupId>
<artifactId>admin-submitter-kafka</artifactId>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,5 @@ import org.springframework.context.annotation.ComponentScan
class AdminApplication

fun main(args: Array<String>) {
runApplication<AdminApplication>(*args)
runApplication<AdminApplication>(*args)
}
Original file line number Diff line number Diff line change
@@ -1,15 +1,19 @@
package co.nilin.opex.admin.app.config

import co.nilin.opex.admin.app.utils.hasRole
import org.springframework.beans.factory.InitializingBean
import org.springframework.beans.factory.annotation.Value
import org.springframework.context.annotation.Bean
import org.springframework.security.authentication.ReactiveAuthenticationManager
import org.springframework.security.config.annotation.web.reactive.EnableWebFluxSecurity
import org.springframework.security.config.web.server.ServerHttpSecurity
import org.springframework.security.core.context.SecurityContextHolder
import org.springframework.security.oauth2.jwt.NimbusReactiveJwtDecoder
import org.springframework.security.oauth2.jwt.ReactiveJwtDecoder
import org.springframework.security.web.server.SecurityWebFilterChain
import org.springframework.web.reactive.function.client.WebClient


@EnableWebFluxSecurity
class SecurityConfig(private val webClient: WebClient) {

Expand All @@ -22,6 +26,7 @@ class SecurityConfig(private val webClient: WebClient) {
.authorizeExchange()
.pathMatchers("/auth/**").hasRole("SCOPE_trust", "admin_finance")
.pathMatchers("/system/**").hasRole("SCOPE_trust", "admin_system")
.pathMatchers("/admin/**").hasRole("SCOPE_trust", "admin_system")
.pathMatchers("/blockchain/**").hasRole("SCOPE_trust", "admin_system")
.pathMatchers("/actuator/health").permitAll()
.anyExchange().authenticated()
Expand All @@ -35,7 +40,9 @@ class SecurityConfig(private val webClient: WebClient) {
@Throws(Exception::class)
fun reactiveJwtDecoder(): ReactiveJwtDecoder? {
return NimbusReactiveJwtDecoder.withJwkSetUri(jwkUrl)
.webClient(webClient)
.build()
.webClient(webClient)
.build()
}


}
Original file line number Diff line number Diff line change
@@ -1,26 +1,73 @@
package co.nilin.opex.admin.app.config

import co.nilin.opex.utility.log.CustomLogger
import org.slf4j.LoggerFactory
import org.springframework.beans.factory.InitializingBean
import org.springframework.beans.factory.annotation.Qualifier
import org.springframework.cloud.client.ServiceInstance
import org.springframework.cloud.client.loadbalancer.LoadBalancerProperties
import org.springframework.cloud.client.loadbalancer.reactive.ReactiveLoadBalancer
import org.springframework.cloud.client.loadbalancer.reactive.ReactorLoadBalancerExchangeFilterFunction
import org.springframework.context.annotation.Bean
import org.springframework.context.annotation.Configuration
import org.springframework.http.HttpHeaders
import org.springframework.http.client.reactive.ReactorClientHttpConnector
import org.springframework.security.core.annotation.CurrentSecurityContext
import org.springframework.security.core.context.ReactiveSecurityContextHolder
import org.springframework.security.core.context.SecurityContextHolder
import org.springframework.security.oauth2.server.resource.authentication.JwtAuthenticationToken
import org.springframework.web.reactive.function.client.ClientRequest
import org.springframework.web.reactive.function.client.ExchangeFilterFunction
import org.springframework.web.reactive.function.client.ExchangeFunction
import org.springframework.web.reactive.function.client.WebClient
import reactor.core.publisher.Mono
import reactor.netty.http.client.HttpClient
import java.util.function.Consumer


@Configuration
class WebClientConfig {
private val logger = LoggerFactory.getLogger(WebClientConfig::class.java)

@Bean
fun webClient(loadBalancerFactory: ReactiveLoadBalancer.Factory<ServiceInstance>): WebClient {
val logger = CustomLogger(HttpClient::class.java)
val connector = HttpClient.create().doOnRequest { _, con -> con.addHandlerFirst(logger) }
return WebClient.builder()
.clientConnector(ReactorClientHttpConnector(connector))
.filter(ReactorLoadBalancerExchangeFilterFunction(loadBalancerFactory, emptyList()))
.build()
.clientConnector(ReactorClientHttpConnector(connector))
.filter(ReactorLoadBalancerExchangeFilterFunction(loadBalancerFactory, emptyList()))
.build()
}


@Bean
@Qualifier("logRequest")
fun backgroundSecurityWebClient(loadBalancerFactory: ReactiveLoadBalancer.Factory<ServiceInstance>): WebClient {
return WebClient.builder()
.filter(
ReactorLoadBalancerExchangeFilterFunction(
loadBalancerFactory, LoadBalancerProperties(), emptyList()
)
)
.filter(logRequest())
.build()
}

private fun logRequest(): ExchangeFilterFunction {
return ExchangeFilterFunction.ofRequestProcessor { clientRequest: ClientRequest ->
logger.info("Request: {} {}", clientRequest.method(), clientRequest.url())
clientRequest.headers().forEach { name: String?, values: List<String?> -> values.forEach(Consumer<String?> { value: String? -> logger.info("{}={}", name, value) }) }
Mono.just<ClientRequest>(clientRequest)
}
}

@Bean
fun initializingBean(): InitializingBean? {
return InitializingBean {
SecurityContextHolder.setStrategyName(
SecurityContextHolder.MODE_INHERITABLETHREADLOCAL)
}
}


}
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,17 @@ package co.nilin.opex.admin.app.controller
import co.nilin.opex.admin.app.data.AddCurrencyRequest
import co.nilin.opex.admin.app.data.EditCurrencyRequest
import co.nilin.opex.admin.app.service.SystemConfigService
import co.nilin.opex.admin.app.service.WhiteListManagement
import co.nilin.opex.admin.core.data.WhitelistAdaptor
import co.nilin.opex.utility.error.data.OpexError
import co.nilin.opex.utility.error.data.OpexException
import org.springframework.web.bind.annotation.*
import javax.ws.rs.core.Response

@RestController
@RequestMapping("/system/v1")
class SystemConfigController(private val service: SystemConfigService) {
class SystemConfigController(private val service: SystemConfigService,
private val whiteListManagement: WhiteListManagement) {

@PostMapping("/currency")
suspend fun addCurrency(@RequestBody body: AddCurrencyRequest) {
Expand All @@ -30,4 +34,20 @@ class SystemConfigController(private val service: SystemConfigService) {
service.deleteCurrency(name)
}

@PostMapping("/whitelist")
suspend fun updateWhitelist(@RequestBody users: WhitelistAdaptor): WhitelistAdaptor? {
return whiteListManagement.addToWhiteList(users)

}

@GetMapping("/whitelist")
suspend fun getWhitelist(): WhitelistAdaptor? {
return whiteListManagement.getWhiteList()
}

@DeleteMapping("/whitelist")
suspend fun deleteWhitelist(@RequestBody users: WhitelistAdaptor): WhitelistAdaptor? {
return whiteListManagement.deleteFromWhiteList(users)

}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@ package co.nilin.opex.admin.app.data
import java.math.BigDecimal

data class AddCurrencyRequest(
val name: String?,
val symbol: String?,
val precision: BigDecimal
val name: String?,
val symbol: String?,
val precision: BigDecimal
) {

fun isValid(): Boolean {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,8 @@ package co.nilin.opex.admin.app.data
import java.math.BigDecimal

data class EditCurrencyRequest(
val symbol: String?,
val precision: BigDecimal
val symbol: String?,
val precision: BigDecimal
) {
fun isValid(): Boolean {
return !symbol.isNullOrEmpty() && precision > BigDecimal.ZERO
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package co.nilin.opex.admin.app.service

import co.nilin.opex.admin.core.data.WhitelistAdaptor
import co.nilin.opex.admin.core.spi.WhiteListPersister
import org.springframework.stereotype.Component

@Component
class WhiteListManagement(private val whiteListPersister: WhiteListPersister) {
suspend fun addToWhiteList(users: WhitelistAdaptor): WhitelistAdaptor? {
return whiteListPersister.addToWhiteList(users)
}

suspend fun deleteFromWhiteList(users: WhitelistAdaptor): WhitelistAdaptor? {
return whiteListPersister.deleteFromWhiteList(users)
}

suspend fun getWhiteList(): WhitelistAdaptor? {
return whiteListPersister.getWhiteList()
}
}
Original file line number Diff line number Diff line change
@@ -1,17 +1,35 @@
package co.nilin.opex.admin.app.utils

import co.nilin.opex.admin.app.config.WebClientConfig
import com.nimbusds.jose.proc.SecurityContext
import com.nimbusds.jose.shaded.json.JSONArray
import kotlinx.coroutines.reactive.awaitFirstOrNull
import org.slf4j.LoggerFactory
import org.springframework.security.authorization.AuthorizationDecision
import org.springframework.security.config.web.server.ServerHttpSecurity
import org.springframework.security.core.Authentication
import org.springframework.security.core.annotation.CurrentSecurityContext
import org.springframework.security.core.context.ReactiveSecurityContextHolder
import org.springframework.security.core.context.SecurityContextHolder
import org.springframework.security.core.context.SecurityContextHolder.MODE_INHERITABLETHREADLOCAL
import org.springframework.security.core.context.SecurityContextHolderStrategy
import org.springframework.security.core.context.SecurityContextImpl
import org.springframework.security.oauth2.jwt.Jwt

fun ServerHttpSecurity.AuthorizeExchangeSpec.Access.hasRole(
authority: String,
role: String
authority: String,
role: String
): ServerHttpSecurity.AuthorizeExchangeSpec = access { mono, _ ->
mono.map { auth ->
val hasAuthority = auth.authorities.any { it.authority == authority }
val hasRole = ((auth.principal as Jwt).claims["roles"] as JSONArray?)?.contains(role) == true
ReactiveSecurityContextHolder.getContext().map { s -> s.authentication = auth }
SecurityContextHolder.getContext().authentication = auth
val logger = LoggerFactory.getLogger(WebClientConfig::class.java)
AuthorizationDecision(hasAuthority && hasRole)
}
}

}



3 changes: 3 additions & 0 deletions admin/admin-app/src/main/resources/application.yml
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,13 @@ app:
auth:
cert-url: lb://opex-auth/auth/realms/opex/protocol/openid-connect/certs
token-url: lb://opex-auth/auth/realms/opex/protocol/openid-connect/token
admin-url: lb://opex-auth/auth/realms/opex/user-management/admin
keycloak:
url: http://auth:8080/auth
realm: opex
client-id: opex-admin
client-secret: ${keycloak_client_secret:secret}
profile:
url: lb://opex-profile/v2/admin/profile
scheduler:
url: http://scanner-scheduler:8080
5 changes: 5 additions & 0 deletions admin/admin-core/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -34,5 +34,10 @@
<groupId>org.jetbrains.kotlinx</groupId>
<artifactId>kotlinx-coroutines-core</artifactId>
</dependency>

<dependency>
<groupId>co.nilin.opex.profile</groupId>
<artifactId>profile-core</artifactId>
</dependency>
</dependencies>
</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package co.nilin.opex.admin.core.data

import java.time.LocalDateTime

data class ProfileRequest(
var userId:String?,
var mobile:String?,
var email:String?,
var nationalCode:String?,
var firstName:String?,
var lastName:String?,
var createDateFrom:LocalDateTime?,
var createDateTo:LocalDateTime?,
var includeKyc:Boolean?,
var includeLimitation:Boolean?,
var includeLinkedAccount:Boolean?,
var accountNumber:String?,
var partialSearch:Boolean?
)
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
package co.nilin.opex.admin.core.data

import co.nilin.opex.kyc.core.data.KycProcess
import co.nilin.opex.kyc.core.data.KycResponse
import co.nilin.opex.kyc.core.data.KycStep
import co.nilin.opex.profile.core.data.limitation.Limitation
import co.nilin.opex.profile.core.data.linkedbankAccount.LinkedAccountResponse
import co.nilin.opex.profile.core.data.profile.Gender
import co.nilin.opex.profile.core.data.profile.KycLevel
import co.nilin.opex.profile.core.data.profile.UserStatus
import java.time.LocalDateTime

data class ProfileResponse(var email:String?,
var userId:String?,
var firstName: String?=null,
var lastName: String?=null,
var address:String?=null,
var mobile:String?=null,
var telephone:String?=null,
var postalCode:String?=null,
var nationality:String?=null,
var identifier:String?=null,
var gender: Gender?=null,
var birthDate: LocalDateTime?=null,
var status: UserStatus?=null,
var createDate: LocalDateTime?=null,
var lastUpdateDate: LocalDateTime?=null,
var creator:String?=null,
var kycLevel: KycLevel?=null,
var linkedAccounts:List<LinkedAccountResponse>?=null,
var limitations:List<Limitation>?=null)
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package co.nilin.opex.admin.core.data

import co.nilin.opex.profile.core.data.limitation.UpdateLimitationRequest
import co.nilin.opex.profile.core.data.profile.Profile
import co.nilin.opex.profile.core.data.profile.UpdateProfileRequest

Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
package co.nilin.opex.admin.core.data

data class WhitelistAdaptor(var data: MutableList<String?>)
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
package co.nilin.opex.admin.core.spi

interface KycProxy {
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package co.nilin.opex.admin.core.spi

import co.nilin.opex.admin.core.data.ProfileRequest
import co.nilin.opex.admin.core.data.ProfileResponse
import co.nilin.opex.profile.core.data.profile.Profile
import kotlinx.coroutines.flow.Flow
import reactor.core.publisher.Mono

interface ProfileProxy {
suspend fun getProfile(profileRequest: ProfileRequest): Flow<ProfileResponse>?


}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package co.nilin.opex.admin.core.spi

import co.nilin.opex.admin.core.data.WhitelistAdaptor

interface WhiteListPersister {

suspend fun addToWhiteList(users: WhitelistAdaptor):WhitelistAdaptor?

suspend fun deleteFromWhiteList(users: WhitelistAdaptor):WhitelistAdaptor?


suspend fun getWhiteList(): WhitelistAdaptor?
}
Loading