robius-matrix-integration – skill Lập trình cho agent AI
CRITICAL: Dùng để tích hợp Matrix SDK với Makepad. Kích hoạt khi có: Matrix SDK, sliding sync, MatrixRequest, timeline, matrix-sdk, matrix client, robrix, matrix room, Matrix 集成, 聊天客户端
Cài skill robius-matrix-integration bằng một lệnh
Chọn công cụ bạn đang dùng, copy lệnh và dán vào terminal. Skill sẽ nằm trong thư mục skills của công cụ đó và sẵn sàng dùng ở phiên làm việc tiếp theo.
Claude Code
mkdir -p ~/.claude/skills && curl -fsSL https://skill.dn1nguoi.com/z/robius-matrix-integration-4bdcf.tgz | tar xz -C ~/.claude/skills
Gọi trong Claude Code: /robius-matrix-integration – rồi mô tả công việc bạn muốn làm.
Codex
mkdir -p ~/.codex/skills && curl -fsSL https://skill.dn1nguoi.com/z/robius-matrix-integration-4bdcf.tgz | tar xz -C ~/.codex/skills
Gọi trong Codex: $robius-matrix-integration – rồi mô tả công việc bạn muốn làm.
Hermes Agent
mkdir -p ~/.hermes/skills && curl -fsSL https://skill.dn1nguoi.com/z/robius-matrix-integration-4bdcf.tgz | tar xz -C ~/.hermes/skills
Gọi trong Hermes Agent: /robius-matrix-integration – rồi mô tả công việc bạn muốn làm.
DeepSeek
mkdir -p ~/.deepcode/skills && curl -fsSL https://skill.dn1nguoi.com/z/robius-matrix-integration-4bdcf.tgz | tar xz -C ~/.deepcode/skills
Gọi trong DeepSeek: /robius-matrix-integration – rồi mô tả công việc bạn muốn làm.
Nội dung SKILL.md
Nội dung SKILL.md gốc bằng tiếng Anh.
Supporting material availability
This catalog copy contains the inline guidance below, but does not include the following supporting paths. They are external prerequisites, not bundled files:
<support-root>/references/matrix-client.md<support-root>/references/timeline-handling.md<support-root>/references/moly-api-integration.md
Ask for the original supporting material or an existing installation before using a step that depends on these paths; this catalog does not identify a verified download source for them. Resolve each path relative to that installation, inspect its contents, and verify any applicable license and execution prerequisites. Do not run a command or claim a referenced procedure was followed until its required file exists. Do not fabricate the missing scripts or treat an unrelated file with the same name as equivalent. Independent steps fully documented here can proceed within the user’s authorized scope; report any dependent step as unavailable.
Robius Matrix SDK Integration Skill
Best practices for integrating external APIs with Makepad applications based on Robrix and Moly codebases.
Source codebases:
- Robrix: Matrix SDK integration - sliding sync, timeline subscriptions, real-time updates
- Moly: OpenAI/LLM API integration - SSE streaming, MCP protocol, multi-provider support
When to Use
Use this skill when:
- Integrating Matrix SDK with Makepad
- Building a Matrix client with Makepad
- Implementing Matrix features (rooms, timelines, messages)
- Handling Matrix SDK async operations in UI
- Keywords: matrix-sdk, matrix client, robrix, matrix timeline, matrix room, sliding sync
Overview
Robrix uses the matrix-sdk and matrix-sdk-ui crates to connect to Matrix homeservers. The key architectural decisions:
1. Sliding Sync: Uses native sliding sync for efficient room list updates
2. Separate Runtime: Tokio runtime runs Matrix operations, Makepad handles UI
3. Request/Response Pattern: UI sends requests, receives actions/updates back
4. Per-Room Background Tasks: Each room has dedicated timeline subscriber task
MatrixRequest Pattern
Request Enum Definition
/// All async requests that can be made to the Matrix worker task
pub enum MatrixRequest {
/// Login requests
Login(LoginRequest),
Logout { is_desktop: bool },
/// Timeline operations
PaginateRoomTimeline {
room_id: OwnedRoomId,
num_events: u16,
direction: PaginationDirection,
},
SendMessage {
room_id: OwnedRoomId,
message: RoomMessageEventContent,
replied_to: Option<Reply>,
},
EditMessage {
room_id: OwnedRoomId,
timeline_event_item_id: TimelineEventItemId,
edited_content: EditedContent,
},
RedactMessage {
room_id: OwnedRoomId,
timeline_event_id: TimelineEventItemId,
reason: Option<String>,
},
/// Room operations
JoinRoom { room_id: OwnedRoomId },
LeaveRoom { room_id: OwnedRoomId },
GetRoomMembers {
room_id: OwnedRoomId,
memberships: RoomMemberships,
local_only: bool,
},
/// User operations
GetUserProfile {
user_id: OwnedUserId,
room_id: Option<OwnedRoomId>,
local_only: bool,
},
IgnoreUser {
ignore: bool,
room_member: RoomMember,
room_id: OwnedRoomId,
},
/// Media operations
FetchAvatar {
mxc_uri: OwnedMxcUri,
on_fetched: fn(AvatarUpdate),
},
FetchMedia {
media_request: MediaRequestParameters,
on_fetched: OnMediaFetchedFn,
destination: MediaCacheEntryRef,
update_sender: Option<crossbeam_channel::Sender<TimelineUpdate>>,
},
/// Typing/read indicators
SendTypingNotice { room_id: OwnedRoomId, typing: bool },
ReadReceipt { room_id: OwnedRoomId, event_id: OwnedEventId },
FullyReadReceipt { room_id: OwnedRoomId, event_id: OwnedEventId },
/// Reactions
ToggleReaction {
room_id: OwnedRoomId,
timeline_event_id: TimelineEventItemId,
reaction: String,
},
/// Subscriptions
SubscribeToTypingNotices { room_id: OwnedRoomId, subscribe: bool },
SubscribeToPinnedEvents { room_id: OwnedRoomId, subscribe: bool },
}Submit Pattern
static REQUEST_SENDER: Mutex<Option<UnboundedSender<MatrixRequest>>> = Mutex::new(None);
/// Submit request from UI thread to async runtime; surface errors without dropping the draft
pub fn submit_async_request(req: MatrixRequest) -> Result<(), String> {
let guard = REQUEST_SENDER.lock().map_err(|_| "request lock poisoned")?;
let sender = guard.as_ref().ok_or("Matrix worker is not ready")?;
sender.send(req).map_err(|_| "Matrix worker has stopped".to_owned())
}
// Usage in UI
let send_result = submit_async_request(MatrixRequest::SendMessage {
room_id: room_id.clone(),
message: RoomMessageEventContent::text_plain(&text),
replied_to: self.reply_to.clone(), // clear draft/reply only after confirmed enqueue
});Worker Task Handler
async fn matrix_worker_task(
mut request_receiver: UnboundedReceiver<MatrixRequest>,
login_sender: Sender<LoginRequest>,
) -> Result<()> {
while let Some(request) = request_receiver.recv().await {
match request {
MatrixRequest::PaginateRoomTimeline { room_id, num_events, direction } => {
let (timeline, sender) = {
let rooms = ALL_JOINED_ROOMS.lock().unwrap();
let Some(room_info) = rooms.get(&room_id) else {
continue; // Room not ready yet
};
(room_info.timeline.clone(), room_info.timeline_update_sender.clone())
};
// Spawn dedicated task for this operation
Handle::current().spawn(async move {
// Notify UI pagination is starting
sender.send(TimelineUpdate::PaginationRunning(direction)).unwrap();
SignalToUI::set_ui_signal();
// Perform pagination
let res = if direction == PaginationDirection::Forwards {
timeline.paginate_forwards(num_events).await
} else {
timeline.paginate_backwards(num_events).await
};
// Send result to UI
match res {
Ok(fully_paginated) => {
sender.send(TimelineUpdate::PaginationIdle {
fully_paginated,
direction,
}).ok();
}
Err(error) => {
sender.send(TimelineUpdate::PaginationError {
error,
direction,
}).ok();
}
}
SignalToUI::set_ui_signal();
});
}
MatrixRequest::JoinRoom { room_id } => {
let Some(client) = get_client() else { continue };
Handle::current().spawn(async move {
let result_action = if let Some(room) = client.get_room(&room_id) {
match room.join().await {
Ok(()) => JoinRoomResultAction::Joined { room_id },
Err(e) => JoinRoomResultAction::Failed { room_id, error: e },
}
} else {
match client.join_room_by_id(&room_id).await {
Ok(_) => JoinRoomResultAction::Joined { room_id },
Err(e) => JoinRoomResultAction::Failed { room_id, error: e },
}
};
Cx::post_action(result_action);
});
}
// ... handle other requests
}
}
Ok(())
}Timeline Updates
TimelineUpdate Enum
pub enum TimelineUpdate {
/// New items added to timeline
NewItems {
new_items: Vector<Arc<TimelineItem>>,
changed_indices: BTreeSet<usize>,
is_append: bool,
},
/// Pagination state changes
PaginationRunning(PaginationDirection),
PaginationIdle {
fully_paginated: bool,
direction: PaginationDirection,
},
PaginationError {
error: Error,
direction: PaginationDirection,
},
/// Message edit result
MessageEdited {
timeline_event_id: TimelineEventItemId,
result: Result<(), Error>,
},
/// Room members fetched
RoomMembersListFetched {
members: Vec<RoomMember>,
sort: PrecomputedMemberSort,
is_local_fetch: bool,
},
/// Unread count updated
NewUnreadMe… (nội dung đầy đủ có trong gói tải về)
Skill liên quan
- robot-framework-skill – Tạo test Robot Framework theo cú pháp keyword-driven bằng Python. Hỗ trợ…
- robots-txt-validator – Robots.txt Validator. Dùng khi làm việc với nội dung robots.txt, crawler và URL cần kiểm…
- ruby – Hướng dẫn mã nguồn chuyên sâu theo ngôn ngữ cho Ruby.
- ruby-pro – Viết mã Ruby đúng chuẩn idiom với metaprogramming, mẫu Rails và tối ưu hiệu năng. Chuyên…
- runapi-cli – Tạo ảnh, video và nhạc/âm thanh bằng AI từ agent sử dụng RunAPI CLI.
- rust – Hướng dẫn mã nguồn chuyên sâu theo ngôn ngữ cho Rust.
- rust-async-patterns – Làm chủ lập trình bất đồng bộ trong Rust với Tokio, async trait, xử lý lỗi và các mẫu…
- rust-pro – Làm chủ Rust 1.75+ với các mẫu async hiện đại, tính năng hệ thống kiểu nâng cao và lập…