Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
W
wendelin.core
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Labels
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Commits
Open sidebar
Kirill Smelkov
wendelin.core
Commits
fa71d1df
Commit
fa71d1df
authored
Apr 22, 2021
by
Kirill Smelkov
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
.
parent
943dfc75
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
154 additions
and
37 deletions
+154
-37
wcfs/δbtail_test.go
wcfs/δbtail_test.go
+154
-37
No files found.
wcfs/δbtail_test.go
View file @
fa71d1df
...
@@ -511,31 +511,33 @@ func xzgetBlkData(ctx context.Context, zconn *zodb.Connection, zblkOid zodb.Oid)
...
@@ -511,31 +511,33 @@ func xzgetBlkData(ctx context.Context, zconn *zodb.Connection, zblkOid zodb.Oid)
return
string
(
data
)
return
string
(
data
)
}
}
// xzgetBlkDataAt loads block data from ZBlk object specified by oid@at.
func
xzgetBlkDataAt
(
db
*
zodb
.
DB
,
zblkOid
zodb
.
Oid
,
at
zodb
.
Tid
)
string
{
X
:=
exc
.
Raiseif
txn
,
ctx
:=
transaction
.
New
(
context
.
Background
())
defer
txn
.
Abort
()
// xverifyΔBTail verifies how ΔBTail handles ZODB update for a tree with changes in between at1->at2.
zconn
,
err
:=
db
.
Open
(
ctx
,
&
zodb
.
ConnOptions
{
At
:
at
});
X
(
err
)
return
xzgetBlkData
(
ctx
,
zconn
,
zblkOid
)
}
// xverifyΔBTail_Update verifies how ΔBTail handles ZODB update for a tree with changes in between t1->t2.
//
//
// it is known that @at1 and @at2 the tree has xkv1 and xkv2 values correspondingly.
// it is known that @at1 and @at2 the tree has xkv1 and xkv2 values correspondingly.
XXX kill
// it is known that for at1->at2 ZODB-level change is δZ.
// it is known that for at1->at2 ZODB-level change is δZ.
XXX kill
//
//
// kadjOK may be optionally provided. if kadjOK != nil computed adjacency
// kadjOK may be optionally provided. if kadjOK != nil computed adjacency
// matrix is verified against it.
// matrix is verified against it.
func
xverifyΔBTail
(
t
*
testing
.
T
,
subj
string
,
db
*
zodb
.
DB
,
treeRoot
zodb
.
Oid
,
at1
,
at2
zodb
.
Tid
,
xkv1
,
xkv2
RBucketSet
,
δZ
*
zodb
.
Event
Commit
,
kadjOK
map
[
Key
]
SetKey
)
{
func
xverifyΔBTail
_Update
(
t
*
testing
.
T
,
subj
string
,
db
*
zodb
.
DB
,
treeRoot
zodb
.
Oid
,
t1
,
t2
*
tTree
Commit
,
kadjOK
map
[
Key
]
SetKey
)
{
// verify transition at1->at2 for all initial states of tracked {keys} from kv1 + kv2 + ∞
// verify transition at1->at2 for all initial states of tracked {keys} from kv1 + kv2 + ∞
allKeys
:=
SetKey
{};
allKeys
.
Add
(
kInf
)
// ∞ simulating ZBigFile.Size() query
allKeys
:=
allTestKeys
(
t1
,
t2
)
maxk1
:=
-
kInf
;
maxk2
:=
-
kInf
allKeyv
:=
allKeys
.
SortedKeys
()
for
_
,
b
:=
range
xkv1
{
for
k
:=
range
b
.
kv
{
allKeys
.
Add
(
k
)
if
k
>
maxk1
{
maxk1
=
k
}
}}
for
_
,
b
:=
range
xkv2
{
for
k
:=
range
b
.
kv
{
allKeys
.
Add
(
k
)
if
k
>
maxk2
{
maxk2
=
k
}
}}
allKeyv
:=
allKeys
.
Elements
()
sort
.
Slice
(
allKeyv
,
func
(
i
,
j
int
)
bool
{
return
allKeyv
[
i
]
<
allKeyv
[
j
]
})
xkv1
:=
t1
.
xkv
xkv2
:=
t2
.
xkv
// kadj = {} k -> adjacent keys. if k is tracked -> changes to adjacents must be in δT.
// kadj = {} k -> adjacent keys. if k is tracked -> changes to adjacents must be in δT.
kadj
:=
map
[
Key
]
SetKey
{}
kadj
:=
map
[
Key
]
SetKey
{}
...
@@ -595,13 +597,13 @@ func xverifyΔBTail(t *testing.T, subj string, db *zodb.DB, treeRoot zodb.Oid, a
...
@@ -595,13 +597,13 @@ func xverifyΔBTail(t *testing.T, subj string, db *zodb.DB, treeRoot zodb.Oid, a
keys
.
Add
(
allKeyv
[
idx
])
keys
.
Add
(
allKeyv
[
idx
])
}
}
xverifyΔBTail
1
(
t
,
subj
,
db
,
treeRoot
,
at1
,
at2
,
xkv1
,
xkv2
,
δZ
,
keys
,
kadj
)
xverifyΔBTail
_Update1
(
t
,
subj
,
db
,
treeRoot
,
t1
.
at
,
t2
.
at
,
xkv1
,
xkv2
,
t2
.
δZ
,
keys
,
kadj
)
}
}
}
}
// xverifyΔBTail1 verifies how ΔBTail handles ZODB update at1->at2 from initial
// xverifyΔBTail
_Update
1 verifies how ΔBTail handles ZODB update at1->at2 from initial
// tracked state defined by initialTrackedKeys.
// tracked state defined by initialTrackedKeys.
func
xverifyΔBTail1
(
t
*
testing
.
T
,
subj
string
,
db
*
zodb
.
DB
,
treeRoot
zodb
.
Oid
,
at1
,
at2
zodb
.
Tid
,
xkv1
,
xkv2
RBucketSet
,
δZ
*
zodb
.
EventCommit
,
initialTrackedKeys
SetKey
,
kadj
map
[
Key
]
SetKey
)
{
func
xverifyΔBTail
_Update
1
(
t
*
testing
.
T
,
subj
string
,
db
*
zodb
.
DB
,
treeRoot
zodb
.
Oid
,
at1
,
at2
zodb
.
Tid
,
xkv1
,
xkv2
RBucketSet
,
δZ
*
zodb
.
EventCommit
,
initialTrackedKeys
SetKey
,
kadj
map
[
Key
]
SetKey
)
{
X
:=
exc
.
Raiseif
X
:=
exc
.
Raiseif
tracef
(
"
\n
>>> Track=%s
\n
"
,
initialTrackedKeys
)
tracef
(
"
\n
>>> Track=%s
\n
"
,
initialTrackedKeys
)
...
@@ -769,6 +771,85 @@ func xverifyΔBTail1(t *testing.T, subj string, db *zodb.DB, treeRoot zodb.Oid,
...
@@ -769,6 +771,85 @@ func xverifyΔBTail1(t *testing.T, subj string, db *zodb.DB, treeRoot zodb.Oid,
}
}
}
}
// xverifyΔBtail_Get verifies δBtail.Get on series of vt ZODB changes.
// XXX
func
xverifyΔBTail_Get
(
t
*
testing
.
T
,
subj
string
,
db
*
zodb
.
DB
,
treeRoot
zodb
.
Oid
,
vt
...*
tTreeCommit
)
{
return
tkeys
:=
allTestKeys
(
vt
...
)
tkeyv
:=
tkeys
.
SortedKeys
()
// verify t1->t2-> ... ->tn Track(keys) Get(keys, @at)
// for all combinations of tracked keys and at
for
kidx
:=
range
IntSets
(
len
(
tkeyv
))
{
keys
:=
SetKey
{}
for
_
,
idx
:=
range
kidx
{
keys
.
Add
(
tkeyv
[
idx
])
}
xverifyΔBTail_Get1
(
t
,
subj
,
db
,
treeRoot
,
vt
,
keys
)
}
}
func
xverifyΔBTail_Get1
(
t
*
testing
.
T
,
subj
string
,
db
*
zodb
.
DB
,
treeRoot
zodb
.
Oid
,
vt
[]
*
tTreeCommit
,
keys
SetKey
)
{
X
:=
exc
.
Raiseif
// XXX subj here ?
// XXX tracked / ?
// t1->t2-> ... -> tn
δbtail
:=
NewΔBtail
(
vt
[
0
]
.
at
,
db
)
for
i
:=
1
;
i
<
len
(
vt
);
i
++
{
_
,
err
:=
δbtail
.
Update
(
vt
[
i
]
.
δZ
);
X
(
err
)
}
// Track(keys)
txn
,
ctx
:=
transaction
.
New
(
context
.
Background
())
defer
txn
.
Abort
()
zconn
,
err
:=
db
.
Open
(
ctx
,
&
zodb
.
ConnOptions
{
At
:
vt
[
len
(
vt
)
-
1
]
.
at
});
X
(
err
)
xtree
,
err
:=
zconn
.
Get
(
ctx
,
treeRoot
);
X
(
err
)
ztree
:=
xtree
.
(
*
Tree
)
for
k
:=
range
keys
{
path
:=
[]
Node
{}
_
,
ok
,
err
:=
ztree
.
VGet
(
ctx
,
k
,
func
(
node
Node
)
{
path
=
append
(
path
,
node
)
});
X
(
err
)
err
=
δbtail
.
Track
(
k
,
ok
,
path
);
X
(
err
)
}
// verify Get(k, @at) for all keys and @at
for
i
:=
1
;
i
<
len
(
vt
);
i
++
{
at
:=
vt
[
i
]
.
at
for
_
,
k
:=
range
keys
.
SortedKeys
()
{
vOid
,
ok
,
rev
,
revExact
,
err
:=
δbtail
.
Get
(
ctx
,
ztree
,
k
,
at
);
X
(
err
)
v
:=
xzgetBlkDataAt
(
db
,
vOid
,
rev
)
v_
,
ok_
:=
vt
[
i
]
.
xkv
.
Get
(
k
)
.
kv
[
k
]
rev_
,
revExact_
:=
vt
[
i
]
.
at
,
false
for
j
:=
i
-
1
;
j
>=
0
;
j
--
{
v__
:=
vt
[
j
]
.
xkv
.
Get
(
k
)
.
kv
[
k
]
if
v__
!=
v_
{
rev_
=
vt
[
j
+
1
]
.
at
revExact_
=
true
break
}
rev_
=
vt
[
j
]
.
at
}
if
v
==
""
{
v
=
DEL
}
if
v_
==
""
{
v_
=
DEL
}
if
!
(
v
==
v_
&&
ok
==
ok_
&&
rev
==
rev_
&&
revExact
==
revExact_
)
{
t
.
Errorf
(
"Get(%d, @%s) ->
\n
have: %s, %v, @%s, %v
\n
want: %s, %v, @%s, %v"
,
k
,
at
,
v
,
ok
,
rev
,
revExact
,
v_
,
ok_
,
rev_
,
revExact_
)
}
}
}
}
// ΔBTestEntry represents one entry in ΔBTail tests.
// ΔBTestEntry represents one entry in ΔBTail tests.
type
ΔBTestEntry
struct
{
type
ΔBTestEntry
struct
{
...
@@ -792,6 +873,15 @@ func ΔBTest(xtest interface{}) ΔBTestEntry {
...
@@ -792,6 +873,15 @@ func ΔBTest(xtest interface{}) ΔBTestEntry {
return
test
return
test
}
}
// ΔBCommit represent test commit changing a tree XXX
type
tTreeCommit
struct
{
tree
string
at
zodb
.
Tid
δZ
*
zodb
.
EventCommit
// δZ.tid == at
xkv
RBucketSet
// full tree state as of @at
// XXX do we also need δkv ?
}
// testΔBTail verifies ΔBTail on sequence of tree topologies coming from testq.
// testΔBTail verifies ΔBTail on sequence of tree topologies coming from testq.
func
testΔBTail
(
t
*
testing
.
T
,
testq
chan
ΔBTestEntry
)
{
func
testΔBTail
(
t
*
testing
.
T
,
testq
chan
ΔBTestEntry
)
{
X
:=
exc
.
Raiseif
X
:=
exc
.
Raiseif
...
@@ -817,8 +907,8 @@ func testΔBTail(t *testing.T, testq chan ΔBTestEntry) {
...
@@ -817,8 +907,8 @@ func testΔBTail(t *testing.T, testq chan ΔBTestEntry) {
err
:=
db
.
Close
();
X
(
err
)
err
:=
db
.
Close
();
X
(
err
)
}()
}()
// XCommitTree calls tg.Commit and returns
δZ
corresponding to committed transaction.
// XCommitTree calls tg.Commit and returns
tTreeCommit
corresponding to committed transaction.
XCommitTree
:=
func
(
tree
string
)
*
zodb
.
Event
Commit
{
XCommitTree
:=
func
(
tree
string
)
*
tTree
Commit
{
defer
exc
.
Contextf
(
"commit %s"
,
tree
)
defer
exc
.
Contextf
(
"commit %s"
,
tree
)
watchq
:=
make
(
chan
zodb
.
Event
)
watchq
:=
make
(
chan
zodb
.
Event
)
...
@@ -836,27 +926,42 @@ func testΔBTail(t *testing.T, testq chan ΔBTestEntry) {
...
@@ -836,27 +926,42 @@ func testΔBTail(t *testing.T, testq chan ΔBTestEntry) {
if
δZ
.
Tid
!=
tid
{
if
δZ
.
Tid
!=
tid
{
exc
.
Raisef
(
"treegen -> %s ; watchq -> %s"
,
tid
,
δZ
)
exc
.
Raisef
(
"treegen -> %s ; watchq -> %s"
,
tid
,
δZ
)
}
}
return
δZ
xkv
:=
XGetTree
(
db
,
δZ
.
Tid
,
tg
.
treeRoot
)
return
&
tTreeCommit
{
tree
:
tree
,
at
:
δZ
.
Tid
,
δZ
:
δZ
,
xkv
:
xkv
,
}
}
}
at1
:=
tg
.
head
var
t0
*
tTreeCommit
xkv1
:=
XGetTree
(
db
,
at1
,
tg
.
treeRoot
)
t1
:=
&
tTreeCommit
{
tree1
:=
"ø"
// initial
tree
:
"ø"
,
// initial
at
:
tg
.
head
,
δZ
:
nil
,
// XXX ok?
xkv
:
XGetTree
(
db
,
tg
.
head
,
tg
.
treeRoot
),
}
for
test
:=
range
testq
{
for
test
:=
range
testq
{
tree2
:=
test
.
tree
t2
:=
XCommitTree
(
test
.
tree
)
δZ
:=
XCommitTree
(
tree2
)
at2
:=
δZ
.
Tid
xkv2
:=
XGetTree
(
db
,
at2
,
tg
.
treeRoot
)
subj
:=
fmt
.
Sprintf
(
"%s -> %s"
,
tree1
,
tree2
)
// ΔBTail.Update
subj
:=
fmt
.
Sprintf
(
"%s -> %s"
,
t1
.
tree
,
t2
.
tree
)
tracef
(
"
\n\n\n
**** %s ****
\n\n
"
,
subj
)
tracef
(
"
\n\n\n
**** %s ****
\n\n
"
,
subj
)
xverifyΔBTail
(
t
,
subj
,
db
,
tg
.
treeRoot
,
at1
,
at2
,
xkv1
,
xkv2
,
δZ
,
test
.
kadjOK
)
xverifyΔBTail
_Update
(
t
,
subj
,
db
,
tg
.
treeRoot
,
t1
,
t2
,
test
.
kadjOK
)
// XXX also verify ΔBtail.Get + SliceByRootRev
// ΔBTail.Get
xverifyΔBTail_Get
(
t
,
"XXX"
,
db
,
tg
.
treeRoot
,
t2
)
xverifyΔBTail_Get
(
t
,
"XXX"
,
db
,
tg
.
treeRoot
,
t1
,
t2
)
if
t0
!=
nil
{
xverifyΔBTail_Get
(
t
,
"XXX"
,
db
,
tg
.
treeRoot
,
t0
,
t1
,
t2
)
}
// XXX ΔBTail.SliceByRootRev
at1
=
at2
t0
,
t1
=
t1
,
t2
xkv1
=
xkv2
tree1
=
tree2
}
}
}
}
...
@@ -1299,6 +1404,18 @@ func xkvFlatten(xkv RBucketSet) map[Key]string {
...
@@ -1299,6 +1404,18 @@ func xkvFlatten(xkv RBucketSet) map[Key]string {
return
kv
return
kv
}
}
// allTestKeys returns all keys from vt + ∞.
func
allTestKeys
(
vt
...*
tTreeCommit
)
SetKey
{
allKeys
:=
SetKey
{};
allKeys
.
Add
(
kInf
)
// ∞ simulating ZBigFile.Size() query
for
_
,
t
:=
range
vt
{
for
_
,
b
:=
range
t
.
xkv
{
for
k
:=
range
b
.
kv
{
allKeys
.
Add
(
k
)
}
}
}
return
allKeys
}
// easies debugging / makes error output stable from run to run.
// easies debugging / makes error output stable from run to run.
func
(
ks
SetKey
)
SortedKeys
()
[]
Key
{
func
(
ks
SetKey
)
SortedKeys
()
[]
Key
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment