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
use async_graphql::{scalar, InputObject, SimpleObject};
use fracpack::{Pack, ToSchema, Unpack};
use pem::{encode, parse, Pem};
use serde::{Deserialize, Deserializer, Serialize, Serializer};
#[derive(Debug, Clone, ToSchema, Pack, Unpack)]
#[fracpack(fracpack_mod = "fracpack")]
pub struct SubjectPublicKeyInfo(pub Vec<u8>);
scalar!(SubjectPublicKeyInfo);
impl Serialize for SubjectPublicKeyInfo {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
let pem = Pem::new("PUBLIC KEY", self.0.clone());
let pem_string = encode(&pem);
serializer.serialize_str(&pem_string)
}
}
impl<'de> Deserialize<'de> for SubjectPublicKeyInfo {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
let pem_string: String = Deserialize::deserialize(deserializer)?;
let pem = parse(&pem_string).map_err(serde::de::Error::custom)?;
if pem.tag() != "PUBLIC KEY" {
return Err(serde::de::Error::custom("Expected a PUBLIC KEY PEM"));
}
Ok(SubjectPublicKeyInfo(pem.contents().to_vec()))
}
}
impl From<Vec<u8>> for SubjectPublicKeyInfo {
fn from(data: Vec<u8>) -> Self {
SubjectPublicKeyInfo(data)
}
}
#[derive(
Debug, Clone, Pack, Unpack, Serialize, Deserialize, ToSchema, SimpleObject, InputObject,
)]
#[fracpack(fracpack_mod = "fracpack")]
#[graphql(input_name = "AuthRecord")]
/// A record containing the authorization claims needed for an account using this auth service.
pub struct AuthRecord {
/// The account whose transactions will be required to contain the specified public key.
pub account: crate::AccountNumber,
/// The public key included in the claims for each transaction sent by this account.
pub pubkey: SubjectPublicKeyInfo,
}
/// The `auth-sig` service is an auth service that can be used to authenticate actions for accounts.
///
/// Any account using this auth service must store in this service a public key that they own.
/// This service will ensure that the specified public key is included in the transaction claims for any
/// transaction sent by this account.
///
/// This service supports K1 or R1 keys (Secp256K1 or Secp256R1) keys.
#[crate::service(name = "auth-sig", dispatch = false, psibase_mod = "crate")]
#[allow(non_snake_case, unused_variables)]
mod service {
use super::SubjectPublicKeyInfo;
use crate::{services::transact::ServiceMethod, AccountNumber, Claim};
/// This is an implementation of the standard auth service interface defined in [SystemService::AuthInterface]
///
/// This action is automatically called by `transact` when an account using this auth service submits a
/// transaction.
///
/// This action verifies that the transaction contains a claim for the user's public key.
#[action]
fn checkAuthSys(
flags: u32,
requester: AccountNumber,
sender: AccountNumber,
action: ServiceMethod,
allowedActions: Vec<ServiceMethod>,
claims: Vec<Claim>,
) {
unimplemented!()
}
/// This is an implementation of the standard auth service interface defined in [SystemService::AuthInterface]
///
/// This action is automatically called by `accounts` when an account is configured to use this auth service.
///
/// Verifies that a particular user is allowed to use a particular auth service.
///
/// This action allows any user who has already set a public key using `AuthSig::setKey`.
#[action]
fn canAuthUserSys(user: AccountNumber) {
unimplemented!()
}
/// Set the sender's public key
///
/// This is the public key that must be claimed by the transaction whenever a sender using this auth service
/// submits a transaction.
#[action]
fn setKey(key: SubjectPublicKeyInfo) {
unimplemented!()
}
/// Check whether a specified set of authorizer accounts are sufficient to authorize sending a
/// transaction from a specified sender.
///
/// * `sender`: The sender account for the transaction potentially being authorized.
/// * `authorizers`: The set of accounts that have already authorized the execution of the transaction.
///
/// Returns:
/// * `true`: If the sender is among the authorizers
/// * `false`: If the sender is not among the authorizers
#[action]
fn isAuthSys(sender: AccountNumber, authorizers: Vec<AccountNumber>) -> bool {
unimplemented!()
}
/// Check whether a specified set of rejecter accounts are sufficient to reject (cancel) a
/// transaction from a specified sender.
///
/// * `sender`: The sender account for the transaction potentially being rejected.
/// * `rejecters`: The set of accounts that have already authorized the rejection of the transaction.
///
/// Returns:
/// * `true`: If the sender is among the rejecters
/// * `false`: If the sender is not among the rejecters
#[action]
fn isRejectSys(sender: AccountNumber, authorizers: Vec<AccountNumber>) -> bool {
unimplemented!()
}
/// Create a new account using this auth service configured with the specified public key.
#[action]
fn newAccount(name: AccountNumber, key: SubjectPublicKeyInfo) {
unimplemented!()
}
}
#[test]
fn verify_schema() {
crate::assert_schema_matches_package::<Wrapper>();
}