亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

使用Java SDK實(shí)現(xiàn)離線簽名

 更新時間:2019年03月28日 10:05:53   作者:比原鏈Bytom  
這篇文章主要介紹了使用Java SDK實(shí)現(xiàn)離線簽名,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

嚴(yán)格來說,tx-signer并不屬于SDK,它是bytomd中構(gòu)建交易、對交易簽名兩大模塊的java實(shí)現(xiàn)版。因此,若想用tx-signer對交易進(jìn)行離線簽名,需要由你在本地保管好自己的私鑰。

如果你的目的是完全脫離于bytomd全節(jié)點(diǎn),可能需要自己做更多額外的工作。比如,在構(gòu)建交易時,需要花費(fèi)若干個utxo(Unspent Transaction Output)作為交易的輸入,如果沒有全節(jié)點(diǎn)則需要自身來維護(hù)utxo。當(dāng)使用tx-signer構(gòu)建完成一筆交易并簽名后,若沒有全節(jié)點(diǎn)的幫助,也需要自己實(shí)現(xiàn)P2P網(wǎng)絡(luò)協(xié)議將交易廣播到其他節(jié)點(diǎn)。

本文不會對以上技術(shù)細(xì)節(jié)進(jìn)行討論,而是利用bytomd全節(jié)點(diǎn)查詢可用的utxo構(gòu)建交易,對交易進(jìn)行簽名并序列化后,同樣使用bytomd提交交易。

準(zhǔn)備工作

將Maven依賴引入到你的項(xiàng)目中

獲取SDK源碼

git clone https://github.com/Bytom/bytom-java-sdk.git

打包成JAR包并安裝到本地的Maven倉庫

$ mvn clean install -DskipTests

在項(xiàng)目的POM文件中添加依賴。其中,第一個依賴是bytomd api的封裝,可用于查詢可用的utxo以及提交交易;第二個依賴用于構(gòu)建交易以及對交易進(jìn)行離線簽名。
 

  <dependency>
    <groupId>io.bytom</groupId>
    <artifactId>java-sdk</artifactId>
    <version>1.0.0</version>
  </dependency>
 
  <dependency>
    <groupId>io.bytom</groupId>
    <artifactId>tx-signer</artifactId>
    <version>1.0.0</version>
  </dependency>

構(gòu)建交易

普通交易

查詢可用的utxo

在本文中,以下將全部使用全節(jié)點(diǎn)來查詢可用的utxo,你也可以構(gòu)建一套自己的utxo維護(hù)方案。

Client client = Client.generateClient();
UnspentOutput.QueryBuilder builder = new UnspentOutput.QueryBuilder();
builder.accountAlias = "bytom";
List<UnspentOutput> outputs = builder.list(client);

利用SDK只需要四行代碼就能查詢可用的utxo(SDK具體文檔詳見java-sdk documentation)。在QueryBuilder中可以指定是否為未確認(rèn)的utxo(默認(rèn)false),也可以通過from和count來進(jìn)行分頁查詢(默認(rèn)查詢所有)。
假設(shè)在當(dāng)前賬戶下查詢得到這樣一個utxo:

{
  "account_alias": "bytom",
  "id": "ffdc59d0478277298de4afa458dfa7623c051a46b7a84939fb8227083411b156",
  "asset_id": "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
  "asset_alias": "BTM",
  "amount": 41250000000,
  "account_id": "0G1R52O1G0A02",
  "address": "sm1qxls6ajp6fejc0j5kp8jwt2nj3kmsqazfumrkrr",
  "control_program_index": 1,
  "program": "001437e1aec83a4e6587ca9609e4e5aa728db7007449",
  "source_id": "2d3a5d920833778cc7c65d7c96fe5f3c4a1a61aa086ee093f44a0522dd499a34",
  "source_pos": 0,
  "valid_height": 4767,
  "change": false,
  "derive_rule": 0
}

構(gòu)建交易

現(xiàn)在需要往0014c832e1579b4f96dc12dcfff39e8fe69a62d3f516這個control program轉(zhuǎn)100個BTM。代碼如下:

String btmAssetID = "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff";
// 下面的字段與utxo中的字段一一對應(yīng)
SpendInput input = new SpendInput();
input.setAssetId(btmAssetID);
input.setAmount(41250000000L);
input.setProgram("001437e1aec83a4e6587ca9609e4e5aa728db7007449");
input.setSourcePosition(0);
input.setSourceID("2d3a5d920833778cc7c65d7c96fe5f3c4a1a61aa086ee093f44a0522dd499a34");
input.setChange(false);
input.setControlProgramIndex(1);
// 選擇使用BIP32還是BIP44來派生地址,默認(rèn)BIP44
input.setBipProtocol(BIPProtocol.BIP44);
// 賬戶對應(yīng)的密鑰索引
input.setKeyIndex(1);
// 自身本地保管的私鑰,用于對交易進(jìn)行簽名
input.setRootPrivateKey("4864bae85cf38bfbb347684abdbc01e311a24f99e2c7fe94f3c071d9c83d8a5a349722316972e382c339b79b7e1d83a565c6b3e7cf46847733a47044ae493257");

Transaction tx = new Transaction.Builder()
        .addInput(input)
        // 加入需要轉(zhuǎn)入的output
        .addOutput(new Output(btmAssetID, 10000000000L, "0014c832e1579b4f96dc12dcfff39e8fe69a62d3f516"))
        // 剩余的BTM用于找零
        .addOutput(new Output(btmAssetID, 31250000000L, "0014bb8a039726df1b649738e9973db14a4b4fd4becf"))
        .setTimeRange(0)
        .build();

String rawTransaction = tx.rawTransaction();

對交易調(diào)用build方法后,自動會對交易進(jìn)行本地的驗(yàn)證和簽名操作。注意,在本地只是做簡單的字段驗(yàn)證,本地驗(yàn)證通過并不代表交易合法。最后對交易調(diào)用rawTransaction方法返回交易序列化后的字符串。

提交交易

本文利用bytomd全節(jié)點(diǎn)來提交交易:

HashMap<String, Object> body = new HashMap<>();
body.put("raw_transaction", "070100010160015e4b5cb973f5bef4eadde4c89b92ee73312b940e84164da0594149554cc8a2adeaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff80c480c1240201160014cb9f2391bafe2bc1159b2c4c8a0f17ba1b4dd94e6302401cb779288be890a28c5209036da1a27d9fe74a51c38e0a10db4817bcf4fd05f68580239eea7dcabf19f144c77bf13d3674b5139aa51a99ba58118386c190af0e20bcbe020b05e1b7d0825953d92bf47897be08cd7751a37adb95d6a2e5224f55ab02013dffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff80b095e42001160014a82f02bc37bc5ed87d5f9fca02f8a6a7d89cdd5c000149ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff80d293ad03012200200824e931fb806bd77fdcd291aad3bd0a4493443a4120062bd659e64a3e0bac6600");
Transaction.SubmitResponse response = client.request("submit-transaction", body, Transaction.SubmitResponse.class);

交易提交成功后,response返回交易ID。

發(fā)行資產(chǎn)交易

查詢可用的utxo

發(fā)行資產(chǎn)時,需要使用BTM作為手續(xù)費(fèi),因此第一步同樣需要查詢當(dāng)前賬戶下可用的utxo,由于上面已經(jīng)提到,這里不再贅述。

查詢需要發(fā)行的資產(chǎn)信息

例如,需要發(fā)行的資產(chǎn)id為7b38dc897329a288ea31031724f5c55bcafec80468a546955023380af2faad14

Asset.QueryBuilder builder = new Asset.QueryBuilder();
builder.setId("7b38dc897329a288ea31031724f5c55bcafec80468a546955023380af2faad14");
List<Asset> assets = builder.list(client);

假設(shè)查詢得到的資產(chǎn)信息如下:

{
      "type": "asset",
      "xpubs": [
        "5ff7f79f0fd4eb9ccb17191b0a1ac9bed5b4a03320a06d2ff8170dd51f9ad9089c4038ec7280b5eb6745ef3d36284e67f5cf2ed2a0177d462d24abf53c0399ed"
      ],
      "quorum": 1,
      "key_index": 3,
      "derive_rule": 0,
      "id": "7b38dc897329a288ea31031724f5c55bcafec80468a546955023380af2faad14",
      "alias": "棒棒雞",
      "vm_version": 1,
      "issue_program": "ae20db11f9dfa39c9e66421c530fe027218edd3d5b1cd98f24c826f4d9c0cd131a475151ad",
      "raw_definition_byte": "7b0a202022646563696d616c73223a20382c0a2020226465736372697074696f6e223a207b7d2c0a2020226e616d65223a2022222c0a20202273796d626f6c223a2022220a7d",
      "definition": {
        "decimals": 8,
        "description": {},
        "name": "",
        "symbol": ""
      }
}

構(gòu)建交易

現(xiàn)在需要發(fā)行1000個棒棒雞資產(chǎn):

IssuanceInput issuanceInput = new IssuanceInput();
issuanceInput.setAssetId("7b38dc897329a288ea31031724f5c55bcafec80468a546955023380af2faad14");
issuanceInput.setAmount(100000000000L);
// issue program
issuanceInput.setProgram("ae20db11f9dfa39c9e66421c530fe027218edd3d5b1cd98f24c826f4d9c0cd131a475151ad");
// 可以不指定,不指定時將隨機(jī)生成一個
issuanceInput.setNonce("ac9d5a527f5ab00a");
issuanceInput.setKeyIndex(5);
// raw definition byte
issuanceInput.setRawAssetDefinition("7b0a202022646563696d616c73223a20382c0a2020226465736372697074696f6e223a207b7d2c0a2020226e616d65223a2022222c0a20202273796d626f6c223a2022220a7d");
// 該資產(chǎn)對應(yīng)的私鑰
issuanceInput.setRootPrivateKey("4864bae85cf38bfbb347684abdbc01e311a24f99e2c7fe94f3c071d9c83d8a5a349722316972e382c339b79b7e1d83a565c6b3e7cf46847733a47044ae493257");

// 創(chuàng)建一個spend input作為手續(xù)費(fèi),假設(shè)當(dāng)前有一個100BTM的utxo,并且使用1BTM作為手續(xù)費(fèi),則后續(xù)還要創(chuàng)建99BTM的找零地址
SpendInput feeInput = new SpendInput(btmAssetID, 10000000000L, "0014cb9f2391bafe2bc1159b2c4c8a0f17ba1b4dd94e");
feeInput.setKeyIndex(1);
feeInput.setChange(true);
feeInput.setSourceID("4b5cb973f5bef4eadde4c89b92ee73312b940e84164da0594149554cc8a2adea");
feeInput.setSourcePosition(2);
feeInput.setControlProgramIndex(457);
feeInput.setRootPrivateKey("4864bae85cf38bfbb347684abdbc01e311a24f99e2c7fe94f3c071d9c83d8a5a349722316972e382c339b79b7e1d83a565c6b3e7cf46847733a47044ae493257");

Transaction tx = new Transaction.Builder()
        .addInput(issuanceInput)
        .addInput(feeInput)
        // 該output用于接收發(fā)行的資產(chǎn)
        .addOutput(new Output("7b38dc897329a288ea31031724f5c55bcafec80468a546955023380af2faad14", 100000000000L, "001437e1aec83a4e6587ca9609e4e5aa728db7007449"))
        // 找零
        .addOutput(new Output(btmAssetID, 9800000000L, "00148be1104e04734e5edaba5eea2e85793896b77c56"))
        .setTimeRange(0)
        .build();

提交交易

提交交易的方式與普通交易一致。

銷毀資產(chǎn)交易

銷毀資產(chǎn)跟發(fā)行資產(chǎn)類似,同樣需要BTM作為手續(xù)費(fèi)。

查詢可用的utxo

查詢方式與普通交易一致。

構(gòu)建交易

這里以銷毀一個BTM為例,假設(shè)查詢得到一個100BTM的utxo:

// 查詢得到一個100BTM的utxo作為輸入
SpendInput input = new SpendInput(btmAssetID, 10000000000L, "0014f1dc52048f439ac7fd74f8106a21da78f00de48f");
input.setRootPrivateKey(rootKey);
input.setChange(true);
input.setKeyIndex(1);
input.setControlProgramIndex(41);
input.setSourceID("0b2cff11d1d056d95237a5f2d06059e5395e86f60e69c1e8201ea624911c0c65");
input.setSourcePosition(0);

// 銷毀資產(chǎn)時,可添加一段附加的文本
String arbitrary = "77656c636f6d65efbc8ce6aca2e8bf8ee69da5e588b0e58e9fe5ad90e4b896e7958c";
// 銷毀99個BTM,剩余1個BTM作為手續(xù)費(fèi)
Output output = Output.newRetireOutput(btmAssetID, 9900000000L, arbitrary);

Transaction transaction = new Transaction.Builder()
        .addInput(input)
        .addOutput(output)
        .setTimeRange(2000000)
        .build();

String rawTransaction = transaction.rawTransaction();

提交交易

提交交易的方式與普通交易一致。

bytom java sdk:https://github.com/Bytom/bytom-java-sdk/

以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • jdk動態(tài)代理使用實(shí)例詳解

    jdk動態(tài)代理使用實(shí)例詳解

    JDK動態(tài)代理是代理模式的一種實(shí)現(xiàn)方式,因?yàn)樗腔诮涌趤碜龃淼?所以也常被稱為接口代理,下面這篇文章主要給大家介紹了關(guān)于jdk動態(tài)代理使用的相關(guān)資料,文中通過實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2022-06-06
  • idea配置檢查XML中SQL語法及書寫sql語句智能提示的方法

    idea配置檢查XML中SQL語法及書寫sql語句智能提示的方法

    idea連接了數(shù)據(jù)庫,也可以執(zhí)行SQL查到數(shù)據(jù),但是無法識別sql語句中的表導(dǎo)致沒有提示,下面這篇文章主要給大家介紹了關(guān)于idea配置檢查XML中SQL語法及書寫sql語句智能提示的相關(guān)資料,需要的朋友可以參考下
    2023-03-03
  • Java ThreadLocal的設(shè)計(jì)理念與作用

    Java ThreadLocal的設(shè)計(jì)理念與作用

    這篇文章主要介紹了Java ThreadLocal的設(shè)計(jì)理念與作用,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-03-03
  • 原來Java中有兩個ArrayList

    原來Java中有兩個ArrayList

    原來Java中有兩個ArrayList,本文就帶著大家一起探究Java中的ArrayList,感興趣的小伙伴們可以參考一下
    2016-01-01
  • 使用Java代碼實(shí)現(xiàn)RocketMQ的生產(chǎn)與消費(fèi)消息

    使用Java代碼實(shí)現(xiàn)RocketMQ的生產(chǎn)與消費(fèi)消息

    這篇文章介紹一下其他的小組件以及使用Java代碼實(shí)現(xiàn)生產(chǎn)者對消息的生成,消費(fèi)者消費(fèi)消息等知識點(diǎn),并通過代碼示例介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下
    2024-07-07
  • springboot獲取URL請求參數(shù)的多種方式

    springboot獲取URL請求參數(shù)的多種方式

    這篇文章主要介紹了springboot獲取URL請求參數(shù)的多種方式,非常不錯,具有參考借鑒價值,需要的朋友可以參考下
    2018-01-01
  • java List.of()與Arrays.asList()方法對比分析

    java List.of()與Arrays.asList()方法對比分析

    這篇文章主要為大家介紹了java List.of()與Arrays.asList()方法對比分析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-11-11
  • Java 實(shí)戰(zhàn)項(xiàng)目之CRM客戶管理系統(tǒng)的實(shí)現(xiàn)流程

    Java 實(shí)戰(zhàn)項(xiàng)目之CRM客戶管理系統(tǒng)的實(shí)現(xiàn)流程

    讀萬卷書不如行萬里路,只學(xué)書上的理論是遠(yuǎn)遠(yuǎn)不夠的,只有在實(shí)戰(zhàn)中才能獲得能力的提升,本篇文章手把手帶你用java+SSM+jsp+mysql+maven實(shí)現(xiàn)一個CRM客戶管理系統(tǒng),大家可以在過程中查缺補(bǔ)漏,提升水平
    2021-11-11
  • Java并發(fā)編程之常用的輔助類詳解

    Java并發(fā)編程之常用的輔助類詳解

    這篇文章主要給大家介紹了關(guān)于Java并發(fā)編程之常用的輔助類的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-01-01
  • Spring框架中Bean的各種加載方式詳解

    Spring框架中Bean的各種加載方式詳解

    這篇文章主要介紹了Spring框架中Bean的各種加載方式詳解,在Java中,"Bean"通常指的是由Spring框架管理的對象實(shí)例,Spring提供了多種方式來加載Bean,以滿足不同的需求和場景,需要的朋友可以參考下
    2023-08-08

最新評論