This repository has been archived by the owner on Jan 17, 2022. It is now read-only.
/
Attester.ts
194 lines (184 loc) · 6.43 KB
/
Attester.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
import { AttestationRequest } from '../types/Claim'
import goWasmExec, { wasmStringify } from '../wasm/wasm_exec_wrapper'
import WasmHooks from '../wasm/WasmHooks'
import Accumulator from './Accumulator'
import IAttester, {
IGabiMsgSession,
InitiateAttestationRequest,
AttesterAttestationSession,
Witness,
Attestation,
AttesterPublicKey,
AttesterPrivateKey,
KeyLength,
DEFAULT_MAX_ATTRIBUTES,
DEFAULT_VALIDITY_DURATION,
DEFAULT_KEY_LENGTH,
} from '../types/Attestation'
export type KeyGenOptions = {
validityDuration?: number
maxAttributes?: number
keyLength?: KeyLength
}
/**
* Converts days to nano seconds.
*
* @param days The amount of days that should be converted.
* @returns The amount of nanoseconds for the specified amount of days.
* @internal
*/
export function daysToNanoSecs(days: number): number {
return days * 24 * 60 * 60 * 1000 * 1000 * 1000
}
/**
* The Attester can be used to create and revoke [[Attestation]]s of [[Credential]]s.
*/
export default class Attester implements IAttester {
readonly privateKey: AttesterPrivateKey
readonly publicKey: AttesterPublicKey
/**
* Generates a new key pair.
*
* @param options An optional object containing options for the key generation.
* @param options.validityDuration The duration in days for which the public key will be valid.
* @param options.maxAttributes The maximum number of attributes that can be signed with the generated private key.
* @param options.keyLength The key length of the new key pair. Note that this key will only support credentials and claimer with the same key length.
* @returns A newly generated key pair.
*/
public static async genKeyPair({
validityDuration,
maxAttributes,
keyLength,
}: KeyGenOptions = {}): Promise<{
privateKey: AttesterPrivateKey
publicKey: AttesterPublicKey
}> {
const durationInNanoSecs = daysToNanoSecs(
validityDuration || DEFAULT_VALIDITY_DURATION
)
const { privateKey, publicKey } = await goWasmExec<{
privateKey: string
publicKey: string
}>(WasmHooks.genKeypair, [
maxAttributes || DEFAULT_MAX_ATTRIBUTES,
durationInNanoSecs,
keyLength || DEFAULT_KEY_LENGTH,
])
return {
privateKey: new AttesterPrivateKey(privateKey),
publicKey: new AttesterPublicKey(publicKey),
}
}
/**
* Generates a new key pair and returns a new [[Attester]].
*
* @param options An optional object containing options for the key generation.
* @param options.validityDuration The duration in days for which the public key will be valid.
* @param options.maxAttributes The maximal number of attributes that can be signed with the generated private key.
* @param options.keyLength The key length of the new key pair. Note that this key will only support credentials and claimer with the same key length.
* @returns A new [[Attester]].
*/
public static async create(options: KeyGenOptions = {}): Promise<Attester> {
const { publicKey, privateKey } = await this.genKeyPair(options)
return new Attester(publicKey, privateKey)
}
/**
* Constructs a new [[Attester]] using an existing private and public key pair.
*
* @param publicKey The public key for the [[Attester]].
* @param privateKey The private key for the [[Attester]].
*/
public constructor(
publicKey: AttesterPublicKey,
privateKey: AttesterPrivateKey
) {
this.publicKey = publicKey
this.privateKey = privateKey
}
/**
* Initiates the attestation session.
*
* @returns A session and a message object. The message should be sent over to the [[Claimer]].
*/
public async startAttestation(): ReturnType<IAttester['startAttestation']> {
const { message, session } = await goWasmExec<IGabiMsgSession>(
WasmHooks.startAttestationSession,
[wasmStringify(this.privateKey), wasmStringify(this.publicKey)]
)
return {
message: new InitiateAttestationRequest(message),
session: new AttesterAttestationSession(session),
}
}
/**
* Creates a new accumulator.
*
* @returns A new [[Accumulator]].
*/
public async createAccumulator(): ReturnType<IAttester['createAccumulator']> {
return new Accumulator(
await goWasmExec<string>(WasmHooks.createAccumulator, [
wasmStringify(this.privateKey),
wasmStringify(this.publicKey),
])
)
}
/**
* Creates an [[Attestation]] for the claim inside the [[AttestationRequest]].
*
* @param p The parameter object.
* @param p.attestationSession The [[Attestation]] session which was generated during [[startAttestation]].
* @param p.attestationRequest The [[AttestationRequest]] received from the [[Claimer]].
* @param p.accumulator The most recent [[Accumulator]].
* @returns The [[Attestation]] object which should be sent to the [[Claimer]] and a [[Witness]] which can be used to revoke the attestation.
*/
public async issueAttestation({
attestationSession,
attestationRequest,
accumulator,
}: {
attestationSession: AttesterAttestationSession
attestationRequest: AttestationRequest
accumulator: Accumulator
}): ReturnType<IAttester['issueAttestation']> {
const { attestation, witness } = await goWasmExec<{
attestation: string
witness: string
}>(WasmHooks.issueAttestation, [
wasmStringify(this.privateKey),
wasmStringify(this.publicKey),
wasmStringify(attestationSession),
wasmStringify(attestationRequest),
wasmStringify(accumulator),
])
return {
attestation: new Attestation(attestation),
witness: new Witness(witness),
}
}
/**
* Revokes an [[Attestation]] which corresponds to the provided [[Witness]].
*
* @param p The parameter object.
* @param p.accumulator The current [[Accumulator]].
* @param p.witnesses The revocation [[Witness]]es belonging to the [[Attestation]]s which are about to be revoked.
* @returns An updated version of the [[Accumulator]].
*/
public async revokeAttestation({
accumulator,
witnesses,
}: {
accumulator: Accumulator
witnesses: Witness[]
}): ReturnType<IAttester['revokeAttestation']> {
return new Accumulator(
await goWasmExec<string>(WasmHooks.revokeAttestation, [
wasmStringify(this.privateKey),
wasmStringify(this.publicKey),
wasmStringify(accumulator),
`[${(witnesses || []).join(',')}]`,
// JSON.stringify((witnesses || []).map((witness) => witness.parse())),
])
)
}
}