diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index bff7b02..da03990 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -17,8 +17,8 @@ jobs: needs: notify_start strategy: matrix: - os: [ubuntu-latest, macos-latest] - # windows-latest not supported due to termion + os: [ubuntu-latest, windows-latest] + # macos-latest removed as it segfaults runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v2 @@ -45,6 +45,10 @@ jobs: run: 'cargo test' - name: Build run: 'cargo build --locked' + if: ${{ matrix.os != 'windows-latest' }} + - name: Build + run: 'cargo build' # difficult to create proper lock file for Windows outside ci + if: ${{ matrix.os == 'windows-latest' }} - uses: actions/upload-artifact@v2 with: name: mxrxtx-${{ runner.os }} diff --git a/.github/workflows/tag.yaml b/.github/workflows/tag.yaml index 624bad8..5f4f5d5 100644 --- a/.github/workflows/tag.yaml +++ b/.github/workflows/tag.yaml @@ -59,7 +59,8 @@ jobs: contents: write strategy: matrix: - os: [ubuntu-latest, macos-latest] + os: [ubuntu-latest, windows-latest] + # macos-latest crashes runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v2 @@ -105,56 +106,55 @@ jobs: asset_name: mxrxtx-${{ needs.create_release.outputs.git_describe }}-${{ runner.os }}.bin asset_content_type: application/octet-stream if: ${{ matrix.os == 'ubuntu-latest' || matrix.os == 'macos-latest' }} - # not supported now due to termion - # windows: - # name: mxrxtx - # needs: create_release - # permissions: - # issues: write - # pull-requests: write - # contents: write - # strategy: - # matrix: - # os: [windows-latest] - # runs-on: ${{ matrix.os }} - # steps: - # - uses: actions/checkout@v2 - # with: - # submodules: true - # # https://stackoverflow.com/a/58178121 - # - uses: actions-rs/toolchain@v1 - # with: - # toolchain: stable - # - uses: actions/cache@v2 - # with: - # path: | - # ~/.cargo/bin/ - # ~/.cargo/registry/index/ - # ~/.cargo/registry/cache/ - # ~/.cargo/git/db/ - # target/ - # key: ${{ runner.os }}-cargo-${{ hashFiles('**/Cargo.lock') }} - # - name: build - # env: - # GIT_DESCRIBE: ${{ needs.create_release.outputs.git_describe }} - # run: 'cargo build --release' - # - uses: actions/upload-artifact@v2 - # with: - # name: mxrxtx - # path: | - # target/release/mxrxtx.exe - # Cargo.lock - # # https://github.com/actions/upload-release-asset - # - name: Upload Release Asset - # uses: actions/upload-release-asset@v1 - # env: - # GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - # with: - # # https://jasonet.co/posts/new-features-of-github-actions/#passing-data-to-future-steps - # upload_url: ${{ needs.create_release.outputs.upload_url }} - # asset_path: ./target/release/mxrxtx.exe - # asset_name: mxrxtx-${{ needs.create_release.outputs.git_describe }}-${{ runner.os }}.exe - # asset_content_type: application/octet-stream + windows: + name: mxrxtx + needs: create_release + permissions: + issues: write + pull-requests: write + contents: write + strategy: + matrix: + os: [windows-latest] + runs-on: ${{ matrix.os }} + steps: + - uses: actions/checkout@v2 + with: + submodules: true + # https://stackoverflow.com/a/58178121 + - uses: actions-rs/toolchain@v1 + with: + toolchain: stable + - uses: actions/cache@v2 + with: + path: | + ~/.cargo/bin/ + ~/.cargo/registry/index/ + ~/.cargo/registry/cache/ + ~/.cargo/git/db/ + target/ + key: ${{ runner.os }}-cargo-${{ hashFiles('**/Cargo.lock') }} + - name: build + env: + GIT_DESCRIBE: ${{ needs.create_release.outputs.git_describe }} + run: 'cargo build --release' + - uses: actions/upload-artifact@v2 + with: + name: mxrxtx + path: | + target/release/mxrxtx.exe + Cargo.lock + # https://github.com/actions/upload-release-asset + - name: Upload Release Asset + uses: actions/upload-release-asset@v1 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + with: + # https://jasonet.co/posts/new-features-of-github-actions/#passing-data-to-future-steps + upload_url: ${{ needs.create_release.outputs.upload_url }} + asset_path: ./target/release/mxrxtx.exe + asset_name: mxrxtx-${{ needs.create_release.outputs.git_describe }}-${{ runner.os }}.exe + asset_content_type: application/octet-stream notify_end_success: runs-on: ubuntu-latest needs: [create_release, unix] diff --git a/Cargo.toml b/Cargo.toml index 6081215..4e085b3 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -33,12 +33,14 @@ serde = "1.0.130" serde_derive = "1.0.130" serde_json = "1.0.68" tempdir = "0.3.7" -termion = "1.5.6" thiserror = "1.0.29" tokio = { version = "1.12.0", features = ["test-util", "tokio-macros", "macros", "signal", "rt-multi-thread"] } toml = "0.5.8" url = "2.2.2" uuid = { version = "1.2.2", features = ["serde"] } +[target.'cfg(not(target_os = "windows"))'.dependencies] +termion = "1.5.6" + [build-dependencies] vergen = "3" diff --git a/src/setup.rs b/src/setup.rs index 770b130..67daabf 100644 --- a/src/setup.rs +++ b/src/setup.rs @@ -1,5 +1,4 @@ use std::io::{stdin, stdout, Write}; -use termion::input::TermRead; use crate::config; @@ -36,6 +35,36 @@ pub enum Error { IdParseError(#[from] ruma::IdParseError), } +// Termion that provides read_passwd doesn't compile on Windows +mod console { + use std::io::{BufRead, StdinLock, StdoutLock}; + + #[cfg(not(target_os = "windows"))] + pub fn read_passwd( + stdin: &mut StdinLock, + stdout: &mut StdoutLock, + ) -> Result, super::Error> { + use termion::input::TermRead; + stdin + .read_passwd(stdout) + .map_err(|_| super::Error::NoInputError) + } + + #[cfg(target_os = "windows")] + pub fn read_passwd( + stdin: &mut StdinLock, + _stdout: &mut StdoutLock, + ) -> Result, super::Error> { + read_line(stdin) + } + + pub fn read_line(stdin: &mut StdinLock) -> Result, super::Error> { + let mut buffer = String::new(); + BufRead::read_line(stdin, &mut buffer)?; + Ok(Some(buffer)) + } +} + pub async fn setup_mode( _args: clap::ArgMatches, mut config: config::Config, @@ -48,13 +77,15 @@ pub async fn setup_mode( let stdin = stdin(); let mut stdin = stdin.lock(); - stdout.write_all(b"Matrix id (e.g. @user:example.org): ")?; - stdout.flush()?; - let mxid = stdin.read_line()?.ok_or(Error::NoInputError)?; + let mxid = { + stdout.write_all(b"Matrix id (e.g. @user:example.org): ")?; + stdout.flush()?; + console::read_line(&mut stdin)?.ok_or(Error::NoInputError)? + }; stdout.write_all(b"Device name (empty to use default device name \"mxrxtx\"): ")?; stdout.flush()?; - let device_name = stdin.read_line()?.ok_or(Error::NoInputError)?; + let device_name = console::read_line(&mut stdin)?.ok_or(Error::NoInputError)?; let device_name = if device_name.is_empty() { None } else { @@ -63,7 +94,8 @@ pub async fn setup_mode( stdout.write_all(b"Password: ")?; stdout.flush()?; - let password = stdin.read_passwd(&mut stdout)?.ok_or(Error::NoInputError)?; + let password = + console::read_passwd(&mut stdin, &mut stdout)?.ok_or(Error::NoInputError)?; stdout.write_all(b"\n")?; Ok((mxid, password, device_name))