Bài viết
Chia sẻ kiến thức của bạn.
Các phương pháp hay nhất để thực hiện lịch trình đầu tư tại Sui
Tôi đang thiết kế một hệ thống bảo lãnh mã thông báo (ví dụ: để phân bổ nhóm hoặc khóa nhà đầu tư) trong Sui Move và cần đảm bảo:
Bảo mật - Không rút tiền sớm
Tính linh hoạt - Hỗ trợ cho vách đá, tuyến tính/dần dần
Hiệu quả khí đốt - Chi phí lưu trữ tối thiểu
Minh bạch - Dễ dàng xác minh tình trạng bảo lãnh
Thách thức hiện tại:
- Khóa thời gian cơ bản hoạt động nhưng thiếu kiểm soát chi tiết
- Vất vả với quản lý nhiều người nhận
- Không chắc chắn cách xử lý các trường hợp chấm dứt sớm
Câu hỏi:
Kiến trúc an toàn nhất để bảo lãnh hợp đồng là gì?
Làm thế nào để thực hiện các đường cong bảo vệ khác nhau (tuyến tính, phân cấp, vách đá)?
Cách tốt nhất để xử lý lịch trình có thể thu hồi so với lịch trình không thể thu hồi?
Các lỗ hổng phổ biến cần tránh?
- Sui
- Move
Câu trả lời
1####1. Kiến trúc đầu tư cốt lõi
#####Triển khai khả thi tối thiểu
module vesting::linear {
use sui::coin;
use sui::clock;
use sui::balance;
use sui::tx_context;
struct VestingSchedule has key {
id: UID,
recipient: address,
total_amount: u64,
start_time: u64, // Clock timestamp
duration_ms: u64, // Total vesting period
claimed: u64
}
/// Initialize vesting
public entry fn create(
recipient: address,
total_amount: u64,
duration_ms: u64,
clock: &Clock,
ctx: &mut TxContext
) {
let schedule = VestingSchedule {
id: object::new(ctx),
recipient,
total_amount,
start_time: clock.timestamp_ms,
duration_ms,
claimed: 0
};
transfer::transfer(schedule, recipient);
}
}
Các thành phần chính:
- D
Clock
ấu thời gian dựa trên (không phải số khối) - Các đối tượng lịch trình tự giám sát
- Bảo lãnh tuyến tính theo mặc định
####2. Mẫu đầu tư nâng cao
#####Cliff + Tuyến sực
public fun claimable_amount(
schedule: &VestingSchedule,
clock: &Clock
): u64 {
let elapsed = clock.timestamp_ms.saturating_sub(schedule.start_time);
// Cliff period (e.g., 1 year)
if (elapsed < CLIFF_MS) return 0;
// Linear vesting after cliff
let vested = (schedule.total_amount * elapsed) / schedule.duration_ms;
vested - schedule.claimed
}
#####** Bảo lãnh được phân loại (Nhiều mốc quan trọng)**
struct GradedVesting has key {
id: UID,
milestones: vector<Milestone>, // [{time: u64, percent: u8}]
claimed: u64
}
public fun graded_claimable(schedule: &GradedVesting, clock: &Clock): u64 {
let total_vested = 0;
let i = 0;
while (i < vector::length(&schedule.milestones)) {
let milestone = vector::borrow(&schedule.milestones, i);
if (clock.timestamp_ms >= milestone.time) {
total_vested = total_vested +
(schedule.total_amount * milestone.percent as u64) / 100;
};
i = i + 1;
};
total_vested - schedule.claimed
}
####3. Nâng cao bảo mật
#####Quyền có thể thu hồi (Điều khiển quản trị viên)
struct AdminCap has key { id: UID }
public entry fn revoke(
schedule: VestingSchedule,
admin_cap: &AdminCap,
ctx: &mut TxContext
) {
assert!(address_of(signer) == admin_cap.admin, EUnauthorized);
let remaining = schedule.total_amount - schedule.claimed;
coin::transfer(remaining, admin_cap.admin, ctx);
object::delete(schedule);
}
#####Chống tiền trong
public entry fn claim(
schedule: &mut VestingSchedule,
clock: &Clock,
ctx: &mut TxContext
) {
let amount = claimable_amount(schedule, clock);
assert!(amount > 0, ENothingToClaim);
assert!(tx_context::epoch(ctx) == clock.epoch(), EStaleClock);
schedule.claimed = schedule.claimed + amount;
transfer::public_transfer(coin::mint(amount, ctx), schedule.recipient);
}
####4. Kỹ thuật tối ưu hóa khí
#####Lịch đăng ký hàng loại
struct BatchVesting has key {
id: UID,
schedules: Table<address, VestingSchedule>
}
// Claim all eligible in one TXN
public entry fn batch_claim(batch: &mut BatchVesting, clock: &Clock) {
let iter = table::iter(&mut batch.schedules);
while (table::has_next(&iter)) {
let (addr, schedule) = table::next(&iter);
let amount = claimable_amount(schedule, clock);
if (amount > 0) transfer_coins(addr, amount);
}
}
#####Giảm giá lưu trữ
// Use small types where possible
struct CompactVesting {
start_time: u64,
duration_ms: u32, // Sufficient for 49-day periods
claimed: u64
}
####5. Các lỗ hổng thông thường
❌** Các cuộc tấn công Oracle theo thời gian**
// UNSAFE: Trusting user-provided timestamps
fun unsafe_claim(user_time: u64) { ... }
❌** Lỗi làm tròng**
// May leave "dust" unclaimed
let vested = (amount * elapsed) / duration; // Use checked_math
❌** Thiếu logic thu quố**
// Irrevocable vesting may violate securities laws
struct DangerousVesting { ... }
####6. Chiến lược kiểm tra
#####Kiểm tra đồng hồ giả mẫu
#[test]
fun test_cliff_period() {
let clock = mock_clock(0);
let schedule = create_vesting(CLIFF_MS * 2);
// Before cliff
test_clock::advance(&mut clock, CLIFF_MS - 1);
assert!(claimable(&schedule, &clock) == 0, ETestFail);
// After cliff
test_clock::advance(&mut clock, 1);
assert!(claimable(...) > 0, ETestFail);
}
#####Kiểm tra Fuzz
#[test]
fun test_overflow_scenarios() {
let schedule = VestingSchedule {
start_time: u64::MAX - 1000,
duration_ms: 2000
};
// Should handle wrap-around correctly
claimable_amount(&schedule, &clock);
}
Bạn có biết câu trả lời không?
Hãy đăng nhập và chia sẻ nó.
Sui is a Layer 1 protocol blockchain designed as the first internet-scale programmable blockchain platform.
Kiếm phần của bạn từ 1000 Sui
Tích lũy điểm danh tiếng và nhận phần thưởng khi giúp cộng đồng Sui phát triển.
- Tại sao BCS yêu cầu thứ tự trường chính xác để khử chuỗi khi cấu trúc Move có các trường được đặt tên?53
- Nhiều lỗi xác minh nguồn” trong các ấn phẩm về mô-đun Sui Move - Giải quyết lỗi tự động43
- Giao dịch Sui thất bại: Đối tượng được dành riêng cho giao dịch khác25
- Làm thế nào để các ràng buộc về khả năng tương tác với các trường động trong các bộ sưu tập không đồng nhất?05