### Python API - Quick Start Source: https://tzst.xi-xu.me/quickstart.html A quick start guide for using the tzst Python library, demonstrating how to create, extract, list, and test archives. ```APIDOC ## Python API - Quick Start This section demonstrates the basic usage of the tzst Python API. ### Create an archive ```python from tzst import create_archive create_archive("backup.tzst", ["documents/", "photos/"], compression_level=5) ``` ### Extract an archive ```python from tzst import extract_archive extract_archive("backup.tzst", "restore/") ``` ### List contents ```python from tzst import list_archive contents = list_archive("backup.tzst", verbose=True) for item in contents: print(f"{item['name']} - {item['size']} bytes") ``` ### Test integrity ```python from tzst import test_archive is_valid = test_archive("backup.tzst") print(f"Archive is {'valid' if is_valid else 'corrupted'}") ``` ``` -------------------------------- ### Set up Development Environment Source: https://tzst.xi-xu.me/development.html Clone the repository and install the project in editable mode with development dependencies. ```bash git clone https://github.com/xixu-me/tzst.git cd tzst pip install -e .[dev] ``` -------------------------------- ### Build HTML Documentation Source: https://tzst.xi-xu.me/development.html Navigate to the docs directory, install dependencies, and build the HTML documentation. ```bash # Navigate to docs directory cd docs # Install documentation dependencies pip install -r requirements.txt # Build HTML documentation make html ``` -------------------------------- ### Install tzst using uv Source: https://tzst.xi-xu.me/quickstart.html Install the tzst tool using uv, a fast Python package installer and tool manager. This is the recommended method. ```bash uv tool install tzst ``` -------------------------------- ### Install tzst from Source Source: https://tzst.xi-xu.me/quickstart.html Clone the tzst repository and install it from source using pip. This method is useful for development or when needing the latest unreleased changes. ```bash git clone https://github.com/xixu-me/tzst.git cd tzst pip install . ``` -------------------------------- ### Test Function with Fixtures Example Source: https://tzst.xi-xu.me/development.html Example of a test function utilizing fixtures for sample archive path and a temporary directory. ```python def test_extract_archive(sample_archive_path, temp_dir): ``` -------------------------------- ### Command Line Interface - Create Archives Source: https://tzst.xi-xu.me/quickstart.html Examples for creating archives with different compression levels, from the current directory, and specifying output locations. ```APIDOC ## Command Line Interface - Create Archives Examples for creating archives. ### Create archive with default compression (level 3) ```bash tzst a backup.tzst documents/ photos/ ``` ### Create with high compression ```bash tzst a backup.tzst documents/ photos/ --compression-level 9 ``` ### Create from current directory ```bash tzst a project.tzst . ``` ### Specify different output location ```bash tzst a /backups/data.tzst /home/user/important/ ``` ``` -------------------------------- ### Set up tzst Development Environment Source: https://tzst.xi-xu.me/index.html Clone the tzst repository, navigate to the directory, and install the package in editable mode with development dependencies. Run pytest to execute the test suite. ```bash git clone https://github.com/xixu-me/tzst.git cd tzst pip install -e .[dev] pytest ``` -------------------------------- ### Install tzst using pip or uv Source: https://tzst.xi-xu.me/index.html Install the tzst library using pip or the recommended uv tool. These commands ensure you have the necessary package for using tzst in your Python projects. ```bash # Install from PyPI pip install tzst # Or using uv (recommended) uv tool install tzst ``` -------------------------------- ### Test Function Example Source: https://tzst.xi-xu.me/development.html Example of a descriptive test function name for creating an archive with a specific compression level. ```python def test_create_archive_with_compression_level_9(): ``` -------------------------------- ### Install tzst using pip Source: https://tzst.xi-xu.me/quickstart.html Install the tzst package using pip. This is a straightforward method for users with Python and pip installed. ```bash pip install tzst ``` -------------------------------- ### Archive Creation Commands Source: https://tzst.xi-xu.me/examples.html Command-line options for creating archives, including using `uvx` for execution without installation and specifying compression levels. ```bash # Basic archive creation tzst a backup.tzst documents/ photos/ # Or with uvx (no installation needed) uvx tzst a backup.tzst documents/ photos/ # Create with specific compression level tzst a backup.tzst documents/ photos/ -l 6 uvx tzst a backup.tzst documents/ photos/ -l 6 # Create from multiple sources tzst a complete-backup.tzst /home/user/documents /home/user/photos /etc/config # Create with verbose output tzst a backup.tzst documents/ photos/ -v ``` -------------------------------- ### Makefile Example for tzst Compression Source: https://tzst.xi-xu.me/performance.html Demonstrates using the `tzst` command-line tool in a Makefile for different compression levels: level 1 for development, level 9 for production, and level 6 for CI/CD artifacts. ```makefile # Fast compression for development build-dev: tzst a build-dev.tzst build/ -l 1 # Production compression build-prod: tzst a build-prod.tzst build/ -l 9 # CI/CD artifacts artifacts: tzst a artifacts.tzst dist/ logs/ -l 6 ``` -------------------------------- ### tzst Python API Quick Start Source: https://tzst.xi-xu.me/quickstart.html Demonstrates the basic usage of the tzst Python API for creating, extracting, listing, and testing archives. ```python from tzst import create_archive, extract_archive, list_archive, test_archive # Create an archive create_archive("backup.tzst", ["documents/", "photos/"], compression_level=5) # Extract an archive extract_archive("backup.tzst", "restore/") # List contents contents = list_archive("backup.tzst", verbose=True) for item in contents: print(f"{item['name']} - {item['size']} bytes") # Test integrity is_valid = test_archive("backup.tzst") print(f"Archive is {'valid' if is_valid else 'corrupted'}") ``` -------------------------------- ### Command Line Interface - List Contents Source: https://tzst.xi-xu.me/quickstart.html Examples for listing archive contents, including simple listings, detailed listings with verbose output, and efficient streaming for large archives. ```APIDOC ## Command Line Interface - List Contents Examples for listing archive contents. ### Simple listing ```bash tzst l backup.tzst ``` ### Detailed listing with file info ```bash tzst l backup.tzst --verbose ``` ### Stream large archives efficiently ```bash tzst l huge-archive.tzst --streaming ``` ``` -------------------------------- ### Mark Test as Integration Source: https://tzst.xi-xu.me/development.html Example of applying the 'integration' marker to a test function. ```python @pytest.mark.integration def test_full_archive_workflow(): ``` -------------------------------- ### Example Conventional Commit Messages Source: https://tzst.xi-xu.me/development.html Examples of valid commit messages following the conventional commit format for different types of changes. ```markdown feat(core): add streaming compression support ``` ```markdown fix(cli): handle invalid archive paths gracefully ``` ```markdown docs(readme): update installation instructions ``` -------------------------------- ### GitHub Actions Example for tzst Archive Creation Source: https://tzst.xi-xu.me/performance.html Shows how to create a release archive using `tzst` within a GitHub Actions workflow, specifying compression level 9. ```yaml - name: Create release archive run: | tzst a release-${{ github.ref_name }}.tzst \ build/ docs/ \ --compression-level 9 ``` -------------------------------- ### Branch Naming Conventions Source: https://tzst.xi-xu.me/development.html Examples of descriptive branch names for different types of contributions. ```git feature/add-streaming-mode fix/handle-corrupted-archives docs/improve-api-documentation test/add-compression-tests ``` -------------------------------- ### Command Line Interface - Extract Archives Source: https://tzst.xi-xu.me/quickstart.html Examples for extracting archives to the current directory, a specific directory, extracting specific files, and handling conflicts. ```APIDOC ## Command Line Interface - Extract Archives Examples for extracting archives. ### Extract to current directory ```bash tzst x backup.tzst ``` ### Extract to specific directory ```bash tzst x backup.tzst --output /restore/ ``` ### Extract specific files only ```bash tzst x backup.tzst documents/report.pdf photos/vacation.jpg ``` ### Extract with conflict resolution ```bash tzst x backup.tzst --conflict-resolution skip ``` ``` -------------------------------- ### Build HTML Documentation on Windows Source: https://tzst.xi-xu.me/development.html Use the make.bat script to build HTML documentation on Windows. ```bash # On Windows, use: make.bat html ``` -------------------------------- ### Create First Archive with Python Source: https://tzst.xi-xu.me/examples.html Use the `create_archive` function for simple archive creation or with custom compression levels. ```python from tzst import create_archive # Simple archive creation files_to_archive = ["document.pdf", "photos/", "config.json"] create_archive("my-archive.tzst", files_to_archive) # With custom compression level create_archive("high-compression.tzst", files_to_archive, compression_level=9) ``` -------------------------------- ### Basic Archive Creation Source: https://tzst.xi-xu.me/api/cli.html Use this command to create a new archive named 'backup.tzst' containing the 'documents/' and 'photos/' directories. ```bash tzst a backup.tzst documents/ photos/ ``` -------------------------------- ### Create Archive with Command Line Source: https://tzst.xi-xu.me/examples.html Equivalent command-line operations for creating archives, including specifying compression levels. ```bash # Create archive tzst a my-archive.tzst document.pdf photos/ config.json # With high compression tzst a high-compression.tzst document.pdf photos/ config.json -l 9 ``` -------------------------------- ### Get Archive Members Source: https://tzst.xi-xu.me/api/core.html Retrieves information about the members within the archive. ```APIDOC ## getmembers() -> list[TarInfo] ### Description Get list of all members in the archive. ``` ```APIDOC ## getnames() -> list[str] ### Description Get list of all member names in the archive. ``` -------------------------------- ### TzstArchive Class Source: https://tzst.xi-xu.me/api/core.html Documentation for the TzstArchive class, its key features, and usage examples. ```APIDOC ## TzstArchive Class ### Description Represents an archive for Tzst operations. Provides methods for managing archive contents. ### Key Features - Initialization with archive path. - Methods for adding, extracting, and listing files. ### Usage Examples ```python # Example of creating and using TzstArchive archive = TzstArchive("my_archive.tzst") archive.add_file("file.txt") archive.extract_all("output_dir") ``` ``` -------------------------------- ### Prepare Archive Creation Inputs Source: https://tzst.xi-xu.me/_modules/tzst/cli.html Prepares and validates inputs for archive creation, including archive path, files, compression level, and temporary file usage. ```python def _prepare_archive_creation(args) -> tuple[Path, list[Path], int, bool] | int: """Prepare and validate inputs for archive creation. Args: args: Parsed command line arguments Returns: tuple or int: Either (archive_path, files, compression_level, use_temp_file) or error code if validation fails """ archive_path = Path(args.archive) files = _process_file_paths(args.files) # Validate files missing_files = _validate_files(files) if missing_files: return _emit_error( args, f"Error: Files not found - {', '.join(map(str, missing_files))}", error_type="files_not_found", details={"missing_files": [str(path) for path in missing_files]}, ) compression_level, use_temp_file = _extract_add_params(args) return archive_path, files, compression_level, use_temp_file ``` -------------------------------- ### Command Line Interface - Basic Usage Source: https://tzst.xi-xu.me/quickstart.html Demonstrates the fundamental commands for creating, extracting, listing, and testing archives using the tzst CLI. ```APIDOC ## Command Line Interface - Basic Usage This section shows the basic commands for interacting with tzst archives. ### Create an archive ```bash tzst a archive.tzst file1.txt file2.txt directory/ ``` ### Extract an archive ```bash tzst x archive.tzst ``` ### List archive contents ```bash tzst l archive.tzst ``` ### Test archive integrity ```bash tzst t archive.tzst ``` ``` -------------------------------- ### Get Tar Archive Member Names Source: https://tzst.xi-xu.me/_modules/tzst/core.html Retrieves a list of names for all members in the archive. Requires the archive to be open and in read mode. ```python if not self._tarfile: raise RuntimeError("Archive not open") if not self.mode.startswith("r"): raise RuntimeError("Archive not open for reading") return self._tarfile.getnames() ``` -------------------------------- ### Get Tar Archive Members Source: https://tzst.xi-xu.me/_modules/tzst/core.html Retrieves a list of TarInfo objects for all members within the archive. Ensures the archive is open for reading. ```python if not self.mode.startswith("r"): raise RuntimeError("Archive not open for reading") return self._tarfile.getmembers() ``` -------------------------------- ### Get list of all members in the archive Source: https://tzst.xi-xu.me/_modules/tzst/core.html Retrieves a list of all TarInfo objects representing members within the archive. Requires the archive to be open. ```python def getmembers(self) -> list[tarfile.TarInfo]: """Get list of all members in the archive.""" if not self._tarfile: raise RuntimeError("Archive not open") ``` -------------------------------- ### Create and Read Tzst Archives Source: https://tzst.xi-xu.me/api/core.html Demonstrates creating a new archive with files and directories, and then reading an existing archive to list contents, test integrity, and extract all files. ```python with TzstArchive("backup.tzst", "w", compression_level=6) as archive: archive.add("important_file.txt") archive.add("documents/", recursive=True) with TzstArchive("backup.tzst", "r") as archive: contents = archive.list(verbose=True) is_valid = archive.test() archive.extractall("restore/") ``` -------------------------------- ### Create tzst Archive with Default Compression Source: https://tzst.xi-xu.me/quickstart.html Create a tzst archive named 'backup.tzst' containing the 'documents/' and 'photos/' directories using the default compression level. ```bash # Create archive with default compression (level 3) tzst a backup.tzst documents/ photos/ ``` -------------------------------- ### Extract a single file from the archive Source: https://tzst.xi-xu.me/_modules/tzst/core.html Use this method to get a file-like object for a specific member. Ensure the archive is open and in read mode. ```python def extractfile(self, member: str | tarfile.TarInfo): """ Extract a file-like object from the archive. Args: member: Member name or TarInfo object Returns: File-like object or None if member is not a file """ if not self._tarfile: raise RuntimeError("Archive not open") if not self.mode.startswith("r"): raise RuntimeError("Archive not open for reading") return self._tarfile.extractfile(member) ``` -------------------------------- ### Create tzst Archive from Current Directory Source: https://tzst.xi-xu.me/quickstart.html Create a tzst archive named 'project.tzst' containing all files and directories from the current working directory. ```bash # Create from current directory tzst a project.tzst . ``` -------------------------------- ### List Archive Contents with Python Source: https://tzst.xi-xu.me/examples.html Use `list_archive` to get a simple list of contents or a detailed listing with timestamps and permissions when `verbose` is True. ```python from tzst import list_archive # Simple listing contents = list_archive("my-archive.tzst") for item in contents: print(f"{item['name']} ({item['size']} bytes)") # Detailed listing with timestamps and permissions contents = list_archive("my-archive.tzst", verbose=True) for item in contents: print(f"{item['name']:30} {item['size']:>10} bytes {item['mtime']}") ``` -------------------------------- ### cmd_version Source: https://tzst.xi-xu.me/api/cli.html Displays version information and system details. ```APIDOC ## cmd_version ### Description Displays version information and system details. ``` -------------------------------- ### Tzst Error Handling Source: https://tzst.xi-xu.me/quickstart.html Provides an example of how to handle potential errors during archive creation, such as compression failures or general archive operation errors, using try-except blocks. ```python from tzst import create_archive, TzstArchiveError, TzstCompressionError try: create_archive("backup.tzst", ["documents/"]) except TzstCompressionError as e: print(f"Compression failed: {e}") except TzstArchiveError as e: print(f"Archive operation failed: {e}") except Exception as e: print(f"Unexpected error: {e}") ``` -------------------------------- ### getnames Source: https://tzst.xi-xu.me/_modules/tzst/core.html Retrieves a list of all member names within the archive. This method is useful for quickly getting an overview of the archive's contents without fetching detailed information. ```APIDOC ## getnames ### Description Get list of all member names in the archive. ### Method ```python def getnames(self) -> list[str]: ``` ### Returns - list[str]: A list of strings, where each string is the name of a member in the archive. ``` -------------------------------- ### Python API - Using the TzstArchive Class Source: https://tzst.xi-xu.me/quickstart.html Demonstrates advanced archive management using the TzstArchive class, including creating archives in write mode and adding files recursively. ```APIDOC ## Python API - Using the TzstArchive Class This section shows how to use the `TzstArchive` class for more control over archive operations. ### Create a new archive ```python from tzst import TzstArchive with TzstArchive("data.tzst", "w", compression_level=6) as archive: archive.add("file.txt") archive.add("directory/", recursive=True) # Add with custom archive name archive.add("config/prod.yaml", arcname="config.yaml") ``` ``` -------------------------------- ### Create Archives with Different Compression Levels Source: https://tzst.xi-xu.me/performance.html Use `create_archive` with varying `compression_level` arguments to balance speed and file size. Levels 1-3 are fast with larger files, while levels 15-22 offer maximum compression at the cost of speed. ```python from tzst import create_archive # For temporary files or frequent operations create_archive("temp.tzst", files, compression_level=1) # Balanced default (recommended) create_archive("backup.tzst", files, compression_level=3) # Long-term storage create_archive("archive.tzst", files, compression_level=9) # Maximum compression for critical space savings create_archive("minimal.tzst", files, compression_level=22) ``` -------------------------------- ### Advanced Archive Creation with TzstArchive Class Source: https://tzst.xi-xu.me/examples.html Use the `TzstArchive` class for fine-grained control over archive creation, including adding individual files, directories recursively, and custom archive names. ```python from tzst import TzstArchive from pathlib import Path # Create archive with fine-grained control with TzstArchive("project-backup.tzst", "w", compression_level=6) as archive: # Add individual files archive.add("README.md") archive.add("LICENSE") # Add directories recursively archive.add("src/", recursive=True) archive.add("tests/", recursive=True) # Add with custom archive names archive.add("config/production.yaml", arcname="config.yaml") archive.add("/tmp/build-info.json", arcname="build-info.json") ``` -------------------------------- ### Run Test Suite Source: https://tzst.xi-xu.me/development.html Execute the project's test suite using pytest and check code quality with ruff for formatting and linting. ```python python -m pytest ``` ```python ruff check . ``` ```python ruff format --check . ``` -------------------------------- ### TzstArchive Initialization Source: https://tzst.xi-xu.me/_modules/tzst/core.html Initializes a TzstArchive object for managing .tzst/.tar.zst archives. Supports read ('r'), write ('w') modes. Append ('a') mode is not supported. Compression level and streaming options can be configured. ```APIDOC ## TzstArchive ### Description A class for handling .tzst/.tar.zst archives. ### Methods #### __init__(self, filename: str | Path, mode: str = "r", compression_level: int = 3, streaming: bool = False) Initialize a TzstArchive. **Parameters** - **filename** (str | Path) - Path to the archive file. - **mode** (str) - Open mode ('r', 'w', 'a'). Defaults to 'r'. - **compression_level** (int) - Zstandard compression level (1-22). Defaults to 3. - **streaming** (bool) - If True, use streaming mode for reading (reduces memory usage for very large archives but may limit some tarfile operations that require seeking. Recommended for archives > 100MB). Defaults to False. **Raises** - ValueError: If an invalid mode or compression level is provided. - NotImplementedError: If append mode ('a') is used. ``` -------------------------------- ### Custom Conflict Resolution for Archive Extraction Source: https://tzst.xi-xu.me/examples.html Implement custom logic to handle file conflicts during archive extraction. This example defines a handler that replaces files older than 30 days. ```python from tzst import extract_archive, ConflictResolution from pathlib import Path import time def custom_conflict_handler(target_path: Path) -> ConflictResolution: """Custom logic for handling file conflicts.""" # Check file age if target_path.exists(): file_age_days = (time.time() - target_path.stat().st_mtime) / (24 * 3600) if file_age_days > 30: print(f"Replacing old file: {target_path}") return ConflictResolution.REPLACE else: print(f"Keeping newer file: {target_path}") return ConflictResolution.SKIP return ConflictResolution.REPLACE # Use custom callback extract_archive("archive.tzst", "output/", conflict_resolution=ConflictResolution.ASK, interactive_callback=custom_conflict_handler) ``` -------------------------------- ### Basic tzst Command Line Operations Source: https://tzst.xi-xu.me/quickstart.html Demonstrates the fundamental command-line operations for tzst: creating an archive, extracting an archive, listing contents, and testing integrity. ```bash # Create an archive tzst a archive.tzst file1.txt file2.txt directory/ # Extract an archive tzst x archive.tzst # List archive contents tzst l archive.tzst # Test archive integrity tzst t archive.tzst ``` -------------------------------- ### Create a Backup Archive with tzst Source: https://tzst.xi-xu.me/quickstart.html Use this script to create a compressed backup of specified directories. It generates a timestamped archive file. ```python #!/usr/bin/env python3 from pathlib import Path from datetime import datetime from tzst import create_archive def create_backup(): timestamp = datetime.now().strftime("%Y%m%d_%H%M%S") backup_name = f"backup_{timestamp}.tzst" # Backup important directories directories = ["documents/", "projects/", "config/"] print(f"Creating backup: {backup_name}") create_archive(backup_name, directories, compression_level=6) print(f"Backup created: {Path(backup_name).stat().st_size / 1024 / 1024:.1f} MB") if __name__ == "__main__": create_backup() ``` -------------------------------- ### List Contents of a Tzst Archive Source: https://tzst.xi-xu.me/_modules/tzst/core.html Use this function to get a list of files within a .tzst archive. Supports verbose output for detailed information and streaming mode for memory efficiency with large archives. ```python import shutil from tzst.archive import TzstArchive def list_archive( archive_path: str | Path, verbose: bool = False, streaming: bool = False ) -> list[dict]: """ List contents of a .tzst archive. Args: archive_path: Path to the archive verbose: Include detailed information streaming: If True, use streaming mode (memory efficient for large archives) Returns: List of file information dictionaries See Also: :meth:`TzstArchive.list`: Method for listing an open archive """ with TzstArchive(archive_path, "r", streaming=streaming) as archive: return archive.list(verbose=verbose) ``` -------------------------------- ### Archive Logs by Date in Python Source: https://tzst.xi-xu.me/examples.html Use this script to archive log files older than a specified number of days. Ensure the 'tzst' library is installed. Log files are identified by filename patterns or modification times. ```python #!/usr/bin/env python3 """ Archive and compress log files by date. """ import re from datetime import datetime, timedelta from pathlib import Path from tzst import create_archive def archive_logs_by_date(log_dir, archive_dir, days_old=7): """Archive log files older than specified days.""" log_dir = Path(log_dir) archive_dir = Path(archive_dir) archive_dir.mkdir(parents=True, exist_ok=True) cutoff_date = datetime.now() - timedelta(days=days_old) # Group log files by date log_groups = {} log_pattern = re.compile(r"(\d{4}-\d{2}-\d{2})") for log_file in log_dir.glob("*.log"): # Try to extract date from filename or modification time date_match = log_pattern.search(log_file.name) if date_match: file_date_str = date_match.group(1) try: file_date = datetime.strptime(file_date_str, "%Y-%m-%d") except ValueError: # Fall back to modification time file_date = datetime.fromtimestamp(log_file.stat().st_mtime) else: # Use modification time file_date = datetime.fromtimestamp(log_file.stat().st_mtime) # Skip recent files if file_date >= cutoff_date: continue # Group by date date_key = file_date.strftime("%Y-%m-%d") if date_key not in log_groups: log_groups[date_key] = [] log_groups[date_key].append(log_file) # Create archives for each date group archived_files = [] for date_key, files in log_groups.items(): archive_name = f"logs_{date_key}.tzst" archive_path = archive_dir / archive_name # Skip if archive already exists if archive_path.exists(): print(f"Archive already exists: {archive_name}") continue print(f"Archiving {len(files)} log files for {date_key}") try: # Create archive with maximum compression (logs compress well) create_archive(archive_path, [str(f) for f in files], compression_level=22) # Verify archive from tzst import test_archive if test_archive(archive_path): # Remove original files after successful archiving for log_file in files: log_file.unlink() archived_files.append(log_file) file_size = archive_path.stat().st_size / 1024 print(f"Created {archive_name} ({file_size:.1f} KB)") else: print(f"Archive validation failed for {archive_name}") archive_path.unlink() except Exception as e: print(f"Failed to archive logs for {date_key}: {e}") print(f"Archived {len(archived_files)} log files") # Usage if __name__ == "__main__": archive_logs_by_date("/var/log", "/var/archives", days_old=7) ``` -------------------------------- ### Archive Creation with High Compression and No Atomic Source: https://tzst.xi-xu.me/api/cli.html Create an archive with a high compression level (15) and disable atomic operations for potentially faster, but less safe, creation. ```bash tzst a backup.tzst files/ -l 15 --no-atomic ``` -------------------------------- ### Python Automated Backup Script Source: https://tzst.xi-xu.me/examples.html This script automates daily backups of specified directories. It creates compressed archives, validates them, and removes backups older than a defined retention period. Ensure the 'tzst' library is installed. ```python #!/usr/bin/env python3 """ Daily backup script with rotation and validation. """ import os import sys from datetime import datetime, timedelta from pathlib import Path from tzst import create_archive, test_archive class BackupManager: def __init__(self, source_dirs, backup_dir, retention_days=30): self.source_dirs = [Path(d) for d in source_dirs] self.backup_dir = Path(backup_dir) self.retention_days = retention_days self.backup_dir.mkdir(parents=True, exist_ok=True) def create_backup(self): """Create a new backup with timestamp.""" timestamp = datetime.now().strftime("%Y%m%d_%H%M%S") backup_name = f"backup_{timestamp}.tzst" backup_path = self.backup_dir / backup_name print(f"Creating backup: {backup_name}") # Collect all existing files files_to_backup = [] for source_dir in self.source_dirs: if source_dir.exists(): files_to_backup.append(str(source_dir)) else: print(f"Warning: Source directory not found: {source_dir}") if not files_to_backup: print("No files to backup!") return None try: # Create backup with high compression for storage efficiency create_archive(backup_path, files_to_backup, compression_level=9) # Validate the backup if test_archive(backup_path): file_size = backup_path.stat().st_size / (1024 * 1024) print(f"Backup created and validated: {file_size:.1f} MB") return backup_path else: print("Backup validation failed!") backup_path.unlink() # Remove invalid backup return None except Exception as e: print(f"Backup failed: {e}") return None def cleanup_old_backups(self): """Remove backups older than retention period.""" cutoff_date = datetime.now() - timedelta(days=self.retention_days) removed_count = 0 for backup_file in self.backup_dir.glob("backup_*.tzst"): # Extract timestamp from filename try: timestamp_str = backup_file.stem.split("_", 1)[1] file_date = datetime.strptime(timestamp_str, "%Y%m%d_%H%M%S") if file_date < cutoff_date: backup_file.unlink() removed_count += 1 print(f"Removed old backup: {backup_file.name}") except (ValueError, IndexError): print(f"Warning: Could not parse backup date: {backup_file.name}") print(f"Cleaned up {removed_count} old backups") def run_backup(self): """Run complete backup process.""" print("Starting backup process...") backup_path = self.create_backup() if backup_path: self.cleanup_old_backups() print("Backup process completed successfully!") return True else: print("Backup process failed!") return False # Configuration if __name__ == "__main__": # Customize these paths for your setup BACKUP_SOURCES = [ "~/Documents", "~/Projects", "~/Pictures", "/etc", # System configs (Linux/macOS) ] BACKUP_DESTINATION = "~/Backups" RETENTION_DAYS = 30 # Expand user paths sources = [os.path.expanduser(path) for path in BACKUP_SOURCES] destination = os.path.expanduser(BACKUP_DESTINATION) # Run backup backup_manager = BackupManager(sources, destination, RETENTION_DAYS) success = backup_manager.run_backup() sys.exit(0 if success else 1) ``` -------------------------------- ### Execute Archive Creation Source: https://tzst.xi-xu.me/_modules/tzst/cli.html Executes the archive creation process, handling output and using atomic file operations by default. ```python def _execute_archive_creation( args, archive_path: Path, files: list[Path], compression_level: int, use_temp_file: bool, ) -> int: """Execute the archive creation process. Args: archive_path: Path where archive will be created files: List of files to add to archive compression_level: Compression level to use use_temp_file: Whether to use atomic file operations Returns: int: Exit code (0 for success, non-zero for failure) """ # Normalize archive path to show the correct final filename normalized_archive_path = _normalize_archive_path(archive_path) if not _wants_json_output(args): print(f"Creating archive: {normalized_archive_path}") for file_path in files: print(f" Adding: {file_path}") # Use atomic file operations by default for better reliability # This creates the archive in a temporary file first, then moves it create_archive(archive_path, files, compression_level, use_temp_file=use_temp_file) if _wants_json_output(args): _emit_json( { "ok": True, "command": "add", "archive": str(archive_path), } ) ``` -------------------------------- ### TzstArchive Initialization Source: https://tzst.xi-xu.me/api/core.html Initializes a TzstArchive object for managing .tzst/.tar.zst archives. Supports different modes, compression levels, and streaming. ```APIDOC ## TzstArchive(filename, mode='r', compression_level=3, streaming=False) ### Description Initializes a TzstArchive. ### Parameters * **filename** (str | Path) - Path to the archive file * **mode** (str) - Open mode ('r', 'w', 'a') * **compression_level** (int) - Zstandard compression level (1-22) * **streaming** (bool) - If True, use streaming mode for reading (reduces memory usage for very large archives but may limit some tarfile operations that require seeking. Recommended for archives > 100MB) ``` -------------------------------- ### Project Structure Source: https://tzst.xi-xu.me/development.html Overview of the main project directory structure, including source code, tests, and documentation. ```directory tzst/ ├── src/tzst/ # Main package source code │ ├── __init__.py # Package initialization and exports │ ├── __main__.py # CLI entry point │ ├── cli.py # Command-line interface │ ├── core.py # Core archive functionality │ └── exceptions.py # Custom exceptions ├── tests/ # Test suite │ ├── conftest.py # Pytest configuration and fixtures │ ├── test_core.py # Core functionality tests │ ├── test_cli.py # CLI tests │ └── test_*.py # Additional test modules ├── docs/ # Documentation source ├── .github/ # GitHub workflows and templates ├── pyproject.toml # Project configuration ├── README.md # Project Readme ├── LICENSE # BSD 3-Clause License └── CONTRIBUTING.md # Contribution guidelines ``` -------------------------------- ### Create TZST Archive Source: https://tzst.xi-xu.me/examples.html Demonstrates creating TZST archives. The default behavior is atomic, using a temporary file for safety. A faster, non-atomic option is also available. ```python from tzst import create_archive # Safe atomic creation (default behavior) # Creates in temporary file first, then moves to final location create_archive("important-data.tzst", ["critical/"], use_temp_file=True) # Direct creation (faster but not atomic) create_archive("temp-data.tzst", ["temp/"], use_temp_file=False) ``` -------------------------------- ### Benchmarking Compression Levels Source: https://tzst.xi-xu.me/examples.html Compare the compression time and resulting file size for different compression levels. This helps in optimizing the trade-off between compression ratio and performance. ```python import time from tzst import create_archive from pathlib import Path def benchmark_compression_levels(files, output_prefix="test"): """Compare different compression levels.""" levels_to_test = [1, 3, 6, 9, 15, 22] results = [] for level in levels_to_test: output_file = f"{output_prefix}_level_{level}.tzst" # Measure compression time start_time = time.time() create_archive(output_file, files, compression_level=level) compress_time = time.time() - start_time # Get file size file_size = Path(output_file).stat().st_size results.append({ 'level': level, 'time': compress_time, 'size': file_size, 'size_mb': file_size / (1024 * 1024) }) print(f"Level {level}: {compress_time:.2f}s, {file_size/1024/1024:.1f} MB") return results # Test different compression levels results = benchmark_compression_levels(["large-directory/"]) ``` -------------------------------- ### Initialize TzstArchive Source: https://tzst.xi-xu.me/_modules/tzst/core.html Initializes a TzstArchive object for managing .tzst/.tar.zst files. Supports read, write, and append modes, with configurable compression levels and streaming options. Note that append mode is not supported. ```python class TzstArchive: """A class for handling .tzst/.tar.zst archives.""" def __init__( self, filename: str | Path, mode: str = "r", compression_level: int = 3, streaming: bool = False, ): """ Initialize a TzstArchive. Args: filename: Path to the archive file mode: Open mode ('r', 'w', 'a') compression_level: Zstandard compression level (1-22) streaming: If True, use streaming mode for reading (reduces memory usage for very large archives but may limit some tarfile operations that require seeking. Recommended for archives > 100MB) """ self.filename = Path(filename) self.mode = mode self.compression_level = compression_level self.streaming = streaming self._tarfile: tarfile.TarFile | None = None self._fileobj: BinaryIO | None = None self._compressed_stream: ( zstd.ZstdCompressionWriter | zstd.ZstdDecompressionReader | io.BytesIO | None ) = None # Validate mode valid_modes = ["r", "w", "a"] if mode not in valid_modes: raise ValueError( f"Invalid mode '{mode}'. Must be one of: {', '.join(valid_modes)}" ) # Validate compression level if not 1 <= compression_level <= 22: raise ValueError( f"Invalid compression level '{compression_level}'. Must be between 1 and 22." ) # Check for unsupported modes immediately - provide clear documentation if mode.startswith("a"): raise NotImplementedError( "Append mode is not currently supported for .tzst/.tar.zst archives. " "This would require decompressing the entire archive, adding new files, " "and recompressing, which is complex and potentially slow for large archives. " "Alternatives: 1) Create multiple archives, 2) Recreate the archive with all files, " "3) Use standard tar format for append operations, then compress separately." ) ``` -------------------------------- ### Main Entry Point Source: https://tzst.xi-xu.me/api/cli.html The main entry point for the tzst command-line interface. It processes command-line arguments, dispatches to appropriate command handlers, displays the version banner, and provides error handling for the overall CLI execution. ```APIDOC ## main tzst.cli.main(_argv : list[str] | None = None_) -> int ### Description Main entry point for the tzst command-line interface. Processes command-line arguments and dispatches to appropriate command handlers. Displays the version banner and provides error handling for the overall CLI execution. ### Parameters #### Optional Parameters - **argv** (list[str] | None) - Command line arguments to parse. If None, uses sys.argv. Defaults to None. ### Returns - **int** - Exit code for the program * 0: Success * 1: Invalid compression level, filter, or command error * 2: Argument parsing error (help, unknown options) * Other codes: Specific to individual command handlers ### Note This function serves as the console script entry point defined in pyproject.toml. It displays the version banner before executing any commands. ### See Also `create_parser()`: Creates the argument parser used by this function The main entry point for the CLI application. Handles argument parsing, command execution, and comprehensive error reporting. **Key Features:** * Robust argument validation and error handling * Support for all archive operations * Consistent exit codes for scripting * User-friendly error messages **Exit Codes:** * `0`: Success * `1`: General error (file not found, archive corruption, etc.) * `2`: Argument parsing error * `130`: Interrupted by user (Ctrl+C) ``` -------------------------------- ### Archive Creation Command Source: https://tzst.xi-xu.me/api/cli.html Creates new archives from files and directories with configurable compression and atomic operations. ```APIDOC ## cmd_add Creates new archives from files and directories with configurable compression and atomic operations. **Features:** * Configurable compression levels (1-22) * Atomic file operations (default) for safe creation * Recursive directory processing * Path validation and normalization **Usage Examples:** ``` # Basic archive creation tzst a backup.tzst documents/ photos/ # High compression with atomic disabled tzst a backup.tzst files/ -l 15 --no-atomic ``` ``` -------------------------------- ### Tzst Performance Optimization and Streaming Source: https://tzst.xi-xu.me/quickstart.html Demonstrates creating archives with different compression levels and extracting large archives using memory-efficient streaming mode. ```python from tzst import create_archive, extract_archive # Create with different compression levels create_archive("fast.tzst", files, compression_level=1) # Fastest create_archive("balanced.tzst", files, compression_level=6) # Balanced create_archive("best.tzst", files, compression_level=22) # Best compression # Memory-efficient operations for large archives extract_archive("huge-archive.tzst", "output/", streaming=True) ``` ```python # Memory-efficient operations with TzstArchive("large-archive.tzst", "r", streaming=True) as archive: contents = archive.list() archive.extractall("output/") is_valid = archive.test() ``` -------------------------------- ### Create Argument Parser Source: https://tzst.xi-xu.me/api/cli.html Creates and configures the command-line argument parser for the tzst CLI interface, setting up all subcommands and their respective arguments. ```APIDOC ## create_parser tzst.cli.create_parser() -> ArgumentParser ### Description Create and configure the command-line argument parser. Sets up the argparse ArgumentParser with all subcommands and their respective arguments for the tzst CLI interface. Includes comprehensive help text and command reference documentation. ### Returns - **ArgumentParser** - Configured parser ready for argument parsing ### Note The parser is configured with RawDescriptionHelpFormatter to preserve formatting in the epilog help text, and includes detailed command reference and security notes. ### Commands Created * a, add, create: Archive creation with compression levels * x, extract: Full extraction with directory structure * e, extract-flat: Flat extraction without directories * l, list: Archive content listing * t, test: Archive integrity testing ### See Also `main()`: The main entry point that uses this parser Creates and configures the comprehensive argument parser for the CLI interface. **Supported Arguments:** * **Global** : `--version`, `--help` * **Archive Creation** : `-l/--level`, `--no-atomic` * **Extraction** : `-o/--output`, `--streaming`, `--filter`, `--conflict-resolution` * **Listing** : `-v/--verbose`, `--streaming` * **Testing** : `--streaming` ``` -------------------------------- ### Run All Tests Source: https://tzst.xi-xu.me/development.html Execute all tests using pytest. Ensure you are in the project's root directory. ```bash # Run all tests python -m pytest ``` -------------------------------- ### Create tzst Archive with High Compression Source: https://tzst.xi-xu.me/quickstart.html Create a tzst archive with a high compression level (9) to maximize space savings, including 'documents/' and 'photos/'. ```bash # Create with high compression tzst a backup.tzst documents/ photos/ --compression-level 9 ``` -------------------------------- ### Safely Create Archive with tzst Source: https://tzst.xi-xu.me/examples.html Demonstrates a safe method for creating archives using a provided operation function. It handles potential errors during the archive creation process. ```python def create_backup_safely(files, output_archive): def create_operation(): from tzst import create_archive return create_archive(output_archive, files) result = safe_archive_operation(create_operation) if result is not None: print(f"Backup created successfully: {output_archive}") else: print("Backup creation failed!") ``` -------------------------------- ### List Contents of tzst Archive with Verbose Output Source: https://tzst.xi-xu.me/quickstart.html List the contents of 'backup.tzst' with detailed file information, including sizes and metadata. ```bash # Detailed listing with file info tzst l backup.tzst --verbose ``` -------------------------------- ### tzst main Source: https://tzst.xi-xu.me/api/cli.html Main entry point for the tzst command-line interface. ```APIDOC ## tzst main ### Description Main entry point for the tzst command-line interface. Processes command-line arguments and dispatches to appropriate command handlers. Displays the version banner and provides error handling for the overall CLI execution. ### Parameters #### Path Parameters - **argv** (list[str] | None, optional): Command line arguments to parse. If None, uses sys.argv. Defaults to None. ### Returns Exit code for the program * 0: Success * 1: Invalid compression level, filter, or command error * 2: Argument parsing error (help, unknown options) * Other codes: Specific to individual command handlers ### Return type int ### Note This function serves as the console script entry point defined in pyproject.toml. It displays the version banner before executing any commands. ### See also `create_parser()` ``` -------------------------------- ### Run Pytest Source: https://tzst.xi-xu.me/development.html A simpler command to run tests, relying on configuration in pyproject.toml for coverage settings. ```bash # Or use the simpler command (coverage settings are in pyproject.toml) pytest ``` -------------------------------- ### Run Tests with Verbose Output Source: https://tzst.xi-xu.me/development.html Execute tests with verbose output to see more details about each test's execution. ```bash # Run with verbose output python -m pytest -v ```