From 4928b025894f0eea842ebd5cc81ef133929b281a Mon Sep 17 00:00:00 2001 From: dangershony Date: Thu, 12 Dec 2019 13:19:47 +0000 Subject: [PATCH] Allow stake to expiery if its enabled --- .../Controllers/StakingController.cs | 47 +++++++++++++++++-- .../Models/GetStakingAddressesModel.cs | 12 +++++ .../Models/RequestModels.cs | 31 +++++++++--- .../Staking/PosMinting.cs | 4 +- src/Stratis.Bitcoin.Features.Wallet/Wallet.cs | 6 +-- 5 files changed, 85 insertions(+), 15 deletions(-) create mode 100644 src/Stratis.Bitcoin.Features.Miner/Models/GetStakingAddressesModel.cs diff --git a/src/Stratis.Bitcoin.Features.Miner/Controllers/StakingController.cs b/src/Stratis.Bitcoin.Features.Miner/Controllers/StakingController.cs index 0f028e5d001..009f5946ac1 100644 --- a/src/Stratis.Bitcoin.Features.Miner/Controllers/StakingController.cs +++ b/src/Stratis.Bitcoin.Features.Miner/Controllers/StakingController.cs @@ -147,15 +147,18 @@ public IActionResult StopStaking([FromBody] bool corsProtection = true) } /// - /// Whitelist an address for staking, this only allowed if is true. + /// Set expiration for an address for staking, this only allowed if is true. /// /// An object that produces a status code 200 HTTP response. - [Route("whitelist")] + [Route("stakingExpiry")] [HttpPost] - public IActionResult Whitelist([FromBody] WhitelistRequest request) + public IActionResult StakingExpiry([FromBody] StakingExpiryRequest request) { try { + if (!this.fullNode.Network.Consensus.IsProofOfStake) + return ErrorHelpers.BuildErrorResponse(HttpStatusCode.MethodNotAllowed, "Method not allowed", "Method not available for Proof of Stake"); + if (!this.minerSettings.EnforceStakingFlag) return ErrorHelpers.BuildErrorResponse(HttpStatusCode.Forbidden, "Operation not allowed", "This operation is only allowed if EnforceStakingFlag is true"); @@ -167,7 +170,7 @@ public IActionResult Whitelist([FromBody] WhitelistRequest request) { if ((address.Address == request.Address) || address.Bech32Address == request.Address) { - address.StakingEnabled = request.Whitelist; + address.StakingExpiry = request.StakingExpiry; } } } @@ -180,5 +183,41 @@ public IActionResult Whitelist([FromBody] WhitelistRequest request) return ErrorHelpers.BuildErrorResponse(HttpStatusCode.BadRequest, e.Message, e.ToString()); } } + + [Route("getStakingNotExpired")] + [HttpGet] + public IActionResult GetStakingNotExpired([FromBody] StakingNotExpiredRequest request) + { + try + { + if (!this.fullNode.Network.Consensus.IsProofOfStake) + return ErrorHelpers.BuildErrorResponse(HttpStatusCode.MethodNotAllowed, "Method not allowed", "Method not available for Proof of Stake"); + + if (!this.minerSettings.EnforceStakingFlag) + return ErrorHelpers.BuildErrorResponse(HttpStatusCode.Forbidden, "Operation not allowed", "This operation is only allowed if EnforceStakingFlag is true"); + + Wallet.Wallet wallet = this.walletManager.GetWallet(request.WalletName); + + GetStakingAddressesModel model = new GetStakingAddressesModel { Addresses = new List() }; + + foreach (Wallet.HdAccount account in wallet.GetAccounts()) + { + foreach (Wallet.HdAddress address in account.GetCombinedAddresses()) + { + if (address.StakingExpiry != null && address.StakingExpiry < DateTime.UtcNow) + { + model.Addresses.Add(request.Segwit ? address.Bech32Address : address.Address); + } + } + } + + return this.Json(model); + } + catch (Exception e) + { + this.logger.LogError("Exception occurred: {0}", e.ToString()); + return ErrorHelpers.BuildErrorResponse(HttpStatusCode.BadRequest, e.Message, e.ToString()); + } + } } } diff --git a/src/Stratis.Bitcoin.Features.Miner/Models/GetStakingAddressesModel.cs b/src/Stratis.Bitcoin.Features.Miner/Models/GetStakingAddressesModel.cs new file mode 100644 index 00000000000..7e21593a92b --- /dev/null +++ b/src/Stratis.Bitcoin.Features.Miner/Models/GetStakingAddressesModel.cs @@ -0,0 +1,12 @@ +using System.Collections.Generic; +using NBitcoin; +using Newtonsoft.Json; + +namespace Stratis.Bitcoin.Features.Miner.Models +{ + public class GetStakingAddressesModel + { + [JsonProperty(PropertyName = "Addresses")] + public IList Addresses { get; set; } + } +} diff --git a/src/Stratis.Bitcoin.Features.Miner/Models/RequestModels.cs b/src/Stratis.Bitcoin.Features.Miner/Models/RequestModels.cs index 58fcfe73eda..e56095afde5 100644 --- a/src/Stratis.Bitcoin.Features.Miner/Models/RequestModels.cs +++ b/src/Stratis.Bitcoin.Features.Miner/Models/RequestModels.cs @@ -1,5 +1,7 @@ -using System.ComponentModel.DataAnnotations; +using System; +using System.ComponentModel.DataAnnotations; using Newtonsoft.Json; +using Newtonsoft.Json.Converters; namespace Stratis.Bitcoin.Features.Miner.Models { @@ -49,10 +51,15 @@ public class MiningRequest : RequestModel } /// - /// Model for the "generate" mining request. + /// Model for the staking request. /// - public class WhitelistRequest : RequestModel + public class StakingExpiryRequest : RequestModel { + public StakingExpiryRequest() + { + this.StakingExpiry = DateTime.UtcNow; + } + /// /// Name of wallet. /// @@ -66,9 +73,21 @@ public class WhitelistRequest : RequestModel public string Address { get; set; } /// - /// Wheather to enable or not. + /// Specify whether UTXOs associated with this address is within the allowed staing time, null will disable staking. /// - [Required(ErrorMessage = "Wheather to enable or not.")] - public bool Whitelist { get; set; } + [JsonProperty(PropertyName = "stakingExpiry", NullValueHandling = NullValueHandling.Ignore)] + [JsonConverter(typeof(IsoDateTimeConverter))] + public DateTime? StakingExpiry { get; set; } + } + + public class StakingNotExpiredRequest : RequestModel + { + /// + /// Name of wallet. + /// + [Required(ErrorMessage = "Name of wallet.")] + public string WalletName { get; set; } + + public bool Segwit { get; set; } } } diff --git a/src/Stratis.Bitcoin.Features.Miner/Staking/PosMinting.cs b/src/Stratis.Bitcoin.Features.Miner/Staking/PosMinting.cs index db6bf091232..f7ce1836450 100644 --- a/src/Stratis.Bitcoin.Features.Miner/Staking/PosMinting.cs +++ b/src/Stratis.Bitcoin.Features.Miner/Staking/PosMinting.cs @@ -446,10 +446,10 @@ internal List GetUtxoStakeDescriptions(WalletSecret wallet { if (this.minerSettings.EnforceStakingFlag) { - if (utxo.Address.StakingEnabled == null) + if (utxo.Address.StakingExpiry == null) return false; - if (utxo.Address.StakingEnabled == false) + if (utxo.Address.StakingExpiry > this.dateTimeProvider.GetUtcNow()) return false; } diff --git a/src/Stratis.Bitcoin.Features.Wallet/Wallet.cs b/src/Stratis.Bitcoin.Features.Wallet/Wallet.cs index 1ee448adb34..290ecdd845d 100644 --- a/src/Stratis.Bitcoin.Features.Wallet/Wallet.cs +++ b/src/Stratis.Bitcoin.Features.Wallet/Wallet.cs @@ -908,10 +908,10 @@ public HdAddress() public ICollection Transactions { get; set; } /// - /// Specify whether UTXOs associated with this address can stake. + /// Specify whether UTXOs associated with this address is within the allowed staing time. /// - [JsonProperty(PropertyName = "stakingEnabled")] - public bool? StakingEnabled { get; set; } + [JsonProperty(PropertyName = "stakingExpiry", NullValueHandling = NullValueHandling.Ignore)] + public DateTime? StakingExpiry { get; set; } /// /// Determines whether this is a change address or a receive address.