Skip to content
Open
1 change: 0 additions & 1 deletion .clippy.toml

This file was deleted.

65 changes: 56 additions & 9 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,22 +6,53 @@ on:

jobs:

check:
name: Test
check_tokio:
name: Test tokio
runs-on: ${{ matrix.os }}
strategy:
matrix:
build: [msrv, stable, beta, nightly, macos, windows]
build: [msrv, stable, nightly, macos, windows]
include:
- build: msrv
os: ubuntu-latest
rust: 1.63
rust: 1.71
- build: stable
os: ubuntu-latest
rust: stable
- build: beta
- build: nightly
os: ubuntu-latest
rust: nightly
- build: macos
os: macos-latest
rust: stable
- build: windows
os: windows-latest
rust: stable
steps:
- uses: actions/checkout@v4
- uses: actions-rs/toolchain@v1
with:
profile: minimal
override: true
toolchain: ${{ matrix.rust }}
- uses: actions-rs/cargo@v1
with:
command: test
args: --no-default-features --features runtime-tokio

check_async:
name: Test async-std
runs-on: ${{ matrix.os }}
strategy:
matrix:
build: [msrv, stable, nightly, macos, windows]
include:
- build: msrv
os: ubuntu-latest
rust: beta
rust: 1.71
- build: stable
os: ubuntu-latest
rust: stable
- build: nightly
os: ubuntu-latest
rust: nightly
Expand All @@ -41,6 +72,7 @@ jobs:
- uses: actions-rs/cargo@v1
with:
command: test
args: --no-default-features --features runtime-async-std

fmt:
name: Check formatting
Expand All @@ -58,8 +90,8 @@ jobs:
command: fmt
args: --all -- --check

lint:
name: Clippy Linting
lint_tokio:
name: Clippy Linting tokio
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
Expand All @@ -72,8 +104,23 @@ jobs:
- uses: actions-rs/cargo@v1
with:
command: clippy
args: --all
args: --no-default-features --features runtime-tokio

lint_async:
name: Clippy Linting async-std
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions-rs/toolchain@v1
with:
profile: minimal
toolchain: stable
components: clippy
override: true
- uses: actions-rs/cargo@v1
with:
command: clippy
args: --no-default-features --features runtime-async-std
docs:
name: Check docs
runs-on: ubuntu-latest
Expand Down
18 changes: 12 additions & 6 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ readme = "README.md"
edition = "2018"
exclude = ["tests/archives/*"]
resolver = "2"
rust-version = "1.71"

description = """
A Rust implementation of an async TAR file reader and writer. This library does not
Expand All @@ -20,21 +21,26 @@ contents are never required to be entirely resident in memory all at once.
"""

[dependencies]
async-std = { version = "1.12.0", features = ["unstable"] }
async-std = { version = "1.12", optional = true }
tokio = { version = "1", optional = true, features = ["fs", "io-util"] }
filetime = "0.2.8"
pin-project = "1.0.8"
tokio-stream = { version = "0.1.11", features = ["fs"], optional = true }
futures-core = "0.3.25"

[dev-dependencies]
async-std = { version = "1.12.0", features = ["unstable", "attributes"] }
async-std = { version = "1.12", features = ["unstable", "attributes"] }
tokio = { version = "1", features = ["rt", "io-std", "rt-multi-thread", "macros"] }
static_assertions = "1.1.0"
tempfile = "3"

[target."cfg(unix)".dependencies]
libc = "0.2"
xattr = { version = "0.2", optional = true }
xattr = { version = "1.6", optional = true }

[target.'cfg(target_os = "redox")'.dependencies]
redox_syscall = "0.2"
redox_syscall = "0.5"

[features]
default = [ "xattr" ]
default = ["xattr", "runtime-async-std"]
runtime-async-std = ["async-std"]
runtime-tokio = ["tokio", "tokio-stream"]
7 changes: 6 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,11 @@

> Based on the great [tar-rs](https://github.com/alexcrichton/tar-rs).

## Features

- `runtime-async-std`: enabled by default, makes this crate compatible with `async-std`
- `runtime-tokio`: makes this crate compatible with `tokio`.

## Reading an archive

```rust,no_run
Expand Down Expand Up @@ -81,7 +86,7 @@ fn main() {

# MSRV

Minimal stable rust version: 1.63
Minimal stable rust version: 1.71

*An increase to the MSRV is accompanied by a minor version bump*

Expand Down
45 changes: 30 additions & 15 deletions examples/extract_file.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,28 +4,43 @@
//! name as the first argument provided, and then prints the contents of that
//! file to stdout.

extern crate async_tar;

#[cfg(feature = "runtime-async-std")]
use async_std::{
io::{copy, stdin, stdout},
path::Path,
prelude::*,
stream::StreamExt,
};
use std::env::args_os;
#[cfg(feature = "runtime-tokio")]
use std::path::Path;
#[cfg(feature = "runtime-tokio")]
use tokio::io::{copy, stdin, stdout};
#[cfg(feature = "runtime-tokio")]
use tokio_stream::StreamExt;

use async_tar::Archive;

fn main() {
async_std::task::block_on(async {
let first_arg = args_os().nth(1).unwrap();
let filename = Path::new(&first_arg);
let ar = Archive::new(stdin());
let mut entries = ar.entries().unwrap();
while let Some(file) = entries.next().await {
let mut f = file.unwrap();
if f.path().unwrap() == filename {
copy(&mut f, &mut stdout()).await.unwrap();
}
async fn inner_main() {
let first_arg = args_os().nth(1).unwrap();
let filename = Path::new(&first_arg);
let ar = Archive::new(stdin());
let mut entries = ar.entries().unwrap();
while let Some(file) = entries.next().await {
let mut f = file.unwrap();
if f.path().unwrap() == filename {
copy(&mut f, &mut stdout()).await.unwrap();
}
});
}
}

#[cfg(feature = "runtime-async-std")]
fn main() {
async_std::task::block_on(inner_main());
}

#[cfg(feature = "runtime-tokio")]
fn main() {
tokio::runtime::Runtime::new()
.unwrap()
.block_on(inner_main());
}
35 changes: 24 additions & 11 deletions examples/list.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,19 +2,32 @@
//!
//! Takes a tarball on stdin and prints out all of the entries inside.

extern crate async_tar;

use async_std::{io::stdin, prelude::*};
#[cfg(feature = "runtime-async-std")]
use async_std::{io::stdin, stream::StreamExt};
#[cfg(feature = "runtime-tokio")]
use tokio::io::stdin;
#[cfg(feature = "runtime-tokio")]
use tokio_stream::StreamExt;

use async_tar::Archive;

async fn inner_main() {
let ar = Archive::new(stdin());
let mut entries = ar.entries().unwrap();
while let Some(file) = entries.next().await {
let f = file.unwrap();
println!("{}", f.path().unwrap().display());
}
}

#[cfg(feature = "runtime-async-std")]
fn main() {
async_std::task::block_on(inner_main());
}

#[cfg(feature = "runtime-tokio")]
fn main() {
async_std::task::block_on(async {
let ar = Archive::new(stdin());
let mut entries = ar.entries().unwrap();
while let Some(file) = entries.next().await {
let f = file.unwrap();
println!("{}", f.path().unwrap().display());
}
});
tokio::runtime::Runtime::new()
.unwrap()
.block_on(inner_main());
}
93 changes: 53 additions & 40 deletions examples/raw_list.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,52 +2,65 @@
//!
//! Takes a tarball on stdin and prints out all of the entries inside.

extern crate async_tar;

#[cfg(feature = "runtime-async-std")]
use async_std::{io::stdin, prelude::*};
#[cfg(feature = "runtime-tokio")]
use tokio::io::stdin;
#[cfg(feature = "runtime-tokio")]
use tokio_stream::StreamExt;

use async_tar::Archive;

fn main() {
async_std::task::block_on(async {
let ar = Archive::new(stdin());
let mut i = 0;
let mut entries = ar.entries_raw().unwrap();
while let Some(file) = entries.next().await {
println!("-------------------------- Entry {}", i);
let mut f = file.unwrap();
println!("path: {}", f.path().unwrap().display());
println!("size: {}", f.header().size().unwrap());
println!("entry size: {}", f.header().entry_size().unwrap());
println!("link name: {:?}", f.link_name().unwrap());
println!("file type: {:#x}", f.header().entry_type().as_byte());
println!("mode: {:#o}", f.header().mode().unwrap());
println!("uid: {}", f.header().uid().unwrap());
println!("gid: {}", f.header().gid().unwrap());
println!("mtime: {}", f.header().mtime().unwrap());
println!("username: {:?}", f.header().username().unwrap());
println!("groupname: {:?}", f.header().groupname().unwrap());
async fn inner_main() {
let ar = Archive::new(stdin());
let mut i = 0;
let mut entries = ar.entries_raw().unwrap();
while let Some(file) = entries.next().await {
println!("-------------------------- Entry {}", i);
let mut f = file.unwrap();
println!("path: {}", f.path().unwrap().display());
println!("size: {}", f.header().size().unwrap());
println!("entry size: {}", f.header().entry_size().unwrap());
println!("link name: {:?}", f.link_name().unwrap());
println!("file type: {:#x}", f.header().entry_type().as_byte());
println!("mode: {:#o}", f.header().mode().unwrap());
println!("uid: {}", f.header().uid().unwrap());
println!("gid: {}", f.header().gid().unwrap());
println!("mtime: {}", f.header().mtime().unwrap());
println!("username: {:?}", f.header().username().unwrap());
println!("groupname: {:?}", f.header().groupname().unwrap());

if f.header().as_ustar().is_some() {
println!("kind: UStar");
} else if f.header().as_gnu().is_some() {
println!("kind: GNU");
} else {
println!("kind: normal");
}
if f.header().as_ustar().is_some() {
println!("kind: UStar");
} else if f.header().as_gnu().is_some() {
println!("kind: GNU");
} else {
println!("kind: normal");
}

if let Ok(Some(extensions)) = f.pax_extensions().await {
println!("pax extensions:");
for e in extensions {
let e = e.unwrap();
println!(
"\t{:?} = {:?}",
String::from_utf8_lossy(e.key_bytes()),
String::from_utf8_lossy(e.value_bytes())
);
}
if let Ok(Some(extensions)) = f.pax_extensions().await {
println!("pax extensions:");
for e in extensions {
let e = e.unwrap();
println!(
"\t{:?} = {:?}",
String::from_utf8_lossy(e.key_bytes()),
String::from_utf8_lossy(e.value_bytes())
);
}
i += 1;
}
});
i += 1;
}
}

#[cfg(feature = "runtime-async-std")]
fn main() {
async_std::task::block_on(inner_main());
}

#[cfg(feature = "runtime-tokio")]
fn main() {
tokio::runtime::Runtime::new()
.unwrap()
.block_on(inner_main());
}
Loading
Loading