diff --git a/src/Neo/Ledger/MemoryPool.cs b/src/Neo/Ledger/MemoryPool.cs
index 35748ef018..bd6cfea33f 100644
--- a/src/Neo/Ledger/MemoryPool.cs
+++ b/src/Neo/Ledger/MemoryPool.cs
@@ -117,6 +117,13 @@ public int Count
///
public int UnVerifiedCount => _unverifiedTransactions.Count;
+ ///
+ /// Transaction policy validator function.
+ /// This function will be called to validate each transaction before adding it to the pool.
+ /// If the function returns false, the transaction will be rejected.
+ ///
+ public Func? PolicyValidator { get; set; }
+
///
/// Initializes a new instance of the class.
///
@@ -307,6 +314,11 @@ internal bool CanTransactionFitInPool(Transaction tx)
internal VerifyResult TryAdd(Transaction tx, DataCache snapshot)
{
+ if (PolicyValidator != null)
+ {
+ if (!PolicyValidator(tx, snapshot)) return VerifyResult.PolicyFail;
+ }
+
var poolItem = new PoolItem(tx);
if (_unsortedTransactions.ContainsKey(tx.Hash)) return VerifyResult.AlreadyInPool;
diff --git a/tests/Neo.UnitTests/Ledger/UT_MemoryPool.cs b/tests/Neo.UnitTests/Ledger/UT_MemoryPool.cs
index d29647a13b..9fd349169a 100644
--- a/tests/Neo.UnitTests/Ledger/UT_MemoryPool.cs
+++ b/tests/Neo.UnitTests/Ledger/UT_MemoryPool.cs
@@ -23,6 +23,7 @@
using System;
using System.Collections;
using System.Collections.Generic;
+using System.ComponentModel;
using System.Linq;
using System.Numerics;
using System.Threading.Tasks;
@@ -158,6 +159,21 @@ public void CapacityTest()
Assert.HasCount(100, _unit);
}
+ [TestMethod]
+ public void CancelTest()
+ {
+ // Add over the capacity items, verify that the verified count increases each time
+
+ _unit.PolicyValidator = new Func((tx, sn) => false);
+ AddTransactions(1);
+ _unit.PolicyValidator = null;
+
+ Assert.AreEqual(0, _unit.SortedTxCount);
+ Assert.AreEqual(0, _unit.VerifiedCount);
+ Assert.AreEqual(0, _unit.UnVerifiedCount);
+ Assert.HasCount(0, _unit);
+ }
+
[TestMethod]
public void BlockPersistMovesTxToUnverifiedAndReverification()
{