use frame_support::{dispatch::DispatchResult, traits::Get, BoundedBTreeMap, BoundedVec};
use parity_scale_codec::{Decode, Encode, EncodeLike, Error, MaxEncodedLen};
use scale_info::TypeInfo;
#[cfg(feature = "std")]
use serde::{Deserialize, Serialize};
use sp_runtime::{
traits::{AtLeast32BitUnsigned, Zero},
DispatchError, MultiSignature, RuntimeDebug,
};
use sp_std::prelude::Vec;
pub use crate::schema::SchemaId;
pub type MessageSourceId = u64;
#[cfg_attr(feature = "std", derive(Serialize, Deserialize))]
#[derive(TypeInfo, Default, Debug, Clone, Copy, PartialEq, MaxEncodedLen, Eq)]
pub struct DelegatorId(pub MessageSourceId);
impl EncodeLike for DelegatorId {}
impl Encode for DelegatorId {
fn encode(&self) -> Vec<u8> {
self.0.encode()
}
}
impl Decode for DelegatorId {
fn decode<I: parity_scale_codec::Input>(
input: &mut I,
) -> Result<Self, parity_scale_codec::Error> {
match <u64>::decode(input) {
Ok(x) => Ok(DelegatorId(x)),
_ => Err(Error::from("Could not decode DelegatorId")),
}
}
}
impl From<MessageSourceId> for DelegatorId {
fn from(t: MessageSourceId) -> Self {
DelegatorId(t)
}
}
impl From<DelegatorId> for MessageSourceId {
fn from(t: DelegatorId) -> MessageSourceId {
t.0
}
}
#[cfg_attr(feature = "std", derive(Deserialize, Serialize))]
#[derive(TypeInfo, RuntimeDebug, Clone, Decode, Encode, MaxEncodedLen, Eq)]
pub struct DelegationResponse<SchemaId, BlockNumber> {
pub provider_id: ProviderId,
pub permissions: Vec<SchemaGrant<SchemaId, BlockNumber>>,
}
#[cfg_attr(feature = "std", derive(Deserialize, Serialize))]
#[derive(TypeInfo, RuntimeDebug, Clone, Decode, Encode, MaxEncodedLen, Eq)]
pub struct SchemaGrant<SchemaId, BlockNumber> {
pub schema_id: SchemaId,
pub revoked_at: BlockNumber,
}
impl<SchemaId, BlockNumber> PartialEq for DelegationResponse<SchemaId, BlockNumber>
where
SchemaId: PartialEq,
BlockNumber: PartialEq,
{
fn eq(&self, other: &Self) -> bool {
self.provider_id == other.provider_id && self.permissions == other.permissions
}
}
impl<SchemaId, BlockNumber> SchemaGrant<SchemaId, BlockNumber> {
pub fn new(schema_id: SchemaId, revoked_at: BlockNumber) -> Self {
SchemaGrant { schema_id, revoked_at }
}
}
impl<SchemaId, BlockNumber> PartialEq for SchemaGrant<SchemaId, BlockNumber>
where
SchemaId: PartialEq,
BlockNumber: PartialEq,
{
fn eq(&self, other: &Self) -> bool {
self.schema_id == other.schema_id && self.revoked_at == other.revoked_at
}
}
#[derive(TypeInfo, RuntimeDebug, Clone, Decode, Encode, MaxEncodedLen, Eq)]
#[scale_info(skip_type_params(MaxSchemaGrantsPerDelegation))]
pub struct Delegation<SchemaId, BlockNumber, MaxSchemaGrantsPerDelegation>
where
MaxSchemaGrantsPerDelegation: Get<u32>,
{
pub revoked_at: BlockNumber,
pub schema_permissions: BoundedBTreeMap<SchemaId, BlockNumber, MaxSchemaGrantsPerDelegation>,
}
impl<SchemaId, BlockNumber, MaxSchemaGrantsPerDelegation> PartialEq
for Delegation<SchemaId, BlockNumber, MaxSchemaGrantsPerDelegation>
where
SchemaId: PartialEq,
BlockNumber: PartialEq,
MaxSchemaGrantsPerDelegation: Get<u32>,
{
fn eq(&self, other: &Self) -> bool {
self.revoked_at == other.revoked_at && self.schema_permissions == other.schema_permissions
}
}
impl<
SchemaId: Ord + Default,
BlockNumber: Ord + Copy + Zero + AtLeast32BitUnsigned + Default,
MaxSchemaGrantsPerDelegation: Get<u32>,
> Default for Delegation<SchemaId, BlockNumber, MaxSchemaGrantsPerDelegation>
{
fn default() -> Self {
Delegation {
revoked_at: BlockNumber::default(),
schema_permissions: BoundedBTreeMap::<
SchemaId,
BlockNumber,
MaxSchemaGrantsPerDelegation,
>::new(),
}
}
}
#[cfg_attr(feature = "std", derive(Serialize, Deserialize))]
#[derive(TypeInfo, Default, Debug, Clone, Copy, PartialEq, MaxEncodedLen, Eq)]
pub struct ProviderId(pub MessageSourceId);
impl EncodeLike for ProviderId {}
impl Encode for ProviderId {
fn encode(&self) -> Vec<u8> {
self.0.encode()
}
}
impl Decode for ProviderId {
fn decode<I: parity_scale_codec::Input>(
input: &mut I,
) -> Result<Self, parity_scale_codec::Error> {
match <u64>::decode(input) {
Ok(x) => Ok(ProviderId(x)),
_ => Err(Error::from("Could not decode ProviderId")),
}
}
}
impl From<MessageSourceId> for ProviderId {
fn from(t: MessageSourceId) -> Self {
ProviderId(t)
}
}
impl From<ProviderId> for MessageSourceId {
fn from(t: ProviderId) -> MessageSourceId {
t.0
}
}
#[derive(MaxEncodedLen, TypeInfo, Debug, Clone, Decode, Encode, PartialEq, Eq)]
#[scale_info(skip_type_params(T))]
pub struct ProviderRegistryEntry<T>
where
T: Get<u32>,
{
pub provider_name: BoundedVec<u8, T>,
}
#[derive(MaxEncodedLen, TypeInfo, Debug, Clone, Decode, Encode, PartialEq, Eq)]
pub struct SignatureRegistryPointer<BlockNumber> {
pub newest: MultiSignature,
pub newest_expires_at: BlockNumber,
pub oldest: MultiSignature,
pub count: u32,
}
pub trait MsaLookup {
type AccountId;
fn get_msa_id(key: &Self::AccountId) -> Option<MessageSourceId>;
}
pub trait MsaValidator {
type AccountId;
fn ensure_valid_msa_key(key: &Self::AccountId) -> Result<MessageSourceId, DispatchError>;
}
pub trait ProviderLookup {
type BlockNumber;
type MaxSchemaGrantsPerDelegation: Get<u32>;
type SchemaId;
fn get_delegation_of(
delegator: DelegatorId,
provider: ProviderId,
) -> Option<Delegation<Self::SchemaId, Self::BlockNumber, Self::MaxSchemaGrantsPerDelegation>>;
}
pub trait DelegationValidator {
type BlockNumber;
type MaxSchemaGrantsPerDelegation: Get<u32>;
type SchemaId;
fn ensure_valid_delegation(
provider: ProviderId,
delegator: DelegatorId,
block_number: Option<Self::BlockNumber>,
) -> Result<
Delegation<Self::SchemaId, Self::BlockNumber, Self::MaxSchemaGrantsPerDelegation>,
DispatchError,
>;
}
pub trait SchemaGrantValidator<BlockNumber> {
fn ensure_valid_schema_grant(
provider_id: ProviderId,
delegator_id: DelegatorId,
schema_id: SchemaId,
block_number: BlockNumber,
) -> DispatchResult;
}
#[cfg_attr(feature = "std", derive(Serialize, Deserialize))]
#[derive(TypeInfo, Debug, Clone, Decode, Encode, PartialEq, Default, MaxEncodedLen)]
pub struct KeyInfoResponse<AccountId> {
pub msa_id: MessageSourceId,
pub msa_keys: Vec<AccountId>,
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn decoding_provider_id_failure() {
let mut da: &[u8] = b"\xf6\xf5";
let decoded = DelegatorId::decode(&mut da);
assert!(decoded.is_err());
}
#[test]
fn decoding_provider_id_success() {
let val = 16777215_u64.encode();
let decoded = ProviderId::decode(&mut &val[..]);
assert_eq!(decoded, Ok(ProviderId(16777215)))
}
#[test]
fn decoding_delegate_id_failure() {
let mut da: &[u8] = b"\xf6\xf5";
let decoded = DelegatorId::decode(&mut da);
assert!(decoded.is_err());
}
#[test]
fn decoding_delegator_id_success() {
let val = 42_u64.encode();
let decoded = DelegatorId::decode(&mut &val[..]);
assert_eq!(decoded, Ok(DelegatorId(42)))
}
}