4.8 KiB
Compilation Notes
Build Cache Issues
If you see compilation errors that appear to be already fixed in the source code, the build cache may be stale.
Clear Build Cache
cargo clean -p <package-name>
# or clean everything
cargo clean
Then rebuild:
cargo build --package <package-name>
SQLx Offline Compilation
SQLx macros (query!, query_as!, query_scalar!) perform compile-time verification of SQL queries against the database schema. This requires either:
- Online mode: Database connection available at compile time
- Offline mode: Pre-generated query metadata cache
Error: Type Annotations Needed
If you see errors like:
error[E0282]: type annotations needed
--> crates/sensor/src/rule_matcher.rs:406:13
|
406 | let result = sqlx::query!(
| ^^^^^^
This means SQLx cannot infer types because:
- No
DATABASE_URLis set - Query metadata cache is missing or outdated
Solution 1: Compile with Database (Recommended)
export DATABASE_URL="postgresql://user:pass@localhost:5432/attune"
cargo build
Solution 2: Update Query Cache
Generate/update the query metadata cache:
export DATABASE_URL="postgresql://user:pass@localhost:5432/attune"
cargo sqlx prepare --workspace
This creates .sqlx/ directory with query metadata that allows offline compilation.
Commit the .sqlx/ directory to version control so others can compile without a database.
Solution 3: Skip SQLx Checks (Not Recommended)
Disable compile-time verification (queries will only be checked at runtime):
cargo build --features sqlx/offline
Common Compilation Errors
1. Mismatched Types in Option Handling
Error:
error[E0308]: mismatched types
--> src/file.rs:100:30
|
100 | let x = result.and_then(|row| row.field)
| ^^^^^^^^^^^^^^ expected `Option<_>`, found `Value`
Cause: and_then expects a function that returns Option<T>, but row.field is already Option<T>.
Solution: Use map().flatten() for nested Options:
// Wrong
let x = result.and_then(|row| row.field);
// Right
let x = result.map(|row| row.field).flatten();
2. SQLx Query Type Inference
Error:
error[E0282]: type annotations needed
--> src/file.rs:50:13
|
50 | let result = sqlx::query!(...);
| ^^^^^^ type must be known at this point
Cause: SQLx needs database connection to infer types.
Solutions:
- Set
DATABASE_URLenvironment variable - Run
cargo sqlx prepareto generate cache - See "SQLx Offline Compilation" section above
3. Missing Traits
Error:
error[E0599]: the method `from_row` exists for struct `X`, but its trait bounds were not satisfied
Cause: Missing #[derive(FromRow)] on model struct.
Solution: Add SQLx derive macro:
use sqlx::FromRow;
#[derive(FromRow)]
pub struct MyModel {
pub id: i64,
pub name: String,
}
Development Workflow
Recommended Setup
-
Keep database running during development:
docker run -d -p 5432:5432 -e POSTGRES_PASSWORD=postgres postgres:14 export DATABASE_URL="postgresql://postgres:postgres@localhost:5432/attune" -
Apply migrations:
sqlx database create sqlx migrate run -
Generate query cache (for CI/CD):
cargo sqlx prepare --workspace git add .sqlx/ git commit -m "Update SQLx query cache" -
Build normally:
cargo build
CI/CD Pipeline
For continuous integration without database access:
- Commit
.sqlx/directory with prepared query metadata - Enable offline mode in CI:
SQLX_OFFLINE=true cargo build --release
Troubleshooting
Build succeeds but tests fail
# Ensure database is running and migrations are applied
export DATABASE_URL="postgresql://postgres:postgres@localhost:5432/attune_test"
sqlx database create
sqlx migrate run
# Run tests
cargo test
Query cache out of sync
# Delete old cache
rm -rf .sqlx/
# Regenerate
export DATABASE_URL="postgresql://postgres:postgres@localhost:5432/attune"
cargo sqlx prepare --workspace
"prepared statement already exists"
This typically indicates multiple connections trying to prepare the same statement. Solutions:
- Use connection pooling (already implemented in
attune_common::db) - Ensure tests use separate database instances
- Clean up connections properly