Major improvements: rollbacks, testing, docs, and code quality
- Fixed rollback implementation with two-phase approach (remove new, downgrade upgraded) - Added explicit package tracking (newly_installed vs upgraded) - Implemented graceful error handling with fail-fast approach - Added comprehensive test suite (20 tests across 3 test files) - Created centralized APT command execution module (apt_commands.rs) - Added configuration system with dry-run, quiet, and APT options - Reduced code duplication and improved maintainability - Added extensive documentation (rollbacks.md, rollbacks-not-featured.md, ffi-bridge.md) - Created configuration usage example - Updated README with crate usage instructions - All tests passing, clean compilation, production-ready
This commit is contained in:
parent
534c0e87a8
commit
2daad2837d
15 changed files with 1412 additions and 139 deletions
89
docs/rollbacks.md
Normal file
89
docs/rollbacks.md
Normal file
|
|
@ -0,0 +1,89 @@
|
|||
# Rollback Implementation
|
||||
|
||||
This document explains how the rollback functionality works in the APT wrapper.
|
||||
|
||||
## Overview
|
||||
|
||||
The rollback system provides a simple way to undo package installations and upgrades. It tracks what packages were changed during a transaction and can restore the system to its previous state.
|
||||
|
||||
## How It Works
|
||||
|
||||
### Package Tracking
|
||||
|
||||
The `AptTransaction` struct tracks two types of package changes:
|
||||
|
||||
- **`newly_installed`**: Packages that weren't installed before the transaction
|
||||
- **`upgraded`**: Packages that were upgraded, with their previous versions stored
|
||||
|
||||
### Two-Phase Rollback
|
||||
|
||||
When `rollback()` is called, it performs two phases:
|
||||
|
||||
1. **Phase 1 - Remove New Packages**: Uses `apt remove -y` to remove all packages in `newly_installed`
|
||||
2. **Phase 2 - Downgrade Upgraded Packages**: Uses `apt install -y package=oldversion` to restore previous versions
|
||||
|
||||
### Example Usage
|
||||
|
||||
```rust
|
||||
use apt_wrapper::AptTransaction;
|
||||
|
||||
// Create and commit a transaction
|
||||
let mut tx = AptTransaction::new()?;
|
||||
tx.add_package("vim")?;
|
||||
tx.add_package("curl")?;
|
||||
tx.commit()?;
|
||||
|
||||
// Later, rollback the changes
|
||||
tx.rollback()?;
|
||||
```
|
||||
|
||||
### Error Handling
|
||||
|
||||
The rollback system uses a "fail fast" approach:
|
||||
|
||||
- **Critical errors** (package not found, permission denied) cause immediate failure
|
||||
- **Soft errors** (package already removed) generate warnings but continue
|
||||
- If a specific version can't be installed, the package is removed instead
|
||||
|
||||
### Limitations
|
||||
|
||||
This implementation is intentionally simple and handles the most common rollback scenarios:
|
||||
|
||||
- ✅ New package installations
|
||||
- ✅ Package upgrades with available previous versions
|
||||
- ✅ Mixed transactions (some new, some upgrades)
|
||||
|
||||
It does **not** handle:
|
||||
- Complex dependency changes
|
||||
- Configuration file modifications
|
||||
- System state beyond package versions
|
||||
- Concurrent package operations
|
||||
|
||||
For more advanced rollback scenarios, see [rollbacks-not-featured.md](rollbacks-not-featured.md).
|
||||
|
||||
## Implementation Details
|
||||
|
||||
### Data Structures
|
||||
|
||||
```rust
|
||||
pub struct AptTransaction {
|
||||
packages: Vec<String>,
|
||||
newly_installed: HashSet<String>, // packages that weren't installed before
|
||||
upgraded: HashMap<String, String>, // package -> old_version for upgrades
|
||||
}
|
||||
```
|
||||
|
||||
### Key Methods
|
||||
|
||||
- `add_package()`: Adds a package to the transaction
|
||||
- `commit()`: Installs packages and categorizes them as new vs upgraded
|
||||
- `rollback()`: Performs the two-phase rollback process
|
||||
- `changed_packages()`: Returns a list of what was changed
|
||||
|
||||
### State Management
|
||||
|
||||
The tracking fields (`newly_installed`, `upgraded`) are only populated after a successful `commit()`. This ensures the rollback data reflects what actually happened during the transaction.
|
||||
|
||||
## Testing
|
||||
|
||||
The rollback functionality is tested in the test suite, but actual package installation/removal is not performed in tests to avoid side effects on the test environment.
|
||||
Loading…
Add table
Add a link
Reference in a new issue