[#151] index page: Add browse via native protocol
All checks were successful
/ DCO (pull_request) Successful in 1m42s
/ Vulncheck (pull_request) Successful in 1m43s
/ Builds (pull_request) Successful in 1m35s
/ Lint (pull_request) Successful in 2m11s
/ Tests (pull_request) Successful in 1m35s
/ Builds (push) Successful in 1m13s
/ Vulncheck (push) Successful in 1m47s
/ Lint (push) Successful in 2m39s
/ Tests (push) Successful in 1m51s
All checks were successful
/ DCO (pull_request) Successful in 1m42s
/ Vulncheck (pull_request) Successful in 1m43s
/ Builds (pull_request) Successful in 1m35s
/ Lint (pull_request) Successful in 2m11s
/ Tests (pull_request) Successful in 1m35s
/ Builds (push) Successful in 1m13s
/ Vulncheck (push) Successful in 1m47s
/ Lint (push) Successful in 2m39s
/ Tests (push) Successful in 1m51s
Signed-off-by: Nikita Zinkevich <n.zinkevich@yadro.com>
This commit is contained in:
parent
9c0b499ea6
commit
43764772aa
16 changed files with 537 additions and 133 deletions
104
tree/tree.go
104
tree/tree.go
|
@ -30,6 +30,11 @@ type (
|
|||
Meta map[string]string
|
||||
}
|
||||
|
||||
multiSystemNode struct {
|
||||
// the first element is latest
|
||||
nodes []*treeNode
|
||||
}
|
||||
|
||||
GetNodesParams struct {
|
||||
CnrID cid.ID
|
||||
BktInfo *data.BucketInfo
|
||||
|
@ -50,18 +55,19 @@ var (
|
|||
)
|
||||
|
||||
const (
|
||||
FileNameKey = "FileName"
|
||||
)
|
||||
FileNameKey = "FileName"
|
||||
settingsFileName = "bucket-settings"
|
||||
|
||||
const (
|
||||
oidKV = "OID"
|
||||
oidKV = "OID"
|
||||
uploadIDKV = "UploadId"
|
||||
sizeKV = "Size"
|
||||
|
||||
// keys for delete marker nodes.
|
||||
isDeleteMarkerKV = "IsDeleteMarker"
|
||||
sizeKV = "Size"
|
||||
|
||||
// versionTree -- ID of a tree with object versions.
|
||||
versionTree = "version"
|
||||
systemTree = "system"
|
||||
|
||||
separator = "/"
|
||||
)
|
||||
|
@ -135,6 +141,45 @@ func newNodeVersionFromTreeNode(treeNode *treeNode) *api.NodeVersion {
|
|||
return version
|
||||
}
|
||||
|
||||
func newMultiNode(nodes []NodeResponse) (*multiSystemNode, error) {
|
||||
var (
|
||||
err error
|
||||
index int
|
||||
maxTimestamp uint64
|
||||
)
|
||||
|
||||
if len(nodes) == 0 {
|
||||
return nil, errors.New("multi node must have at least one node")
|
||||
}
|
||||
|
||||
treeNodes := make([]*treeNode, len(nodes))
|
||||
|
||||
for i, node := range nodes {
|
||||
if treeNodes[i], err = newTreeNode(node); err != nil {
|
||||
return nil, fmt.Errorf("parse system node response: %w", err)
|
||||
}
|
||||
|
||||
if timestamp := getMaxTimestamp(node); timestamp > maxTimestamp {
|
||||
index = i
|
||||
maxTimestamp = timestamp
|
||||
}
|
||||
}
|
||||
|
||||
treeNodes[0], treeNodes[index] = treeNodes[index], treeNodes[0]
|
||||
|
||||
return &multiSystemNode{
|
||||
nodes: treeNodes,
|
||||
}, nil
|
||||
}
|
||||
|
||||
func (m *multiSystemNode) Latest() *treeNode {
|
||||
return m.nodes[0]
|
||||
}
|
||||
|
||||
func (m *multiSystemNode) Old() []*treeNode {
|
||||
return m.nodes[1:]
|
||||
}
|
||||
|
||||
func (c *Tree) GetLatestVersion(ctx context.Context, cnrID *cid.ID, objectName string) (*api.NodeVersion, error) {
|
||||
nodes, err := c.GetVersions(ctx, cnrID, objectName)
|
||||
if err != nil {
|
||||
|
@ -165,6 +210,55 @@ func (c *Tree) GetVersions(ctx context.Context, cnrID *cid.ID, objectName string
|
|||
return c.service.GetNodes(ctx, p)
|
||||
}
|
||||
|
||||
func (c *Tree) CheckSettingsNodeExist(ctx context.Context, bktInfo *data.BucketInfo) error {
|
||||
_, err := c.getSystemNode(ctx, bktInfo, settingsFileName)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (c *Tree) getSystemNode(ctx context.Context, bktInfo *data.BucketInfo, name string) (*multiSystemNode, error) {
|
||||
p := &GetNodesParams{
|
||||
CnrID: bktInfo.CID,
|
||||
BktInfo: bktInfo,
|
||||
TreeID: systemTree,
|
||||
Path: []string{name},
|
||||
LatestOnly: false,
|
||||
AllAttrs: true,
|
||||
}
|
||||
nodes, err := c.service.GetNodes(ctx, p)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
nodes = filterMultipartNodes(nodes)
|
||||
|
||||
if len(nodes) == 0 {
|
||||
return nil, ErrNodeNotFound
|
||||
}
|
||||
|
||||
return newMultiNode(nodes)
|
||||
}
|
||||
|
||||
func filterMultipartNodes(nodes []NodeResponse) []NodeResponse {
|
||||
res := make([]NodeResponse, 0, len(nodes))
|
||||
|
||||
LOOP:
|
||||
for _, node := range nodes {
|
||||
for _, meta := range node.GetMeta() {
|
||||
if meta.GetKey() == uploadIDKV {
|
||||
continue LOOP
|
||||
}
|
||||
}
|
||||
|
||||
res = append(res, node)
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
func getLatestVersionNode(nodes []NodeResponse) (NodeResponse, error) {
|
||||
var (
|
||||
maxCreationTime uint64
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue