Problem
All code snippets in guides are currently written inline in markdown. This creates two maintenance problems:
- Snippets drift from reality. Inline code isn't compiled or tested — it can fall out of date with CDK releases, API changes, or best-practice evolution. Bumping a dependency doesn't automatically update the docs.
- No connection to runnable examples. A developer reading a snippet has no direct path to a working project. ICP Ninja can open any Ninja-enabled example from the
dfinity/examples repo via https://icp.ninja/i?g=https://github.com/dfinity/examples/<lang>/<example>, but our docs don't link to it.
Scope
In scope: Guide pages where code snippets can be sourced from compilable, Ninja-openable examples in dfinity/examples. The snippet pipeline (region markers → remark plugin → CodeExample component) with "Open in ICP Ninja" integration.
Out of scope: Guides that are primarily about tooling, specifications, or configuration. Their snippets are CLI commands, Candid type definitions, icp.yaml config, or conceptual patterns — these should remain inline or be synced from their respective source repos (icp-cli docs, Candid spec). Specifically:
- Candid interface — type mappings,
.did files, didc CLI usage → sync from Candid spec
- Canister lifecycle —
icp deploy, upgrade hooks, icp canister commands → sync from icp-cli docs
- Canister settings, snapshots, subnet selection — CLI/config guides
- Custom domains, reproducible builds — infrastructure/config guides
- Rosetta API — exchange integration (REST API, not canister code)
- Agentic development, developer tools, migrating from dfx — tooling guides
Ideal examples design (from scratch)
If we could design the examples repo from scratch to serve both educational docs and ICP Ninja, here's how the examples would map to the full guide structure. Each example is a self-contained, Ninja-openable project in both Motoko and Rust, with // #region markers for doc snippet extraction.
Design principles
- One example per guide topic — each guide has a primary example that demonstrates its core concepts
- Both languages — every example exists in Motoko and Rust (with rare exceptions for language-specific topics)
- Regions map to guide sections — each
#region produces one focused snippet for one guide section
- Progressive complexity — examples in getting-started are minimal; examples in advanced guides build on earlier concepts
- Real functionality — every example does something meaningful, not just "hello world with extra steps"
Getting started
| Example |
Languages |
Guide |
Regions / snippets |
hello_world |
Mo + Rs |
Quickstart |
greeting_function, update_call, query_call |
Backend development
| Example |
Languages |
Guide |
Regions / snippets |
daily_planner |
Mo + Rs |
Data persistence |
stable_storage, crud_operations, schema_evolution |
http_requests |
Mo + Rs |
HTTPS outcalls |
http_get, http_post, transform_function, cycles_cost |
periodic_tasks |
Mo + Rs |
Timers |
one_shot_timer, recurring_timer, timer_cancellation, post_upgrade_reregister |
random_lottery |
Mo + Rs |
Onchain randomness |
raw_rand_call, random_in_range, fair_selection |
certified_kv |
Mo + Rs |
Certified variables |
set_certified, build_witness, query_certified |
llm_chatbot |
Mo + Rs |
Onchain AI |
one_shot_prompt, multi_turn_chat, streaming_response |
Canister calls
| Example |
Languages |
Guide |
Regions / snippets |
inter_canister |
Mo + Rs |
Onchain calls |
basic_call, error_handling, bounded_wait, pub_sub_pattern |
parallel_calls |
Mo + Rs |
Parallel calls |
join_all, composite_query, partial_failure |
frontend_agent |
JS + Mo + Rs |
Offchain calls |
agent_setup, query_call, update_call, auth_delegation |
Frontend development
| Example |
Languages |
Guide |
Regions / snippets |
react_starter |
JS + Mo |
Frontend frameworks |
vite_config, agent_init, canister_call, auth_flow |
photo_gallery |
JS + Rs |
Asset canister |
upload_asset, permissions, spa_routing |
Authentication
| Example |
Languages |
Guide |
Regions / snippets |
ii_login (→ who_am_i) |
JS + Mo + Rs |
Internet Identity |
auth_client_setup, login_flow, delegation_handling, whoami_check |
Testing
| Example |
Languages |
Guide |
Regions / snippets |
tested_canister |
Mo + Rs + JS |
Testing strategies / PocketIC |
unit_test, pocket_ic_setup, deploy_and_call, time_travel, multi_subnet |
Security
| Example |
Languages |
Guide |
Regions / snippets |
access_control |
Mo + Rs |
Access management |
owner_check, role_guard, anonymous_rejection, inspect_message |
safe_upgrades |
Mo + Rs |
Secure upgrades |
pre_upgrade_hook, post_upgrade_hook, stable_migration, candid_compat |
rate_limiter |
Mo + Rs |
DoS prevention |
per_caller_throttle, cycle_drain_guard, inspect_filter |
encrypted_notes |
Mo + Rs + JS |
Encryption with VetKeys |
derive_key, encrypt_client, decrypt_client, access_control_gate |
safe_calls |
Mo + Rs |
Inter-canister call safety |
caller_guard, saga_pattern, callback_trap_handling |
Chain fusion
| Example |
Languages |
Guide |
Regions / snippets |
basic_bitcoin |
Mo + Rs |
Bitcoin integration |
generate_address, get_utxos, create_transaction, sign_and_send |
basic_ethereum |
Mo + Rs |
Ethereum integration |
evm_rpc_call, read_erc20, sign_transaction, send_raw_tx |
basic_solana |
Rs |
Solana integration |
sol_rpc_call, read_balance, sign_transaction |
basic_dogecoin |
Rs |
Dogecoin integration |
generate_address, send_doge |
DeFi
| Example |
Languages |
Guide |
Regions / snippets |
token_transfer |
Mo + Rs |
Token ledgers |
icrc1_transfer, balance_check, icrc2_approve, transfer_from, subaccount_derive |
ckbtc_deposit |
Mo + Rs |
Chain-key tokens |
deposit_flow, check_utxos, withdrawal, subaccount_sweep |
wallet_connect (→ oisy-signer-demo) |
JS |
Wallet integration |
signer_setup, connect_flow, signed_transfer, session_management |
Governance
| Example |
Languages |
Guide |
Regions / snippets |
sns_governed |
Mo + Rs |
Launching / Managing / Testing SNS |
sns_init_config, proposal_submit, neuron_stake, upgrade_proposal |
Canister management
| Example |
Languages |
Guide |
Regions / snippets |
canister_logs |
Mo + Rs |
Canister logs |
debug_print, log_levels, trap_backtrace |
optimized_canister |
Rs |
Canister optimization / Large Wasm |
simd_operation, performance_counter, low_wasm_memory_hook |
Coverage summary
| Guide section |
# guides |
# with example |
# inline-only |
Notes |
| Getting started |
2 |
1 |
1 |
choose-your-path is a navigation page |
| Backends |
6 |
6 |
0 |
Full coverage |
| Canister calls |
4 |
3 |
1 |
candid is a spec/tooling guide |
| Frontends |
4 |
2 |
2 |
certification, custom-domains are config guides |
| Authentication |
2 |
1 |
1 |
verifiable-credentials is specialized |
| Testing |
2 |
1 |
1 |
strategies is an overview page |
| Security |
5 |
5 |
0 |
Full coverage |
| Chain fusion |
4 |
4 |
0 |
Full coverage |
| DeFi |
3 |
2 |
1 |
rosetta is a REST API guide |
| Governance |
3 |
1 |
2 |
SNS testing could share the example |
| Canister management |
8 |
2 |
6 |
Most are CLI/config guides |
| Tools |
3 |
0 |
3 |
All tooling/config guides |
| Total |
48 |
28 |
20 |
58% of guides can source from examples |
Gap analysis vs current dfinity/examples
Examples that already exist and are Ninja-enabled (both languages):
hello_world ✅, canister_logs ✅, send_http_get / send_http_post ✅, daily_planner ✅, llm_chatbot ✅, who_am_i ✅, evm_block_explorer ✅, threshold-ecdsa ✅, query_stats ✅, tokenmania ✅
Examples that already exist and are Ninja-enabled (frontend/JS):
oisy-signer-demo (hosting) ✅ — covers the wallet integration guide (wallet_connect); frontend-only, uses ICRC signer standards via @slide-computer/signer. Demonstrates: signer setup, connect flow, signed ICRC-1 transfers, session management.
Examples that exist but need work:
who_am_i → too minimal for access management guide (needs roles, guards, inspect_message); however, the frontend already covers the full II login flow (AuthClient, login/logout, delegation, whoami) — serves double duty for both access management and Internet Identity guides
daily_planner → may need regions for persistence patterns specifically
token_transfer / token_transfer_from → not Ninja-enabled, uses outdated APIs
periodic_tasks → Rust-only, needs Motoko version
inter-canister-calls → Rust-only, needs Motoko version
basic_bitcoin → Motoko-only on Ninja, needs Rust version
encrypted-notes-dapp-vetkd → exists in both but may be too complex for focused snippets
Examples that need to be created:
certified_kv — certified variables with Merkle tree
random_lottery — onchain randomness patterns
safe_calls — inter-canister call safety (CallerGuard, saga)
rate_limiter — DoS prevention patterns
safe_upgrades — upgrade safety patterns
tested_canister — unit + integration test patterns
frontend_agent — offchain calls with JS agent
ckbtc_deposit — chain-key token deposit/withdrawal
sns_governed — SNS governance example
basic_solana — Solana integration
basic_dogecoin — Dogecoin integration
Proposed solution (technical)
1. Region markers in example source code
Add comment markers in dfinity/examples source files:
Rust:
// #region http_get
#[update]
async fn get_icp_usd_exchange() -> String {
// ...
}
// #endregion http_get
Motoko:
// #region http_get
public func get_icp_usd_exchange() : async Text {
// ...
};
// #endregion http_get
2. Remark plugin for snippet extraction
A custom remark plugin processes a code fence directive at build time:
```rust snippet="send_http_get/src/lib.rs#http_get"
```
The plugin resolves to .sources/examples/rust/send_http_get/src/lib.rs, extracts the region, and injects it as the code block content. Missing regions cause build failures — catching renames/deletions in CI.
3. CodeExample component with ICP Ninja button
<CodeExample
example="send_http_get"
motoko="src/Main.mo#http_get"
rust="src/lib.rs#http_get"
/>
Renders language tabs with the extracted snippet plus an "Open in ICP Ninja" button linking to https://icp.ninja/i?g=https://github.com/dfinity/examples/<lang>/<example>.
4. Changes needed in dfinity/examples
- Add
// #region / // #endregion markers to source files
- Upgrade code quality to doc-grade where needed (modern APIs, educational comments, error handling)
- Both Motoko and Rust implementations for examples referenced by dual-language guides
- Consolidate into existing examples rather than creating docs-only copies
5. What stays inline in docs
- CLI commands and
icp.yaml config (synced from icp-cli docs)
- Candid type definitions and
.did files (synced from Candid spec)
- Conceptual patterns not tied to a runnable project
- Snippets for guides where no Ninja-enabled example exists yet
Suggested prototype
HTTPS outcalls guide (docs/guides/backends/https-outcalls.mdx) is the best starting point:
send_http_get and send_http_post are Ninja-enabled in both languages
- The guide already has substantial dual-language code for GET and POST requests
- Clear mapping: guide sections → example regions
Rollout
- Prototype remark plugin + Astro component using
send_http_get/send_http_post
- Add region markers to those examples in a PR to
dfinity/examples
- Validate: snippets render, Ninja links work, submodule bump updates content
- Migrate remaining guides incrementally
- Expand Ninja coverage (add missing Motoko/Rust versions, create new examples) as needed
Problem
All code snippets in guides are currently written inline in markdown. This creates two maintenance problems:
dfinity/examplesrepo viahttps://icp.ninja/i?g=https://github.com/dfinity/examples/<lang>/<example>, but our docs don't link to it.Scope
In scope: Guide pages where code snippets can be sourced from compilable, Ninja-openable examples in
dfinity/examples. The snippet pipeline (region markers → remark plugin → CodeExample component) with "Open in ICP Ninja" integration.Out of scope: Guides that are primarily about tooling, specifications, or configuration. Their snippets are CLI commands, Candid type definitions,
icp.yamlconfig, or conceptual patterns — these should remain inline or be synced from their respective source repos (icp-cli docs, Candid spec). Specifically:.didfiles,didcCLI usage → sync from Candid specicp deploy, upgrade hooks,icp canistercommands → sync from icp-cli docsIdeal examples design (from scratch)
If we could design the examples repo from scratch to serve both educational docs and ICP Ninja, here's how the examples would map to the full guide structure. Each example is a self-contained, Ninja-openable project in both Motoko and Rust, with
// #regionmarkers for doc snippet extraction.Design principles
#regionproduces one focused snippet for one guide sectionGetting started
hello_worldgreeting_function,update_call,query_callBackend development
daily_plannerstable_storage,crud_operations,schema_evolutionhttp_requestshttp_get,http_post,transform_function,cycles_costperiodic_tasksone_shot_timer,recurring_timer,timer_cancellation,post_upgrade_reregisterrandom_lotteryraw_rand_call,random_in_range,fair_selectioncertified_kvset_certified,build_witness,query_certifiedllm_chatbotone_shot_prompt,multi_turn_chat,streaming_responseCanister calls
inter_canisterbasic_call,error_handling,bounded_wait,pub_sub_patternparallel_callsjoin_all,composite_query,partial_failurefrontend_agentagent_setup,query_call,update_call,auth_delegationFrontend development
react_startervite_config,agent_init,canister_call,auth_flowphoto_galleryupload_asset,permissions,spa_routingAuthentication
ii_login(→who_am_i)auth_client_setup,login_flow,delegation_handling,whoami_checkTesting
tested_canisterunit_test,pocket_ic_setup,deploy_and_call,time_travel,multi_subnetSecurity
access_controlowner_check,role_guard,anonymous_rejection,inspect_messagesafe_upgradespre_upgrade_hook,post_upgrade_hook,stable_migration,candid_compatrate_limiterper_caller_throttle,cycle_drain_guard,inspect_filterencrypted_notesderive_key,encrypt_client,decrypt_client,access_control_gatesafe_callscaller_guard,saga_pattern,callback_trap_handlingChain fusion
basic_bitcoingenerate_address,get_utxos,create_transaction,sign_and_sendbasic_ethereumevm_rpc_call,read_erc20,sign_transaction,send_raw_txbasic_solanasol_rpc_call,read_balance,sign_transactionbasic_dogecoingenerate_address,send_dogeDeFi
token_transfericrc1_transfer,balance_check,icrc2_approve,transfer_from,subaccount_deriveckbtc_depositdeposit_flow,check_utxos,withdrawal,subaccount_sweepwallet_connect(→oisy-signer-demo)signer_setup,connect_flow,signed_transfer,session_managementGovernance
sns_governedsns_init_config,proposal_submit,neuron_stake,upgrade_proposalCanister management
canister_logsdebug_print,log_levels,trap_backtraceoptimized_canistersimd_operation,performance_counter,low_wasm_memory_hookCoverage summary
choose-your-pathis a navigation pagecandidis a spec/tooling guidecertification,custom-domainsare config guidesverifiable-credentialsis specializedstrategiesis an overview pagerosettais a REST API guideGap analysis vs current
dfinity/examplesExamples that already exist and are Ninja-enabled (both languages):
hello_world✅,canister_logs✅,send_http_get/send_http_post✅,daily_planner✅,llm_chatbot✅,who_am_i✅,evm_block_explorer✅,threshold-ecdsa✅,query_stats✅,tokenmania✅Examples that already exist and are Ninja-enabled (frontend/JS):
oisy-signer-demo(hosting) ✅ — covers the wallet integration guide (wallet_connect); frontend-only, uses ICRC signer standards via@slide-computer/signer. Demonstrates: signer setup, connect flow, signed ICRC-1 transfers, session management.Examples that exist but need work:
who_am_i→ too minimal for access management guide (needs roles, guards, inspect_message); however, the frontend already covers the full II login flow (AuthClient, login/logout, delegation, whoami) — serves double duty for both access management and Internet Identity guidesdaily_planner→ may need regions for persistence patterns specificallytoken_transfer/token_transfer_from→ not Ninja-enabled, uses outdated APIsperiodic_tasks→ Rust-only, needs Motoko versioninter-canister-calls→ Rust-only, needs Motoko versionbasic_bitcoin→ Motoko-only on Ninja, needs Rust versionencrypted-notes-dapp-vetkd→ exists in both but may be too complex for focused snippetsExamples that need to be created:
certified_kv— certified variables with Merkle treerandom_lottery— onchain randomness patternssafe_calls— inter-canister call safety (CallerGuard, saga)rate_limiter— DoS prevention patternssafe_upgrades— upgrade safety patternstested_canister— unit + integration test patternsfrontend_agent— offchain calls with JS agentckbtc_deposit— chain-key token deposit/withdrawalsns_governed— SNS governance examplebasic_solana— Solana integrationbasic_dogecoin— Dogecoin integrationProposed solution (technical)
1. Region markers in example source code
Add comment markers in
dfinity/examplessource files:Rust:
Motoko:
2. Remark plugin for snippet extraction
A custom remark plugin processes a code fence directive at build time:
The plugin resolves to
.sources/examples/rust/send_http_get/src/lib.rs, extracts the region, and injects it as the code block content. Missing regions cause build failures — catching renames/deletions in CI.3. CodeExample component with ICP Ninja button
Renders language tabs with the extracted snippet plus an "Open in ICP Ninja" button linking to
https://icp.ninja/i?g=https://github.com/dfinity/examples/<lang>/<example>.4. Changes needed in
dfinity/examples// #region/// #endregionmarkers to source files5. What stays inline in docs
icp.yamlconfig (synced from icp-cli docs).didfiles (synced from Candid spec)Suggested prototype
HTTPS outcalls guide (
docs/guides/backends/https-outcalls.mdx) is the best starting point:send_http_getandsend_http_postare Ninja-enabled in both languagesRollout
send_http_get/send_http_postdfinity/examples