diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index e4da4a8..34633c4 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -11,15 +11,15 @@ # Contributors: # ZettaScale Zenoh Team, # -name: CI +name: Release on: - push: - branches: ["**"] - pull_request: - branches: ["**"] + release: + types: [published] schedule: - - cron: "0 6 * * 1-5" + - cron: "0 1 * * 1-5" + workflow_dispatch: + jobs: check: @@ -32,6 +32,8 @@ jobs: steps: - uses: actions/checkout@v2 + with: + submodules: recursive - name: Install Rust toolchain uses: actions-rs/toolchain@v1 @@ -64,6 +66,8 @@ jobs: steps: - uses: actions/checkout@v2 + with: + submodules: recursive - name: Install latest Rust toolchain uses: actions-rs/toolchain@v1 diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 34d2cc7..f273a9e 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,14 +11,15 @@ # Contributors: # ZettaScale Zenoh Team, # -name: Release +name: CI on: - release: - types: [published] + push: + branches: ["**"] + pull_request: + branches: ["**"] schedule: - - cron: "0 1 * * 1-5" - workflow_dispatch: + - cron: "0 6 * * 1-5" jobs: checks: @@ -26,6 +27,8 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v2 + with: + submodules: recursive - name: Install Rust toolchain uses: actions-rs/toolchain@v1 with: @@ -137,6 +140,7 @@ jobs: uses: actions/checkout@v2 with: fetch-depth: 500 # NOTE: get long history for git-version crate to correctly compute a version + submodules: recursive - name: Fetch Git tags # NOTE: workaround for https://github.com/actions/checkout/issues/290 shell: bash run: git fetch --tags --force @@ -258,54 +262,55 @@ jobs: ${{ steps.package.outputs.BIN_PKG_NAME }} ${{ steps.package.outputs.DEBS_PKG_NAME }} - # docker-build: - # name: Docker build and push - # needs: [checks, builds] - # runs-on: ubuntu-latest - # steps: - # - uses: actions/checkout@v2 - # with: - # fetch-depth: 500 # NOTE: get long history for git-version crate to correctly compute a version - # - name: Fetch Git tags # NOTE: workaround for https://github.com/actions/checkout/issues/290 - # shell: bash - # run: git fetch --tags --force - # - name: Download packages from previous job - # uses: actions/download-artifact@v2 - # with: - # path: PACKAGES - # - name: Unzip PACKAGES - # run: | - # ls PACKAGES - # mkdir -p docker/linux/amd - # unzip PACKAGES/x86_64-unknown-linux-musl/zenoh-bridge-ros1-${{ needs.checks.outputs.PKG_VERSION }}-x86_64-unknown-linux-musl.zip -d docker/linux/amd64/ - # mkdir -p docker/linux/arm64 - # unzip PACKAGES/aarch64-unknown-linux-musl/zenoh-bridge-ros1-${{ needs.checks.outputs.PKG_VERSION }}-aarch64-unknown-linux-musl.zip -d docker/linux/arm64/ - # tree docker - # - name: Set up Docker Buildx - # uses: docker/setup-buildx-action@v1 - # - name: Docker meta - set tags and labels - # id: meta - # uses: docker/metadata-action@v3 - # with: - # images: eclipse/zenoh-bridge-ros1 - # - name: Login to DockerHub - # uses: docker/login-action@v1 - # with: - # username: ${{ secrets.DOCKER_COM_USERNAME }} - # password: ${{ secrets.DOCKER_COM_PASSWORD }} - # - name: Build and push - # uses: docker/build-push-action@v2 - # with: - # context: . - # platforms: linux/amd64,linux/arm64 - # file: .github/workflows/Dockerfile - # push: true - # tags: ${{ steps.meta.outputs.tags }} - # labels: ${{ steps.meta.outputs.labels }} + docker-build: + name: Docker build and push + needs: [checks, builds] + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v2 + with: + fetch-depth: 500 # NOTE: get long history for git-version crate to correctly compute a version + submodules: recursive + - name: Fetch Git tags # NOTE: workaround for https://github.com/actions/checkout/issues/290 + shell: bash + run: git fetch --tags --force + - name: Download packages from previous job + uses: actions/download-artifact@v2 + with: + path: PACKAGES + - name: Unzip PACKAGES + run: | + ls PACKAGES + mkdir -p docker/linux/amd + unzip PACKAGES/x86_64-unknown-linux-musl/zenoh-bridge-ros1-${{ needs.checks.outputs.PKG_VERSION }}-x86_64-unknown-linux-musl.zip -d docker/linux/amd64/ + mkdir -p docker/linux/arm64 + unzip PACKAGES/aarch64-unknown-linux-musl/zenoh-bridge-ros1-${{ needs.checks.outputs.PKG_VERSION }}-aarch64-unknown-linux-musl.zip -d docker/linux/arm64/ + tree docker + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v1 + - name: Docker meta - set tags and labels + id: meta + uses: docker/metadata-action@v3 + with: + images: eclipse/zenoh-bridge-ros1 + - name: Login to DockerHub + uses: docker/login-action@v1 + with: + username: ${{ secrets.DOCKER_COM_USERNAME }} + password: ${{ secrets.DOCKER_COM_PASSWORD }} + - name: Build and push + uses: docker/build-push-action@v2 + with: + context: . + platforms: linux/amd64,linux/arm64 + file: .github/workflows/Dockerfile + push: false # true todo: temporary disabled + tags: ${{ steps.meta.outputs.tags }} + labels: ${{ steps.meta.outputs.labels }} publication: name: Release publication - if: needs.checks.outputs.IS_RELEASE == 'true' + if: false # needs.checks.outputs.IS_RELEASE == 'true' todo: temporary disabled needs: [checks, builds] runs-on: ubuntu-latest steps: @@ -341,6 +346,8 @@ jobs: echo "---- cleanup identity" ssh-add -D - uses: actions/checkout@v2 + with: + submodules: recursive - name: Install Rust toolchain uses: actions-rs/toolchain@v1 - name: Publish to crates.io diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..d992dce --- /dev/null +++ b/.gitmodules @@ -0,0 +1,4 @@ +[submodule "rosrust"] + path = rosrust + url = git@github.com:ZettaScaleLabs/rosrust.git + branch = feature/fix_bugs diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..1dd0b82 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,51 @@ +# Contributing to Eclipse zenoh + +Thanks for your interest in this project. + +## Project description + +Eclipse zenoh provides is a stack designed to + 1. minimize network overhead, + 2. support extremely constrained devices, + 3. supports devices with low duty-cycle by allowing the negotiation of data exchange modes and schedules, + 4. provide a rich set of abstraction for distributing, querying and storing data along the entire system, and + 5. provide extremely low latency and high throughput. + +* https://projects.eclipse.org/projects/iot.zenoh + +## Developer resources + +Information regarding source code management, builds, coding standards, and +more. + +* https://projects.eclipse.org/projects/iot.zenoh/developer + +The project maintains the following source code repositories + +* https://github.com/eclipse-zenoh + +## Eclipse Contributor Agreement + +Before your contribution can be accepted by the project team contributors must +electronically sign the Eclipse Contributor Agreement (ECA). + +* http://www.eclipse.org/legal/ECA.php + +Commits that are provided by non-committers must have a Signed-off-by field in +the footer indicating that the author is aware of the terms by which the +contribution has been provided to the project. The non-committer must +additionally have an Eclipse Foundation account and must have a signed Eclipse +Contributor Agreement (ECA) on file. + +For more information, please see the Eclipse Committer Handbook: +https://www.eclipse.org/projects/handbook/#resources-commit + +## Contact + +Contact the project developers via the project's "dev" list. + +* https://accounts.eclipse.org/mailing-list/zenoh-dev + +Or via the Gitter channel. + +* https://gitter.im/atolab/zenoh diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md new file mode 100644 index 0000000..75d9c63 --- /dev/null +++ b/CONTRIBUTORS.md @@ -0,0 +1,7 @@ +# Contributors to Eclipse zenoh-plugin-ros1 + +These are the contributors to Eclipse zenoh (the initial contributors and the contributors listed in the Git log). + + +| GitHub username | Name | +| --------------- | -----------------------------| diff --git a/Cargo.lock b/Cargo.lock index 109a7a2..b76bdad 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2259,7 +2259,6 @@ dependencies = [ [[package]] name = "ros_message" version = "0.1.1" -source = "git+https://github.com/ZettaScaleLabs/rosrust.git?branch=feature/fix_bugs#ff2ed4fe87ae3579ab64453345e54afae7a594a4" dependencies = [ "array-init", "hex", @@ -2275,7 +2274,6 @@ dependencies = [ [[package]] name = "rosrust" version = "0.9.11" -source = "git+https://github.com/ZettaScaleLabs/rosrust.git?branch=feature/fix_bugs#ff2ed4fe87ae3579ab64453345e54afae7a594a4" dependencies = [ "byteorder", "colored", @@ -2298,7 +2296,6 @@ dependencies = [ [[package]] name = "rosrust_codegen" version = "0.9.6" -source = "git+https://github.com/ZettaScaleLabs/rosrust.git?branch=feature/fix_bugs#ff2ed4fe87ae3579ab64453345e54afae7a594a4" dependencies = [ "error-chain 0.12.4", "hex", @@ -2329,7 +2326,7 @@ dependencies = [ "serde_json", "sha1_smol", "threadpool", - "time 0.3.28", + "time 0.3.29", "tiny_http", "url 2.4.1", ] @@ -2545,9 +2542,9 @@ dependencies = [ [[package]] name = "semver" -version = "1.0.18" +version = "1.0.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b0293b4b29daaf487284529cc2f5675b8e57c61f70167ba415a463651fd6a918" +checksum = "ad977052201c6de01a8ef2aa3378c4bd23217a056337d1d6da40468d267a4fb0" [[package]] name = "serde" @@ -2935,9 +2932,9 @@ dependencies = [ [[package]] name = "time" -version = "0.3.28" +version = "0.3.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "17f6bb557fd245c28e6411aa56b6403c689ad95061f50e4be16c274e70a17e48" +checksum = "426f806f4089c493dcac0d24c29c01e2c38baf8e30f1b716ee37e83d200b18fe" dependencies = [ "deranged", "libc", @@ -2948,9 +2945,9 @@ dependencies = [ [[package]] name = "time-core" -version = "0.1.1" +version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7300fbefb4dadc1af235a9cef3737cea692a9d97e1b9cbcd4ebdae6f8868e6fb" +checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" [[package]] name = "tiny_http" @@ -3018,9 +3015,9 @@ dependencies = [ [[package]] name = "tokio-tungstenite" -version = "0.20.0" +version = "0.20.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b2dbec703c26b00d74844519606ef15d09a7d6857860f84ad223dec002ddea2" +checksum = "212d5dcb2a1ce06d81107c3d0ffa3121fe974b73f068c8282cb1c32328113b6c" dependencies = [ "futures-util", "log 0.4.20", @@ -3069,9 +3066,9 @@ checksum = "efd1f82c56340fdf16f2a953d7bda4f8fdffba13d93b00844c25572110b26079" [[package]] name = "tungstenite" -version = "0.20.0" +version = "0.20.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e862a1c4128df0112ab625f55cd5c934bcb4312ba80b39ae4b4835a3fd58e649" +checksum = "9e3dac10fd62eaf6617d3a904ae222845979aec67c615d1c842b4002c7666fb9" dependencies = [ "byteorder", "bytes", @@ -3557,8 +3554,8 @@ dependencies = [ [[package]] name = "zenoh" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-global-executor", "async-std", @@ -3620,16 +3617,16 @@ dependencies = [ [[package]] name = "zenoh-buffers" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "zenoh-collections", ] [[package]] name = "zenoh-codec" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "log 0.4.20", "serde", @@ -3640,13 +3637,13 @@ dependencies = [ [[package]] name = "zenoh-collections" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" [[package]] name = "zenoh-config" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "flume", "json5", @@ -3663,8 +3660,8 @@ dependencies = [ [[package]] name = "zenoh-core" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "lazy_static", @@ -3673,8 +3670,8 @@ dependencies = [ [[package]] name = "zenoh-crypto" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "aes", "hmac", @@ -3686,8 +3683,8 @@ dependencies = [ [[package]] name = "zenoh-ext" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "bincode", @@ -3706,8 +3703,8 @@ dependencies = [ [[package]] name = "zenoh-keyexpr" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "hashbrown 0.14.0", "keyed-set", @@ -3720,8 +3717,8 @@ dependencies = [ [[package]] name = "zenoh-link" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", @@ -3739,8 +3736,8 @@ dependencies = [ [[package]] name = "zenoh-link-commons" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", @@ -3755,8 +3752,8 @@ dependencies = [ [[package]] name = "zenoh-link-quic" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-rustls", "async-std", @@ -3779,8 +3776,8 @@ dependencies = [ [[package]] name = "zenoh-link-tcp" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", @@ -3795,8 +3792,8 @@ dependencies = [ [[package]] name = "zenoh-link-tls" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-rustls", "async-std", @@ -3818,8 +3815,8 @@ dependencies = [ [[package]] name = "zenoh-link-udp" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", @@ -3837,8 +3834,8 @@ dependencies = [ [[package]] name = "zenoh-link-unixsock_stream" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", @@ -3855,8 +3852,8 @@ dependencies = [ [[package]] name = "zenoh-link-ws" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", @@ -3875,8 +3872,8 @@ dependencies = [ [[package]] name = "zenoh-macros" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "proc-macro2", "quote", @@ -3892,6 +3889,7 @@ version = "0.10.0-dev" dependencies = [ "async-global-executor", "async-std", + "async-trait", "atoi", "ctrlc", "duration-string", @@ -3921,8 +3919,8 @@ dependencies = [ [[package]] name = "zenoh-plugin-trait" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "libloading", "log 0.4.20", @@ -3934,8 +3932,8 @@ dependencies = [ [[package]] name = "zenoh-protocol" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "const_format", "hex", @@ -3950,16 +3948,16 @@ dependencies = [ [[package]] name = "zenoh-result" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "anyhow", ] [[package]] name = "zenoh-sync" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "event-listener", @@ -3973,8 +3971,8 @@ dependencies = [ [[package]] name = "zenoh-transport" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-executor", "async-global-executor", @@ -4004,8 +4002,8 @@ dependencies = [ [[package]] name = "zenoh-util" -version = "0.10.0-dev" -source = "git+https://github.com/eclipse-zenoh/zenoh.git#46c8fa1f13ac8bab76366332bf30585b53be9d11" +version = "0.10.0-rc" +source = "git+https://github.com/eclipse-zenoh/zenoh.git?branch=release-0.10.0-rc#37f80d9befc757ca091a748e41217b8cd1bdf16c" dependencies = [ "async-std", "async-trait", diff --git a/Cargo.toml b/Cargo.toml index 198ab0c..3c42522 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -17,6 +17,7 @@ members = [ "zenoh-bridge-ros1", "zenoh-plugin-ros1", ] +exclude = [ "rosrust" ] [workspace.package] version = "0.10.0-dev" @@ -33,6 +34,7 @@ categories = ["network-programming"] [workspace.dependencies] atoi = "2.0.0" async-std = "=1.12.0" +async-trait = "0.1" clap = "3.2.23" ctrlc = "3.2.5" env_logger = "0.9.1" @@ -47,11 +49,11 @@ rand = "0.8.5" strum = "0.24" strum_macros = "0.24" duration-string = "0.3.0" -zenoh = { git = "https://github.com/eclipse-zenoh/zenoh.git", features = ["unstable"] } -zenoh-ext = { git = "https://github.com/eclipse-zenoh/zenoh.git", features = ["unstable"] } -zenoh-core = { git = "https://github.com/eclipse-zenoh/zenoh.git" } -zenoh-plugin-trait = { git = "https://github.com/eclipse-zenoh/zenoh.git", default-features = false } -rosrust = { git = "https://github.com/ZettaScaleLabs/rosrust.git", branch = "feature/fix_bugs" } +zenoh = { version = "0.10.0-rc", git = "https://github.com/eclipse-zenoh/zenoh.git", branch = "release-0.10.0-rc" } +zenoh-ext = { version = "0.10.0-rc", git = "https://github.com/eclipse-zenoh/zenoh.git", branch = "release-0.10.0-rc" } +zenoh-core = { version = "0.10.0-rc", git = "https://github.com/eclipse-zenoh/zenoh.git", branch = "release-0.10.0-rc" } +zenoh-plugin-trait = { version = "0.10.0-rc", git = "https://github.com/eclipse-zenoh/zenoh.git", branch = "release-0.10.0-rc", default-features = false } +rosrust = { version = "0.9.11", path = "rosrust/rosrust" } flume = "0.11" hex = "0.4.3" xml-rpc = "0.0.12" diff --git a/Cross.toml b/Cross.toml new file mode 100644 index 0000000..127ef5e --- /dev/null +++ b/Cross.toml @@ -0,0 +1,18 @@ +[target.x86_64-unknown-linux-musl] +image = "jenoch/rust-cross:x86_64-unknown-linux-musl" + +[target.arm-unknown-linux-gnueabi] +image = "jenoch/rust-cross:arm-unknown-linux-gnueabi" + +[target.arm-unknown-linux-gnueabihf] +image = "jenoch/rust-cross:arm-unknown-linux-gnueabihf" + +[target.armv7-unknown-linux-gnueabihf] +image = "jenoch/rust-cross:armv7-unknown-linux-gnueabihf" + +[target.aarch64-unknown-linux-gnu] +image = "jenoch/rust-cross:aarch64-unknown-linux-gnu" + +[target.aarch64-unknown-linux-musl] +image = "jenoch/rust-cross:aarch64-unknown-linux-musl" + diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..f3d2286 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,55 @@ +# +# Copyright (c) 2022 ZettaScale Technology +# +# This program and the accompanying materials are made available under the +# terms of the Eclipse Public License 2.0 which is available at +# http://www.eclipse.org/legal/epl-2.0, or the Apache License, Version 2.0 +# which is available at https://www.apache.org/licenses/LICENSE-2.0. +# +# SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 +# +# Contributors: +# ZettaScale Zenoh Team, +# + + +### +### Build part +### +FROM rust:slim-buster as builder + +WORKDIR /usr/src/zenoh-plugin-ros1 + +# List of installed tools: +# * for zenoh-plugin-ros1 +# - git +# - clang +RUN apt-get update && apt-get -y install git clang build-essential + +COPY . . +# if exists, copy .git directory to be used by git-version crate to determine the version +COPY .gi? .git/ + +RUN cargo install --locked --path zenoh-bridge-ros1 + + +### +### Run part +### +FROM debian:buster-slim + +COPY --from=builder /usr/local/cargo/bin/zenoh-bridge-ros1 /usr/local/bin/zenoh-bridge-ros1 +RUN ldconfig -v + +RUN echo '#!/bin/bash' > /entrypoint.sh +RUN echo 'echo " * Starting: zenoh-bridge-ros1 $*"' >> /entrypoint.sh +RUN echo 'exec zenoh-bridge-ros1 $*' >> /entrypoint.sh +RUN chmod +x /entrypoint.sh + +EXPOSE 7446/udp +EXPOSE 7447/tcp +EXPOSE 8000/tcp + +ENV RUST_LOG info + +ENTRYPOINT ["/entrypoint.sh"] diff --git a/NOTICE.md b/NOTICE.md new file mode 100644 index 0000000..5b6751c --- /dev/null +++ b/NOTICE.md @@ -0,0 +1,41 @@ +# Notices for Eclipse zenoh-plugin-ros1 + +This content is produced and maintained by the Eclipse zenoh project. + + * Project home: https://projects.eclipse.org/projects/iot.zenoh + +## Trademarks + +Eclipse zenoh is trademark of the Eclipse Foundation. +Eclipse, and the Eclipse Logo are registered trademarks of the Eclipse Foundation. + +## Copyright + +All content is the property of the respective authors or their employers. +For more information regarding authorship of content, please consult the +listed source code repository logs. + +## Declared Project Licenses + +This program and the accompanying materials are made available under the +terms of the Eclipse Public License 2.0 which is available at +http://www.eclipse.org/legal/epl-2.0, or the Apache License, Version 2.0 +which is available at https://www.apache.org/licenses/LICENSE-2.0. + +SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 + +## Source Code + +The project maintains the following source code repositories: + + * https://github.com/eclipse-zenoh/zenoh.git + * https://github.com/eclipse-zenoh/zenoh-c.git + * https://github.com/eclipse-zenoh/zenoh-java.git + * https://github.com/eclipse-zenoh/zenoh-go.git + * https://github.com/eclipse-zenoh/zenoh-python.git + * https://github.com/eclipse-zenoh/zenoh-plugin-dds.git + +## Third-party Content + + *To be completed...* + diff --git a/rosrust b/rosrust new file mode 160000 index 0000000..ff2ed4f --- /dev/null +++ b/rosrust @@ -0,0 +1 @@ +Subproject commit ff2ed4fe87ae3579ab64453345e54afae7a594a4 diff --git a/zenoh-plugin-ros1/Cargo.toml b/zenoh-plugin-ros1/Cargo.toml index a792380..9f558f8 100644 --- a/zenoh-plugin-ros1/Cargo.toml +++ b/zenoh-plugin-ros1/Cargo.toml @@ -42,6 +42,7 @@ log = { workspace = true } serde = { workspace = true } serde_json = { workspace = true } async-global-executor = { workspace = true } +async-trait = { workspace = true } rand = { workspace = true } strum = { workspace = true } strum_macros = { workspace = true } @@ -73,4 +74,4 @@ maintainer = "zenoh-dev@eclipse.org" copyright = "2017, 2022 ZettaScale Technology Inc." section = "net" license-file = ["../LICENSE", "0"] -depends = "zenohd (=0.10.0-dev)" \ No newline at end of file +depends = "zenohd (=0.10.0-dev)" diff --git a/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/rosclient_test_helpers.rs b/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/rosclient_test_helpers.rs index 7c2bcc3..5c6c77e 100644 --- a/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/rosclient_test_helpers.rs +++ b/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/rosclient_test_helpers.rs @@ -16,25 +16,22 @@ use std::time::Duration; use rosrust::{Publisher, RawMessage, Subscriber}; -use super::{ros1_client::Ros1Client, test_helpers::wait}; +use super::{ros1_client::Ros1Client, test_helpers::wait_sync}; pub fn wait_for_rosclient_to_connect(rosclient: &Ros1Client) -> bool { - async_std::task::block_on(wait( - || rosclient.topic_types().is_ok(), - Duration::from_secs(10), - )) + wait_sync(|| rosclient.topic_types().is_ok(), Duration::from_secs(10)) } pub fn wait_for_publishers(subscriber: &Subscriber, count: usize) -> bool { - async_std::task::block_on(wait( + wait_sync( || subscriber.publisher_count() == count, Duration::from_secs(10), - )) + ) } pub fn wait_for_subscribers(publisher: &Publisher, count: usize) -> bool { - async_std::task::block_on(wait( + wait_sync( || publisher.subscriber_count() == count, Duration::from_secs(10), - )) + ) } diff --git a/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/test_helpers.rs b/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/test_helpers.rs index d1eae1a..e53b7c8 100644 --- a/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/test_helpers.rs +++ b/zenoh-plugin-ros1/src/ros_to_zenoh_bridge/test_helpers.rs @@ -12,6 +12,9 @@ // ZettaScale Zenoh Team, // +use async_std::prelude::FutureExt; +use async_trait::async_trait; +use futures::Future; use log::error; use rosrust::{Client, RawMessage, RawMessageDescription}; use std::process::Command; @@ -19,11 +22,13 @@ use std::sync::atomic::AtomicBool; use std::sync::atomic::AtomicUsize; use std::sync::atomic::Ordering::*; use std::sync::{Arc, Mutex, RwLock}; +use std::time::Duration; use std::{net::SocketAddr, str::FromStr, sync::atomic::AtomicU16}; use zenoh::config::ModeDependentValue; use zenoh::prelude::OwnedKeyExpr; use zenoh::prelude::SplitBuffer; use zenoh::sample::Sample; +use zenoh::Session; use zenoh_core::{bail, zlock, zresult::ZResult, AsyncResolve, SyncResolve}; use super::discovery::LocalResources; @@ -77,7 +82,7 @@ impl IsolatedROSMaster { } } -pub async fn wait(waiter: Waiter, timeout: core::time::Duration) -> bool +pub fn wait_sync(waiter: Waiter, timeout: Duration) -> bool where Waiter: Fn() -> bool, { @@ -85,17 +90,43 @@ where let millis = timeout.as_millis() / cycles + 1; for _i in 0..cycles { - async_std::task::sleep(core::time::Duration::from_millis( - millis.try_into().unwrap(), - )) - .await; if waiter() { return true; } + std::thread::sleep(Duration::from_millis(millis.try_into().unwrap())); } false } +pub async fn wait_async_fn(waiter: Waiter, timeout: Duration) -> bool +where + Waiter: Fn() -> bool, +{ + let sleep_millis = 10u64; + let cycles = (timeout.as_millis() as u64) / sleep_millis + 1; + + for _i in 0..cycles { + if waiter() { + return true; + } + async_std::task::sleep(Duration::from_millis(sleep_millis)).await; + } + false +} + +pub async fn wait_async(waiter: Waiter, timeout: Duration) -> bool +where + Waiter: Fn() -> Fut + Send + Sync, + Fut: Future, +{ + let w = async { + while !waiter().await { + async_std::task::sleep(Duration::from_millis(10)).await + } + }; + w.timeout(timeout).await.is_ok() +} + pub struct RunningBridge { flag: Arc, @@ -152,14 +183,11 @@ impl RunningBridge { self.assert_status(RosStatus::Ok).await; } pub async fn assert_status(&self, status: RosStatus) { - assert!( - self.wait_ros_status(status, core::time::Duration::from_secs(10)) - .await - ); + assert!(self.wait_ros_status(status, Duration::from_secs(10)).await); } - pub async fn wait_ros_status(&self, status: RosStatus, timeout: core::time::Duration) -> bool { - wait( - move || { + pub async fn wait_ros_status(&self, status: RosStatus, timeout: Duration) -> bool { + wait_async_fn( + || { let val = self.ros_status.lock().unwrap(); *val == status }, @@ -173,16 +201,16 @@ impl RunningBridge { } pub async fn assert_bridge_status BridgeStatus>(&self, status: F) { assert!( - self.wait_bridge_status(status, core::time::Duration::from_secs(120)) + self.wait_bridge_status(status, Duration::from_secs(120)) .await ); } pub async fn wait_bridge_status BridgeStatus>( &self, status: F, - timeout: core::time::Duration, + timeout: Duration, ) -> bool { - wait( + wait_async_fn( move || { let expected = (status)(); let real = self.bridge_status.lock().unwrap(); @@ -252,6 +280,7 @@ impl ROSEnvironment { } pub struct BridgeChecker { + session: Arc, ros_client: ros1_client::Ros1Client, zenoh_client: zenoh_client::ZenohClient, pub local_resources: LocalResources, @@ -263,6 +292,7 @@ impl BridgeChecker { pub fn new(config: zenoh::config::Config, ros_master_uri: &str) -> BridgeChecker { let session = zenoh::open(config).res_sync().unwrap().into_arc(); BridgeChecker { + session: session.clone(), ros_client: ros1_client::Ros1Client::new("test_ros_node", ros_master_uri).unwrap(), zenoh_client: zenoh_client::ZenohClient::new(session.clone()), local_resources: LocalResources::new("*".to_string(), "*".to_string(), session), @@ -270,6 +300,19 @@ impl BridgeChecker { } } + pub async fn assert_zenoh_peers(&self, peer_count: usize) { + assert!( + self.wait_for_zenoh_peers(peer_count, Duration::from_secs(30)) + .await + ); + } + + async fn wait_for_zenoh_peers(&self, peer_count: usize, timeout: Duration) -> bool { + let waiter = + || async { self.session.info().peers_zid().res_async().await.count() == peer_count }; + wait_async(waiter, timeout).await + } + pub async fn make_zenoh_subscriber( &self, name: &str, @@ -607,9 +650,10 @@ impl Drop for ROS1Client { } } -pub trait Publisher { +#[async_trait] +pub trait Publisher: Sync { fn put(&self, data: Vec); - fn ready(&self) -> bool { + async fn ready(&self) -> bool { true } } @@ -619,6 +663,7 @@ impl Publisher for ZenohPublisher { async_std::task::spawn_blocking(move || inner.put(data).res_sync().unwrap()); } } +#[async_trait] impl Publisher for ROS1Publisher { fn put(&self, data: Vec) { let inner = self.inner.clone(); @@ -627,10 +672,11 @@ impl Publisher for ROS1Publisher { }); } - fn ready(&self) -> bool { + async fn ready(&self) -> bool { self.inner.data.subscriber_count() != 0 } } +#[async_trait] impl Publisher for ZenohQuery { fn put(&self, data: Vec) { async_std::task::spawn(Self::query_loop( @@ -642,14 +688,14 @@ impl Publisher for ZenohQuery { )); } - fn ready(&self) -> bool { + async fn ready(&self) -> bool { let data = (0..10).collect(); - async_std::task::block_on( - async move { Self::make_query(&self.inner, &self.key, &data).await }, - ) - .is_ok() + Self::make_query(&self.inner, &self.key, &data) + .await + .is_ok() } } +#[async_trait] impl Publisher for ROS1Client { fn put(&self, data: Vec) { let running = self.running.clone(); @@ -666,14 +712,18 @@ impl Publisher for ROS1Client { }); } - fn ready(&self) -> bool { + async fn ready(&self) -> bool { let description = RawMessageDescription { msg_definition: String::from("*"), md5sum: self.topic.md5.clone(), msg_type: self.topic.datatype.clone(), }; let data = (0..10).collect(); - Self::make_query(description, &data, &self.ros1_client).is_ok() + let ros1_client = self.ros1_client.clone(); + async_std::task::spawn_blocking(move || { + Self::make_query(description, &data, &ros1_client).is_ok() + }) + .await } } @@ -690,7 +740,7 @@ pub struct ROS1Service { pub _inner: RAIICounter, } -pub trait Subscriber { +pub trait Subscriber: Sync { fn ready(&self) -> bool { true } diff --git a/zenoh-plugin-ros1/tests/bridge_to_bridge.rs b/zenoh-plugin-ros1/tests/bridge_to_bridge.rs index 702fbd4..edb75e0 100644 --- a/zenoh-plugin-ros1/tests/bridge_to_bridge.rs +++ b/zenoh-plugin-ros1/tests/bridge_to_bridge.rs @@ -13,14 +13,18 @@ // use std::sync::Arc; +use std::time::Duration; use std::{collections::HashSet, sync::atomic::AtomicU64}; +use async_std::prelude::FutureExt; use log::{debug, trace}; use rosrust::RawMessage; use std::sync::atomic::{AtomicUsize, Ordering::*}; use strum_macros::Display; use zenoh::prelude::{KeyExpr, OwnedKeyExpr}; -use zenoh_plugin_ros1::ros_to_zenoh_bridge::test_helpers::{self, wait, Publisher, Subscriber}; +use zenoh_plugin_ros1::ros_to_zenoh_bridge::test_helpers::{ + self, wait_async, Publisher, Subscriber, +}; use zenoh_plugin_ros1::ros_to_zenoh_bridge::{ bridging_mode::BridgingMode, environment::Environment, @@ -193,27 +197,42 @@ impl SrcDstPair { async fn start(&self) { self.wait_for_ready().await; - self.start_ping_pong().await; + assert!(self.start_ping_pong().await); } async fn wait_for_ready(&self) { assert!( - wait( - move || { self.src.ready() && self.dst.ready() }, + wait_async( + || async { self.src.ready().await && self.dst.ready() }, core::time::Duration::from_secs(30) ) .await ); } - async fn start_ping_pong(&self) { + async fn start_ping_pong(&self) -> bool { debug!("Starting ping-pong!"); let mut data = Vec::new(); data.reserve(TestParams::data_size() as usize); for i in 0..TestParams::data_size() { data.push((i % 255) as u8); } - self.src.put(data.clone()); + + async { + while { + self.src.put(data.clone()); + !test_helpers::wait_async_fn( + || self.counter.load(Relaxed) > 0, + Duration::from_secs(5), + ) + .await + } { + debug!("Restarting ping-pong!"); + } + } + .timeout(Duration::from_secs(30)) + .await + .is_ok() } async fn check_pps(&self, pps_measurements: u32) { diff --git a/zenoh-plugin-ros1/tests/discovery_test.rs b/zenoh-plugin-ros1/tests/discovery_test.rs index 04b1203..c02fc33 100644 --- a/zenoh-plugin-ros1/tests/discovery_test.rs +++ b/zenoh-plugin-ros1/tests/discovery_test.rs @@ -27,7 +27,7 @@ use zenoh_plugin_ros1::ros_to_zenoh_bridge::{ topic_descriptor::TopicDescriptor, }; -const TIMEOUT: Duration = Duration::from_secs(10); +const TIMEOUT: Duration = Duration::from_secs(60); fn session_builder(cfg: &IsolatedConfig) -> OpenBuilder { zenoh::open(cfg.peer()) diff --git a/zenoh-plugin-ros1/tests/ping_pong_test.rs b/zenoh-plugin-ros1/tests/ping_pong_test.rs index 3ae33c1..44a0a48 100644 --- a/zenoh-plugin-ros1/tests/ping_pong_test.rs +++ b/zenoh-plugin-ros1/tests/ping_pong_test.rs @@ -12,6 +12,7 @@ // ZettaScale Zenoh Team, // +use async_std::prelude::FutureExt; use strum_macros::Display; use zenoh::prelude::SplitBuffer; use zenoh_core::SyncResolve; @@ -22,15 +23,16 @@ use std::{ atomic::{AtomicBool, AtomicU64, Ordering::*}, Arc, }, + time::Duration, }; use zenoh_plugin_ros1::ros_to_zenoh_bridge::{ bridging_mode::BridgingMode, environment::Environment, test_helpers::{ - BridgeChecker, Publisher, ROS1Client, ROS1Publisher, ROS1Service, ROS1Subscriber, - ROSEnvironment, RunningBridge, Subscriber, TestParams, ZenohPublisher, ZenohQuery, - ZenohQueryable, ZenohSubscriber, + self, wait_async_fn, BridgeChecker, Publisher, ROS1Client, ROS1Publisher, ROS1Service, + ROS1Subscriber, ROSEnvironment, RunningBridge, Subscriber, TestParams, ZenohPublisher, + ZenohQuery, ZenohQueryable, ZenohSubscriber, }, }; use zenoh_plugin_ros1::ros_to_zenoh_bridge::{ @@ -234,13 +236,13 @@ impl PingPong { let rpub = ros1_pub.clone(); let zenoh_sub = backend .make_zenoh_subscriber(key, move |msg| { + c.fetch_add(1, Relaxed); let data = msg.value.payload.contiguous().to_vec(); debug!( "PingPong: transferring {} bytes from Zenoh to ROS1!", data.len() ); rpub.data.send(rosrust::RawMessage(data)).unwrap(); - c.fetch_add(1, Relaxed); }) .await; @@ -268,12 +270,12 @@ impl PingPong { let c = cycles.clone(); let zpub = zenoh_pub.clone(); let ros1_sub = backend.make_ros_subscriber(key, move |msg: rosrust::RawMessage| { + c.fetch_add(1, Relaxed); debug!( "PingPong: transferring {} bytes from ROS1 to Zenoh!", msg.0.len() ); zpub.put(msg.0).res_sync().unwrap(); - c.fetch_add(1, Relaxed); }); PingPong { @@ -289,17 +291,28 @@ impl PingPong { async fn start(&self) { self.wait_for_pub_sub_ready().await; - self.start_ping_pong().await; + assert!(self.start_ping_pong().await); } - async fn start_ping_pong(&self) { + async fn start_ping_pong(&self) -> bool { debug!("Starting ping-pong!"); let mut data = Vec::new(); data.reserve(TestParams::data_size() as usize); for i in 0..TestParams::data_size() { data.push((i % 255) as u8); } - self.pub_sub.publisher.put(data.clone()); + + async { + while { + self.pub_sub.publisher.put(data.clone()); + !wait_async_fn(|| self.cycles.load(Relaxed) > 0, Duration::from_secs(5)).await + } { + debug!("Restarting ping-pong!"); + } + } + .timeout(Duration::from_secs(30)) + .await + .is_ok() } async fn check_pps(&self, pps_measurements: u32) { @@ -319,8 +332,8 @@ impl PingPong { let mut duration: u64 = 0; self.cycles.store(0, Relaxed); - while !(result > 0.0 || duration >= 10000) { - async_std::task::sleep(core::time::Duration::from_millis(duration_milliseconds)).await; + while !(result > 0.0 || duration >= 30000) { + async_std::task::sleep(Duration::from_millis(duration_milliseconds)).await; duration += duration_milliseconds; result += self.cycles.load(Relaxed) as f64; } @@ -330,32 +343,14 @@ impl PingPong { async fn wait_for_pub_sub_ready(&self) { assert!( - Self::wait( - move || { self.pub_sub.publisher.ready() && self.pub_sub.subscriber.ready() }, - core::time::Duration::from_secs(30) + test_helpers::wait_async( + || async { + self.pub_sub.publisher.ready().await && self.pub_sub.subscriber.ready() + }, + Duration::from_secs(30) ) .await ); - async_std::task::sleep(time::Duration::from_secs(1)).await; - } - - async fn wait(waiter: Waiter, timeout: core::time::Duration) -> bool - where - Waiter: Fn() -> bool, - { - let cycles = 1000; - let micros = timeout.as_micros() / cycles; - - for _i in 0..cycles { - async_std::task::sleep(core::time::Duration::from_micros( - micros.try_into().unwrap(), - )) - .await; - if waiter() { - return true; - } - } - false } } @@ -383,6 +378,7 @@ impl TestEnvironment { // - performs wait and ensures that everything is properly connected and negotiated within the bridge async_std::task::block_on(bridge.assert_ros_ok()); async_std::task::block_on(bridge.assert_bridge_empy()); + async_std::task::block_on(checker.assert_zenoh_peers(1)); TestEnvironment { bridge,