This repository has been archived by the owner on Nov 15, 2021. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 189
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Added support for StateTransaction and StateDescriptors (#193)
- Loading branch information
1 parent
12a0136
commit 2200802
Showing
12 changed files
with
317 additions
and
27 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,153 @@ | ||
from neocore.IO.BinaryReader import BinaryReader | ||
from neocore.IO.BinaryWriter import BinaryWriter | ||
from neo.Core.Mixins import SerializableMixin | ||
from neo.IO.MemoryStream import StreamManager | ||
from neocore.Fixed8 import Fixed8 | ||
|
||
from enum import Enum | ||
|
||
|
||
class StateType(Enum): | ||
Account = 0x40 | ||
Validator = 0x48 | ||
|
||
|
||
class StateDescriptor(SerializableMixin): | ||
|
||
Type = None | ||
Key = None | ||
Field = None | ||
Value = None | ||
|
||
@property | ||
def SystemFee(self): | ||
if self.Type == StateType.Account: | ||
return Fixed8.Zero() | ||
elif self.Type == StateType.Validator: | ||
return self.GetSystemFee_Validator() | ||
|
||
def Size(self): | ||
""" | ||
Get the total size in bytes of the object. | ||
Returns: | ||
int: size. | ||
""" | ||
return super(StateDescriptor, self).Size() | ||
|
||
def Deserialize(self, reader: BinaryReader): | ||
""" | ||
Deserialize full object. | ||
Args: | ||
reader (neocore.IO.BinaryReader): | ||
""" | ||
|
||
self.Type = StateType(reader.ReadByte()) | ||
|
||
self.Key = reader.ReadVarBytes(max=100) | ||
self.Field = reader.ReadVarString(max=32).decode('utf-8') | ||
self.Value = reader.ReadVarBytes(max=65535) | ||
|
||
if self.Type == StateType.Account: | ||
self.CheckAccountState() | ||
elif self.Type == StateType.Validator: | ||
self.CheckValidatorState() | ||
|
||
@staticmethod | ||
def DeserializeFromDB(buffer): | ||
""" | ||
Deserialize full object. | ||
Args: | ||
buffer (bytes, bytearray, BytesIO): (Optional) data to create the stream from. | ||
Returns: | ||
ValidatorState: | ||
""" | ||
m = StreamManager.GetStream(buffer) | ||
reader = BinaryReader(m) | ||
v = StateDescriptor() | ||
v.Deserialize(reader) | ||
|
||
StreamManager.ReleaseStream(m) | ||
|
||
return v | ||
|
||
def Serialize(self, writer: BinaryWriter): | ||
""" | ||
Serialize full object. | ||
Args: | ||
writer (neo.IO.BinaryWriter): | ||
""" | ||
byt = None | ||
if self.Type == StateType.Account: | ||
byt = b'\x40' | ||
elif self.Type == StateType.Validator: | ||
byt = b'\x48' | ||
writer.WriteByte(byt) | ||
writer.WriteVarBytes(self.Key) | ||
writer.WriteVarString(self.Field) | ||
writer.WriteVarBytes(self.Value) | ||
|
||
def GetSystemFee_Validator(self): | ||
|
||
if self.Field == "Registered": | ||
for character in self.Value: | ||
if character != '0': | ||
return Fixed8.FromDecimal(1000) | ||
return Fixed8.Zero() | ||
|
||
raise Exception("Invalid operation") | ||
|
||
def CheckAccountState(self): | ||
if len(self.Key) != 20: | ||
raise Exception("Invalid Key format") | ||
if self.Field != "Votes": | ||
raise Exception("Invalid Field") | ||
|
||
def CheckValidatorState(self): | ||
if len(self.Key) != 33: | ||
raise Exception("Invalid Validator State Key Format") | ||
if self.Field != "Registered": | ||
raise Exception("Invalid Field for validator") | ||
|
||
def ToJson(self): | ||
""" | ||
Convert object members to a dictionary that can be parsed as JSON. | ||
Returns: | ||
dict: | ||
""" | ||
|
||
type = '' | ||
if self.Type == StateType.Validator: | ||
type = 'Validator' | ||
elif self.Type == StateType.Account: | ||
type = 'Account' | ||
|
||
return { | ||
'type': type, | ||
'key': self.Key.hex(), | ||
'field': self.Field, | ||
'value': self.Value.hex() | ||
} | ||
|
||
def Verify(self): | ||
|
||
if self.Type == StateType.Account: | ||
return self.VerifyAccountState() | ||
elif self.Type == StateType.Validator: | ||
return self.VerifyValidatorState() | ||
raise Exception("Invalid State Descriptor") | ||
|
||
def VerifyAccountState(self): | ||
# @TODO | ||
# Implement VerifyAccount State | ||
raise NotImplementedError() | ||
|
||
def VerifyValidatorState(self): | ||
if self.Field == 'Registered': | ||
return True | ||
return False |
This file was deleted.
Oops, something went wrong.
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
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
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,128 @@ | ||
from neo.Core.TX.Transaction import * | ||
from neocore.Fixed8 import Fixed8 | ||
from neo.Core.State.StateDescriptor import StateDescriptor | ||
|
||
|
||
class StateTransaction(Transaction): | ||
|
||
Descriptors = None | ||
|
||
def Size(self): | ||
""" | ||
Get the total size in bytes of the object. | ||
Returns: | ||
int: size. | ||
""" | ||
|
||
return super(StateTransaction, self).Size() | ||
|
||
def __init__(self, *args, **kwargs): | ||
""" | ||
Create an instance. | ||
Args: | ||
*args: | ||
**kwargs: | ||
""" | ||
super(StateTransaction, self).__init__(*args, **kwargs) | ||
|
||
self.Type = TransactionType.StateTransaction | ||
|
||
def NetworkFee(self): | ||
""" | ||
Get the network fee for a claim transaction. | ||
Returns: | ||
Fixed8: currently fixed to 0. | ||
""" | ||
return Fixed8(0) | ||
|
||
def SystemFee(self): | ||
amount = Fixed8.Zero() | ||
for d in self.Descriptors: | ||
amount += d.SystemFee | ||
return amount | ||
|
||
def DeserializeExclusiveData(self, reader): | ||
""" | ||
Deserialize full object. | ||
Args: | ||
reader (neo.IO.BinaryReader): | ||
Raises: | ||
Exception: If the transaction type is incorrect or if there are no claims. | ||
""" | ||
self.Descriptors = [] | ||
self.Type = TransactionType.StateTransaction | ||
|
||
self.Descriptors = reader.ReadSerializableArray('neo.Core.State.StateDescriptor.StateDescriptor') | ||
|
||
# num_descriptors = reader.ReadByte() | ||
# if num_descriptors > 16: | ||
# raise Exception("Invalid number of descriptors") | ||
# for i in range(0, num_descriptors): | ||
# descriptor = StateDescriptor() | ||
# descriptor.Deserialize(reader) | ||
# self.Descriptors.append(descriptor) | ||
|
||
def GetScriptHashesForVerifying(self): | ||
""" | ||
Get a list of script hashes for verifying transactions. | ||
Raises: | ||
Exception: if there are no valid transactions to claim from. | ||
Returns: | ||
list: of UInt160 type script hashes. | ||
""" | ||
|
||
raise NotImplementedError() | ||
|
||
def GetScriptHashesForVerifying_Account(self, descriptor): | ||
raise NotImplementedError() | ||
|
||
def GetScriptHashesForVerifying_Validator(self, descriptor): | ||
raise NotImplementedError() | ||
|
||
def SerializeExclusiveData(self, writer): | ||
""" | ||
Serialize object. | ||
Args: | ||
writer (neo.IO.BinaryWriter): | ||
""" | ||
writer.WriteSerializableArray(self.Descriptors) | ||
|
||
def ToJson(self): | ||
""" | ||
Convert object members to a dictionary that can be parsed as JSON. | ||
Returns: | ||
dict: | ||
""" | ||
|
||
json = super(StateTransaction, self).ToJson() | ||
descriptors = [d.ToJson() for d in self.Descriptors] | ||
|
||
json['descriptors'] = descriptors | ||
|
||
return json | ||
|
||
def Verify(self, mempool): | ||
""" | ||
Verify the transaction. | ||
Args: | ||
mempool: | ||
Returns: | ||
bool: True if verified. False otherwise. | ||
""" | ||
|
||
for descriptor in self.Descriptors: | ||
if not descriptor.Verify(): | ||
return False | ||
|
||
return super(StateTransaction, self).Verify(mempool) |
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
Oops, something went wrong.