State-driven, resumable download API for Tauri 2.x apps.
This plugin provides a cross-platform download interface with resumable downloads, progress tracking, and proper resource management.
- Parallel, resumable download support
- Persistable, thread-safe store
- State and progress notifications
- Cross-platform support (Linux, Windows, macOS, Android, iOS)
| Platform | Supported |
|---|---|
| Linux | ✓ |
| Windows | ✓ |
| macOS | ✓ |
| Android | ✓ |
| iOS¹ | ✓ |
¹ Supports fully interruptible and resumable background downloads, even when the app
is suspended or terminated using
URLSession with a
background configuration.
-
Install NPM dependencies:
npm install
-
Build the TypeScript bindings:
npm run build
-
Build the Rust plugin:
cargo build
Run Rust tests:
cargo testThis plugin requires a Rust version of at least 1.77.2
Add the plugin to your Cargo.toml:
src-tauri/Cargo.toml
[dependencies]
tauri-plugin-download = { git = "https://github.com/silvermine/tauri-plugin-download" }Install the JavaScript bindings:
npm install @silvermine/tauri-plugin-downloadInitialize the plugin in your tauri::Builder:
fn main() {
tauri::Builder::default()
.plugin(tauri_plugin_download::init())
.run(tauri::generate_context!())
.expect("error while running tauri application");
}import { list } from 'tauri-plugin-download';
async function listDownloads() {
const downloads = await list();
for (const download of downloads) {
console.debug(`Found '${download.path}': [${download.status}, ${download.progress}%]`);
}
}import { get, DownloadStatus } from 'tauri-plugin-download';
async function getDownload() {
const download = await get('/path/to/file.zip');
if (download.status === DownloadStatus.Pending) {
console.debug(`Download '${download.path}' not found in store`);
} else {
console.debug(`Found '${download.path}': [${download.status}, ${download.progress}%]`);
}
}The API uses discriminated unions with type guards for compile-time safety. Only valid methods are available based on the download's status.
import { get, DownloadStatus, hasAction, DownloadAction } from 'tauri-plugin-download';
async function createAndStartDownload() {
const download = await get('/path/to/file.zip');
if (download.status === DownloadStatus.Pending) {
// Download not in store - create it first
const { download: created } = await download.create('https://example.com/file.zip');
await created.start();
}
}
async function manageDownload() {
const download = await get('/path/to/file.zip');
if (hasAction(download, DownloadAction.Start)) {
await download.start(); // TypeScript knows start() is available
} else if (hasAction(download, DownloadAction.Pause)) {
await download.pause(); // TypeScript knows pause() is available
} else if (hasAction(download, DownloadAction.Resume)) {
await download.resume(); // TypeScript knows resume() is available
}
}Listeners can be attached to downloads in any status, including Pending.
This allows you to set up listeners before creating the download.
import { get, DownloadStatus } from 'tauri-plugin-download';
async function setupAndStartDownload() {
const download = await get('/path/to/file.zip');
// Attach listener (works for Pending downloads too)
const unlisten = await download.listen((updated) => {
console.debug(`'${updated.path}': ${updated.progress}%`);
});
// Create and start if pending
if (download.status === DownloadStatus.Pending) {
const { download: created } = await download.create('https://example.com/file.zip');
await created.start();
}
// To stop listening
unlisten();
}Check out the examples/tauri-app directory for a working example of how to use this plugin.
This project follows the Silvermine standardization guidelines. Key standards include:
- EditorConfig: Consistent editor settings across the team
- Markdownlint: Markdown linting for documentation
- Commitlint: Conventional commit message format
- Code Style: 3-space indentation, LF line endings
npm run standardsMIT
Contributions are welcome! Please follow the established coding standards and commit message conventions.