mirror of
https://github.com/siyuan-note/siyuan.git
synced 2025-12-17 07:00:12 +01:00
🧑💻 Add kernel API /api/av/batchReplaceAttributeViewBlocks https://github.com/siyuan-note/siyuan/issues/15313
This commit is contained in:
parent
50e8e88aaf
commit
2b864265d0
3 changed files with 89 additions and 27 deletions
|
|
@ -27,6 +27,36 @@ import (
|
||||||
"github.com/siyuan-note/siyuan/kernel/util"
|
"github.com/siyuan-note/siyuan/kernel/util"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func batchReplaceAttributeViewBlocks(c *gin.Context) {
|
||||||
|
// Add kernel API `/api/av/batchReplaceAttributeViewBlocks` https://github.com/siyuan-note/siyuan/issues/15313
|
||||||
|
ret := gulu.Ret.NewResult()
|
||||||
|
defer c.JSON(http.StatusOK, ret)
|
||||||
|
|
||||||
|
arg, ok := util.JsonArg(c, ret)
|
||||||
|
if !ok {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
avID := arg["avID"].(string)
|
||||||
|
isDetached := arg["isDetached"].(bool)
|
||||||
|
oldNewArg := arg["oldNew"].([]interface{})
|
||||||
|
var oldNew []map[string]string
|
||||||
|
for _, v := range oldNewArg {
|
||||||
|
for o, n := range v.(map[string]interface{}) {
|
||||||
|
oldNew = append(oldNew, map[string]string{o: n.(string)})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
err := model.BatchReplaceAttributeViewBlocks(avID, isDetached, oldNew)
|
||||||
|
if err != nil {
|
||||||
|
ret.Code = -1
|
||||||
|
ret.Msg = err.Error()
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
model.ReloadAttrView(avID)
|
||||||
|
}
|
||||||
|
|
||||||
func setAttrViewGroup(c *gin.Context) {
|
func setAttrViewGroup(c *gin.Context) {
|
||||||
ret := gulu.Ret.NewResult()
|
ret := gulu.Ret.NewResult()
|
||||||
defer c.JSON(http.StatusOK, ret)
|
defer c.JSON(http.StatusOK, ret)
|
||||||
|
|
@ -737,6 +767,7 @@ func setAttributeViewBlockAttr(c *gin.Context) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func batchSetAttributeViewBlockAttrs(c *gin.Context) {
|
func batchSetAttributeViewBlockAttrs(c *gin.Context) {
|
||||||
|
// Add kernel API `/api/av/batchSetAttributeViewBlockAttrs` https://github.com/siyuan-note/siyuan/issues/15310
|
||||||
ret := gulu.Ret.NewResult()
|
ret := gulu.Ret.NewResult()
|
||||||
defer c.JSON(http.StatusOK, ret)
|
defer c.JSON(http.StatusOK, ret)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -457,6 +457,7 @@ func ServeAPI(ginServer *gin.Engine) {
|
||||||
ginServer.Handle("POST", "/api/av/getCurrentAttrViewImages", model.CheckAuth, getCurrentAttrViewImages)
|
ginServer.Handle("POST", "/api/av/getCurrentAttrViewImages", model.CheckAuth, getCurrentAttrViewImages)
|
||||||
ginServer.Handle("POST", "/api/av/changeAttrViewLayout", model.CheckAuth, changeAttrViewLayout)
|
ginServer.Handle("POST", "/api/av/changeAttrViewLayout", model.CheckAuth, changeAttrViewLayout)
|
||||||
ginServer.Handle("POST", "/api/av/setAttrViewGroup", model.CheckAuth, setAttrViewGroup)
|
ginServer.Handle("POST", "/api/av/setAttrViewGroup", model.CheckAuth, setAttrViewGroup)
|
||||||
|
ginServer.Handle("POST", "/api/av/batchReplaceAttributeViewBlocks", model.CheckAuth, batchReplaceAttributeViewBlocks)
|
||||||
|
|
||||||
ginServer.Handle("POST", "/api/ai/chatGPT", model.CheckAuth, model.CheckAdminRole, chatGPT)
|
ginServer.Handle("POST", "/api/ai/chatGPT", model.CheckAuth, model.CheckAdminRole, chatGPT)
|
||||||
ginServer.Handle("POST", "/api/ai/chatGPTWithAction", model.CheckAuth, model.CheckAdminRole, chatGPTWithAction)
|
ginServer.Handle("POST", "/api/ai/chatGPTWithAction", model.CheckAuth, model.CheckAdminRole, chatGPTWithAction)
|
||||||
|
|
|
||||||
|
|
@ -3837,32 +3837,44 @@ func RemoveAttributeViewKey(avID, keyID string, removeRelationDest bool) (err er
|
||||||
}
|
}
|
||||||
|
|
||||||
func (tx *Transaction) doReplaceAttrViewBlock(operation *Operation) (ret *TxErr) {
|
func (tx *Transaction) doReplaceAttrViewBlock(operation *Operation) (ret *TxErr) {
|
||||||
err := replaceAttributeViewBlock(operation, tx)
|
err := replaceAttributeViewBlock(operation.AvID, operation.PreviousID, operation.NextID, operation.IsDetached, tx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &TxErr{code: TxErrHandleAttributeView, id: operation.AvID}
|
return &TxErr{code: TxErrHandleAttributeView, id: operation.AvID}
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func replaceAttributeViewBlock(operation *Operation, tx *Transaction) (err error) {
|
func replaceAttributeViewBlock(avID, oldBlockID, newBlockID string, isDetached bool, tx *Transaction) (err error) {
|
||||||
attrView, err := av.ParseAttributeView(operation.AvID)
|
attrView, err := av.ParseAttributeView(avID)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if err = replaceAttributeViewBlock0(attrView, oldBlockID, newBlockID, isDetached, tx); nil != err {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if err = av.SaveAttributeView(attrView); nil != err {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func replaceAttributeViewBlock0(attrView *av.AttributeView, oldBlockID, newBlockID string, isDetached bool, tx *Transaction) (err error) {
|
||||||
|
avID := attrView.ID
|
||||||
var node *ast.Node
|
var node *ast.Node
|
||||||
var tree *parse.Tree
|
var tree *parse.Tree
|
||||||
if !operation.IsDetached {
|
if !isDetached {
|
||||||
node, tree, _ = getNodeByBlockID(tx, operation.NextID)
|
node, tree, _ = getNodeByBlockID(tx, newBlockID)
|
||||||
}
|
}
|
||||||
|
|
||||||
now := util.CurrentTimeMillis()
|
now := util.CurrentTimeMillis()
|
||||||
// 检查是否已经存在绑定块,如果存在的话则重新绑定
|
// 检查是否已经存在绑定块,如果存在的话则重新绑定
|
||||||
for _, keyValues := range attrView.KeyValues {
|
for _, keyValues := range attrView.KeyValues {
|
||||||
for _, value := range keyValues.Values {
|
for _, value := range keyValues.Values {
|
||||||
if av.KeyTypeBlock == value.Type && nil != value.Block && value.BlockID == operation.NextID {
|
if av.KeyTypeBlock == value.Type && nil != value.Block && value.BlockID == newBlockID {
|
||||||
if !operation.IsDetached {
|
if !isDetached {
|
||||||
bindBlockAv0(tx, operation.AvID, node, tree)
|
bindBlockAv0(tx, avID, node, tree)
|
||||||
value.IsDetached = false
|
value.IsDetached = false
|
||||||
icon, content := getNodeAvBlockText(node)
|
icon, content := getNodeAvBlockText(node)
|
||||||
content = util.UnescapeHTML(content)
|
content = util.UnescapeHTML(content)
|
||||||
|
|
@ -3881,38 +3893,38 @@ func replaceAttributeViewBlock(operation *Operation, tx *Transaction) (err error
|
||||||
if av.KeyTypeRelation == value.Type {
|
if av.KeyTypeRelation == value.Type {
|
||||||
if nil != value.Relation {
|
if nil != value.Relation {
|
||||||
for i, relBlockID := range value.Relation.BlockIDs {
|
for i, relBlockID := range value.Relation.BlockIDs {
|
||||||
if relBlockID == operation.PreviousID {
|
if relBlockID == oldBlockID {
|
||||||
value.Relation.BlockIDs[i] = operation.NextID
|
value.Relation.BlockIDs[i] = newBlockID
|
||||||
changedAvIDs = append(changedAvIDs, attrView.ID)
|
changedAvIDs = append(changedAvIDs, attrView.ID)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if value.BlockID != operation.PreviousID {
|
if value.BlockID != oldBlockID {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
if av.KeyTypeBlock == value.Type && value.BlockID != operation.NextID {
|
if av.KeyTypeBlock == value.Type && value.BlockID != newBlockID {
|
||||||
// 换绑
|
// 换绑
|
||||||
unbindBlockAv(tx, operation.AvID, value.BlockID)
|
unbindBlockAv(tx, avID, value.BlockID)
|
||||||
}
|
}
|
||||||
|
|
||||||
value.BlockID = operation.NextID
|
value.BlockID = newBlockID
|
||||||
if av.KeyTypeBlock == value.Type && nil != value.Block {
|
if av.KeyTypeBlock == value.Type && nil != value.Block {
|
||||||
value.Block.ID = operation.NextID
|
value.Block.ID = newBlockID
|
||||||
value.IsDetached = operation.IsDetached
|
value.IsDetached = isDetached
|
||||||
if !operation.IsDetached {
|
if !isDetached {
|
||||||
icon, content := getNodeAvBlockText(node)
|
icon, content := getNodeAvBlockText(node)
|
||||||
content = util.UnescapeHTML(content)
|
content = util.UnescapeHTML(content)
|
||||||
value.Block.Icon, value.Block.Content = icon, content
|
value.Block.Icon, value.Block.Content = icon, content
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if av.KeyTypeBlock == value.Type && !operation.IsDetached {
|
if av.KeyTypeBlock == value.Type && !isDetached {
|
||||||
bindBlockAv(tx, operation.AvID, operation.NextID)
|
bindBlockAv(tx, avID, newBlockID)
|
||||||
|
|
||||||
avIDs := replaceRelationAvValues(operation.AvID, operation.PreviousID, operation.NextID)
|
avIDs := replaceRelationAvValues(avID, oldBlockID, newBlockID)
|
||||||
changedAvIDs = append(changedAvIDs, avIDs...)
|
changedAvIDs = append(changedAvIDs, avIDs...)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -3921,23 +3933,41 @@ func replaceAttributeViewBlock(operation *Operation, tx *Transaction) (err error
|
||||||
replacedRowID := false
|
replacedRowID := false
|
||||||
for _, v := range attrView.Views {
|
for _, v := range attrView.Views {
|
||||||
for i, itemID := range v.ItemIDs {
|
for i, itemID := range v.ItemIDs {
|
||||||
if itemID == operation.PreviousID {
|
if itemID == oldBlockID {
|
||||||
v.ItemIDs[i] = operation.NextID
|
v.ItemIDs[i] = newBlockID
|
||||||
replacedRowID = true
|
replacedRowID = true
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if !replacedRowID {
|
if !replacedRowID {
|
||||||
v.ItemIDs = append(v.ItemIDs, operation.NextID)
|
v.ItemIDs = append(v.ItemIDs, newBlockID)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
err = av.SaveAttributeView(attrView)
|
|
||||||
|
|
||||||
changedAvIDs = gulu.Str.RemoveDuplicatedElem(changedAvIDs)
|
changedAvIDs = gulu.Str.RemoveDuplicatedElem(changedAvIDs)
|
||||||
for _, avID := range changedAvIDs {
|
for _, id := range changedAvIDs {
|
||||||
ReloadAttrView(avID)
|
ReloadAttrView(id)
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func BatchReplaceAttributeViewBlocks(avID string, isDetached bool, oldNew []map[string]string) (err error) {
|
||||||
|
attrView, err := av.ParseAttributeView(avID)
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, oldNewMap := range oldNew {
|
||||||
|
for oldBlockID, newBlockID := range oldNewMap {
|
||||||
|
if err = replaceAttributeViewBlock0(attrView, oldBlockID, newBlockID, isDetached, nil); nil != err {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if err = av.SaveAttributeView(attrView); nil != err {
|
||||||
|
return
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue