4
  1. I initially tried the implementation as taught in this question. (How can I save string value on Substrate)
  2. However, an error occurred in relation to "ink_abi" and the struct could not be defined.
  3. Looking at the latest "ink! example"(), I tried to copy it because the struct was defined, but the following command does not work. (https://github.com/paritytech/ink/blob/master/examples/runtime-storage/lib.rs)
cargo +nightly generate-metadata
  1. How can I save the string data to the blockchain with "substrate ink!"?
  2. I would like to see a sample source if available.
Michael
  • 41,989
  • 11
  • 82
  • 128
s.Takahashi
  • 469
  • 4
  • 15

2 Answers2

3

Use ink_prelude::string::String

#![cfg_attr(not(feature = "std"), no_std)]
use ink_lang as ink;

#[ink::contract]
mod foo {
    use ink_prelude::string::String;

    // ...
}

And don't forget to add ink_prelude to your [dependencies] section in your .toml

see: https://paritytech.github.io/ink/ink_prelude/string/struct.String.html

2

In ink! you can directly use the String type.

Here is a simple implementation of an ink! contract doing this with tests (modified from the incrementer example:

#![cfg_attr(not(feature = "std"), no_std)]

use ink_lang as ink;

#[ink::contract(version = "0.1.0")]
mod basic_string {
    #[ink(storage)]
    struct BasicString {
        value: String,
    }

    impl BasicString {
        #[ink(constructor)]
        fn new(init_value: String) -> Self {
            Self { value: init_value }
        }

        #[ink(constructor)]
        fn default() -> Self {
            Self::new(Default::default())
        }

        #[ink(message)]
        fn set(&mut self, new: String) {
            self.value = new;
        }

        #[ink(message)]
        fn get(&self) -> String {
            self.value.clone()
        }
    }

    #[cfg(test)]
    mod tests {
        use super::*;

        #[test]
        fn default_works() {
            let contract = BasicString::default();
            assert_eq!(contract.get(), "");
        }

        #[test]
        fn it_works() {
            let mut contract = BasicString::new("Hello World!".into());
            assert_eq!(contract.get(), "Hello World!");
            contract.set("Goodbye!".into());
            assert_eq!(contract.get(), "Goodbye!");
        }
    }
}
Shawn Tabrizi
  • 12,206
  • 1
  • 38
  • 69
  • I never dreamed that "String" could be used as is. Thank you for your response. However, when the data registered in the blockchain is acquired by "RPC Call", the value is always ({"vec":{"elems":"0x3c5b6f626a656374204f626a6563745d"}}. Why? – s.Takahashi Aug 18 '20 at 08:46
  • 1
    I mentioned in your other post that this hex value converts to string `?<[object Object]`, which implies to me some JavaScript issues. We can follow up in you other post. – Shawn Tabrizi Aug 18 '20 at 12:04
  • 4
    @ShawnTabrizi hi, I tried to put ```String``` as the type in the struct but it failed due to error[E0412]: cannot find type `String` in this scope. – Afeez Aziz Jan 21 '21 at 13:00