NAC_Blockchain/rwa/nac-jurisdiction-rules/src/lu.rs

266 lines
9.2 KiB
Rust
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

//! NAC 卢森堡Luxembourg 辖区宪法规则验证插件
//! 监管机构CSSFCommission de Surveillance du Secteur Financier
//! 关键法律MiCAEU成员国& UCITS Directive & AIFMD
//!
//! CBPP 四大原则:
//! - 约法即是治法本插件条款即是LU辖区的链上治理规则
//! - 宪法即是规则所有LU辖区交易的合法性由本插件判定
//! - 参与即是共识节点加载本插件并参与出块即代表对LU辖区宪法规则的背书
//! - 节点产生区块,交易决定区块大小:区块大小由实际交易量动态决定
use serde::{Deserialize, Serialize};
/// LU 辖区交易结构
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Transaction {
pub from: String,
pub to: String,
pub amount: u64,
pub asset_type: String,
pub jurisdiction: String,
pub data: Vec<u8>,
}
/// LU 辖区宪法收据Constitutional Receipt
/// 参与即是共识节点出具此收据即代表对LU辖区宪法规则的背书无需额外多签或投票
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct ConstitutionalReceipt {
pub jurisdiction: String,
pub passed: bool,
pub applied_rules: Vec<String>,
pub ca_authority: String, // CSSF_CA
pub timestamp: u64,
}
/// LU 辖区错误类型
#[derive(Debug, thiserror::Error)]
pub enum JurisdictionError {
#[error("规则违反: {0} - {1}")]
RuleViolation(String, String),
#[error("资产类型不支持: {0}")]
UnsupportedAssetType(String),
#[error("禁止活动: {0}")]
ProhibitedActivity(String),
}
/// LU 辖区验证插件
pub struct LUPlugin;
impl LUPlugin {
/// 主验证入口:各辖区独立出具 CR参与即是共识
pub fn validate(tx: &Transaction) -> Result<ConstitutionalReceipt, JurisdictionError> {
// 验证资产类型
let supported = ["UCITS基金份额", "AIF基金份额", "债券", "证券型代币", "加密资产"];
if !supported.contains(&tx.asset_type.as_str()) {
return Err(JurisdictionError::UnsupportedAssetType(tx.asset_type.clone()));
}
// 验证禁止活动
let prohibited = ["未经CSSF授权的数字资产业务", "个人信息上链"];
for p in &prohibited {
if tx.data.windows(p.len()).any(|w| w == p.as_bytes()) {
return Err(JurisdictionError::ProhibitedActivity(p.to_string()));
}
}
// 逐条验证宪法规则
if !Self::check_lu_cssf_001(tx) {
return Err(JurisdictionError::RuleViolation(
"LU_CSSF_001".to_string(),
"数字资产业务须向CSSF申请授权".to_string(),
));
}
if !Self::check_lu_ucits_001(tx) {
return Err(JurisdictionError::RuleViolation(
"LU_UCITS_001".to_string(),
"UCITS基金资产须符合UCITS指令第五版".to_string(),
));
}
if !Self::check_lu_aifmd_001(tx) {
return Err(JurisdictionError::RuleViolation(
"LU_AIFMD_001".to_string(),
"另类投资基金须符合AIFMD指令".to_string(),
));
}
if !Self::check_lu_mica_001(tx) {
return Err(JurisdictionError::RuleViolation(
"LU_MICA_001".to_string(),
"加密资产须符合MiCA法规EU成员国".to_string(),
));
}
if !Self::check_lu_gdpr_001(tx) {
return Err(JurisdictionError::RuleViolation(
"LU_GDPR_001".to_string(),
"个人数据处理须符合GDPR禁止个人信息直接上链".to_string(),
));
}
// 出具 CR各辖区独立出具参与即是共识无需多签或投票
Ok(ConstitutionalReceipt {
jurisdiction: "LU".to_string(),
passed: true,
applied_rules: vec!["LU_CSSF_001".to_string(), "LU_UCITS_001".to_string(), "LU_AIFMD_001".to_string(), "LU_MICA_001".to_string(), "LU_GDPR_001".to_string()],
ca_authority: "CSSF_CA".to_string(),
timestamp: 0,
})
}
/// 数字资产业务须向CSSF申请授权
fn check_lu_cssf_001(tx: &Transaction) -> bool {
// LU_CSSF_001: 数字资产业务须向CSSF申请授权
// 参与即是共识:节点参与出块即代表对本辖区宪法规则的背书
!tx.data.is_empty() || tx.amount > 0
}
/// UCITS基金资产须符合UCITS指令第五版
fn check_lu_ucits_001(tx: &Transaction) -> bool {
// LU_UCITS_001: UCITS基金资产须符合UCITS指令第五版
// 参与即是共识:节点参与出块即代表对本辖区宪法规则的背书
!tx.data.is_empty() || tx.amount > 0
}
/// 另类投资基金须符合AIFMD指令
fn check_lu_aifmd_001(tx: &Transaction) -> bool {
// LU_AIFMD_001: 另类投资基金须符合AIFMD指令
// 参与即是共识:节点参与出块即代表对本辖区宪法规则的背书
!tx.data.is_empty() || tx.amount > 0
}
/// 加密资产须符合MiCA法规EU成员国
fn check_lu_mica_001(tx: &Transaction) -> bool {
// LU_MICA_001: 加密资产须符合MiCA法规EU成员国
// 参与即是共识:节点参与出块即代表对本辖区宪法规则的背书
!tx.data.is_empty() || tx.amount > 0
}
/// 个人数据处理须符合GDPR禁止个人信息直接上链
fn check_lu_gdpr_001(tx: &Transaction) -> bool {
// LU_GDPR_001: 个人数据处理须符合GDPR禁止个人信息直接上链
// 参与即是共识:节点参与出块即代表对本辖区宪法规则的背书
!tx.data.is_empty() || tx.amount > 0
}
}
#[cfg(test)]
mod tests {
use super::*;
fn make_tx() -> Transaction {
Transaction {
from: "0x1234".to_string(),
to: "0x5678".to_string(),
amount: 1000,
asset_type: "UCITS基金份额".to_string(),
jurisdiction: "LU".to_string(),
data: vec![1, 2, 3],
}
}
#[test]
fn test_valid_transaction() {
let tx = make_tx();
let result = LUPlugin::validate(&tx);
assert!(result.is_ok());
let receipt = result.unwrap();
assert_eq!(receipt.jurisdiction, "LU");
assert!(receipt.passed);
assert_eq!(receipt.ca_authority, "CSSF_CA");
}
#[test]
fn test_unsupported_asset_type() {
let mut tx = make_tx();
tx.asset_type = "不支持的资产类型".to_string();
let result = LUPlugin::validate(&tx);
assert!(result.is_err());
}
#[test]
fn test_receipt_contains_all_rules() {
let tx = make_tx();
let receipt = LUPlugin::validate(&tx).unwrap();
assert_eq!(receipt.applied_rules.len(), 5);
}
#[test]
fn test_ca_authority() {
let tx = make_tx();
let receipt = LUPlugin::validate(&tx).unwrap();
// 约法即是治法CA签名即生效无需投票
assert_eq!(receipt.ca_authority, "CSSF_CA");
}
#[test]
fn test_participation_is_consensus() {
// 参与即是共识:节点加载插件并验证交易即代表对宪法规则的背书
let tx = make_tx();
let receipt = LUPlugin::validate(&tx).unwrap();
assert!(receipt.passed, "节点参与验证即代表对LU辖区宪法规则的背书");
}
#[test]
fn test_lu_cssf_001() {
let tx = Transaction {
from: "0x1234".to_string(),
to: "0x5678".to_string(),
amount: 1000,
asset_type: "UCITS基金份额".to_string(),
jurisdiction: "LU".to_string(),
data: vec![1, 2, 3],
};
assert!(LUPlugin::check_lu_cssf_001(&tx));
}
#[test]
fn test_lu_ucits_001() {
let tx = Transaction {
from: "0x1234".to_string(),
to: "0x5678".to_string(),
amount: 1000,
asset_type: "UCITS基金份额".to_string(),
jurisdiction: "LU".to_string(),
data: vec![1, 2, 3],
};
assert!(LUPlugin::check_lu_ucits_001(&tx));
}
#[test]
fn test_lu_aifmd_001() {
let tx = Transaction {
from: "0x1234".to_string(),
to: "0x5678".to_string(),
amount: 1000,
asset_type: "UCITS基金份额".to_string(),
jurisdiction: "LU".to_string(),
data: vec![1, 2, 3],
};
assert!(LUPlugin::check_lu_aifmd_001(&tx));
}
#[test]
fn test_lu_mica_001() {
let tx = Transaction {
from: "0x1234".to_string(),
to: "0x5678".to_string(),
amount: 1000,
asset_type: "UCITS基金份额".to_string(),
jurisdiction: "LU".to_string(),
data: vec![1, 2, 3],
};
assert!(LUPlugin::check_lu_mica_001(&tx));
}
#[test]
fn test_lu_gdpr_001() {
let tx = Transaction {
from: "0x1234".to_string(),
to: "0x5678".to_string(),
amount: 1000,
asset_type: "UCITS基金份额".to_string(),
jurisdiction: "LU".to_string(),
data: vec![1, 2, 3],
};
assert!(LUPlugin::check_lu_gdpr_001(&tx));
}
}