MDBOOK009 - Invalid Playground Configuration
Severity: Warning
Category: mdBook-specific
Auto-fix: Not available
Rule Description
This rule validates {{#playground}}
directives and playground configuration in code blocks. It ensures proper syntax for making code examples editable and runnable in the Rust Playground.
Why This Rule Exists
Valid playground configuration is important because:
- Enables interactive code examples for readers
- Ensures code can run in the Rust Playground
- Provides hands-on learning experiences
- Validates that examples are executable
- Maintains consistent playground behavior
Examples
❌ Incorrect (violates rule)
<!-- Invalid directive syntax -->
{{#playgrounds ./file.rs}}
{{playground ./file.rs}}
<!-- Invalid playground attributes -->
```rust,playground
fn main() {
println!("Hello");
}
```
<!-- Missing file -->
{{#playground ./missing.rs}}
✅ Correct
<!-- Include file as playground -->
{{#playground ./examples/hello.rs}}
<!-- Inline editable code -->
```rust,editable
fn main() {
println!("Hello, world!");
}
```
<!-- Non-editable but runnable -->
```rust,no_run
fn main() {
// This compiles but won't run
}
```
<!-- Editable with hidden lines -->
```rust,editable
# fn hidden_setup() {}
fn main() {
println!("Visible code");
}
```
Playground Attributes
Code Block Attributes
Attribute | Description |
---|---|
editable | Makes code block editable in browser |
no_run | Code compiles but doesn't run |
compile_fail | Example that should fail compilation |
ignore | Code block is not tested |
should_panic | Code should panic when run |
Examples with Attributes
<!-- Editable example -->
```rust,editable
fn main() {
let x = 5;
println!("x = {}", x);
}
```
<!-- Example that should fail -->
```rust,compile_fail
fn main() {
let x: i32 = "not a number";
}
```
<!-- Example that panics -->
```rust,should_panic
fn main() {
panic!("This is expected!");
}
```
Configuration
# book.toml
[output.html.playground]
editable = true # Make code blocks editable by default
copyable = true # Add copy button to code blocks
copy-js = true # Include JavaScript for copy functionality
line-numbers = false # Show line numbers in code blocks
[MDBOOK009]
require_editable = false # Require editable attribute (default: false)
validate_compilation = false # Check if code compiles (default: false)
Common Issues and Solutions
Issue: Playground Not Enabled
# book.toml - Enable playground
[output.html.playground]
editable = true
Issue: Code Doesn't Compile
<!-- Missing main function -->
```rust,editable
println!("Hello"); // Error: not in a function
```
<!-- Fixed -->
```rust,editable
fn main() {
println!("Hello");
}
```
Issue: Hidden Lines Shown
<!-- Wrong: Hidden lines visible in playground -->
```rust,editable
# use std::io;
# fn setup() {}
fn main() {
// User code
}
```
<!-- Note: Hidden lines work but are still editable -->
Best Practices
- Provide complete examples: Include all necessary code
- Use hidden lines sparingly: Only for necessary boilerplate
- Test in playground: Verify examples work in actual playground
- Add context: Explain what users should try changing
- Keep examples focused: One concept per playground
Interactive Example Template
## Try It Yourself
Modify the code below to experiment with different values:
```rust,editable
fn calculate_area(width: f64, height: f64) -> f64 {
width * height
}
fn main() {
// Try changing these values!
let width = 10.0;
let height = 5.0;
let area = calculate_area(width, height);
println!("Area: {} square units", area);
// Challenge: Add a perimeter calculation
}
```
**Suggestions to try:**
- Change the dimensions
- Add a perimeter function
- Handle negative values
Advanced Usage
Custom Playground URL
# book.toml
[output.html.playground]
editable = true
site = "https://play.rust-lang.org"
Playground with Dependencies
<!-- Note: Dependencies must be available in playground -->
```rust,editable
// Available in playground: rand, regex, lazy_static, etc.
use rand::Rng;
fn main() {
let mut rng = rand::thread_rng();
let n: u32 = rng.gen_range(0..10);
println!("Random number: {}", n);
}
```
When to Disable
Consider disabling this rule if:
- Your book doesn't use playground features
- You're targeting offline readers
- You have custom code execution environment
- Your examples require local dependencies
Disable in Config
# .mdbook-lint.toml
disabled_rules = ["MDBOOK009"]
Disable Inline
<!-- mdbook-lint-disable MDBOOK009 -->
{{#playground ./complex-example.rs}}
<!-- mdbook-lint-enable MDBOOK009 -->
Troubleshooting
Playground Not Working
- Check
book.toml
configuration - Verify code compiles standalone
- Test in actual Rust Playground
- Check browser console for errors
Common Error Messages
Error | Solution |
---|---|
"Playground not configured" | Enable in book.toml |
"Code doesn't compile" | Add missing imports/main function |
"File not found" | Check file path in directive |
"Invalid attribute" | Use supported attributes only |
Related Rules
- MDBOOK007 - Include directive validation
- MDBOOK008 - Rustdoc include validation
- MD040 - Code block language tags