-
Notifications
You must be signed in to change notification settings - Fork 20
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
New Denovo feature: verify any transaction
- Loading branch information
1 parent
5abe579
commit acd3805
Showing
7 changed files
with
299 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,68 @@ | ||
// Denovo | ||
// Copyright (c) 2020 Autarkysoft | ||
// Distributed under the MIT software license, see the accompanying | ||
// file LICENCE or http://www.opensource.org/licenses/mit-license.php. | ||
|
||
using Autarkysoft.Bitcoin.Blockchain; | ||
using Autarkysoft.Bitcoin.Blockchain.Scripts; | ||
using Autarkysoft.Bitcoin.Encoders; | ||
using Denovo.MVVM; | ||
|
||
namespace Denovo.Models | ||
{ | ||
public class UtxoModel : InpcBase | ||
{ | ||
public UtxoModel() { } | ||
|
||
public UtxoModel(byte[] txHash, uint index) | ||
{ | ||
TxId = Base16.EncodeReverse(txHash); | ||
Index = index; | ||
} | ||
|
||
|
||
private string _txId; | ||
public string TxId | ||
{ | ||
get => _txId; | ||
set => SetField(ref _txId, value); | ||
} | ||
|
||
private uint _index; | ||
public uint Index | ||
{ | ||
get => _index; | ||
set => SetField(ref _index, value); | ||
} | ||
|
||
private ulong _amaount; | ||
public ulong Amount | ||
{ | ||
get => _amaount; | ||
set => SetField(ref _amaount, value); | ||
} | ||
|
||
private string _scr = string.Empty; | ||
public string Script | ||
{ | ||
get => _scr; | ||
set => SetField(ref _scr, value); | ||
} | ||
|
||
|
||
public bool TryConvertToUtxo(out Utxo result, out string error) | ||
{ | ||
if (!Base16.TryDecode(Script, out byte[] scrBa)) | ||
{ | ||
error = "Invalid pubkey script hex."; | ||
result = null; | ||
return false; | ||
} | ||
|
||
var scr = new PubkeyScript(scrBa); | ||
result = new Utxo(Index, Amount, scr); | ||
error = null; | ||
return true; | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,124 @@ | ||
// Denovo | ||
// Copyright (c) 2020 Autarkysoft | ||
// Distributed under the MIT software license, see the accompanying | ||
// file LICENCE or http://www.opensource.org/licenses/mit-license.php. | ||
|
||
using Autarkysoft.Bitcoin; | ||
using Autarkysoft.Bitcoin.Blockchain; | ||
using Autarkysoft.Bitcoin.Blockchain.Transactions; | ||
using Autarkysoft.Bitcoin.Encoders; | ||
using Denovo.Models; | ||
using Denovo.MVVM; | ||
using System; | ||
using System.Linq; | ||
|
||
namespace Denovo.ViewModels | ||
{ | ||
public class VerifyTxViewModel : VmWithSizeBase | ||
{ | ||
public VerifyTxViewModel() : base(800, 750) | ||
{ | ||
VerifyCommand = new BindableCommand(Verify, () => IsVerifyEnable); | ||
} | ||
|
||
|
||
|
||
private readonly Transaction tx = new(); | ||
// TODO: add block height and network type | ||
private readonly TransactionVerifier verifier = new(new Consensus(int.MaxValue, NetworkType.MainNet)); | ||
|
||
|
||
private string _txHex; | ||
public string TxHex | ||
{ | ||
get => _txHex; | ||
set | ||
{ | ||
if (SetField(ref _txHex, value)) | ||
{ | ||
if (string.IsNullOrWhiteSpace(value)) | ||
{ | ||
Result = "Enter a valid transaction hex."; | ||
} | ||
else if (!Base16.TryDecode(value, out byte[] ba)) | ||
{ | ||
UtxoList = Array.Empty<UtxoModel>(); | ||
IsVerifyEnable = false; | ||
Result = "Invalid hexadecimal transaction."; | ||
} | ||
else if (!tx.TryDeserialize(new FastStreamReader(ba), out string error)) | ||
{ | ||
UtxoList = Array.Empty<UtxoModel>(); | ||
IsVerifyEnable = false; | ||
Result = $"Error deserializing transaction: {error}"; | ||
} | ||
else | ||
{ | ||
// Has to recompute hashes when more than one tx is verified | ||
tx.ComputeTransactionHashes(); | ||
|
||
Result = string.Empty; | ||
UtxoList = tx.TxInList.Select(x => new UtxoModel(x.TxHash, x.Index)).ToArray(); | ||
IsVerifyEnable = true; | ||
} | ||
} | ||
} | ||
} | ||
|
||
private UtxoModel[] _utxos; | ||
public UtxoModel[] UtxoList | ||
{ | ||
get => _utxos; | ||
private set => SetField(ref _utxos, value); | ||
} | ||
|
||
private string _res; | ||
public string Result | ||
{ | ||
get => _res; | ||
private set => SetField(ref _res, value); | ||
} | ||
|
||
private bool _isEnable; | ||
public bool IsVerifyEnable | ||
{ | ||
get => _isEnable; | ||
private set | ||
{ | ||
if (SetField(ref _isEnable, value)) | ||
{ | ||
VerifyCommand.RaiseCanExecuteChanged(); | ||
} | ||
} | ||
} | ||
|
||
|
||
public BindableCommand VerifyCommand { get; private set; } | ||
private void Verify() | ||
{ | ||
var temp = new Utxo[UtxoList.Length]; | ||
for (int i = 0; i < UtxoList.Length; i++) | ||
{ | ||
if (!UtxoList[i].TryConvertToUtxo(out Utxo u, out string error)) | ||
{ | ||
Result = $"Failed to set UTXO at index = {i}.{Environment.NewLine}{error}"; | ||
return; | ||
} | ||
|
||
temp[i] = u; | ||
} | ||
|
||
verifier.Init(); | ||
if (verifier.Verify(tx, temp, out string err)) | ||
{ | ||
Result = $"Transaction is valid (assuming all given UTXOs existed and were unspent at the time)." + | ||
$"{Environment.NewLine}Transaction fee: {verifier.TotalFee} satoshi" + | ||
$"{Environment.NewLine}Transaction SigOp count: {verifier.TotalSigOpCount}"; | ||
} | ||
else | ||
{ | ||
Result = $"Failed to verify the given transaction. Error: {err}"; | ||
} | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,68 @@ | ||
<UserControl xmlns="https://github.com/avaloniaui" | ||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" | ||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" | ||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" | ||
xmlns:vm="clr-namespace:Denovo.ViewModels;assembly=Denovo" | ||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="550" | ||
x:Class="Denovo.Views.VerifyTxView" | ||
FontSize="14"> | ||
|
||
<Design.DataContext> | ||
<vm:VerifyTxViewModel/> | ||
</Design.DataContext> | ||
|
||
<Grid RowDefinitions="100,*,auto,70"> | ||
<TextBox Text="{Binding TxHex}" | ||
Watermark="Transaction hex" | ||
ScrollViewer.VerticalScrollBarVisibility="Visible" | ||
Grid.Row="0"/> | ||
|
||
<ItemsControl Items="{Binding UtxoList}" Grid.Row="1" ScrollViewer.VerticalScrollBarVisibility="Visible"> | ||
<ItemsControl.ItemsPanel> | ||
<ItemsPanelTemplate> | ||
<StackPanel Orientation="Vertical"/> | ||
</ItemsPanelTemplate> | ||
</ItemsControl.ItemsPanel> | ||
<ItemsControl.ItemTemplate> | ||
<DataTemplate> | ||
<StackPanel Orientation="Horizontal"> | ||
<TextBox Text="{Binding TxId}" | ||
TextWrapping="NoWrap" | ||
ToolTip.Tip="Transaction ID" | ||
Watermark="Transaction ID" | ||
UseFloatingWatermark="False" | ||
Width="150"/> | ||
|
||
<TextBox Text="{Binding Index}" | ||
ToolTip.Tip="Index" | ||
Watermark="Index" | ||
UseFloatingWatermark="False" | ||
Width="50"/> | ||
|
||
<TextBox Text="{Binding Amount}" | ||
ToolTip.Tip="Amount (satoshi)" | ||
Watermark="Amount (satoshi)" | ||
UseFloatingWatermark="False" | ||
Width="150"/> | ||
|
||
<TextBox Text="{Binding Script}" | ||
TextWrapping="NoWrap" | ||
ToolTip.Tip="Script (hex)" | ||
Watermark="Script (hex)" | ||
UseFloatingWatermark="False" | ||
Width="370"/> | ||
</StackPanel> | ||
</DataTemplate> | ||
</ItemsControl.ItemTemplate> | ||
</ItemsControl> | ||
|
||
<Button Content="Verify" | ||
Command="{Binding VerifyCommand}" | ||
Margin="5" | ||
Grid.Row="2"/> | ||
|
||
<TextBox Text="{Binding Result, Mode=OneWay}" | ||
IsReadOnly="True" | ||
Grid.Row="3"/> | ||
</Grid> | ||
</UserControl> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
// Denovo | ||
// Copyright (c) 2020 Autarkysoft | ||
// Distributed under the MIT software license, see the accompanying | ||
// file LICENCE or http://www.opensource.org/licenses/mit-license.php. | ||
|
||
using Avalonia.Controls; | ||
using Avalonia.Markup.Xaml; | ||
|
||
namespace Denovo.Views | ||
{ | ||
public partial class VerifyTxView : UserControl | ||
{ | ||
public VerifyTxView() => InitializeComponent(); | ||
private void InitializeComponent() => AvaloniaXamlLoader.Load(this); | ||
} | ||
} |