Skip to content

Commit 5c6d698

Browse files
Merge pull request #225 from walt-id/tdiesler-ghi213
Tdiesler ghi213
2 parents df3c5f2 + 69d4020 commit 5c6d698

File tree

2 files changed

+197
-146
lines changed

2 files changed

+197
-146
lines changed
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,11 @@
11
package id.walt.auditor
22

33
import com.beust.klaxon.JsonObject
4-
import com.beust.klaxon.Klaxon
54
import com.beust.klaxon.KlaxonException
65
import id.walt.auditor.dynamic.DynamicPolicy
76
import id.walt.auditor.dynamic.DynamicPolicyArg
87
import id.walt.common.deepMerge
9-
import id.walt.common.resolveContent
10-
import id.walt.model.dif.PresentationDefinition
11-
import id.walt.services.context.ContextManager
12-
import id.walt.services.hkvstore.HKVKey
138
import mu.KotlinLogging
14-
import java.io.StringReader
159
import java.lang.reflect.InvocationTargetException
1610
import kotlin.reflect.KClass
1711
import kotlin.reflect.full.createInstance
@@ -77,155 +71,37 @@ class DynamicPolicyFactory(
7771
}
7872

7973
object PolicyRegistry {
80-
const val SAVED_POLICY_ROOT_KEY = "policies"
81-
private var _policies: LinkedHashMap<String, PolicyFactory<*, *>>? = null
82-
private val policies: LinkedHashMap<String, PolicyFactory<*, *>>
83-
get() {
84-
if (_policies == null) {
85-
initPolicies()
86-
}
87-
return _policies!!
88-
}
89-
val defaultPolicyId: String = SignaturePolicy::class.simpleName!!
9074

91-
fun <P : ParameterizedVerificationPolicy<A>, A : Any> register(
92-
policy: KClass<P>,
93-
argType: KClass<A>,
94-
description: String? = null,
95-
optionalArgument: Boolean = false
96-
) = policies.put(policy.simpleName!!, PolicyFactory(policy, argType, policy.simpleName!!, description, optionalArgument))
75+
private val delegate = PolicyRegistryService.getService()
9776

98-
fun <P : SimpleVerificationPolicy> register(policy: KClass<P>, description: String? = null) =
99-
policies.put(policy.simpleName!!, PolicyFactory<P, Unit>(policy, null, policy.simpleName!!, description))
100-
101-
fun registerSavedPolicy(name: String, dynamicPolicyArg: DynamicPolicyArg, immutable: Boolean = false) = policies.put(
102-
name,
103-
DynamicPolicyFactory(dynamicPolicyArg, immutable, name = name, description = dynamicPolicyArg.description)
104-
)
105-
106-
fun <A : Any> getPolicy(id: String, argument: A? = null) = policies[id]!!.create(argument)
107-
fun getPolicy(id: String) = getPolicy(id, null)
108-
fun contains(id: String) = policies.containsKey(id)
109-
fun listPolicies() = policies.keys
110-
fun listPolicyInfo() = policies.values.map { p ->
111-
VerificationPolicyMetadata(
112-
p.name,
113-
p.description,
114-
p.requiredArgumentType,
115-
isMutable(p.name)
116-
)
117-
}
77+
val defaultPolicyId: String = delegate.defaultPolicyId
11878

119-
fun getPolicyWithJsonArg(id: String, argumentJson: JsonObject?): VerificationPolicy {
120-
val policyFactory = policies[id] ?: throw IllegalArgumentException("No policy exists with id: $id")
121-
val argument =
122-
policyFactory.argType?.let {
123-
argumentJson?.let {
124-
if (policyFactory.argType == JsonObject::class) {
125-
argumentJson
126-
} else {
127-
Klaxon().fromJsonObject(
128-
argumentJson,
129-
policyFactory.argType.java,
130-
policyFactory.argType
131-
)
132-
}
133-
}
134-
}
79+
fun <P : ParameterizedVerificationPolicy<A>, A : Any> register(policy: KClass<P>, argType: KClass<A>, description: String? = null, optionalArgument: Boolean = false) =
80+
delegate.register(policy, argType, description, optionalArgument)
13581

136-
return policyFactory.create(argument)
137-
}
82+
fun <P : SimpleVerificationPolicy> register(policy: KClass<P>, description: String? = null) =
83+
delegate.register(policy, description)
13884

139-
fun getPolicyWithJsonArg(id: String, argumentJson: String?): VerificationPolicy {
140-
return getPolicyWithJsonArg(id, argumentJson?.let { Klaxon().parseJsonObject(StringReader(it)) })
141-
}
85+
fun <A : Any> getPolicy(id: String, argument: A? = null) =
86+
delegate.getPolicy(id, argument)
14287

143-
fun isMutable(name: String): Boolean {
144-
val polF = policies[name] ?: return false
145-
return polF is DynamicPolicyFactory && !polF.immutable
146-
}
88+
fun getPolicy(id: String) = delegate.getPolicy(id)
89+
fun contains(id: String) = delegate.contains(id)
90+
fun listPolicies() = delegate.listPolicies()
91+
fun listPolicyInfo() = delegate.listPolicyInfo()
14792

148-
fun createSavedPolicy(name: String, dynPolArg: DynamicPolicyArg, override: Boolean, download: Boolean): Boolean {
149-
if (!contains(name) || (isMutable(name) && override)) {
150-
val policyContent = when (download) {
151-
true -> resolveContent(dynPolArg.policy)
152-
false -> dynPolArg.policy
153-
}
154-
val dynPolArgMod = DynamicPolicyArg(
155-
name,
156-
dynPolArg.description,
157-
dynPolArg.input,
158-
policyContent,
159-
dynPolArg.dataPath,
160-
dynPolArg.policyQuery,
161-
dynPolArg.policyEngine,
162-
dynPolArg.applyToVC,
163-
dynPolArg.applyToVP
164-
)
165-
ContextManager.hkvStore.put(HKVKey(SAVED_POLICY_ROOT_KEY, name), Klaxon().toJsonString(dynPolArgMod))
166-
registerSavedPolicy(name, dynPolArgMod)
167-
return true
168-
}
169-
return false
170-
}
93+
fun getPolicyWithJsonArg(id: String, argumentJson: JsonObject?): VerificationPolicy =
94+
delegate.getPolicyWithJsonArg(id, argumentJson)
17195

172-
fun deleteSavedPolicy(name: String): Boolean {
173-
if (isMutable(name)) {
174-
ContextManager.hkvStore.delete(HKVKey(SAVED_POLICY_ROOT_KEY, name))
175-
policies.remove(name)
176-
return true
177-
}
178-
return false
179-
}
96+
fun getPolicyWithJsonArg(id: String, argumentJson: String?): VerificationPolicy =
97+
delegate.getPolicyWithJsonArg(id, argumentJson)
18098

181-
private fun initSavedPolicies() {
182-
ContextManager.hkvStore.listChildKeys(HKVKey(SAVED_POLICY_ROOT_KEY)).forEach {
183-
registerSavedPolicy(it.name, Klaxon().parse(ContextManager.hkvStore.getAsString(it)!!)!!)
184-
}
185-
}
99+
fun isMutable(name: String): Boolean =
100+
delegate.isMutable(name)
186101

187-
private fun initPolicies() {
188-
_policies = linkedMapOf()
189-
register(SignaturePolicy::class, "Verify by signature")
190-
//register(JsonSchemaPolicy::class, "Verify by JSON schema")
191-
register(TrustedSchemaRegistryPolicy::class, "Verify by EBSI Trusted Schema Registry")
192-
register(TrustedIssuerDidPolicy::class, "Verify by trusted issuer did")
193-
register(
194-
TrustedIssuerRegistryPolicy::class,
195-
TrustedIssuerRegistryPolicyArg::class,
196-
"Verify by an EBSI Trusted Issuers Registry compliant api.",
197-
true
198-
)
199-
register(TrustedSubjectDidPolicy::class, "Verify by trusted subject did")
200-
register(IssuedDateBeforePolicy::class, "Verify by issuance date")
201-
register(ValidFromBeforePolicy::class, "Verify by valid from")
202-
register(ExpirationDateAfterPolicy::class, "Verify by expiration date")
203-
//register(GaiaxTrustedPolicy::class, "Verify Gaiax trusted fields")
204-
register(GaiaxSDPolicy::class, "Verify Gaiax SD fields")
205-
register(ChallengePolicy::class, ChallengePolicyArg::class, "Verify challenge")
206-
register(
207-
PresentationDefinitionPolicy::class,
208-
PresentationDefinition::class,
209-
"Verify that verifiable presentation complies with presentation definition"
210-
)
211-
register(CredentialStatusPolicy::class, "Verify by credential status")
212-
register(DynamicPolicy::class, DynamicPolicyArg::class, "Verify credential by rego policy")
213-
214-
// predefined, hardcoded rego policy specializations
215-
// VerifiableMandate policy as specialized rego policy
216-
registerSavedPolicy(
217-
"VerifiableMandatePolicy", DynamicPolicyArg(
218-
"VerifiableMandatePolicy", "Predefined policy for verifiable mandates",
219-
JsonObject(), "$.credentialSubject.policySchemaURI",
220-
"$.credentialSubject.holder", "data.system.main"
221-
),
222-
immutable = true
223-
)
224-
225-
// other saved (Rego) policies
226-
initSavedPolicies()
227-
228-
//RegoPolicy(RegoPolicyArg(mapOf(), "")).argument.input
229-
}
102+
fun createSavedPolicy(name: String, dynPolArg: DynamicPolicyArg, override: Boolean, download: Boolean): Boolean =
103+
delegate.createSavedPolicy(name, dynPolArg, override, download)
230104

105+
fun deleteSavedPolicy(name: String): Boolean =
106+
delegate.deleteSavedPolicy(name)
231107
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,175 @@
1+
package id.walt.auditor
2+
3+
import com.beust.klaxon.JsonObject
4+
import com.beust.klaxon.Klaxon
5+
import id.walt.auditor.dynamic.DynamicPolicy
6+
import id.walt.auditor.dynamic.DynamicPolicyArg
7+
import id.walt.common.resolveContent
8+
import id.walt.model.dif.PresentationDefinition
9+
import id.walt.servicematrix.ServiceProvider
10+
import id.walt.servicematrix.ServiceRegistry
11+
import id.walt.services.WaltIdService
12+
import id.walt.services.context.ContextManager
13+
import id.walt.services.hkvstore.HKVKey
14+
import java.io.StringReader
15+
import java.util.concurrent.atomic.*
16+
import kotlin.reflect.KClass
17+
18+
open class PolicyRegistryService: WaltIdService() {
19+
override val implementation: PolicyRegistryService get() = serviceImplementation()
20+
21+
companion object: ServiceProvider {
22+
const val SAVED_POLICY_ROOT_KEY = "policies"
23+
override fun getService() = ServiceRegistry.getService(PolicyRegistryService::class)
24+
override fun defaultImplementation() = PolicyRegistryService()
25+
}
26+
27+
private val initialized = AtomicBoolean()
28+
private val _policies: MutableMap<String, PolicyFactory<*, *>> = mutableMapOf()
29+
private val policies get() = run {
30+
if (initialized.compareAndSet(false, true)) {
31+
initPolicies()
32+
}
33+
_policies
34+
}
35+
36+
val defaultPolicyId: String = SignaturePolicy::class.simpleName!!
37+
38+
fun <P : ParameterizedVerificationPolicy<A>, A : Any> register(
39+
policy: KClass<P>,
40+
argType: KClass<A>,
41+
description: String? = null,
42+
optionalArgument: Boolean = false
43+
) = policies.put(policy.simpleName!!, PolicyFactory(policy, argType, policy.simpleName!!, description, optionalArgument))
44+
45+
fun <P : SimpleVerificationPolicy> register(policy: KClass<P>, description: String? = null) =
46+
policies.put(policy.simpleName!!, PolicyFactory<P, Unit>(policy, null, policy.simpleName!!, description))
47+
48+
private fun registerSavedPolicy(name: String, dynamicPolicyArg: DynamicPolicyArg, immutable: Boolean = false) =
49+
policies.put(name, DynamicPolicyFactory(dynamicPolicyArg, immutable, name = name, description = dynamicPolicyArg.description)
50+
)
51+
52+
fun <A : Any> getPolicy(id: String, argument: A? = null) = policies[id]!!.create(argument)
53+
fun getPolicy(id: String) = getPolicy(id, null)
54+
fun contains(id: String) = policies.containsKey(id)
55+
fun listPolicies() = policies.keys
56+
fun listPolicyInfo() = policies.values.map { p ->
57+
VerificationPolicyMetadata(
58+
p.name,
59+
p.description,
60+
p.requiredArgumentType,
61+
isMutable(p.name)
62+
)
63+
}
64+
65+
fun getPolicyWithJsonArg(id: String, argumentJson: JsonObject?): VerificationPolicy {
66+
val policyFactory = policies[id] ?: throw IllegalArgumentException("No policy exists with id: $id")
67+
val argument =
68+
policyFactory.argType?.let {
69+
argumentJson?.let {
70+
if (policyFactory.argType == JsonObject::class) {
71+
argumentJson
72+
} else {
73+
Klaxon().fromJsonObject(
74+
argumentJson,
75+
policyFactory.argType.java,
76+
policyFactory.argType
77+
)
78+
}
79+
}
80+
}
81+
82+
return policyFactory.create(argument)
83+
}
84+
85+
fun getPolicyWithJsonArg(id: String, argumentJson: String?): VerificationPolicy {
86+
return getPolicyWithJsonArg(id, argumentJson?.let { Klaxon().parseJsonObject(StringReader(it)) })
87+
}
88+
89+
fun isMutable(name: String): Boolean {
90+
val polF = policies[name] ?: return false
91+
return polF is DynamicPolicyFactory && !polF.immutable
92+
}
93+
94+
fun createSavedPolicy(name: String, dynPolArg: DynamicPolicyArg, override: Boolean, download: Boolean): Boolean {
95+
if (!contains(name) || (isMutable(name) && override)) {
96+
val policyContent = when (download) {
97+
true -> resolveContent(dynPolArg.policy)
98+
false -> dynPolArg.policy
99+
}
100+
val dynPolArgMod = DynamicPolicyArg(
101+
name,
102+
dynPolArg.description,
103+
dynPolArg.input,
104+
policyContent,
105+
dynPolArg.dataPath,
106+
dynPolArg.policyQuery,
107+
dynPolArg.policyEngine,
108+
dynPolArg.applyToVC,
109+
dynPolArg.applyToVP
110+
)
111+
ContextManager.hkvStore.put(HKVKey(SAVED_POLICY_ROOT_KEY, name), Klaxon().toJsonString(dynPolArgMod))
112+
registerSavedPolicy(name, dynPolArgMod)
113+
return true
114+
}
115+
return false
116+
}
117+
118+
fun deleteSavedPolicy(name: String): Boolean {
119+
if (isMutable(name)) {
120+
ContextManager.hkvStore.delete(HKVKey(SAVED_POLICY_ROOT_KEY, name))
121+
policies.remove(name)
122+
return true
123+
}
124+
return false
125+
}
126+
127+
open fun initSavedPolicies() {
128+
ContextManager.hkvStore.listChildKeys(HKVKey(SAVED_POLICY_ROOT_KEY)).forEach {
129+
registerSavedPolicy(it.name, Klaxon().parse(ContextManager.hkvStore.getAsString(it)!!)!!)
130+
}
131+
}
132+
133+
open fun initPolicies() {
134+
register(SignaturePolicy::class, "Verify by signature")
135+
//register(JsonSchemaPolicy::class, "Verify by JSON schema")
136+
register(TrustedSchemaRegistryPolicy::class, "Verify by EBSI Trusted Schema Registry")
137+
register(TrustedIssuerDidPolicy::class, "Verify by trusted issuer did")
138+
PolicyRegistry.register(
139+
TrustedIssuerRegistryPolicy::class,
140+
TrustedIssuerRegistryPolicyArg::class,
141+
"Verify by an EBSI Trusted Issuers Registry compliant api.",
142+
true
143+
)
144+
register(TrustedSubjectDidPolicy::class, "Verify by trusted subject did")
145+
register(IssuedDateBeforePolicy::class, "Verify by issuance date")
146+
register(ValidFromBeforePolicy::class, "Verify by valid from")
147+
register(ExpirationDateAfterPolicy::class, "Verify by expiration date")
148+
//register(GaiaxTrustedPolicy::class, "Verify Gaiax trusted fields")
149+
register(GaiaxSDPolicy::class, "Verify Gaiax SD fields")
150+
register(ChallengePolicy::class, ChallengePolicyArg::class, "Verify challenge")
151+
register(
152+
PresentationDefinitionPolicy::class,
153+
PresentationDefinition::class,
154+
"Verify that verifiable presentation complies with presentation definition"
155+
)
156+
register(CredentialStatusPolicy::class, "Verify by credential status")
157+
register(DynamicPolicy::class, DynamicPolicyArg::class, "Verify credential by rego policy")
158+
159+
// predefined, hardcoded rego policy specializations
160+
// VerifiableMandate policy as specialized rego policy
161+
registerSavedPolicy(
162+
"VerifiableMandatePolicy", DynamicPolicyArg(
163+
"VerifiableMandatePolicy", "Predefined policy for verifiable mandates",
164+
JsonObject(), "$.credentialSubject.policySchemaURI",
165+
"$.credentialSubject.holder", "data.system.main"
166+
),
167+
immutable = true
168+
)
169+
170+
// other saved (Rego) policies
171+
initSavedPolicies()
172+
173+
//RegoPolicy(RegoPolicyArg(mapOf(), "")).argument.input
174+
}
175+
}

0 commit comments

Comments
 (0)