objattrtest.py: cleanups, import cleanups
This commit is contained in:
parent
b98d5312ec
commit
18d0b285ee
4 changed files with 135 additions and 103 deletions
|
|
@ -96,6 +96,9 @@ class ImmutableAttr: # Descriptor
|
|||
ok_dtypes = (type,type(None),type(lambda:0))
|
||||
|
||||
def __init__(self,dtype,typeconv=True,set_none_ok=False,include_proto=False):
|
||||
self.set_none_ok = set_none_ok
|
||||
self.typeconv = typeconv
|
||||
|
||||
assert isinstance(dtype,self.ok_dtypes), 'ImmutableAttr_check1'
|
||||
if include_proto:
|
||||
assert typeconv, 'ImmutableAttr_check2'
|
||||
|
|
|
|||
|
|
@ -23,19 +23,17 @@ test/objattrtest.py: Test immutable attributes of MMGen data objects
|
|||
# TODO: test 'typeconv' during instance creation
|
||||
|
||||
import sys,os
|
||||
from collections import namedtuple
|
||||
|
||||
import include.test_init
|
||||
|
||||
# Import these _after_ local path's been added to sys.path
|
||||
from mmgen.common import *
|
||||
from mmgen.addrlist import *
|
||||
from mmgen.passwdlist import *
|
||||
from mmgen.tx.base import Base
|
||||
from mmgen.proto.btc.tw.unspent import BitcoinTwUnspentOutputs
|
||||
from mmgen.cfg import Config
|
||||
from mmgen.util import msg,msg_r,gmsg,die
|
||||
from mmgen.color import red,yellow,green,blue,purple,nocolor
|
||||
from mmgen.obj import ImmutableAttr,ListItemAttr
|
||||
|
||||
opts_data = {
|
||||
'sets': [
|
||||
('show_nonstandard_init', True, 'verbose', True),
|
||||
('show_descriptor_type', True, 'verbose', True),
|
||||
],
|
||||
'text': {
|
||||
|
|
@ -44,7 +42,6 @@ opts_data = {
|
|||
'options': """
|
||||
-h, --help Print this help message
|
||||
--, --longhelp Print help message for long options (common options)
|
||||
-i, --show-nonstandard-init Display non-standard attribute initialization info
|
||||
-d, --show-descriptor-type Display the attribute's descriptor type
|
||||
-v, --verbose Produce more verbose output
|
||||
"""
|
||||
|
|
@ -56,15 +53,24 @@ cfg = Config(opts_data=opts_data)
|
|||
from test.include.common import set_globals
|
||||
set_globals(cfg)
|
||||
|
||||
from test.objattrtest_py_d.oat_common import *
|
||||
from test.objattrtest_py_d.oat_common import sample_objs
|
||||
|
||||
pd = namedtuple('permission_bits', ['read_ok','delete_ok','reassign_ok'])
|
||||
pd = namedtuple('attr_bits', ['read_ok','delete_ok','reassign_ok','typeconv','set_none_ok'])
|
||||
perm_bits = ('read_ok','delete_ok','reassign_ok')
|
||||
attr_dfls = {
|
||||
'reassign_ok': False,
|
||||
'delete_ok': False,
|
||||
'typeconv': True,
|
||||
'set_none_ok': False,
|
||||
}
|
||||
|
||||
def parse_permbits(bits):
|
||||
def parse_attrbits(bits):
|
||||
return pd(
|
||||
bool(0b001 & bits), # read
|
||||
bool(0b010 & bits), # delete
|
||||
bool(0b100 & bits), # reassign
|
||||
bool(0b00001 & bits), # read
|
||||
bool(0b00010 & bits), # delete
|
||||
bool(0b00100 & bits), # reassign
|
||||
bool(0b01000 & bits), # typeconv
|
||||
bool(0b10000 & bits), # set_none
|
||||
)
|
||||
|
||||
def get_descriptor_obj(objclass,attrname):
|
||||
|
|
@ -81,13 +87,13 @@ def test_attr_perm(obj,attrname,perm_name,perm_value,dobj,attrval_type):
|
|||
pstem = pname.rstrip('e')
|
||||
|
||||
try:
|
||||
if perm_name == 'read_ok':
|
||||
if perm_name == 'read_ok': # non-existent perm
|
||||
getattr(obj,attrname)
|
||||
elif perm_name == 'reassign_ok':
|
||||
try:
|
||||
so = sample_objs[attrval_type.__name__]
|
||||
except:
|
||||
die( 'SampleObjError', f'unable to find sample object of type {attrval_type.__name__!r}' )
|
||||
raise SampleObjError(f'unable to find sample object of type {attrval_type.__name__!r}')
|
||||
# ListItemAttr allows setting an attribute if its value is None
|
||||
if type(dobj) == ListItemAttr and getattr(obj,attrname) == None:
|
||||
setattr(obj,attrname,so)
|
||||
|
|
@ -116,26 +122,27 @@ def test_attr(data,obj,attrname,dobj,bits,attrval_type):
|
|||
if hasattr(dobj,'__dict__'):
|
||||
d = dobj.__dict__
|
||||
bits = bits._asdict()
|
||||
for k in ('reassign_ok','delete_ok'):
|
||||
colors = {
|
||||
'reassign_ok': purple,
|
||||
'delete_ok': red,
|
||||
'typeconv': green,
|
||||
'set_none_ok': yellow,
|
||||
}
|
||||
for k in bits:
|
||||
if k in d:
|
||||
if d[k] != bits[k]:
|
||||
fs = 'init value {iv}={a} for attr {n!r} does not match test data ({iv}={b})'
|
||||
die(4,fs.format(iv=k,n=attrname,a=d[k],b=bits[k]))
|
||||
if cfg.verbose and d[k] == True:
|
||||
msg_r(f' {k}={d[k]!r}')
|
||||
if cfg.verbose and d[k] != attr_dfls[k]:
|
||||
msg_r(colors[k](f' {k}={d[k]!r}'))
|
||||
|
||||
if cfg.show_nonstandard_init:
|
||||
for k,v in (('typeconv',False),('set_none_ok',True)):
|
||||
if d[k] == v:
|
||||
msg_r(f' {k}={v}')
|
||||
|
||||
def test_object(test_data,objname):
|
||||
def test_object(mod,test_data,objname):
|
||||
|
||||
if '.' in objname:
|
||||
on1,on2 = objname.split('.')
|
||||
cls = getattr(globals()[on1],on2)
|
||||
cls = getattr(getattr(mod,on1),on2)
|
||||
else:
|
||||
cls = globals()[objname]
|
||||
cls = getattr(mod,objname)
|
||||
|
||||
fs = 'Testing attribute ' + ('{!r:<15}{dt:13}' if cfg.show_descriptor_type else '{!r}')
|
||||
data = test_data[objname]
|
||||
|
|
@ -145,23 +152,25 @@ def test_object(test_data,objname):
|
|||
dobj = get_descriptor_obj(type(obj),attrname)
|
||||
if cfg.verbose:
|
||||
msg_r(fs.format(attrname,dt=type(dobj).__name__.replace('MMGen','')))
|
||||
bits = parse_permbits(adata[0])
|
||||
bits = parse_attrbits(adata[0])
|
||||
test_attr(data,obj,attrname,dobj,bits,adata[1])
|
||||
for perm_name,perm_value in bits._asdict().items():
|
||||
test_attr_perm(obj,attrname,perm_name,perm_value,dobj,adata[1])
|
||||
for bit_name,bit_value in bits._asdict().items():
|
||||
if bit_name in perm_bits:
|
||||
test_attr_perm(obj,attrname,bit_name,bit_value,dobj,adata[1])
|
||||
cfg._util.vmsg('')
|
||||
|
||||
def do_loop():
|
||||
import importlib
|
||||
modname = f'test.objattrtest_py_d.oat_{proto.coin.lower()}_{proto.network}'
|
||||
test_data = importlib.import_module(modname).tests
|
||||
mod = importlib.import_module(modname)
|
||||
test_data = getattr(mod,'tests')
|
||||
gmsg(f'Running immutable attribute tests for {proto.coin} {proto.network}')
|
||||
|
||||
utests = cfg._args
|
||||
for obj in test_data:
|
||||
if utests and obj not in utests: continue
|
||||
msg((blue if cfg.verbose else nocolor)(f'Testing {obj}'))
|
||||
test_object(test_data,obj)
|
||||
test_object(mod,test_data,obj)
|
||||
|
||||
proto = cfg._proto
|
||||
|
||||
|
|
|
|||
|
|
@ -7,13 +7,17 @@
|
|||
test.objattrtest_py_d.oat_btc_mainnet: BTC mainnet test vectors for MMGen data objects
|
||||
"""
|
||||
|
||||
from .oat_common import *
|
||||
from .oat_common import sample_objs,seed_bin,atd
|
||||
from ..include.common import cfg
|
||||
from mmgen.protocol import init_proto
|
||||
from mmgen.amt import BTCAmt
|
||||
|
||||
proto = init_proto( cfg, 'btc', need_amt=True )
|
||||
|
||||
from mmgen.key import PrivKey,WifKey
|
||||
from mmgen.addr import CoinAddr,MMGenID,AddrIdx,MMGenAddrType,MMGenPasswordType
|
||||
from mmgen.amt import BTCAmt
|
||||
from mmgen.tw.shared import TwMMGenID
|
||||
|
||||
sample_objs.update({
|
||||
'PrivKey': PrivKey(proto,seed_bin,compressed=True,pubkey_type='std'),
|
||||
'WifKey': WifKey(proto,'5HwzecKMWD82ppJK3qMKpC7ohXXAwcyAN5VgdJ9PLFaAzpBG4sX'),
|
||||
|
|
@ -23,104 +27,122 @@ sample_objs.update({
|
|||
'TwMMGenID': TwMMGenID(proto,'F00F00BB:S:23'),
|
||||
})
|
||||
|
||||
from mmgen.addrlist import AddrListEntry
|
||||
from mmgen.passwdlist import PasswordListEntry
|
||||
from mmgen.obj import TwComment,CoinTxID,HexStr
|
||||
from mmgen.seed import SeedID,SeedBase
|
||||
from mmgen.subseed import SubSeed,SubSeedIdx
|
||||
from mmgen.seedsplit import (
|
||||
SeedShareCount,
|
||||
SeedSplitIDString,
|
||||
SeedShareIdx,
|
||||
MasterShareIdx,
|
||||
SeedShareList,
|
||||
SeedShareLast,
|
||||
SeedShareMaster,
|
||||
SeedShareMasterJoining
|
||||
)
|
||||
from mmgen.proto.btc.tw.unspent import BitcoinTwUnspentOutputs
|
||||
from mmgen.tx.base import Base
|
||||
|
||||
tests = {
|
||||
# addr.py
|
||||
'AddrListEntry': atd({
|
||||
'addr': (0b001, CoinAddr),
|
||||
'idx': (0b001, AddrIdx),
|
||||
'comment': (0b101, TwComment),
|
||||
'sec': (0b001, PrivKey),
|
||||
# 'viewkey': (0b001, ViewKey), # TODO
|
||||
# 'wallet_passwd': (0b001, WalletPassword), # TODO
|
||||
'addr': (0b01001, CoinAddr),
|
||||
'idx': (0b01001, AddrIdx),
|
||||
'comment': (0b01101, TwComment),
|
||||
'sec': (0b01001, PrivKey),
|
||||
# 'viewkey': (0b01001, ViewKey), # TODO
|
||||
# 'wallet_passwd': (0b01001, WalletPassword), # TODO
|
||||
},
|
||||
(proto,),
|
||||
{}
|
||||
),
|
||||
'PasswordListEntry': atd({
|
||||
'passwd': (0b001, str),
|
||||
'idx': (0b001, AddrIdx),
|
||||
'comment':(0b101, TwComment),
|
||||
'sec': (0b001, PrivKey),
|
||||
'passwd': (0b00001, str),
|
||||
'idx': (0b01001, AddrIdx),
|
||||
'comment':(0b01101, TwComment),
|
||||
'sec': (0b01001, PrivKey),
|
||||
},
|
||||
(proto,),
|
||||
{'passwd':'ΑlphaΩmega', 'idx':1 },
|
||||
),
|
||||
# obj.py
|
||||
'PrivKey': atd({
|
||||
'compressed': (0b001, bool),
|
||||
'wif': (0b001, WifKey),
|
||||
'compressed': (0b00001, bool),
|
||||
'wif': (0b00001, WifKey),
|
||||
},
|
||||
(proto,seed_bin),
|
||||
{'compressed':True, 'pubkey_type':'std'},
|
||||
),
|
||||
'MMGenAddrType': atd({
|
||||
'name': (0b001, str),
|
||||
'pubkey_type': (0b001, str),
|
||||
'compressed': (0b001, bool),
|
||||
'gen_method': (0b001, str),
|
||||
'addr_fmt': (0b001, str),
|
||||
'wif_label': (0b001, str),
|
||||
'extra_attrs': (0b001, tuple),
|
||||
'desc': (0b001, str),
|
||||
'name': (0b01001, str),
|
||||
'pubkey_type': (0b01001, str),
|
||||
'compressed': (0b11001, bool),
|
||||
'gen_method': (0b11001, str),
|
||||
'addr_fmt': (0b11001, str),
|
||||
'wif_label': (0b11001, str),
|
||||
'extra_attrs': (0b11001, tuple),
|
||||
'desc': (0b01001, str),
|
||||
},
|
||||
(proto,'S'),
|
||||
{},
|
||||
),
|
||||
# seed.py
|
||||
'SeedBase': atd({
|
||||
'data': (0b001, bytes),
|
||||
'sid': (0b001, SeedID),
|
||||
'data': (0b00001, bytes),
|
||||
'sid': (0b00001, SeedID),
|
||||
},
|
||||
[cfg,seed_bin],
|
||||
{},
|
||||
),
|
||||
'SubSeed': atd({
|
||||
'idx': (0b001, int),
|
||||
'nonce': (0b001, int),
|
||||
'ss_idx': (0b001, SubSeedIdx),
|
||||
'idx': (0b00001, int),
|
||||
'nonce': (0b00001, int),
|
||||
'ss_idx': (0b01001, SubSeedIdx),
|
||||
},
|
||||
[sample_objs['SubSeedList'],1,1,'short'],
|
||||
{},
|
||||
),
|
||||
'SeedShareList': atd({
|
||||
'count': (0b001, SeedShareCount),
|
||||
'id_str': (0b001, SeedSplitIDString),
|
||||
'count': (0b01001, SeedShareCount),
|
||||
'id_str': (0b01001, SeedSplitIDString),
|
||||
},
|
||||
[sample_objs['Seed'],sample_objs['SeedShareCount']],
|
||||
{},
|
||||
),
|
||||
'SeedShareLast': atd({
|
||||
'idx': (0b001, SeedShareIdx),
|
||||
'idx': (0b01001, SeedShareIdx),
|
||||
},
|
||||
[sample_objs['SeedShareList']],
|
||||
{},
|
||||
),
|
||||
'SeedShareMaster': atd({
|
||||
'idx': (0b001, MasterShareIdx),
|
||||
'nonce': (0b001, int),
|
||||
'idx': (0b01001, MasterShareIdx),
|
||||
'nonce': (0b00001, int),
|
||||
},
|
||||
[sample_objs['SeedShareList'],7,0],
|
||||
{},
|
||||
),
|
||||
'SeedShareMasterJoining': atd({
|
||||
'id_str': (0b001, SeedSplitIDString),
|
||||
'count': (0b001, SeedShareCount),
|
||||
'id_str': (0b01001, SeedSplitIDString),
|
||||
'count': (0b01001, SeedShareCount),
|
||||
},
|
||||
[cfg,sample_objs['MasterShareIdx'], sample_objs['Seed'], 'foo', 2],
|
||||
{},
|
||||
),
|
||||
# twuo.py
|
||||
'BitcoinTwUnspentOutputs.MMGenTwUnspentOutput': atd({
|
||||
'txid': (0b001, CoinTxID),
|
||||
'vout': (0b001, int),
|
||||
'amt': (0b001, BTCAmt),
|
||||
'amt2': (0b001, BTCAmt),
|
||||
'comment': (0b101, TwComment),
|
||||
'twmmid': (0b001, TwMMGenID),
|
||||
'addr': (0b001, CoinAddr),
|
||||
'confs': (0b001, int),
|
||||
'scriptPubKey': (0b001, HexStr),
|
||||
'skip': (0b101, str),
|
||||
'txid': (0b01001, CoinTxID),
|
||||
'vout': (0b01001, int),
|
||||
'amt': (0b01001, BTCAmt),
|
||||
'amt2': (0b01001, BTCAmt),
|
||||
'comment': (0b01101, TwComment),
|
||||
'twmmid': (0b01001, TwMMGenID),
|
||||
'addr': (0b01001, CoinAddr),
|
||||
'confs': (0b00001, int),
|
||||
'scriptPubKey': (0b01001, HexStr),
|
||||
'skip': (0b00101, str),
|
||||
},
|
||||
(proto,),
|
||||
{
|
||||
|
|
@ -133,30 +155,30 @@ tests = {
|
|||
),
|
||||
# tx.py
|
||||
'Base.Input': atd({
|
||||
'vout': (0b001, int),
|
||||
'amt': (0b001, BTCAmt),
|
||||
'comment': (0b101, TwComment),
|
||||
'mmid': (0b001, MMGenID),
|
||||
'addr': (0b001, CoinAddr),
|
||||
'confs': (0b001, int),
|
||||
'txid': (0b001, CoinTxID),
|
||||
'have_wif': (0b011, bool),
|
||||
'scriptPubKey': (0b001, HexStr),
|
||||
'sequence': (0b001, int),
|
||||
'vout': (0b01001, int),
|
||||
'amt': (0b01001, BTCAmt),
|
||||
'comment': (0b01101, TwComment),
|
||||
'mmid': (0b01001, MMGenID),
|
||||
'addr': (0b01001, CoinAddr),
|
||||
'confs': (0b01001, int),
|
||||
'txid': (0b01001, CoinTxID),
|
||||
'have_wif': (0b00011, bool),
|
||||
'scriptPubKey': (0b01001, HexStr),
|
||||
'sequence': (0b00001, int),
|
||||
},
|
||||
(proto,),
|
||||
{ 'amt':BTCAmt('0.01'), 'addr':sample_objs['CoinAddr'] },
|
||||
),
|
||||
'Base.Output': atd({
|
||||
'vout': (0b001, int),
|
||||
'amt': (0b001, BTCAmt),
|
||||
'comment': (0b101, TwComment),
|
||||
'mmid': (0b001, MMGenID),
|
||||
'addr': (0b001, CoinAddr),
|
||||
'confs': (0b001, int),
|
||||
'txid': (0b001, CoinTxID),
|
||||
'have_wif': (0b011, bool),
|
||||
'is_chg': (0b001, bool),
|
||||
'vout': (0b01001, int),
|
||||
'amt': (0b01001, BTCAmt),
|
||||
'comment': (0b01101, TwComment),
|
||||
'mmid': (0b01001, MMGenID),
|
||||
'addr': (0b01001, CoinAddr),
|
||||
'confs': (0b01001, int),
|
||||
'txid': (0b01001, CoinTxID),
|
||||
'have_wif': (0b00011, bool),
|
||||
'is_chg': (0b00001, bool),
|
||||
},
|
||||
(proto,),
|
||||
{ 'amt':BTCAmt('0.01'), 'addr':sample_objs['CoinAddr'] },
|
||||
|
|
|
|||
|
|
@ -7,18 +7,16 @@
|
|||
test.objattrtest_py_d.oat_common: shared data for MMGen data objects tests
|
||||
"""
|
||||
|
||||
import os
|
||||
from decimal import Decimal
|
||||
|
||||
from mmgen.obj import *
|
||||
from mmgen.seedsplit import *
|
||||
from mmgen.protocol import *
|
||||
from mmgen.addr import *
|
||||
from mmgen.tx import *
|
||||
from mmgen.tw.unspent import *
|
||||
from mmgen.key import *
|
||||
from ..include.common import cfg,getrand
|
||||
|
||||
from mmgen.obj import TwComment,CoinTxID,HexStr
|
||||
from mmgen.seed import Seed,SeedID
|
||||
from mmgen.subseed import SubSeedIdx,SubSeedList
|
||||
from mmgen.seedsplit import SeedShareList,SeedShareCount,SeedSplitIDString,SeedShareIdx,MasterShareIdx
|
||||
from mmgen.addr import AddrIdx
|
||||
|
||||
from collections import namedtuple
|
||||
atd = namedtuple('attrtest_entry',['attrs','args','kwargs'])
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue