mirror of
https://github.com/anyproto/anytype-heart.git
synced 2025-06-09 17:44:59 +09:00
Merge branch 'master' of ssh://github.com/anytypeio/go-anytype-middleware into protocol-refactor
# Conflicts: # clientlibrary/service/service.pb.go # core/debug.go # docs/proto.md # pb/commands.pb.go # pb/service/service.pb.go
This commit is contained in:
commit
68f0677239
12 changed files with 801 additions and 625 deletions
|
@ -47,7 +47,9 @@ var dumpTree = &cobra.Command{
|
|||
|
||||
dbg := app.MustComponent(debug.CName).(debug.Debug)
|
||||
|
||||
filename, err := dbg.DumpTree(debugThread, debugOutputFile, false)
|
||||
isAnonymize := false
|
||||
dumpWithSvg := false
|
||||
filename, err := dbg.DumpTree(debugThread, debugOutputFile, isAnonymize, dumpWithSvg)
|
||||
if err != nil {
|
||||
console.Fatal("failed to dump tree: %s", err.Error())
|
||||
}
|
||||
|
|
|
@ -2,7 +2,6 @@ package stext
|
|||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/anytypeio/go-anytype-middleware/metrics"
|
||||
"sort"
|
||||
"strings"
|
||||
"time"
|
||||
|
@ -12,6 +11,7 @@ import (
|
|||
"github.com/anytypeio/go-anytype-middleware/core/block/editor/template"
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/simple/link"
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/simple/text"
|
||||
"github.com/anytypeio/go-anytype-middleware/metrics"
|
||||
"github.com/anytypeio/go-anytype-middleware/pb"
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/logging"
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/pb/model"
|
||||
|
@ -156,6 +156,12 @@ func (t *textImpl) Split(ctx *state.Context, req pb.RpcBlockSplitRequest) (newId
|
|||
func (t *textImpl) Merge(ctx *state.Context, firstId, secondId string) (err error) {
|
||||
startTime := time.Now()
|
||||
s := t.NewStateCtx(ctx)
|
||||
|
||||
// Don't merge blocks inside header block
|
||||
if s.IsParentOf(template.HeaderLayoutId, secondId) {
|
||||
return
|
||||
}
|
||||
|
||||
first, err := getText(s, firstId)
|
||||
if err != nil {
|
||||
return
|
||||
|
|
|
@ -5,6 +5,7 @@ import (
|
|||
"time"
|
||||
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/editor/smartblock/smarttest"
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/editor/template"
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/simple"
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/simple/link"
|
||||
"github.com/anytypeio/go-anytype-middleware/core/block/simple/text"
|
||||
|
@ -130,27 +131,56 @@ func TestTextImpl_Split(t *testing.T) {
|
|||
}
|
||||
|
||||
func TestTextImpl_Merge(t *testing.T) {
|
||||
sb := smarttest.New("test")
|
||||
tb1 := newTextBlock("1", "one")
|
||||
tb1.Model().ChildrenIds = []string{"ch1"}
|
||||
tb2 := newTextBlock("2", "two")
|
||||
tb2.Model().ChildrenIds = []string{"ch2"}
|
||||
sb.AddBlock(simple.New(&model.Block{Id: "test", ChildrenIds: []string{"1", "2"}})).
|
||||
AddBlock(tb1).
|
||||
AddBlock(tb2).
|
||||
AddBlock(simple.New(&model.Block{Id: "ch1"})).
|
||||
AddBlock(simple.New(&model.Block{Id: "ch2"}))
|
||||
tb := NewText(sb)
|
||||
t.Run("should merge two text blocks", func(t *testing.T) {
|
||||
sb := smarttest.New("test")
|
||||
tb1 := newTextBlock("1", "one")
|
||||
tb1.Model().ChildrenIds = []string{"ch1"}
|
||||
tb2 := newTextBlock("2", "two")
|
||||
tb2.Model().ChildrenIds = []string{"ch2"}
|
||||
sb.AddBlock(simple.New(&model.Block{Id: "test", ChildrenIds: []string{"1", "2"}})).
|
||||
AddBlock(tb1).
|
||||
AddBlock(tb2).
|
||||
AddBlock(simple.New(&model.Block{Id: "ch1"})).
|
||||
AddBlock(simple.New(&model.Block{Id: "ch2"}))
|
||||
tb := NewText(sb)
|
||||
|
||||
err := tb.Merge(nil, "1", "2")
|
||||
require.NoError(t, err)
|
||||
err := tb.Merge(nil, "1", "2")
|
||||
require.NoError(t, err)
|
||||
|
||||
r := sb.NewState()
|
||||
assert.False(t, r.Exists("2"))
|
||||
require.True(t, r.Exists("1"))
|
||||
r := sb.NewState()
|
||||
assert.False(t, r.Exists("2"))
|
||||
require.True(t, r.Exists("1"))
|
||||
|
||||
assert.Equal(t, "onetwo", r.Pick("1").Model().GetText().Text)
|
||||
assert.Equal(t, []string{"ch1", "ch2"}, r.Pick("1").Model().ChildrenIds)
|
||||
assert.Equal(t, "onetwo", r.Pick("1").Model().GetText().Text)
|
||||
assert.Equal(t, []string{"ch1", "ch2"}, r.Pick("1").Model().ChildrenIds)
|
||||
})
|
||||
|
||||
t.Run("shouldn't merge blocks inside header block", func(t *testing.T) {
|
||||
sb := smarttest.New("test")
|
||||
tb1 := newTextBlock("1", "one")
|
||||
tb1.Model().ChildrenIds = []string{"ch1"}
|
||||
tb2 := newTextBlock("2", "two")
|
||||
tb2.Model().ChildrenIds = []string{"ch2"}
|
||||
sb.AddBlock(simple.New(&model.Block{Id: template.HeaderLayoutId, ChildrenIds: []string{"1", "2"}})).
|
||||
AddBlock(tb1).
|
||||
AddBlock(tb2).
|
||||
AddBlock(simple.New(&model.Block{Id: "ch1"})).
|
||||
AddBlock(simple.New(&model.Block{Id: "ch2"}))
|
||||
|
||||
tb := NewText(sb)
|
||||
|
||||
err := tb.Merge(nil, "1", "2")
|
||||
require.NoError(t, err)
|
||||
|
||||
r := sb.NewState()
|
||||
require.True(t, r.Exists("1"))
|
||||
require.True(t, r.Exists("2"))
|
||||
|
||||
assert.Equal(t, "one", r.Pick("1").Model().GetText().Text)
|
||||
assert.Equal(t, "two", r.Pick("2").Model().GetText().Text)
|
||||
assert.Equal(t, []string{"ch1"}, r.Pick("1").Model().ChildrenIds)
|
||||
assert.Equal(t, []string{"ch2"}, r.Pick("2").Model().ChildrenIds)
|
||||
})
|
||||
}
|
||||
|
||||
func TestTextImpl_SetMark(t *testing.T) {
|
||||
|
|
|
@ -134,7 +134,7 @@ func (mw *Middleware) DebugTree(req *pb.RpcDebugTreeRequest) *pb.RpcDebugTreeRes
|
|||
}
|
||||
|
||||
dbg := app.MustComponent(debug.CName).(debug.Debug)
|
||||
filename, err := dbg.DumpTree(req.ObjectId, req.Path, !req.Unanonymized)
|
||||
filename, err := dbg.DumpTree(req.ObjectId, req.Path, !req.Unanonymized, req.GenerateSvg)
|
||||
return response(err, filename)
|
||||
}
|
||||
|
||||
|
|
|
@ -6,22 +6,26 @@ import (
|
|||
"github.com/anytypeio/go-anytype-middleware/app"
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/core"
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/localstore/objectstore"
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/logging"
|
||||
"github.com/gogo/protobuf/jsonpb"
|
||||
"io"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"time"
|
||||
"strings"
|
||||
)
|
||||
|
||||
const CName = "debug"
|
||||
|
||||
var logger = logging.Logger("anytype-debug")
|
||||
|
||||
func New() Debug {
|
||||
return new(debug)
|
||||
}
|
||||
|
||||
type Debug interface {
|
||||
app.Component
|
||||
DumpTree(blockId, path string, anonymize bool) (filename string, err error)
|
||||
DumpTree(blockId, path string, anonymize bool, withSvg bool) (filename string, err error)
|
||||
DumpLocalstore(objectIds []string, path string) (filename string, err error)
|
||||
}
|
||||
|
||||
|
@ -40,13 +44,43 @@ func (d *debug) Name() (name string) {
|
|||
return CName
|
||||
}
|
||||
|
||||
func (d *debug) DumpTree(blockId, path string, anonymize bool) (filename string, err error) {
|
||||
func (d *debug) DumpTree(blockId, path string, anonymize bool, withSvg bool) (filename string, err error) {
|
||||
// 0 - get first block
|
||||
block, err := d.core.GetBlock(blockId)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
// 1 - create ZIP file
|
||||
// <path>/at.dbg.bafkudtugh626rrqzah3kam4yj4lqbaw4bjayn2rz4ah4n5fpayppbvmq.20220322.121049.23.zip
|
||||
builder := &treeBuilder{b: block, s: d.store, anonymized: anonymize}
|
||||
return builder.Build(path)
|
||||
zipFilename, err := builder.Build(path)
|
||||
if err != nil {
|
||||
logger.Fatal("build tree error:", err)
|
||||
return "", err
|
||||
}
|
||||
|
||||
// if client never asked for SVG generation -> return
|
||||
if !withSvg {
|
||||
return zipFilename, err
|
||||
}
|
||||
|
||||
// 2 - create SVG file near ZIP
|
||||
// <path>/at.dbg.bafkudtugh626rrqzah3kam4yj4lqbaw4bjayn2rz4ah4n5fpayppbvmq.20220322.121049.23.svg
|
||||
//
|
||||
// this will return "graphviz is not supported on the current platform" error if no graphviz!
|
||||
// generate a filename just like zip file had
|
||||
maxReplacements := 1
|
||||
svgFilename := strings.Replace(zipFilename, ".zip", ".svg", maxReplacements)
|
||||
|
||||
err = CreateSvg(block, svgFilename)
|
||||
if err != nil {
|
||||
logger.Fatal("svg build error:", err)
|
||||
return "", err
|
||||
}
|
||||
|
||||
// return zip filename, but not svgFilename
|
||||
return zipFilename, nil
|
||||
}
|
||||
|
||||
func (d *debug) DumpLocalstore(objIds []string, path string) (filename string, err error) {
|
||||
|
|
13
core/debug/svg_builder.go
Normal file
13
core/debug/svg_builder.go
Normal file
|
@ -0,0 +1,13 @@
|
|||
// +build !linux,!darwin android ios nographviz
|
||||
// +build !amd64
|
||||
|
||||
package debug
|
||||
|
||||
import (
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/core"
|
||||
"fmt"
|
||||
)
|
||||
|
||||
func CreateSvg(block core.SmartBlock, svgFilename string)(err error){
|
||||
return fmt.Errorf("graphviz is not supported on the current platform")
|
||||
}
|
44
core/debug/svg_builder_nix.go
Normal file
44
core/debug/svg_builder_nix.go
Normal file
|
@ -0,0 +1,44 @@
|
|||
// +build linux darwin
|
||||
// +build !android,!ios,!nographviz
|
||||
// +build amd64 arm64
|
||||
|
||||
package debug
|
||||
|
||||
import (
|
||||
"github.com/anytypeio/go-anytype-middleware/pkg/lib/core"
|
||||
"github.com/anytypeio/go-anytype-middleware/change"
|
||||
"github.com/goccy/go-graphviz"
|
||||
"os"
|
||||
)
|
||||
|
||||
// This will create SVG image of the SmartBlock (i.e a DAG)
|
||||
func CreateSvg(block core.SmartBlock, svgFilename string)(err error){
|
||||
t, _, err := change.BuildTree(block)
|
||||
if err != nil {
|
||||
logger.Fatal("build tree error:", err)
|
||||
return err
|
||||
}
|
||||
|
||||
gv, err := t.Graphviz()
|
||||
if err != nil {
|
||||
logger.Fatal("can't make graphviz data:", err)
|
||||
return err
|
||||
}
|
||||
|
||||
gvo, err := graphviz.ParseBytes([]byte(gv))
|
||||
if err != nil {
|
||||
logger.Fatal("can't open graphviz data:", err)
|
||||
return err
|
||||
}
|
||||
|
||||
f, err := os.Create(svgFilename)
|
||||
if err != nil {
|
||||
logger.Fatal("can't create SVG file:", err)
|
||||
return err
|
||||
}
|
||||
defer f.Close()
|
||||
|
||||
g := graphviz.New()
|
||||
return g.Render(gvo, graphviz.SVG, f)
|
||||
}
|
||||
|
|
@ -1,3 +1,7 @@
|
|||
// +build linux darwin
|
||||
// +build !android,!ios,!nographviz
|
||||
// +build amd64 arm64
|
||||
|
||||
package debug
|
||||
|
||||
import (
|
||||
|
|
|
@ -6288,6 +6288,7 @@ Get marks list in the selected range in text block.
|
|||
| objectId | [string](#string) | | |
|
||||
| path | [string](#string) | | |
|
||||
| unanonymized | [bool](#bool) | | set to true to disable mocking of the actual data inside changes |
|
||||
| generateSvg | [bool](#bool) | | set to true to write both ZIP and SVG files |
|
||||
|
||||
|
||||
|
||||
|
|
1241
pb/commands.pb.go
1241
pb/commands.pb.go
File diff suppressed because it is too large
Load diff
|
@ -3870,6 +3870,7 @@ message Rpc {
|
|||
string objectId = 1;
|
||||
string path = 2;
|
||||
bool unanonymized = 3; // set to true to disable mocking of the actual data inside changes
|
||||
bool generateSvg = 4; // set to true to write both ZIP and SVG files
|
||||
}
|
||||
|
||||
message Response {
|
||||
|
|
|
@ -112,7 +112,7 @@ func (w *Wallet) AccountAt(index int, passphrase string) (Keypair, error) {
|
|||
seed, err := bip39.NewSeedWithErrorChecking(w.RecoveryPhrase, passphrase)
|
||||
if err != nil {
|
||||
if err == bip39.ErrInvalidMnemonic {
|
||||
return nil, fmt.Errorf("invalid mnemonic phrase")
|
||||
return nil, fmt.Errorf("invalid recovery phrase")
|
||||
}
|
||||
return nil, err
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue