refactor(workflow): Move the database component in the Workflow package into the common crossdomain package (#704)

This commit is contained in:
Ryo
2025-08-12 15:42:58 +08:00
committed by GitHub
parent e7011f2549
commit 9ff065cebd
29 changed files with 834 additions and 1353 deletions

View File

@@ -1,31 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package code
import (
"github.com/coze-dev/coze-studio/backend/infra/contract/coderunner"
)
func GetCodeRunner() coderunner.Runner {
return runnerImpl
}
func SetCodeRunner(runner coderunner.Runner) {
runnerImpl = runner
}
var runnerImpl coderunner.Runner

View File

@@ -1,61 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package conversation
import "context"
type ClearMessageRequest struct {
Name string
}
type ClearMessageResponse struct {
IsSuccess bool
}
type CreateConversationRequest struct {
Name string
}
type CreateConversationResponse struct {
Result map[string]any
}
type ListMessageRequest struct {
ConversationName string
Limit *int
BeforeID *string
AfterID *string
}
type Message struct {
ID string `json:"id"`
Role string `json:"role"`
ContentType string `json:"contentType"`
Content string `json:"content"`
}
type ListMessageResponse struct {
Messages []*Message
FirstID string
LastID string
HasMore bool
}
var ConversationManagerImpl ConversationManager
type ConversationManager interface {
ClearMessage(context.Context, *ClearMessageRequest) (*ClearMessageResponse, error)
CreateConversation(ctx context.Context, c *CreateConversationRequest) (*CreateConversationResponse, error)
MessageList(ctx context.Context, req *ListMessageRequest) (*ListMessageResponse, error)
}

View File

@@ -1,148 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package database
import (
"context"
)
type SQLParam struct {
Value string
IsNull bool
}
type CustomSQLRequest struct {
DatabaseInfoID int64
SQL string
Params []SQLParam
IsDebugRun bool
UserID string
ConnectorID int64
}
type Object = map[string]any
type Response struct {
RowNumber *int64
Objects []Object
}
type Operator string
type ClauseRelation string
const (
ClauseRelationAND ClauseRelation = "and"
ClauseRelationOR ClauseRelation = "or"
)
const (
OperatorEqual Operator = "="
OperatorNotEqual Operator = "!="
OperatorGreater Operator = ">"
OperatorLesser Operator = "<"
OperatorGreaterOrEqual Operator = ">="
OperatorLesserOrEqual Operator = "<="
OperatorIn Operator = "in"
OperatorNotIn Operator = "not_in"
OperatorIsNull Operator = "is_null"
OperatorIsNotNull Operator = "is_not_null"
OperatorLike Operator = "like"
OperatorNotLike Operator = "not_like"
)
type ClauseGroup struct {
Single *Clause
Multi *MultiClause
}
type Clause struct {
Left string
Operator Operator
}
type MultiClause struct {
Clauses []*Clause
Relation ClauseRelation
}
type Condition struct {
Left string
Operator Operator
Right any
}
type ConditionGroup struct {
Conditions []*Condition
Relation ClauseRelation
}
type DeleteRequest struct {
DatabaseInfoID int64
ConditionGroup *ConditionGroup
IsDebugRun bool
UserID string
ConnectorID int64
}
type QueryRequest struct {
DatabaseInfoID int64
SelectFields []string
Limit int64
ConditionGroup *ConditionGroup
OrderClauses []*OrderClause
IsDebugRun bool
UserID string
ConnectorID int64
}
type OrderClause struct {
FieldID string
IsAsc bool
}
type UpdateRequest struct {
DatabaseInfoID int64
ConditionGroup *ConditionGroup
Fields map[string]any
IsDebugRun bool
UserID string
ConnectorID int64
}
type InsertRequest struct {
DatabaseInfoID int64
Fields map[string]any
IsDebugRun bool
UserID string
ConnectorID int64
}
func GetDatabaseOperator() DatabaseOperator {
return databaseOperatorImpl
}
func SetDatabaseOperator(d DatabaseOperator) {
databaseOperatorImpl = d
}
var (
databaseOperatorImpl DatabaseOperator
)
//go:generate mockgen -destination databasemock/database_mock.go --package databasemock -source database.go
type DatabaseOperator interface {
Execute(ctx context.Context, request *CustomSQLRequest) (*Response, error)
Query(ctx context.Context, request *QueryRequest) (*Response, error)
Update(context.Context, *UpdateRequest) (*Response, error)
Insert(ctx context.Context, request *InsertRequest) (*Response, error)
Delete(context.Context, *DeleteRequest) (*Response, error)
}

View File

@@ -1,133 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
// Code generated by MockGen. DO NOT EDIT.
// Source: database.go
//
// Generated by this command:
//
// mockgen -destination databasemock/database_mock.go --package databasemock -source database.go
//
// Package databasemock is a generated GoMock package.
package databasemock
import (
context "context"
reflect "reflect"
database "github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
gomock "go.uber.org/mock/gomock"
)
// MockDatabaseOperator is a mock of DatabaseOperator interface.
type MockDatabaseOperator struct {
ctrl *gomock.Controller
recorder *MockDatabaseOperatorMockRecorder
isgomock struct{}
}
// MockDatabaseOperatorMockRecorder is the mock recorder for MockDatabaseOperator.
type MockDatabaseOperatorMockRecorder struct {
mock *MockDatabaseOperator
}
// NewMockDatabaseOperator creates a new mock instance.
func NewMockDatabaseOperator(ctrl *gomock.Controller) *MockDatabaseOperator {
mock := &MockDatabaseOperator{ctrl: ctrl}
mock.recorder = &MockDatabaseOperatorMockRecorder{mock}
return mock
}
// EXPECT returns an object that allows the caller to indicate expected use.
func (m *MockDatabaseOperator) EXPECT() *MockDatabaseOperatorMockRecorder {
return m.recorder
}
// Delete mocks base method.
func (m *MockDatabaseOperator) Delete(arg0 context.Context, arg1 *database.DeleteRequest) (*database.Response, error) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Delete", arg0, arg1)
ret0, _ := ret[0].(*database.Response)
ret1, _ := ret[1].(error)
return ret0, ret1
}
// Delete indicates an expected call of Delete.
func (mr *MockDatabaseOperatorMockRecorder) Delete(arg0, arg1 any) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Delete", reflect.TypeOf((*MockDatabaseOperator)(nil).Delete), arg0, arg1)
}
// Execute mocks base method.
func (m *MockDatabaseOperator) Execute(ctx context.Context, request *database.CustomSQLRequest) (*database.Response, error) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Execute", ctx, request)
ret0, _ := ret[0].(*database.Response)
ret1, _ := ret[1].(error)
return ret0, ret1
}
// Execute indicates an expected call of Execute.
func (mr *MockDatabaseOperatorMockRecorder) Execute(ctx, request any) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Execute", reflect.TypeOf((*MockDatabaseOperator)(nil).Execute), ctx, request)
}
// Insert mocks base method.
func (m *MockDatabaseOperator) Insert(ctx context.Context, request *database.InsertRequest) (*database.Response, error) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Insert", ctx, request)
ret0, _ := ret[0].(*database.Response)
ret1, _ := ret[1].(error)
return ret0, ret1
}
// Insert indicates an expected call of Insert.
func (mr *MockDatabaseOperatorMockRecorder) Insert(ctx, request any) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Insert", reflect.TypeOf((*MockDatabaseOperator)(nil).Insert), ctx, request)
}
// Query mocks base method.
func (m *MockDatabaseOperator) Query(ctx context.Context, request *database.QueryRequest) (*database.Response, error) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Query", ctx, request)
ret0, _ := ret[0].(*database.Response)
ret1, _ := ret[1].(error)
return ret0, ret1
}
// Query indicates an expected call of Query.
func (mr *MockDatabaseOperatorMockRecorder) Query(ctx, request any) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Query", reflect.TypeOf((*MockDatabaseOperator)(nil).Query), ctx, request)
}
// Update mocks base method.
func (m *MockDatabaseOperator) Update(arg0 context.Context, arg1 *database.UpdateRequest) (*database.Response, error) {
m.ctrl.T.Helper()
ret := m.ctrl.Call(m, "Update", arg0, arg1)
ret0, _ := ret[0].(*database.Response)
ret1, _ := ret[1].(error)
return ret0, ret1
}
// Update indicates an expected call of Update.
func (mr *MockDatabaseOperatorMockRecorder) Update(arg0, arg1 any) *gomock.Call {
mr.mock.ctrl.T.Helper()
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "Update", reflect.TypeOf((*MockDatabaseOperator)(nil).Update), arg0, arg1)
}

View File

@@ -32,13 +32,12 @@ import (
"github.com/stretchr/testify/assert"
"go.uber.org/mock/gomock"
"github.com/coze-dev/coze-studio/backend/infra/contract/coderunner"
crossmodel "github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/crossdomain/contract/database/databasemock"
"github.com/coze-dev/coze-studio/backend/crossdomain/impl/code"
userentity "github.com/coze-dev/coze-studio/backend/domain/user/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/code"
crossdatabase "github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database/databasemock"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/knowledge"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/knowledge/knowledgemock"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/model"
@@ -50,6 +49,7 @@ import (
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/compose"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/execute"
"github.com/coze-dev/coze-studio/backend/infra/contract/coderunner"
mockWorkflow "github.com/coze-dev/coze-studio/backend/internal/mock/domain/workflow"
mockcode "github.com/coze-dev/coze-studio/backend/internal/mock/domain/workflow/crossdomain/code"
"github.com/coze-dev/coze-studio/backend/internal/testutil"
@@ -105,10 +105,10 @@ func TestIntentDetectorAndDatabase(t *testing.T) {
}
mockModelManager.EXPECT().GetModel(gomock.Any(), gomock.Any()).Return(chatModel, nil, nil).AnyTimes()
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
n := int64(2)
resp := &crossdatabase.Response{
Objects: []crossdatabase.Object{
resp := &crossmodel.Response{
Objects: []crossmodel.Object{
{
"v2": "123",
},
@@ -119,7 +119,7 @@ func TestIntentDetectorAndDatabase(t *testing.T) {
RowNumber: &n,
}
mockDatabaseOperator.EXPECT().Execute(gomock.Any(), gomock.Any()).Return(resp, nil).AnyTimes()
mockey.Mock(crossdatabase.GetDatabaseOperator).Return(mockDatabaseOperator).Build()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
workflowSC, err := CanvasToWorkflowSchema(ctx, c)
assert.NoError(t, err)
@@ -144,44 +144,44 @@ func TestIntentDetectorAndDatabase(t *testing.T) {
})
}
func mockUpdate(t *testing.T) func(context.Context, *crossdatabase.UpdateRequest) (*crossdatabase.Response, error) {
return func(ctx context.Context, req *crossdatabase.UpdateRequest) (*crossdatabase.Response, error) {
assert.Equal(t, req.ConditionGroup.Conditions[0], &crossdatabase.Condition{
func mockUpdate(t *testing.T) func(context.Context, *crossmodel.UpdateRequest) (*crossmodel.Response, error) {
return func(ctx context.Context, req *crossmodel.UpdateRequest) (*crossmodel.Response, error) {
assert.Equal(t, req.ConditionGroup.Conditions[0], &crossmodel.ConditionStr{
Left: "v2",
Operator: "=",
Right: int64(1),
})
assert.Equal(t, req.ConditionGroup.Conditions[1], &crossdatabase.Condition{
assert.Equal(t, req.ConditionGroup.Conditions[1], &crossmodel.ConditionStr{
Left: "v1",
Operator: "=",
Right: "abc",
})
assert.Equal(t, req.ConditionGroup.Relation, crossdatabase.ClauseRelationAND)
assert.Equal(t, req.ConditionGroup.Relation, crossmodel.ClauseRelationAND)
assert.Equal(t, req.Fields, map[string]interface{}{
"1783392627713": int64(123),
})
return &crossdatabase.Response{}, nil
return &crossmodel.Response{}, nil
}
}
func mockInsert(t *testing.T) func(ctx context.Context, request *crossdatabase.InsertRequest) (*crossdatabase.Response, error) {
return func(ctx context.Context, req *crossdatabase.InsertRequest) (*crossdatabase.Response, error) {
func mockInsert(t *testing.T) func(ctx context.Context, request *crossmodel.InsertRequest) (*crossmodel.Response, error) {
return func(ctx context.Context, req *crossmodel.InsertRequest) (*crossmodel.Response, error) {
v := req.Fields["1785960530945"]
assert.Equal(t, v, int64(123))
vs := req.Fields["1783122026497"]
assert.Equal(t, vs, "input for database curd")
n := int64(10)
return &crossdatabase.Response{
return &crossmodel.Response{
RowNumber: &n,
}, nil
}
}
func mockQuery(t *testing.T) func(ctx context.Context, request *crossdatabase.QueryRequest) (*crossdatabase.Response, error) {
return func(ctx context.Context, req *crossdatabase.QueryRequest) (*crossdatabase.Response, error) {
assert.Equal(t, req.ConditionGroup.Conditions[0], &crossdatabase.Condition{
func mockQuery(t *testing.T) func(ctx context.Context, request *crossmodel.QueryRequest) (*crossmodel.Response, error) {
return func(ctx context.Context, req *crossmodel.QueryRequest) (*crossmodel.Response, error) {
assert.Equal(t, req.ConditionGroup.Conditions[0], &crossmodel.ConditionStr{
Left: "v1",
Operator: "=",
Right: "abc",
@@ -191,26 +191,26 @@ func mockQuery(t *testing.T) func(ctx context.Context, request *crossdatabase.Qu
"1783122026497", "1784288924673", "1783392627713",
})
n := int64(10)
return &crossdatabase.Response{
return &crossmodel.Response{
RowNumber: &n,
Objects: []crossdatabase.Object{
Objects: []crossmodel.Object{
{"v1": "vv"},
},
}, nil
}
}
func mockDelete(t *testing.T) func(context.Context, *crossdatabase.DeleteRequest) (*crossdatabase.Response, error) {
return func(ctx context.Context, req *crossdatabase.DeleteRequest) (*crossdatabase.Response, error) {
func mockDelete(t *testing.T) func(context.Context, *crossmodel.DeleteRequest) (*crossmodel.Response, error) {
return func(ctx context.Context, req *crossmodel.DeleteRequest) (*crossmodel.Response, error) {
nn := int64(10)
assert.Equal(t, req.ConditionGroup.Conditions[0], &crossdatabase.Condition{
assert.Equal(t, req.ConditionGroup.Conditions[0], &crossmodel.ConditionStr{
Left: "v2",
Operator: "=",
Right: nn,
})
n := int64(1)
return &crossdatabase.Response{
return &crossmodel.Response{
RowNumber: &n,
}, nil
}
@@ -228,8 +228,8 @@ func TestDatabaseCURD(t *testing.T) {
_ = ctx
ctrl := gomock.NewController(t)
defer ctrl.Finish()
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockey.Mock(crossdatabase.GetDatabaseOperator).Return(mockDatabaseOperator).Build()
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockey.Mock(crossdatabase.DefaultSVC).Return(mockDatabaseOperator).Build()
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery(t))
mockDatabaseOperator.EXPECT().Update(gomock.Any(), gomock.Any()).DoAndReturn(mockUpdate(t))
mockDatabaseOperator.EXPECT().Insert(gomock.Any(), gomock.Any()).DoAndReturn(mockInsert(t))

View File

@@ -25,7 +25,7 @@ import (
"golang.org/x/exp/maps"
code2 "github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/code"
code2 "github.com/coze-dev/coze-studio/backend/crossdomain/impl/code"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/schema"

View File

@@ -24,10 +24,9 @@ import (
"github.com/stretchr/testify/assert"
"go.uber.org/mock/gomock"
"github.com/coze-dev/coze-studio/backend/infra/contract/coderunner"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/nodes"
"github.com/coze-dev/coze-studio/backend/infra/contract/coderunner"
mockcode "github.com/coze-dev/coze-studio/backend/internal/mock/domain/workflow/crossdomain/code"
"github.com/coze-dev/coze-studio/backend/pkg/ctxcache"
)

View File

@@ -1,64 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package conversation
import (
"context"
"errors"
"github.com/cloudwego/eino/compose"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/conversation"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/nodes"
)
type ClearMessageConfig struct {
Clearer conversation.ConversationManager
}
type MessageClear struct {
config *ClearMessageConfig
}
func NewClearMessage(ctx context.Context, cfg *ClearMessageConfig) (*MessageClear, error) {
if cfg == nil {
return nil, errors.New("config is required")
}
if cfg.Clearer == nil {
return nil, errors.New("clearer is required")
}
return &MessageClear{
config: cfg,
}, nil
}
func (c *MessageClear) Clear(ctx context.Context, input map[string]any) (map[string]any, error) {
name, ok := nodes.TakeMapValue(input, compose.FieldPath{"ConversationName"})
if !ok {
return nil, errors.New("input map should contains 'ConversationName' key ")
}
response, err := c.config.Clearer.ClearMessage(ctx, &conversation.ClearMessageRequest{
Name: name.(string),
})
if err != nil {
return nil, err
}
return map[string]any{
"isSuccess": response.IsSuccess,
}, nil
}

View File

@@ -1,62 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package conversation
import (
"context"
"errors"
"github.com/cloudwego/eino/compose"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/conversation"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/nodes"
)
type CreateConversationConfig struct {
Creator conversation.ConversationManager
}
type CreateConversation struct {
config *CreateConversationConfig
}
func NewCreateConversation(ctx context.Context, cfg *CreateConversationConfig) (*CreateConversation, error) {
if cfg == nil {
return nil, errors.New("config is required")
}
if cfg.Creator == nil {
return nil, errors.New("creator is required")
}
return &CreateConversation{
config: cfg,
}, nil
}
func (c *CreateConversation) Create(ctx context.Context, input map[string]any) (map[string]any, error) {
name, ok := nodes.TakeMapValue(input, compose.FieldPath{"ConversationName"})
if !ok {
return nil, errors.New("input map should contains 'ConversationName' key ")
}
response, err := c.config.Creator.CreateConversation(ctx, &conversation.CreateConversationRequest{
Name: name.(string),
})
if err != nil {
return nil, err
}
return response.Result, nil
}

View File

@@ -1,108 +0,0 @@
/*
* Copyright 2025 coze-dev Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package conversation
import (
"context"
"encoding/json"
"errors"
"github.com/cloudwego/eino/compose"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/conversation"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/nodes"
)
type MessageListConfig struct {
Lister conversation.ConversationManager
}
type MessageList struct {
config *MessageListConfig
}
type Param struct {
ConversationName string
Limit *int
BeforeID *string
AfterID *string
}
func NewMessageList(ctx context.Context, cfg *MessageListConfig) (*MessageList, error) {
if cfg == nil {
return nil, errors.New("config is required")
}
if cfg.Lister == nil {
return nil, errors.New("lister is required")
}
return &MessageList{
config: cfg,
}, nil
}
func (m *MessageList) List(ctx context.Context, input map[string]any) (map[string]any, error) {
param := &Param{}
name, ok := nodes.TakeMapValue(input, compose.FieldPath{"ConversationName"})
if !ok {
return nil, errors.New("ConversationName is required")
}
param.ConversationName = name.(string)
limit, ok := nodes.TakeMapValue(input, compose.FieldPath{"Limit"})
if ok {
limit := limit.(int)
param.Limit = &limit
}
beforeID, ok := nodes.TakeMapValue(input, compose.FieldPath{"BeforeID"})
if ok {
beforeID := beforeID.(string)
param.BeforeID = &beforeID
}
afterID, ok := nodes.TakeMapValue(input, compose.FieldPath{"AfterID"})
if ok {
afterID := afterID.(string)
param.BeforeID = &afterID
}
r, err := m.config.Lister.MessageList(ctx, &conversation.ListMessageRequest{
ConversationName: param.ConversationName,
Limit: param.Limit,
BeforeID: param.BeforeID,
AfterID: param.AfterID,
})
if err != nil {
return nil, err
}
result := make(map[string]any)
objects := make([]any, 0, len(r.Messages))
for _, msg := range r.Messages {
object := make(map[string]any)
bs, _ := json.Marshal(msg)
err := json.Unmarshal(bs, &object)
if err != nil {
return nil, err
}
objects = append(objects, object)
}
result["messageList"] = objects
result["firstId"] = r.FirstID
result["hasMore"] = r.HasMore
return result, nil
}

View File

@@ -21,7 +21,7 @@ import (
einoCompose "github.com/cloudwego/eino/compose"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/schema"

View File

@@ -25,7 +25,7 @@ import (
"github.com/cloudwego/eino/compose"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/execute"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/nodes"
@@ -349,7 +349,7 @@ func convertClauseGroupToConditionGroup(_ context.Context, clauseGroup *database
)
conditionGroup := &database.ConditionGroup{
Conditions: make([]*database.Condition, 0),
Conditions: make([]*database.ConditionStr, 0),
Relation: database.ClauseRelationAND,
}
@@ -362,7 +362,7 @@ func convertClauseGroupToConditionGroup(_ context.Context, clauseGroup *database
}
}
conditionGroup.Conditions = append(conditionGroup.Conditions, &database.Condition{
conditionGroup.Conditions = append(conditionGroup.Conditions, &database.ConditionStr{
Left: clause.Left,
Operator: clause.Operator,
Right: rightValue,
@@ -373,7 +373,7 @@ func convertClauseGroupToConditionGroup(_ context.Context, clauseGroup *database
if clauseGroup.Multi != nil {
conditionGroup.Relation = clauseGroup.Multi.Relation
conditionGroup.Conditions = make([]*database.Condition, len(clauseGroup.Multi.Clauses))
conditionGroup.Conditions = make([]*database.ConditionStr, len(clauseGroup.Multi.Clauses))
multiSelect := clauseGroup.Multi
for idx, clause := range multiSelect.Clauses {
if !notNeedTakeMapValue(clause.Operator) {
@@ -382,7 +382,7 @@ func convertClauseGroupToConditionGroup(_ context.Context, clauseGroup *database
return nil, fmt.Errorf("cannot take multi clause from input")
}
}
conditionGroup.Conditions[idx] = &database.Condition{
conditionGroup.Conditions[idx] = &database.ConditionStr{
Left: clause.Left,
Operator: clause.Operator,
Right: rightValue,

View File

@@ -24,7 +24,8 @@ import (
"strconv"
"strings"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
@@ -85,18 +86,16 @@ func (c *CustomSQLConfig) Build(_ context.Context, ns *schema.NodeSchema, _ ...s
}
return &CustomSQL{
databaseInfoID: c.DatabaseInfoID,
sqlTemplate: c.SQLTemplate,
outputTypes: ns.OutputTypes,
customSQLExecutor: database.GetDatabaseOperator(),
databaseInfoID: c.DatabaseInfoID,
sqlTemplate: c.SQLTemplate,
outputTypes: ns.OutputTypes,
}, nil
}
type CustomSQL struct {
databaseInfoID int64
sqlTemplate string
outputTypes map[string]*vo.TypeInfo
customSQLExecutor database.DatabaseOperator
databaseInfoID int64
sqlTemplate string
outputTypes map[string]*vo.TypeInfo
}
func (c *CustomSQL) Invoke(ctx context.Context, input map[string]any) (map[string]any, error) {
@@ -155,7 +154,7 @@ func (c *CustomSQL) Invoke(ctx context.Context, input map[string]any) (map[strin
templateSQL = strings.Replace(templateSQL, "`?`", "?", -1)
req.SQL = templateSQL
req.Params = sqlParams
response, err := c.customSQLExecutor.Execute(ctx, req)
response, err := crossdatabase.DefaultSVC().Execute(ctx, req)
if err != nil {
return nil, err
}

View File

@@ -24,8 +24,9 @@ import (
"github.com/stretchr/testify/assert"
"go.uber.org/mock/gomock"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database/databasemock"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/crossdomain/contract/database/databasemock"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/execute"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/schema"
@@ -78,10 +79,9 @@ func TestCustomSQL_Execute(t *testing.T) {
},
}).Build().UnPatch()
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Execute(gomock.Any(), gomock.Any()).DoAndReturn(mockSQLer.Execute()).AnyTimes()
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
cfg := &CustomSQLConfig{
DatabaseInfoID: 111,

View File

@@ -22,7 +22,8 @@ import (
"fmt"
"strconv"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
@@ -87,7 +88,6 @@ func (d *DeleteConfig) Build(_ context.Context, ns *schema.NodeSchema, _ ...sche
databaseInfoID: d.DatabaseInfoID,
clauseGroup: d.ClauseGroup,
outputTypes: ns.OutputTypes,
deleter: database.GetDatabaseOperator(),
}, nil
}
@@ -95,7 +95,6 @@ type Delete struct {
databaseInfoID int64
clauseGroup *database.ClauseGroup
outputTypes map[string]*vo.TypeInfo
deleter database.DatabaseOperator
}
func (d *Delete) Invoke(ctx context.Context, in map[string]any) (map[string]any, error) {
@@ -111,7 +110,7 @@ func (d *Delete) Invoke(ctx context.Context, in map[string]any) (map[string]any,
ConnectorID: getConnectorID(ctx),
}
response, err := d.deleter.Delete(ctx, request)
response, err := crossdatabase.DefaultSVC().Delete(ctx, request)
if err != nil {
return nil, err
}

View File

@@ -22,7 +22,8 @@ import (
"fmt"
"strconv"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
@@ -73,14 +74,12 @@ func (i *InsertConfig) Build(_ context.Context, ns *schema.NodeSchema, _ ...sche
return &Insert{
databaseInfoID: i.DatabaseInfoID,
outputTypes: ns.OutputTypes,
inserter: database.GetDatabaseOperator(),
}, nil
}
type Insert struct {
databaseInfoID int64
outputTypes map[string]*vo.TypeInfo
inserter database.DatabaseOperator
}
func (is *Insert) Invoke(ctx context.Context, input map[string]any) (map[string]any, error) {
@@ -93,7 +92,7 @@ func (is *Insert) Invoke(ctx context.Context, input map[string]any) (map[string]
ConnectorID: getConnectorID(ctx),
}
response, err := is.inserter.Insert(ctx, req)
response, err := crossdatabase.DefaultSVC().Insert(ctx, req)
if err != nil {
return nil, err
}

View File

@@ -22,7 +22,8 @@ import (
"fmt"
"strconv"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
@@ -114,7 +115,6 @@ func (q *QueryConfig) Build(_ context.Context, ns *schema.NodeSchema, _ ...schem
outputTypes: ns.OutputTypes,
clauseGroup: q.ClauseGroup,
limit: q.Limit,
op: database.GetDatabaseOperator(),
}, nil
}
@@ -125,7 +125,6 @@ type Query struct {
outputTypes map[string]*vo.TypeInfo
clauseGroup *database.ClauseGroup
limit int64
op database.DatabaseOperator
}
func (ds *Query) Invoke(ctx context.Context, in map[string]any) (map[string]any, error) {
@@ -146,7 +145,7 @@ func (ds *Query) Invoke(ctx context.Context, in map[string]any) (map[string]any,
req.ConditionGroup = conditionGroup
response, err := ds.op.Query(ctx, req)
response, err := crossdatabase.DefaultSVC().Query(ctx, req)
if err != nil {
return nil, err
}

View File

@@ -26,8 +26,9 @@ import (
"github.com/stretchr/testify/assert"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database/databasemock"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/crossdomain/contract/database/databasemock"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/execute"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/schema"
@@ -95,10 +96,9 @@ func TestDataset_Query(t *testing.T) {
assert.Equal(t, cGroup.Conditions[0].Operator, cfg.ClauseGroup.Single.Operator)
}}
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery.Query())
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
ds, err := cfg.Build(context.Background(), &schema.NodeSchema{
OutputTypes: map[string]*vo.TypeInfo{
@@ -159,10 +159,9 @@ func TestDataset_Query(t *testing.T) {
assert.Equal(t, cGroup.Relation, cfg.ClauseGroup.Multi.Relation)
}}
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery.Query()).AnyTimes()
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
ds, err := cfg.Build(context.Background(), &schema.NodeSchema{
OutputTypes: map[string]*vo.TypeInfo{
@@ -219,10 +218,9 @@ func TestDataset_Query(t *testing.T) {
assert.Equal(t, cGroup.Conditions[0].Operator, cfg.ClauseGroup.Single.Operator)
}}
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery.Query()).AnyTimes()
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
ds, err := cfg.Build(context.Background(), &schema.NodeSchema{
OutputTypes: map[string]*vo.TypeInfo{
@@ -278,10 +276,9 @@ func TestDataset_Query(t *testing.T) {
assert.Equal(t, cGroup.Conditions[0].Left, cfg.ClauseGroup.Single.Left)
assert.Equal(t, cGroup.Conditions[0].Operator, cfg.ClauseGroup.Single.Operator)
}}
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery.Query()).AnyTimes()
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
ds, err := cfg.Build(context.Background(), &schema.NodeSchema{
OutputTypes: map[string]*vo.TypeInfo{
@@ -347,10 +344,9 @@ func TestDataset_Query(t *testing.T) {
assert.Equal(t, cGroup.Conditions[0].Operator, cfg.ClauseGroup.Single.Operator)
}}
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery.Query()).AnyTimes()
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
ds, err := cfg.Build(context.Background(), &schema.NodeSchema{
OutputTypes: map[string]*vo.TypeInfo{
@@ -425,10 +421,9 @@ func TestDataset_Query(t *testing.T) {
assert.Equal(t, cGroup.Conditions[0].Operator, cfg.ClauseGroup.Single.Operator)
}}
mockDatabaseOperator := databasemock.NewMockDatabaseOperator(ctrl)
mockDatabaseOperator := databasemock.NewMockDatabase(ctrl)
mockDatabaseOperator.EXPECT().Query(gomock.Any(), gomock.Any()).DoAndReturn(mockQuery.Query()).AnyTimes()
defer mockey.Mock(database.GetDatabaseOperator).Return(mockDatabaseOperator).Build().UnPatch()
crossdatabase.SetDefaultSVC(mockDatabaseOperator)
ds, err := cfg.Build(context.Background(), &schema.NodeSchema{
OutputTypes: map[string]*vo.TypeInfo{

View File

@@ -22,7 +22,8 @@ import (
"fmt"
"strconv"
"github.com/coze-dev/coze-studio/backend/domain/workflow/crossdomain/database"
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
crossdatabase "github.com/coze-dev/coze-studio/backend/crossdomain/contract/database"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity"
"github.com/coze-dev/coze-studio/backend/domain/workflow/entity/vo"
"github.com/coze-dev/coze-studio/backend/domain/workflow/internal/canvas/convert"
@@ -89,7 +90,6 @@ func (u *UpdateConfig) Build(_ context.Context, ns *schema.NodeSchema, _ ...sche
databaseInfoID: u.DatabaseInfoID,
clauseGroup: u.ClauseGroup,
outputTypes: ns.OutputTypes,
updater: database.GetDatabaseOperator(),
}, nil
}
@@ -97,7 +97,6 @@ type Update struct {
databaseInfoID int64
clauseGroup *database.ClauseGroup
outputTypes map[string]*vo.TypeInfo
updater database.DatabaseOperator
}
type updateInventory struct {
@@ -126,7 +125,7 @@ func (u *Update) Invoke(ctx context.Context, in map[string]any) (map[string]any,
ConnectorID: getConnectorID(ctx),
}
response, err := u.updater.Update(ctx, req)
response, err := crossdatabase.DefaultSVC().Update(ctx, req)
if err != nil {
return nil, err