diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 0000000..bc5e930 --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,10 @@ +version: 2 +updates: + - package-ecosystem: "cargo" + directory: "." + schedule: + interval: "daily" + - package-ecosystem: "github-actions" + directory: "." + schedule: + interval: "daily" diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 7cf6e1c..0b0529f 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -10,28 +10,28 @@ env: jobs: build: - name: Build project runs-on: ubuntu-latest - if: "!contains(github.event.head_commit.message, '[ci skip]')" - steps: - - name: Checkout code - uses: actions/checkout@v3 + - name: "ACTIONS: Checkout" + uses: actions/checkout@v4 - - name: Install rust toolchain + - name: "Install: Rust toolchain" uses: dsherret/rust-toolchain-file@v1 - - name: Cache + - name: "ACTIONS: Setup caching" uses: Swatinem/rust-cache@v2 - - name: Cargo build + - name: "Build" run: cargo build --release - - name: Cargo test + - name: "Test" run: cargo test --release - - name: Cargo clippy + - name: "Test: Doc examples" + run: cargo test --release --doc + + - name: "Check clippy" run: cargo clippy --release --all-targets -- -D warnings - - name: Cargo fmt + - name: "Check formatting" run: cargo fmt -- --check diff --git a/.github/workflows/crates-io.yml b/.github/workflows/crates-io.yml new file mode 100644 index 0000000..6232130 --- /dev/null +++ b/.github/workflows/crates-io.yml @@ -0,0 +1,32 @@ +name: Crates IO + +on: + workflow_dispatch: + inputs: + publish: + description: "If publish packages" + type: boolean + default: false + +env: + CARGO_TERM_COLOR: always + +jobs: + check: + runs-on: ubuntu-latest + env: + CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }} + steps: + - name: "ACTIONS: Checkout" + uses: actions/checkout@v4 + + - name: "Install: Rust toolchain" + uses: dsherret/rust-toolchain-file@v1 + + - name: "Check packages" + if: ${{ !inputs.publish }} + run: cargo publish --dry-run + + - name: "Publish packages" + if: ${{ inputs.publish }} + run: cargo publish diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml deleted file mode 100644 index da7af9c..0000000 --- a/.github/workflows/docs.yml +++ /dev/null @@ -1,50 +0,0 @@ -name: Docs - -on: - push: - branches: [ master ] - pull_request: - branches: [ master ] - workflow_dispatch: - -permissions: - id-token: write - pages: write - -env: - CARGO_TERM_COLOR: always - -jobs: - docs: - runs-on: ubuntu-latest - if: github.actor != 'dependabot[bot]' - steps: - - uses: actions/checkout@v3 - - - name: Cache - uses: Swatinem/rust-cache@v2 - - - name: Test doc examples - if: github.event_name == 'pull_request' - run: cargo test --doc - - - name: Build docs - env: - RUSTDOCFLAGS: --enable-index-page -Zunstable-options - run: | - cargo doc --no-deps --workspace - rm -f target/doc/.lock - - - name: Setup GitHub Pages - if: github.event_name == 'push' - uses: actions/configure-pages@v3 - - - name: Upload Pages artifact - if: github.event_name == 'push' - uses: actions/upload-pages-artifact@v2 - with: - path: target/doc - - - name: Deploy to GitHub Pages - if: github.event_name == 'push' - uses: actions/deploy-pages@v2 diff --git a/.github/workflows/sync.yml b/.github/workflows/sync.yml new file mode 100644 index 0000000..711a448 --- /dev/null +++ b/.github/workflows/sync.yml @@ -0,0 +1,35 @@ +name: Sync version + +on: + workflow_dispatch: + +permissions: + contents: write + +jobs: + sync: + runs-on: ubuntu-latest + steps: + - name: "ACTIONS: Checkout" + uses: actions/checkout@v4 + + - name: "Versioning: Sync version with gstd" + run: | + CRATE_NAME="gstd" + GSTD_VERSION=$( + curl -s https://crates.io/api/v1/crates/$CRATE_NAME/versions | + jq -r '.versions[] | .num' | grep -E "^[0-9]+\.[0-9]+\.[0-9]+$" | + head -n 1 + ) + + # version = "x.y.z" -> version = "$GSTD_VERSION" + sed -i 's/\(^version = "\)\([0-9]\+\.[0-9]\+\.[0-9]\+\)/\1'$GSTD_VERSION'/' Cargo.toml + # gstd = { version = "=x.y.z", ... } -> gstd = { version = "=$GSTD_VERSION", ... } + sed -i 's/\(gstd = { version = "=\)\([0-9]\+\.[0-9]\+\.[0-9]\+\)/\1'$GSTD_VERSION'/' Cargo.toml + + - name: "ACTIONS: Create commit" + uses: stefanzweifel/git-auto-commit-action@v5 + with: + commit_message: >- + chore(deps): sync with latest gstd version + file_pattern: Cargo.toml diff --git a/Cargo.toml b/Cargo.toml index c6468bc..9c7361f 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "gstd-fluent" -version = "0.1.0" +version = "1.3.0" authors = ["Gear Technologies"] edition = "2021" description = "A wrapper over gstd that provides a fluent interface to interact with the Gear Protocol" @@ -10,7 +10,17 @@ keywords = ["gstd", "smart-contracts", "gear-tech", "gear-foundation"] categories = ["api-bindings", "no-std"] [dependencies] -gstd = { git = "https://github.com/gear-tech/gear.git", rev = "946ac47" } +gstd = { version = "=1.3.0", default-features = false } [features] +default = ["panic-message"] + +panic-handler = ["gstd/panic-handler"] +panic-message = ["gstd/panic-message"] +panic-location = ["gstd/panic-location"] + +nightly = ["gstd/nightly"] +panic-info-message = ["gstd/panic-info-message"] +oom-handler = ["gstd/oom-handler"] + debug = ["gstd/debug"] diff --git a/README.md b/README.md index 450206e..04d6447 100644 --- a/README.md +++ b/README.md @@ -10,16 +10,17 @@ [lic_badge]: https://img.shields.io/badge/License-MIT-success [lic_href]: LICENSE -[docs_badge]: https://img.shields.io/badge/Docs-online-5023dd -[docs_href]: https://dapp.rs/gstd-fluent/gstd_fluent/ +[docs_badge]: https://img.shields.io/badge/Docs-online-5023dd?logo=rust +[docs_href]: https://docs.rs/gstd-fluent/ A wrapper over [gstd](https://github.com/gear-tech/gear/tree/master/gstd) that provides a fluent interface to interact with the Gear Protocol. To use the default implementation, you should replace `gstd` with `gstd-fluent` in your `Cargo.toml` file: -```toml -gstd-fluent = { git = "https://github.com/gear-foundation/gstd-fluent.git" } +```diff +- gstd = "x.y.z" ++ gstd-fluent = "x.y.z" ``` Then update your code like this: diff --git a/rust-toolchain.toml b/rust-toolchain.toml index bebef8b..a9c63a6 100644 --- a/rust-toolchain.toml +++ b/rust-toolchain.toml @@ -1,5 +1,4 @@ [toolchain] -channel = "nightly-2023-04-25" +channel = "stable" targets = ["wasm32-unknown-unknown"] -profile = "minimal" -components = ["rustfmt", "clippy"] +profile = "default" diff --git a/src/functions.rs b/src/functions.rs index 4084e0c..c0ff596 100644 --- a/src/functions.rs +++ b/src/functions.rs @@ -46,9 +46,17 @@ pub fn send_input>( } /// Creates a builder that allows to create a new program from the already existing on-chain code. -pub fn create_program>( +pub fn create_program_bytes>( code_id: CodeId, payload: Buffer, ) -> CreateProgramBuilder<(CodeIdW, PayloadBytesW, (), (), ())> { CreateProgramBuilder::bytes(code_id, payload) } + +/// Creates a builder that allows to create a new program from the already existing on-chain code. +pub fn create_program( + code_id: CodeId, + payload: Encodable, +) -> CreateProgramBuilder<(CodeIdW, PayloadEncodableW, (), (), ())> { + CreateProgramBuilder::encode(code_id, payload) +} diff --git a/src/generated/create_program.rs b/src/generated/create_program.rs index 280d60b..b1988c7 100644 --- a/src/generated/create_program.rs +++ b/src/generated/create_program.rs @@ -19,6 +19,14 @@ impl> CreateProgramBuilder<(CodeIdW, PayloadBytesW, } } +impl CreateProgramBuilder<(CodeIdW, PayloadEncodableW, (), (), ())> { + pub fn encode(code_id: CodeId, payload: Encodable) -> Self { + Self { + fields: (CodeIdW(code_id), PayloadEncodableW(payload), (), (), ()), + } + } +} + impl CreateProgramBuilder<(CodeId, Payload, (), Delay, GasLimit)> { pub fn with_value(self, value: u128) -> CreateProgramBuilder<(CodeId, Payload, ValueW, Delay, GasLimit)> { let (code_id, payload, _, delay, gas_limit) = self.fields; @@ -65,27 +73,55 @@ impl CreateProgramBuilder<(CodeId, Payload, Va impl, Value: Into> CreateProgramBuilder<(CodeIdW, PayloadBytesW, Value, (), ())> { pub fn execute(self) -> Result<(MessageId, ActorId)> { let (CodeIdW(code_id), PayloadBytesW(payload), value, _, _) = self.fields; - ProgramGenerator::create_program(code_id, payload, value.into().0) + ProgramGenerator::create_program_bytes(code_id, payload, value.into().0) } } impl, Value: Into> CreateProgramBuilder<(CodeIdW, PayloadBytesW, Value, (), GasLimitW)> { pub fn execute(self) -> Result<(MessageId, ActorId)> { let (CodeIdW(code_id), PayloadBytesW(payload), value, _, GasLimitW(gas_limit)) = self.fields; - ProgramGenerator::create_program_with_gas(code_id, payload, gas_limit, value.into().0) + ProgramGenerator::create_program_bytes_with_gas(code_id, payload, gas_limit, value.into().0) } } impl, Value: Into> CreateProgramBuilder<(CodeIdW, PayloadBytesW, Value, DelayW, ())> { pub fn execute(self) -> Result<(MessageId, ActorId)> { let (CodeIdW(code_id), PayloadBytesW(payload), value, DelayW(delay), _) = self.fields; - ProgramGenerator::create_program_delayed(code_id, payload, value.into().0, delay) + ProgramGenerator::create_program_bytes_delayed(code_id, payload, value.into().0, delay) } } impl, Value: Into> CreateProgramBuilder<(CodeIdW, PayloadBytesW, Value, DelayW, GasLimitW)> { pub fn execute(self) -> Result<(MessageId, ActorId)> { let (CodeIdW(code_id), PayloadBytesW(payload), value, DelayW(delay), GasLimitW(gas_limit)) = self.fields; + ProgramGenerator::create_program_bytes_with_gas_delayed(code_id, payload, gas_limit, value.into().0, delay) + } +} + +impl> CreateProgramBuilder<(CodeIdW, PayloadEncodableW, Value, (), ())> { + pub fn execute(self) -> Result<(MessageId, ActorId)> { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, _, _) = self.fields; + ProgramGenerator::create_program(code_id, payload, value.into().0) + } +} + +impl> CreateProgramBuilder<(CodeIdW, PayloadEncodableW, Value, (), GasLimitW)> { + pub fn execute(self) -> Result<(MessageId, ActorId)> { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, _, GasLimitW(gas_limit)) = self.fields; + ProgramGenerator::create_program_with_gas(code_id, payload, gas_limit, value.into().0) + } +} + +impl> CreateProgramBuilder<(CodeIdW, PayloadEncodableW, Value, DelayW, ())> { + pub fn execute(self) -> Result<(MessageId, ActorId)> { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, DelayW(delay), _) = self.fields; + ProgramGenerator::create_program_delayed(code_id, payload, value.into().0, delay) + } +} + +impl> CreateProgramBuilder<(CodeIdW, PayloadEncodableW, Value, DelayW, GasLimitW)> { + pub fn execute(self) -> Result<(MessageId, ActorId)> { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, DelayW(delay), GasLimitW(gas_limit)) = self.fields; ProgramGenerator::create_program_with_gas_delayed(code_id, payload, gas_limit, value.into().0, delay) } } @@ -111,27 +147,55 @@ impl CreateProgramBuilderForReply<( impl, Value: Into, ReplyDeposit: Into> CreateProgramBuilderForReply<(CodeIdW, PayloadBytesW, Value, (), ReplyDeposit, ())> { pub fn execute(self) -> Result { let (CodeIdW(code_id), PayloadBytesW(payload), value, _, reply_deposit, _) = self.fields; - ProgramGenerator::create_program_for_reply(code_id, payload, value.into().0, reply_deposit.into().0) + ProgramGenerator::create_program_bytes_for_reply(code_id, payload, value.into().0, reply_deposit.into().0) } } impl, Value: Into, ReplyDeposit: Into> CreateProgramBuilderForReply<(CodeIdW, PayloadBytesW, Value, GasLimitW, ReplyDeposit, ())> { pub fn execute(self) -> Result { let (CodeIdW(code_id), PayloadBytesW(payload), value, GasLimitW(gas_limit), reply_deposit, _) = self.fields; - ProgramGenerator::create_program_with_gas_for_reply(code_id, payload, gas_limit, value.into().0, reply_deposit.into().0) + ProgramGenerator::create_program_bytes_with_gas_for_reply(code_id, payload, gas_limit, value.into().0, reply_deposit.into().0) } } impl, Value: Into, ReplyDeposit: Into, Decodable: Decode> CreateProgramBuilderForReply<(CodeIdW, PayloadBytesW, Value, (), ReplyDeposit, DecodableW)> { pub fn execute(self) -> Result> { let (CodeIdW(code_id), PayloadBytesW(payload), value, _, reply_deposit, _) = self.fields; - ProgramGenerator::create_program_for_reply_as(code_id, payload, value.into().0, reply_deposit.into().0) + ProgramGenerator::create_program_bytes_for_reply_as(code_id, payload, value.into().0, reply_deposit.into().0) } } impl, Value: Into, ReplyDeposit: Into, Decodable: Decode> CreateProgramBuilderForReply<(CodeIdW, PayloadBytesW, Value, GasLimitW, ReplyDeposit, DecodableW)> { pub fn execute(self) -> Result> { let (CodeIdW(code_id), PayloadBytesW(payload), value, GasLimitW(gas_limit), reply_deposit, _) = self.fields; + ProgramGenerator::create_program_bytes_with_gas_for_reply_as(code_id, payload, gas_limit, value.into().0, reply_deposit.into().0) + } +} + +impl, ReplyDeposit: Into> CreateProgramBuilderForReply<(CodeIdW, PayloadEncodableW, Value, (), ReplyDeposit, ())> { + pub fn execute(self) -> Result { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, _, reply_deposit, _) = self.fields; + ProgramGenerator::create_program_for_reply(code_id, payload, value.into().0, reply_deposit.into().0) + } +} + +impl, ReplyDeposit: Into> CreateProgramBuilderForReply<(CodeIdW, PayloadEncodableW, Value, GasLimitW, ReplyDeposit, ())> { + pub fn execute(self) -> Result { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, GasLimitW(gas_limit), reply_deposit, _) = self.fields; + ProgramGenerator::create_program_with_gas_for_reply(code_id, payload, gas_limit, value.into().0, reply_deposit.into().0) + } +} + +impl, ReplyDeposit: Into, Decodable: Decode> CreateProgramBuilderForReply<(CodeIdW, PayloadEncodableW, Value, (), ReplyDeposit, DecodableW)> { + pub fn execute(self) -> Result> { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, _, reply_deposit, _) = self.fields; + ProgramGenerator::create_program_for_reply_as(code_id, payload, value.into().0, reply_deposit.into().0) + } +} + +impl, ReplyDeposit: Into, Decodable: Decode> CreateProgramBuilderForReply<(CodeIdW, PayloadEncodableW, Value, GasLimitW, ReplyDeposit, DecodableW)> { + pub fn execute(self) -> Result> { + let (CodeIdW(code_id), PayloadEncodableW(payload), value, GasLimitW(gas_limit), reply_deposit, _) = self.fields; ProgramGenerator::create_program_with_gas_for_reply_as(code_id, payload, gas_limit, value.into().0, reply_deposit.into().0) } } diff --git a/src/lib.rs b/src/lib.rs index ccde9c1..86ab1e7 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,8 +1,8 @@ -//! A wrapper over [`gstd`](https://docs.gear.rs/gstd/) that provides a fluent interface to interact +//! A wrapper over [`gstd`](https://docs.rs/gstd/) that provides a fluent interface to interact //! with the Gear Protocol. //! //! This library can be used instead of the standard library when writing Gear programs. Compared to -//! the [`gstd`](https://docs.gear.rs/gstd/) crate, this library provides higher-level functions +//! the [`gstd`](https://docs.rs/gstd/) crate, this library provides higher-level functions //! that allow you to write Gear programs code in a more convenient way. //! //! ### Example @@ -125,7 +125,10 @@ //! //! // This is pseudo-code to show all possible methods //! fn how_to_use_create_program() { -//! builder::create_program(CodeId::default(), b"payload") +//! // Supported functions: +//! // - `builder::create_program(...)` +//! // - `builder::create_program_bytes(...)` +//! builder::create_program(CodeId::default(), String::from("payload")) //! // Possible methods (stage 1): //! .with_value(1) //! .with_delay(2)