feat: manually mirror opencoze's code from bytedance
Change-Id: I09a73aadda978ad9511264a756b2ce51f5761adf
This commit is contained in:
@@ -0,0 +1,76 @@
|
||||
/*
|
||||
* 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 convertor
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/table"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/rdb/entity"
|
||||
)
|
||||
|
||||
func ConvertResultSetToString(resultSet *entity.ResultSet, physicalToFieldName map[string]string, physicalToFieldType map[string]table.FieldItemType) []map[string]string {
|
||||
records := make([]map[string]string, 0, len(resultSet.Rows))
|
||||
|
||||
for _, row := range resultSet.Rows {
|
||||
record := make(map[string]string)
|
||||
|
||||
for physicalName, value := range row {
|
||||
if logicalName, exists := physicalToFieldName[physicalName]; exists {
|
||||
if value == nil {
|
||||
record[logicalName] = ""
|
||||
} else {
|
||||
fieldType, hasType := physicalToFieldType[physicalName]
|
||||
if hasType {
|
||||
convertedValue := ConvertDBValueToString(value, fieldType)
|
||||
record[logicalName] = convertedValue
|
||||
} else {
|
||||
record[logicalName] = fmt.Sprintf("%v", value)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if value == nil {
|
||||
record[physicalName] = ""
|
||||
} else {
|
||||
record[physicalName] = ConvertSystemFieldToString(physicalName, value)
|
||||
}
|
||||
}
|
||||
}
|
||||
records = append(records, record)
|
||||
}
|
||||
|
||||
return records
|
||||
}
|
||||
|
||||
func ConvertResultSet(resultSet *entity.ResultSet, physicalToFieldName map[string]string, physicalToFieldType map[string]table.FieldItemType) []map[string]any {
|
||||
records := make([]map[string]any, 0, len(resultSet.Rows))
|
||||
|
||||
for _, row := range resultSet.Rows {
|
||||
record := make(map[string]any)
|
||||
|
||||
for physicalName, value := range row {
|
||||
if logicalName, exists := physicalToFieldName[physicalName]; exists {
|
||||
record[logicalName] = value
|
||||
} else {
|
||||
record[physicalName] = value
|
||||
}
|
||||
}
|
||||
records = append(records, record)
|
||||
}
|
||||
|
||||
return records
|
||||
}
|
||||
218
backend/domain/memory/database/internal/convertor/types.go
Normal file
218
backend/domain/memory/database/internal/convertor/types.go
Normal file
@@ -0,0 +1,218 @@
|
||||
/*
|
||||
* 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 convertor
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strconv"
|
||||
"time"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/table"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/rdb/entity"
|
||||
)
|
||||
|
||||
const (
|
||||
TimeFormat = "2006-01-02 15:04:05"
|
||||
)
|
||||
|
||||
func SwitchToDataType(itemType table.FieldItemType) entity.DataType {
|
||||
switch itemType {
|
||||
case table.FieldItemType_Text:
|
||||
return entity.TypeVarchar
|
||||
case table.FieldItemType_Number:
|
||||
return entity.TypeBigInt
|
||||
case table.FieldItemType_Date:
|
||||
return entity.TypeTimestamp
|
||||
case table.FieldItemType_Float:
|
||||
return entity.TypeDouble
|
||||
case table.FieldItemType_Boolean:
|
||||
return entity.TypeBoolean
|
||||
default:
|
||||
// 默认使用 VARCHAR
|
||||
return entity.TypeVarchar
|
||||
}
|
||||
}
|
||||
|
||||
// ConvertValueByType converts a string value to the specified type.
|
||||
func ConvertValueByType(value string, fieldType table.FieldItemType) (interface{}, error) {
|
||||
if value == "" {
|
||||
return nil, nil
|
||||
}
|
||||
|
||||
switch fieldType {
|
||||
case table.FieldItemType_Number:
|
||||
intVal, err := strconv.ParseInt(value, 10, 64)
|
||||
if err != nil {
|
||||
return 0, fmt.Errorf("cannot convert %s to number", value)
|
||||
}
|
||||
|
||||
return intVal, nil
|
||||
|
||||
case table.FieldItemType_Float:
|
||||
if floatVal, err := strconv.ParseFloat(value, 64); err == nil {
|
||||
return floatVal, nil
|
||||
}
|
||||
|
||||
return 0.0, fmt.Errorf("cannot convert %s to float", value)
|
||||
|
||||
case table.FieldItemType_Boolean:
|
||||
if boolVal, err := strconv.ParseBool(value); err == nil {
|
||||
return boolVal, nil
|
||||
}
|
||||
|
||||
// if err, try 0/1
|
||||
if value == "0" {
|
||||
return false, nil
|
||||
}
|
||||
if value == "1" {
|
||||
return true, nil
|
||||
}
|
||||
|
||||
return false, fmt.Errorf("cannot convert %s to boolean", value)
|
||||
|
||||
case table.FieldItemType_Date:
|
||||
t, err := time.Parse(TimeFormat, value) // database use this format
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("cannot convert %s to date", value)
|
||||
}
|
||||
|
||||
return t, nil
|
||||
|
||||
case table.FieldItemType_Text:
|
||||
return value, nil
|
||||
|
||||
default:
|
||||
return value, nil
|
||||
}
|
||||
}
|
||||
|
||||
// ConvertDBValueToString converts a database value to a string.
|
||||
func ConvertDBValueToString(value interface{}, fieldType table.FieldItemType) string {
|
||||
switch fieldType {
|
||||
case table.FieldItemType_Text:
|
||||
if byteArray, ok := value.([]uint8); ok {
|
||||
return string(byteArray)
|
||||
}
|
||||
|
||||
case table.FieldItemType_Number:
|
||||
switch v := value.(type) {
|
||||
case int64:
|
||||
return strconv.FormatInt(v, 10)
|
||||
case []uint8:
|
||||
return string(v)
|
||||
}
|
||||
|
||||
case table.FieldItemType_Float:
|
||||
switch v := value.(type) {
|
||||
case float64:
|
||||
return strconv.FormatFloat(v, 'f', -1, 64)
|
||||
case []uint8:
|
||||
return string(v)
|
||||
}
|
||||
|
||||
case table.FieldItemType_Boolean:
|
||||
switch v := value.(type) {
|
||||
case bool:
|
||||
return strconv.FormatBool(v)
|
||||
case int64:
|
||||
return strconv.FormatBool(v != 0)
|
||||
case []uint8:
|
||||
boolStr := string(v)
|
||||
if boolStr == "1" || boolStr == "true" {
|
||||
return "true"
|
||||
}
|
||||
return "false"
|
||||
}
|
||||
|
||||
case table.FieldItemType_Date:
|
||||
switch v := value.(type) {
|
||||
case time.Time:
|
||||
return v.Format(TimeFormat)
|
||||
case []uint8:
|
||||
return string(v)
|
||||
}
|
||||
}
|
||||
|
||||
return fmt.Sprintf("%v", value)
|
||||
}
|
||||
|
||||
// ConvertSystemFieldToString converts a system field value to a string.
|
||||
func ConvertSystemFieldToString(fieldName string, value interface{}) string {
|
||||
switch fieldName {
|
||||
case database.DefaultIDColName:
|
||||
if intVal, ok := value.(int64); ok {
|
||||
return strconv.FormatInt(intVal, 10)
|
||||
}
|
||||
case database.DefaultUidColName, database.DefaultCidColName:
|
||||
if byteArray, ok := value.([]uint8); ok {
|
||||
return string(byteArray)
|
||||
}
|
||||
case database.DefaultCreateTimeColName:
|
||||
switch v := value.(type) {
|
||||
case time.Time:
|
||||
return v.Format(TimeFormat)
|
||||
case []uint8:
|
||||
// 尝试解析字符串表示的时间
|
||||
return string(v)
|
||||
}
|
||||
}
|
||||
|
||||
return fmt.Sprintf("%v", value)
|
||||
}
|
||||
|
||||
func ConvertLogicOperator(logic database.Logic) entity.LogicalOperator {
|
||||
switch logic {
|
||||
case database.Logic_And:
|
||||
return entity.AND
|
||||
case database.Logic_Or:
|
||||
return entity.OR
|
||||
default:
|
||||
return entity.AND // 默认使用AND
|
||||
}
|
||||
}
|
||||
|
||||
func ConvertOperator(op database.Operation) entity.Operator {
|
||||
switch op {
|
||||
case database.Operation_EQUAL:
|
||||
return entity.OperatorEqual
|
||||
case database.Operation_NOT_EQUAL:
|
||||
return entity.OperatorNotEqual
|
||||
case database.Operation_GREATER_THAN:
|
||||
return entity.OperatorGreater
|
||||
case database.Operation_GREATER_EQUAL:
|
||||
return entity.OperatorGreaterEqual
|
||||
case database.Operation_LESS_THAN:
|
||||
return entity.OperatorLess
|
||||
case database.Operation_LESS_EQUAL:
|
||||
return entity.OperatorLessEqual
|
||||
case database.Operation_IN:
|
||||
return entity.OperatorIn
|
||||
case database.Operation_NOT_IN:
|
||||
return entity.OperatorNotIn
|
||||
case database.Operation_LIKE:
|
||||
return entity.OperatorLike
|
||||
case database.Operation_NOT_LIKE:
|
||||
return entity.OperatorNotLike
|
||||
case database.Operation_IS_NULL:
|
||||
return entity.OperatorIsNull
|
||||
case database.Operation_IS_NOT_NULL:
|
||||
return entity.OperatorIsNotNull
|
||||
default:
|
||||
return entity.OperatorEqual
|
||||
}
|
||||
}
|
||||
138
backend/domain/memory/database/internal/dal/agent_to_database.go
Normal file
138
backend/domain/memory/database/internal/dal/agent_to_database.go
Normal file
@@ -0,0 +1,138 @@
|
||||
/*
|
||||
* 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 dal
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"sync"
|
||||
|
||||
"gorm.io/gorm"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/table"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/model"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/query"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/idgen"
|
||||
)
|
||||
|
||||
var (
|
||||
agentToDatabaseOnce sync.Once
|
||||
singletonAgentToDb *AgentToDatabaseImpl
|
||||
)
|
||||
|
||||
type AgentToDatabaseImpl struct {
|
||||
IDGen idgen.IDGenerator
|
||||
query *query.Query
|
||||
}
|
||||
|
||||
func NewAgentToDatabaseDAO(db *gorm.DB, idGen idgen.IDGenerator) *AgentToDatabaseImpl {
|
||||
agentToDatabaseOnce.Do(func() {
|
||||
singletonAgentToDb = &AgentToDatabaseImpl{
|
||||
IDGen: idGen,
|
||||
query: query.Use(db),
|
||||
}
|
||||
})
|
||||
|
||||
return singletonAgentToDb
|
||||
}
|
||||
|
||||
func (d *AgentToDatabaseImpl) BatchCreate(ctx context.Context, relations []*database.AgentToDatabase) ([]int64, error) {
|
||||
if len(relations) == 0 {
|
||||
return []int64{}, nil
|
||||
}
|
||||
|
||||
ids, err := d.IDGen.GenMultiIDs(ctx, len(relations))
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("generate IDs failed: %v", err)
|
||||
}
|
||||
|
||||
agentToDbs := make([]*model.AgentToDatabase, len(relations))
|
||||
for i, relation := range relations {
|
||||
agentToDbs[i] = &model.AgentToDatabase{
|
||||
ID: ids[i],
|
||||
AgentID: relation.AgentID,
|
||||
DatabaseID: relation.DatabaseID,
|
||||
IsDraft: relation.TableType == table.TableType_DraftTable,
|
||||
PromptDisable: relation.PromptDisabled,
|
||||
}
|
||||
}
|
||||
|
||||
res := d.query.AgentToDatabase
|
||||
err = res.WithContext(ctx).CreateInBatches(agentToDbs, 10)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("batch create agent to database relations failed: %v", err)
|
||||
}
|
||||
|
||||
return ids, nil
|
||||
}
|
||||
|
||||
func (d *AgentToDatabaseImpl) BatchDelete(ctx context.Context, basicRelations []*database.AgentToDatabaseBasic) error {
|
||||
if len(basicRelations) == 0 {
|
||||
return nil
|
||||
}
|
||||
|
||||
res := d.query.AgentToDatabase
|
||||
|
||||
for _, relation := range basicRelations {
|
||||
q := res.WithContext(ctx).
|
||||
Where(res.AgentID.Eq(relation.AgentID)).
|
||||
Where(res.DatabaseID.Eq(relation.DatabaseID))
|
||||
|
||||
_, err := q.Delete()
|
||||
if err != nil {
|
||||
return fmt.Errorf("delete relation failed for agent=%d, database=%d: %v",
|
||||
relation.AgentID, relation.DatabaseID, err)
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (d *AgentToDatabaseImpl) ListByAgentID(ctx context.Context, agentID int64, tableType table.TableType) ([]*database.AgentToDatabase, error) {
|
||||
res := d.query.AgentToDatabase
|
||||
|
||||
q := res.WithContext(ctx).Where(res.AgentID.Eq(agentID))
|
||||
|
||||
if tableType == table.TableType_DraftTable {
|
||||
q = q.Where(res.IsDraft.Is(true))
|
||||
} else {
|
||||
q = q.Where(res.IsDraft.Is(false))
|
||||
}
|
||||
|
||||
records, err := q.Find()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("list agent to database relations failed: %v", err)
|
||||
}
|
||||
|
||||
relations := make([]*database.AgentToDatabase, 0, len(records))
|
||||
for _, info := range records {
|
||||
tType := table.TableType_OnlineTable
|
||||
if info.IsDraft {
|
||||
tType = table.TableType_DraftTable
|
||||
}
|
||||
relation := &database.AgentToDatabase{
|
||||
AgentID: info.AgentID,
|
||||
DatabaseID: info.DatabaseID,
|
||||
TableType: tType,
|
||||
PromptDisabled: info.PromptDisable,
|
||||
}
|
||||
relations = append(relations, relation)
|
||||
}
|
||||
|
||||
return relations, nil
|
||||
}
|
||||
@@ -0,0 +1,340 @@
|
||||
/*
|
||||
* 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 dal
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"gorm.io/gorm"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/table"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/entity"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/model"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/query"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/idgen"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/errorx"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/lang/ptr"
|
||||
"github.com/coze-dev/coze-studio/backend/types/errno"
|
||||
)
|
||||
|
||||
var (
|
||||
draftOnce sync.Once
|
||||
singletonDraft *DraftImpl
|
||||
)
|
||||
|
||||
type DraftImpl struct {
|
||||
IDGen idgen.IDGenerator
|
||||
query *query.Query
|
||||
}
|
||||
|
||||
func NewDraftDatabaseDAO(db *gorm.DB, idGen idgen.IDGenerator) *DraftImpl {
|
||||
draftOnce.Do(func() {
|
||||
singletonDraft = &DraftImpl{
|
||||
IDGen: idGen,
|
||||
query: query.Use(db),
|
||||
}
|
||||
})
|
||||
|
||||
return singletonDraft
|
||||
}
|
||||
|
||||
func (d *DraftImpl) CreateWithTX(ctx context.Context, tx *query.QueryTx, database *entity.Database, draftID, onlineID int64, physicalTableName string) (*entity.Database, error) {
|
||||
now := time.Now().UnixMilli()
|
||||
|
||||
draftInfo := &model.DraftDatabaseInfo{
|
||||
ID: draftID,
|
||||
AppID: database.AppID,
|
||||
SpaceID: database.SpaceID,
|
||||
RelatedOnlineID: onlineID,
|
||||
IsVisible: 1, // 默认可见
|
||||
PromptDisabled: func() int32 {
|
||||
if database.PromptDisabled {
|
||||
return 1
|
||||
} else {
|
||||
return 0
|
||||
}
|
||||
}(),
|
||||
TableName_: database.TableName,
|
||||
TableDesc: database.TableDesc,
|
||||
TableField: database.FieldList,
|
||||
CreatorID: database.CreatorID,
|
||||
IconURI: database.IconURI,
|
||||
PhysicalTableName: physicalTableName,
|
||||
RwMode: int64(database.RwMode),
|
||||
CreatedAt: now,
|
||||
UpdatedAt: now,
|
||||
}
|
||||
|
||||
table := tx.DraftDatabaseInfo
|
||||
|
||||
err := table.WithContext(ctx).Create(draftInfo)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
database.CreatedAtMs = now
|
||||
database.UpdatedAtMs = now
|
||||
|
||||
return database, nil
|
||||
}
|
||||
|
||||
// Get 获取草稿数据库信息
|
||||
func (d *DraftImpl) Get(ctx context.Context, id int64) (*entity.Database, error) {
|
||||
res := d.query.DraftDatabaseInfo
|
||||
|
||||
info, err := res.WithContext(ctx).Where(res.ID.Eq(id)).First()
|
||||
if err != nil {
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return nil, errorx.New(errno.ErrMemoryDatabaseNotFoundCode)
|
||||
}
|
||||
return nil, fmt.Errorf("query draft database failed: %v", err)
|
||||
}
|
||||
|
||||
// 构建返回的数据库对象
|
||||
db := &entity.Database{
|
||||
ID: info.ID,
|
||||
SpaceID: info.SpaceID,
|
||||
CreatorID: info.CreatorID,
|
||||
IconURI: info.IconURI,
|
||||
|
||||
AppID: info.AppID,
|
||||
IsVisible: info.IsVisible == 1,
|
||||
PromptDisabled: info.PromptDisabled == 1,
|
||||
TableName: info.TableName_,
|
||||
TableDesc: info.TableDesc,
|
||||
FieldList: info.TableField,
|
||||
Status: table.BotTableStatus_Online,
|
||||
ActualTableName: info.PhysicalTableName,
|
||||
RwMode: table.BotTableRWMode(info.RwMode),
|
||||
OnlineID: &info.RelatedOnlineID,
|
||||
DraftID: &info.ID,
|
||||
}
|
||||
|
||||
return db, nil
|
||||
}
|
||||
|
||||
func (d *DraftImpl) MGet(ctx context.Context, ids []int64) ([]*entity.Database, error) {
|
||||
if len(ids) == 0 {
|
||||
return []*entity.Database{}, nil
|
||||
}
|
||||
|
||||
res := d.query.DraftDatabaseInfo
|
||||
|
||||
records, err := res.WithContext(ctx).
|
||||
Where(res.ID.In(ids...)).
|
||||
Find()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("batch query draft database failed: %v", err)
|
||||
}
|
||||
|
||||
databases := make([]*entity.Database, 0, len(records))
|
||||
for _, info := range records {
|
||||
|
||||
db := &entity.Database{
|
||||
ID: info.ID,
|
||||
SpaceID: info.SpaceID,
|
||||
CreatorID: info.CreatorID,
|
||||
IconURI: info.IconURI,
|
||||
|
||||
AppID: info.AppID,
|
||||
IsVisible: info.IsVisible == 1,
|
||||
PromptDisabled: info.PromptDisabled == 1,
|
||||
TableName: info.TableName_,
|
||||
TableDesc: info.TableDesc,
|
||||
FieldList: info.TableField,
|
||||
Status: table.BotTableStatus_Online,
|
||||
ActualTableName: info.PhysicalTableName,
|
||||
RwMode: table.BotTableRWMode(info.RwMode),
|
||||
OnlineID: &info.RelatedOnlineID,
|
||||
DraftID: &info.ID,
|
||||
|
||||
CreatedAtMs: info.CreatedAt,
|
||||
UpdatedAtMs: info.UpdatedAt,
|
||||
}
|
||||
|
||||
databases = append(databases, db)
|
||||
}
|
||||
|
||||
return databases, nil
|
||||
}
|
||||
|
||||
// UpdateWithTX 使用事务更新草稿数据库信息
|
||||
func (d *DraftImpl) UpdateWithTX(ctx context.Context, tx *query.QueryTx, database *entity.Database) (*entity.Database, error) {
|
||||
fieldJson, err := json.Marshal(database.FieldList)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("marshal field list failed: %v", err)
|
||||
}
|
||||
|
||||
fieldJsonStr := string(fieldJson)
|
||||
now := time.Now().UnixMilli()
|
||||
|
||||
updates := map[string]interface{}{
|
||||
"app_id": database.AppID,
|
||||
"table_name": database.TableName,
|
||||
"table_desc": database.TableDesc,
|
||||
"table_field": fieldJsonStr,
|
||||
"icon_uri": database.IconURI,
|
||||
"prompt_disabled": func() int32 {
|
||||
if database.PromptDisabled {
|
||||
return 1
|
||||
}
|
||||
return 0
|
||||
}(),
|
||||
"rw_mode": int64(database.RwMode),
|
||||
"updated_at": now,
|
||||
}
|
||||
|
||||
// 执行更新
|
||||
res := tx.DraftDatabaseInfo
|
||||
_, err = res.WithContext(ctx).Where(res.ID.Eq(database.ID)).Updates(updates)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("update draft database failed: %v", err)
|
||||
}
|
||||
|
||||
database.UpdatedAtMs = now
|
||||
return database, nil
|
||||
}
|
||||
|
||||
func (d *DraftImpl) DeleteWithTX(ctx context.Context, tx *query.QueryTx, id int64) error {
|
||||
res := tx.DraftDatabaseInfo
|
||||
_, err := res.WithContext(ctx).Where(res.ID.Eq(id)).Delete(&model.DraftDatabaseInfo{})
|
||||
if err != nil {
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return errorx.New(errno.ErrMemoryDatabaseNotFoundCode)
|
||||
}
|
||||
return fmt.Errorf("delete draft database failed: %v", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// List 列出符合条件的数据库信息
|
||||
func (d *DraftImpl) List(ctx context.Context, filter *entity.DatabaseFilter, page *entity.Pagination, orderBy []*database.OrderBy) ([]*entity.Database, int64, error) {
|
||||
res := d.query.DraftDatabaseInfo
|
||||
|
||||
q := res.WithContext(ctx)
|
||||
|
||||
// 添加过滤条件
|
||||
if filter != nil {
|
||||
if filter.CreatorID != nil {
|
||||
q = q.Where(res.CreatorID.Eq(*filter.CreatorID))
|
||||
}
|
||||
|
||||
if filter.SpaceID != nil {
|
||||
q = q.Where(res.SpaceID.Eq(*filter.SpaceID))
|
||||
}
|
||||
|
||||
if filter.AppID != nil {
|
||||
q = q.Where(res.AppID.Eq(*filter.AppID))
|
||||
}
|
||||
|
||||
if filter.TableName != nil {
|
||||
q = q.Where(res.TableName_.Like("%" + *filter.TableName + "%"))
|
||||
}
|
||||
|
||||
q = q.Where(res.IsVisible.Eq(1))
|
||||
}
|
||||
|
||||
count, err := q.Count()
|
||||
if err != nil {
|
||||
return nil, 0, fmt.Errorf("count online database failed: %v", err)
|
||||
}
|
||||
|
||||
limit := int64(50)
|
||||
if page != nil && page.Limit > 0 {
|
||||
limit = int64(page.Limit)
|
||||
}
|
||||
|
||||
offset := 0
|
||||
if page != nil && page.Offset > 0 {
|
||||
offset = page.Offset
|
||||
}
|
||||
|
||||
if len(orderBy) > 0 {
|
||||
for _, order := range orderBy {
|
||||
switch order.Field {
|
||||
case "created_at":
|
||||
if order.Direction == table.SortDirection_Desc {
|
||||
q = q.Order(res.CreatedAt.Desc())
|
||||
} else {
|
||||
q = q.Order(res.CreatedAt)
|
||||
}
|
||||
case "updated_at":
|
||||
if order.Direction == table.SortDirection_Desc {
|
||||
q = q.Order(res.UpdatedAt.Desc())
|
||||
} else {
|
||||
q = q.Order(res.UpdatedAt)
|
||||
}
|
||||
default:
|
||||
q = q.Order(res.CreatedAt.Desc())
|
||||
}
|
||||
}
|
||||
} else {
|
||||
q = q.Order(res.CreatedAt.Desc())
|
||||
}
|
||||
|
||||
records, err := q.Limit(int(limit)).Offset(offset).Find()
|
||||
if err != nil {
|
||||
return nil, 0, fmt.Errorf("list online database failed: %v", err)
|
||||
}
|
||||
|
||||
databases := make([]*entity.Database, 0, len(records))
|
||||
for _, info := range records {
|
||||
db := &entity.Database{
|
||||
ID: info.ID,
|
||||
SpaceID: info.SpaceID,
|
||||
CreatorID: info.CreatorID,
|
||||
IconURI: info.IconURI,
|
||||
|
||||
AppID: info.AppID,
|
||||
IsVisible: info.IsVisible == 1,
|
||||
PromptDisabled: info.PromptDisabled == 1,
|
||||
TableName: info.TableName_,
|
||||
TableDesc: info.TableDesc,
|
||||
FieldList: info.TableField,
|
||||
Status: table.BotTableStatus_Online,
|
||||
ActualTableName: info.PhysicalTableName,
|
||||
RwMode: table.BotTableRWMode(info.RwMode),
|
||||
TableType: ptr.Of(table.TableType_DraftTable),
|
||||
OnlineID: &info.RelatedOnlineID,
|
||||
DraftID: &info.ID,
|
||||
}
|
||||
|
||||
databases = append(databases, db)
|
||||
}
|
||||
|
||||
return databases, count, nil
|
||||
}
|
||||
|
||||
func (d *DraftImpl) BatchDeleteWithTX(ctx context.Context, tx *query.QueryTx, ids []int64) error {
|
||||
if len(ids) == 0 {
|
||||
return nil
|
||||
}
|
||||
|
||||
res := tx.DraftDatabaseInfo
|
||||
_, err := res.WithContext(ctx).Where(res.ID.In(ids...)).Delete()
|
||||
if err != nil {
|
||||
return fmt.Errorf("batch delete draft database failed: %v", err)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package model
|
||||
|
||||
const TableNameAgentToDatabase = "agent_to_database"
|
||||
|
||||
// AgentToDatabase agent_to_database info
|
||||
type AgentToDatabase struct {
|
||||
ID int64 `gorm:"column:id;primaryKey;comment:ID" json:"id"` // ID
|
||||
AgentID int64 `gorm:"column:agent_id;not null;comment:Agent ID" json:"agent_id"` // Agent ID
|
||||
DatabaseID int64 `gorm:"column:database_id;not null;comment:ID of database_info" json:"database_id"` // ID of database_info
|
||||
IsDraft bool `gorm:"column:is_draft;not null;comment:Is draft" json:"is_draft"` // Is draft
|
||||
PromptDisable bool `gorm:"column:prompt_disable;not null;comment:Support prompt calls: 1 not supported, 0 supported" json:"prompt_disable"` // Support prompt calls: 1 not supported, 0 supported
|
||||
}
|
||||
|
||||
// TableName AgentToDatabase's table name
|
||||
func (*AgentToDatabase) TableName() string {
|
||||
return TableNameAgentToDatabase
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package model
|
||||
|
||||
import (
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
const TableNameDraftDatabaseInfo = "draft_database_info"
|
||||
|
||||
// DraftDatabaseInfo draft database info
|
||||
type DraftDatabaseInfo struct {
|
||||
ID int64 `gorm:"column:id;primaryKey;comment:ID" json:"id"` // ID
|
||||
AppID int64 `gorm:"column:app_id;comment:App ID" json:"app_id"` // App ID
|
||||
SpaceID int64 `gorm:"column:space_id;not null;comment:Space ID" json:"space_id"` // Space ID
|
||||
RelatedOnlineID int64 `gorm:"column:related_online_id;not null;comment:The primary key ID of online_database_info table" json:"related_online_id"` // The primary key ID of online_database_info table
|
||||
IsVisible int32 `gorm:"column:is_visible;not null;default:1;comment:Visibility: 0 invisible, 1 visible" json:"is_visible"` // Visibility: 0 invisible, 1 visible
|
||||
PromptDisabled int32 `gorm:"column:prompt_disabled;not null;comment:Support prompt calls: 1 not supported, 0 supported" json:"prompt_disabled"` // Support prompt calls: 1 not supported, 0 supported
|
||||
TableName_ string `gorm:"column:table_name;not null;comment:Table name" json:"table_name"` // Table name
|
||||
TableDesc string `gorm:"column:table_desc;comment:Table description" json:"table_desc"` // Table description
|
||||
TableField []*database.FieldItem `gorm:"column:table_field;comment:Table field info;serializer:json" json:"table_field"` // Table field info
|
||||
CreatorID int64 `gorm:"column:creator_id;not null;comment:Creator ID" json:"creator_id"` // Creator ID
|
||||
IconURI string `gorm:"column:icon_uri;not null;comment:Icon Uri" json:"icon_uri"` // Icon Uri
|
||||
PhysicalTableName string `gorm:"column:physical_table_name;comment:The name of the real physical table" json:"physical_table_name"` // The name of the real physical table
|
||||
RwMode int64 `gorm:"column:rw_mode;not null;default:1;comment:Read and write permission modes: 1. Limited read and write mode 2. Read-only mode 3. Full read and write mode" json:"rw_mode"` // Read and write permission modes: 1. Limited read and write mode 2. Read-only mode 3. Full read and write mode
|
||||
CreatedAt int64 `gorm:"column:created_at;not null;autoCreateTime:milli;comment:Create Time in Milliseconds" json:"created_at"` // Create Time in Milliseconds
|
||||
UpdatedAt int64 `gorm:"column:updated_at;not null;autoUpdateTime:milli;comment:Update Time in Milliseconds" json:"updated_at"` // Update Time in Milliseconds
|
||||
DeletedAt gorm.DeletedAt `gorm:"column:deleted_at;comment:Delete Time" json:"deleted_at"` // Delete Time
|
||||
}
|
||||
|
||||
// TableName DraftDatabaseInfo's table name
|
||||
func (*DraftDatabaseInfo) TableName() string {
|
||||
return TableNameDraftDatabaseInfo
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package model
|
||||
|
||||
import (
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
const TableNameOnlineDatabaseInfo = "online_database_info"
|
||||
|
||||
// OnlineDatabaseInfo online database info
|
||||
type OnlineDatabaseInfo struct {
|
||||
ID int64 `gorm:"column:id;primaryKey;comment:ID" json:"id"` // ID
|
||||
AppID int64 `gorm:"column:app_id;comment:App ID" json:"app_id"` // App ID
|
||||
SpaceID int64 `gorm:"column:space_id;not null;comment:Space ID" json:"space_id"` // Space ID
|
||||
RelatedDraftID int64 `gorm:"column:related_draft_id;not null;comment:The primary key ID of draft_database_info table" json:"related_draft_id"` // The primary key ID of draft_database_info table
|
||||
IsVisible int32 `gorm:"column:is_visible;not null;default:1;comment:Visibility: 0 invisible, 1 visible" json:"is_visible"` // Visibility: 0 invisible, 1 visible
|
||||
PromptDisabled int32 `gorm:"column:prompt_disabled;not null;comment:Support prompt calls: 1 not supported, 0 supported" json:"prompt_disabled"` // Support prompt calls: 1 not supported, 0 supported
|
||||
TableName_ string `gorm:"column:table_name;not null;comment:Table name" json:"table_name"` // Table name
|
||||
TableDesc string `gorm:"column:table_desc;comment:Table description" json:"table_desc"` // Table description
|
||||
TableField []*database.FieldItem `gorm:"column:table_field;comment:Table field info;serializer:json" json:"table_field"` // Table field info
|
||||
CreatorID int64 `gorm:"column:creator_id;not null;comment:Creator ID" json:"creator_id"` // Creator ID
|
||||
IconURI string `gorm:"column:icon_uri;not null;comment:Icon Uri" json:"icon_uri"` // Icon Uri
|
||||
PhysicalTableName string `gorm:"column:physical_table_name;comment:The name of the real physical table" json:"physical_table_name"` // The name of the real physical table
|
||||
RwMode int64 `gorm:"column:rw_mode;not null;default:1;comment:Read and write permission modes: 1. Limited read and write mode 2. Read-only mode 3. Full read and write mode" json:"rw_mode"` // Read and write permission modes: 1. Limited read and write mode 2. Read-only mode 3. Full read and write mode
|
||||
CreatedAt int64 `gorm:"column:created_at;not null;autoCreateTime:milli;comment:Create Time in Milliseconds" json:"created_at"` // Create Time in Milliseconds
|
||||
UpdatedAt int64 `gorm:"column:updated_at;not null;autoUpdateTime:milli;comment:Update Time in Milliseconds" json:"updated_at"` // Update Time in Milliseconds
|
||||
DeletedAt gorm.DeletedAt `gorm:"column:deleted_at;comment:Delete Time" json:"deleted_at"` // Delete Time
|
||||
}
|
||||
|
||||
// TableName OnlineDatabaseInfo's table name
|
||||
func (*OnlineDatabaseInfo) TableName() string {
|
||||
return TableNameOnlineDatabaseInfo
|
||||
}
|
||||
@@ -0,0 +1,345 @@
|
||||
/*
|
||||
* 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 dal
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"gorm.io/gorm"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/table"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/entity"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/model"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/query"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/idgen"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/errorx"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/lang/ptr"
|
||||
"github.com/coze-dev/coze-studio/backend/types/errno"
|
||||
)
|
||||
|
||||
var (
|
||||
onlineOnce sync.Once
|
||||
singletonOnline *OlineImpl
|
||||
)
|
||||
|
||||
type OlineImpl struct {
|
||||
IDGen idgen.IDGenerator
|
||||
query *query.Query
|
||||
}
|
||||
|
||||
func NewOnlineDatabaseDAO(db *gorm.DB, idGen idgen.IDGenerator) *OlineImpl {
|
||||
onlineOnce.Do(func() {
|
||||
singletonOnline = &OlineImpl{
|
||||
IDGen: idGen,
|
||||
query: query.Use(db),
|
||||
}
|
||||
})
|
||||
|
||||
return singletonOnline
|
||||
}
|
||||
|
||||
func (o *OlineImpl) CreateWithTX(ctx context.Context, tx *query.QueryTx, database *entity.Database, draftID, onlineID int64, physicalTableName string) (*entity.Database, error) {
|
||||
now := time.Now().UnixMilli()
|
||||
onlineInfo := &model.OnlineDatabaseInfo{
|
||||
ID: onlineID,
|
||||
AppID: database.AppID,
|
||||
SpaceID: database.SpaceID,
|
||||
RelatedDraftID: draftID,
|
||||
IsVisible: 1, // 默认可见
|
||||
PromptDisabled: func() int32 {
|
||||
if database.PromptDisabled {
|
||||
return 1
|
||||
} else {
|
||||
return 0
|
||||
}
|
||||
}(),
|
||||
TableName_: database.TableName,
|
||||
TableDesc: database.TableDesc,
|
||||
TableField: database.FieldList,
|
||||
CreatorID: database.CreatorID,
|
||||
IconURI: database.IconURI,
|
||||
PhysicalTableName: physicalTableName,
|
||||
RwMode: int64(database.RwMode),
|
||||
CreatedAt: now,
|
||||
UpdatedAt: now,
|
||||
}
|
||||
|
||||
table := tx.OnlineDatabaseInfo
|
||||
|
||||
err := table.WithContext(ctx).Create(onlineInfo)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
database.CreatedAtMs = now
|
||||
database.UpdatedAtMs = now
|
||||
|
||||
return database, nil
|
||||
}
|
||||
|
||||
// Get 获取线上数据库信息
|
||||
func (o *OlineImpl) Get(ctx context.Context, id int64) (*entity.Database, error) {
|
||||
res := o.query.OnlineDatabaseInfo
|
||||
|
||||
info, err := res.WithContext(ctx).Where(res.ID.Eq(id)).First()
|
||||
if err != nil {
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return nil, errorx.New(errno.ErrMemoryDatabaseNotFoundCode)
|
||||
}
|
||||
return nil, fmt.Errorf("query online database failed: %v", err)
|
||||
}
|
||||
|
||||
db := &entity.Database{
|
||||
ID: info.ID,
|
||||
SpaceID: info.SpaceID,
|
||||
CreatorID: info.CreatorID,
|
||||
IconURI: info.IconURI,
|
||||
|
||||
AppID: info.AppID,
|
||||
DraftID: &info.RelatedDraftID,
|
||||
OnlineID: &info.ID,
|
||||
IsVisible: info.IsVisible == 1,
|
||||
PromptDisabled: info.PromptDisabled == 1,
|
||||
TableName: info.TableName_,
|
||||
TableDesc: info.TableDesc,
|
||||
FieldList: info.TableField,
|
||||
Status: table.BotTableStatus_Online,
|
||||
ActualTableName: info.PhysicalTableName,
|
||||
RwMode: table.BotTableRWMode(info.RwMode),
|
||||
}
|
||||
|
||||
return db, nil
|
||||
}
|
||||
|
||||
// UpdateWithTX 使用事务更新线上数据库信息
|
||||
func (o *OlineImpl) UpdateWithTX(ctx context.Context, tx *query.QueryTx, database *entity.Database) (*entity.Database, error) {
|
||||
fieldJson, err := json.Marshal(database.FieldList)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("marshal field list failed: %v", err)
|
||||
}
|
||||
|
||||
fieldJsonStr := string(fieldJson)
|
||||
now := time.Now().UnixMilli()
|
||||
|
||||
// 构建更新内容
|
||||
updates := map[string]interface{}{
|
||||
"app_id": database.AppID,
|
||||
"table_name": database.TableName,
|
||||
"table_desc": database.TableDesc,
|
||||
"table_field": fieldJsonStr,
|
||||
"icon_uri": database.IconURI,
|
||||
"prompt_disabled": func() int32 {
|
||||
if database.PromptDisabled {
|
||||
return 1
|
||||
}
|
||||
return 0
|
||||
}(),
|
||||
"rw_mode": int64(database.RwMode),
|
||||
"updated_at": now,
|
||||
}
|
||||
|
||||
// 执行更新
|
||||
res := tx.OnlineDatabaseInfo
|
||||
_, err = res.WithContext(ctx).Where(res.ID.Eq(database.ID)).Updates(updates)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("update online database failed: %v", err)
|
||||
}
|
||||
|
||||
_, err = res.WithContext(ctx).Where(res.ID.In(database.ID)).Updates(updates)
|
||||
|
||||
database.UpdatedAtMs = now
|
||||
return database, nil
|
||||
}
|
||||
|
||||
func (o *OlineImpl) DeleteWithTX(ctx context.Context, tx *query.QueryTx, id int64) error {
|
||||
res := tx.OnlineDatabaseInfo
|
||||
_, err := res.WithContext(ctx).Where(res.ID.Eq(id)).Delete(&model.OnlineDatabaseInfo{})
|
||||
if err != nil {
|
||||
if errors.Is(err, gorm.ErrRecordNotFound) {
|
||||
return errorx.New(errno.ErrMemoryDatabaseNotFoundCode)
|
||||
}
|
||||
return fmt.Errorf("delete online database failed: %v", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// MGet 批量获取在线数据库信息
|
||||
func (o *OlineImpl) MGet(ctx context.Context, ids []int64) ([]*entity.Database, error) {
|
||||
if len(ids) == 0 {
|
||||
return []*entity.Database{}, nil
|
||||
}
|
||||
|
||||
res := o.query.OnlineDatabaseInfo
|
||||
|
||||
// 查询未删除的、ID在给定列表中的记录
|
||||
records, err := res.WithContext(ctx).
|
||||
Where(res.ID.In(ids...)).
|
||||
Find()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("batch query online database failed: %v", err)
|
||||
}
|
||||
|
||||
// 构建返回结果
|
||||
databases := make([]*entity.Database, 0, len(records))
|
||||
for _, info := range records {
|
||||
db := &entity.Database{
|
||||
ID: info.ID,
|
||||
SpaceID: info.SpaceID,
|
||||
CreatorID: info.CreatorID,
|
||||
IconURI: info.IconURI,
|
||||
|
||||
AppID: info.AppID,
|
||||
DraftID: &info.RelatedDraftID,
|
||||
OnlineID: &info.ID,
|
||||
IsVisible: info.IsVisible == 1,
|
||||
PromptDisabled: info.PromptDisabled == 1,
|
||||
TableName: info.TableName_,
|
||||
TableDesc: info.TableDesc,
|
||||
FieldList: info.TableField,
|
||||
Status: table.BotTableStatus_Online,
|
||||
ActualTableName: info.PhysicalTableName,
|
||||
RwMode: table.BotTableRWMode(info.RwMode),
|
||||
|
||||
CreatedAtMs: info.CreatedAt,
|
||||
UpdatedAtMs: info.UpdatedAt,
|
||||
}
|
||||
|
||||
databases = append(databases, db)
|
||||
}
|
||||
|
||||
return databases, nil
|
||||
}
|
||||
|
||||
// List 列出符合条件的数据库信息
|
||||
func (o *OlineImpl) List(ctx context.Context, filter *entity.DatabaseFilter, page *entity.Pagination, orderBy []*database.OrderBy) ([]*entity.Database, int64, error) {
|
||||
res := o.query.OnlineDatabaseInfo
|
||||
|
||||
// 构建基础查询
|
||||
q := res.WithContext(ctx)
|
||||
|
||||
// 添加过滤条件
|
||||
if filter != nil {
|
||||
if filter.CreatorID != nil {
|
||||
q = q.Where(res.CreatorID.Eq(*filter.CreatorID))
|
||||
}
|
||||
|
||||
if filter.SpaceID != nil {
|
||||
q = q.Where(res.SpaceID.Eq(*filter.SpaceID))
|
||||
}
|
||||
|
||||
if filter.AppID != nil {
|
||||
q = q.Where(res.AppID.Eq(*filter.AppID))
|
||||
}
|
||||
|
||||
if filter.TableName != nil {
|
||||
q = q.Where(res.TableName_.Like("%" + *filter.TableName + "%"))
|
||||
}
|
||||
|
||||
q = q.Where(res.IsVisible.Eq(1))
|
||||
}
|
||||
|
||||
count, err := q.Count()
|
||||
if err != nil {
|
||||
return nil, 0, fmt.Errorf("count online database failed: %v", err)
|
||||
}
|
||||
|
||||
limit := int64(50) // default
|
||||
if page != nil && page.Limit > 0 {
|
||||
limit = int64(page.Limit)
|
||||
}
|
||||
|
||||
offset := 0
|
||||
if page != nil && page.Offset > 0 {
|
||||
offset = page.Offset
|
||||
}
|
||||
|
||||
// 处理排序
|
||||
if len(orderBy) > 0 {
|
||||
for _, order := range orderBy {
|
||||
switch order.Field {
|
||||
case "created_at":
|
||||
if order.Direction == table.SortDirection_Desc {
|
||||
q = q.Order(res.CreatedAt.Desc())
|
||||
} else {
|
||||
q = q.Order(res.CreatedAt)
|
||||
}
|
||||
case "updated_at":
|
||||
if order.Direction == table.SortDirection_Desc {
|
||||
q = q.Order(res.UpdatedAt.Desc())
|
||||
} else {
|
||||
q = q.Order(res.UpdatedAt)
|
||||
}
|
||||
default:
|
||||
q = q.Order(res.CreatedAt.Desc())
|
||||
}
|
||||
}
|
||||
} else {
|
||||
q = q.Order(res.CreatedAt.Desc())
|
||||
}
|
||||
|
||||
records, err := q.Limit(int(limit)).Offset(offset).Find()
|
||||
if err != nil {
|
||||
return nil, 0, fmt.Errorf("list online database failed: %v", err)
|
||||
}
|
||||
|
||||
databases := make([]*entity.Database, 0, len(records))
|
||||
for _, info := range records {
|
||||
d := &entity.Database{
|
||||
ID: info.ID,
|
||||
SpaceID: info.SpaceID,
|
||||
CreatorID: info.CreatorID,
|
||||
IconURI: info.IconURI,
|
||||
|
||||
AppID: info.AppID,
|
||||
DraftID: &info.RelatedDraftID,
|
||||
OnlineID: &info.ID,
|
||||
IsVisible: info.IsVisible == 1,
|
||||
PromptDisabled: info.PromptDisabled == 1,
|
||||
TableName: info.TableName_,
|
||||
TableDesc: info.TableDesc,
|
||||
FieldList: info.TableField,
|
||||
Status: table.BotTableStatus_Online,
|
||||
ActualTableName: info.PhysicalTableName,
|
||||
RwMode: table.BotTableRWMode(info.RwMode),
|
||||
TableType: ptr.Of(table.TableType_OnlineTable),
|
||||
}
|
||||
|
||||
databases = append(databases, d)
|
||||
}
|
||||
|
||||
return databases, count, nil
|
||||
}
|
||||
|
||||
func (o *OlineImpl) BatchDeleteWithTX(ctx context.Context, tx *query.QueryTx, ids []int64) error {
|
||||
if len(ids) == 0 {
|
||||
return nil
|
||||
}
|
||||
|
||||
res := tx.OnlineDatabaseInfo
|
||||
_, err := res.WithContext(ctx).Where(res.ID.In(ids...)).Delete()
|
||||
if err != nil {
|
||||
return fmt.Errorf("batch delete online database failed: %v", err)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
@@ -0,0 +1,397 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package query
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"gorm.io/gorm"
|
||||
"gorm.io/gorm/clause"
|
||||
"gorm.io/gorm/schema"
|
||||
|
||||
"gorm.io/gen"
|
||||
"gorm.io/gen/field"
|
||||
|
||||
"gorm.io/plugin/dbresolver"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/model"
|
||||
)
|
||||
|
||||
func newAgentToDatabase(db *gorm.DB, opts ...gen.DOOption) agentToDatabase {
|
||||
_agentToDatabase := agentToDatabase{}
|
||||
|
||||
_agentToDatabase.agentToDatabaseDo.UseDB(db, opts...)
|
||||
_agentToDatabase.agentToDatabaseDo.UseModel(&model.AgentToDatabase{})
|
||||
|
||||
tableName := _agentToDatabase.agentToDatabaseDo.TableName()
|
||||
_agentToDatabase.ALL = field.NewAsterisk(tableName)
|
||||
_agentToDatabase.ID = field.NewInt64(tableName, "id")
|
||||
_agentToDatabase.AgentID = field.NewInt64(tableName, "agent_id")
|
||||
_agentToDatabase.DatabaseID = field.NewInt64(tableName, "database_id")
|
||||
_agentToDatabase.IsDraft = field.NewBool(tableName, "is_draft")
|
||||
_agentToDatabase.PromptDisable = field.NewBool(tableName, "prompt_disable")
|
||||
|
||||
_agentToDatabase.fillFieldMap()
|
||||
|
||||
return _agentToDatabase
|
||||
}
|
||||
|
||||
// agentToDatabase agent_to_database info
|
||||
type agentToDatabase struct {
|
||||
agentToDatabaseDo
|
||||
|
||||
ALL field.Asterisk
|
||||
ID field.Int64 // ID
|
||||
AgentID field.Int64 // Agent ID
|
||||
DatabaseID field.Int64 // ID of database_info
|
||||
IsDraft field.Bool // Is draft
|
||||
PromptDisable field.Bool // Support prompt calls: 1 not supported, 0 supported
|
||||
|
||||
fieldMap map[string]field.Expr
|
||||
}
|
||||
|
||||
func (a agentToDatabase) Table(newTableName string) *agentToDatabase {
|
||||
a.agentToDatabaseDo.UseTable(newTableName)
|
||||
return a.updateTableName(newTableName)
|
||||
}
|
||||
|
||||
func (a agentToDatabase) As(alias string) *agentToDatabase {
|
||||
a.agentToDatabaseDo.DO = *(a.agentToDatabaseDo.As(alias).(*gen.DO))
|
||||
return a.updateTableName(alias)
|
||||
}
|
||||
|
||||
func (a *agentToDatabase) updateTableName(table string) *agentToDatabase {
|
||||
a.ALL = field.NewAsterisk(table)
|
||||
a.ID = field.NewInt64(table, "id")
|
||||
a.AgentID = field.NewInt64(table, "agent_id")
|
||||
a.DatabaseID = field.NewInt64(table, "database_id")
|
||||
a.IsDraft = field.NewBool(table, "is_draft")
|
||||
a.PromptDisable = field.NewBool(table, "prompt_disable")
|
||||
|
||||
a.fillFieldMap()
|
||||
|
||||
return a
|
||||
}
|
||||
|
||||
func (a *agentToDatabase) GetFieldByName(fieldName string) (field.OrderExpr, bool) {
|
||||
_f, ok := a.fieldMap[fieldName]
|
||||
if !ok || _f == nil {
|
||||
return nil, false
|
||||
}
|
||||
_oe, ok := _f.(field.OrderExpr)
|
||||
return _oe, ok
|
||||
}
|
||||
|
||||
func (a *agentToDatabase) fillFieldMap() {
|
||||
a.fieldMap = make(map[string]field.Expr, 5)
|
||||
a.fieldMap["id"] = a.ID
|
||||
a.fieldMap["agent_id"] = a.AgentID
|
||||
a.fieldMap["database_id"] = a.DatabaseID
|
||||
a.fieldMap["is_draft"] = a.IsDraft
|
||||
a.fieldMap["prompt_disable"] = a.PromptDisable
|
||||
}
|
||||
|
||||
func (a agentToDatabase) clone(db *gorm.DB) agentToDatabase {
|
||||
a.agentToDatabaseDo.ReplaceConnPool(db.Statement.ConnPool)
|
||||
return a
|
||||
}
|
||||
|
||||
func (a agentToDatabase) replaceDB(db *gorm.DB) agentToDatabase {
|
||||
a.agentToDatabaseDo.ReplaceDB(db)
|
||||
return a
|
||||
}
|
||||
|
||||
type agentToDatabaseDo struct{ gen.DO }
|
||||
|
||||
type IAgentToDatabaseDo interface {
|
||||
gen.SubQuery
|
||||
Debug() IAgentToDatabaseDo
|
||||
WithContext(ctx context.Context) IAgentToDatabaseDo
|
||||
WithResult(fc func(tx gen.Dao)) gen.ResultInfo
|
||||
ReplaceDB(db *gorm.DB)
|
||||
ReadDB() IAgentToDatabaseDo
|
||||
WriteDB() IAgentToDatabaseDo
|
||||
As(alias string) gen.Dao
|
||||
Session(config *gorm.Session) IAgentToDatabaseDo
|
||||
Columns(cols ...field.Expr) gen.Columns
|
||||
Clauses(conds ...clause.Expression) IAgentToDatabaseDo
|
||||
Not(conds ...gen.Condition) IAgentToDatabaseDo
|
||||
Or(conds ...gen.Condition) IAgentToDatabaseDo
|
||||
Select(conds ...field.Expr) IAgentToDatabaseDo
|
||||
Where(conds ...gen.Condition) IAgentToDatabaseDo
|
||||
Order(conds ...field.Expr) IAgentToDatabaseDo
|
||||
Distinct(cols ...field.Expr) IAgentToDatabaseDo
|
||||
Omit(cols ...field.Expr) IAgentToDatabaseDo
|
||||
Join(table schema.Tabler, on ...field.Expr) IAgentToDatabaseDo
|
||||
LeftJoin(table schema.Tabler, on ...field.Expr) IAgentToDatabaseDo
|
||||
RightJoin(table schema.Tabler, on ...field.Expr) IAgentToDatabaseDo
|
||||
Group(cols ...field.Expr) IAgentToDatabaseDo
|
||||
Having(conds ...gen.Condition) IAgentToDatabaseDo
|
||||
Limit(limit int) IAgentToDatabaseDo
|
||||
Offset(offset int) IAgentToDatabaseDo
|
||||
Count() (count int64, err error)
|
||||
Scopes(funcs ...func(gen.Dao) gen.Dao) IAgentToDatabaseDo
|
||||
Unscoped() IAgentToDatabaseDo
|
||||
Create(values ...*model.AgentToDatabase) error
|
||||
CreateInBatches(values []*model.AgentToDatabase, batchSize int) error
|
||||
Save(values ...*model.AgentToDatabase) error
|
||||
First() (*model.AgentToDatabase, error)
|
||||
Take() (*model.AgentToDatabase, error)
|
||||
Last() (*model.AgentToDatabase, error)
|
||||
Find() ([]*model.AgentToDatabase, error)
|
||||
FindInBatch(batchSize int, fc func(tx gen.Dao, batch int) error) (results []*model.AgentToDatabase, err error)
|
||||
FindInBatches(result *[]*model.AgentToDatabase, batchSize int, fc func(tx gen.Dao, batch int) error) error
|
||||
Pluck(column field.Expr, dest interface{}) error
|
||||
Delete(...*model.AgentToDatabase) (info gen.ResultInfo, err error)
|
||||
Update(column field.Expr, value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateSimple(columns ...field.AssignExpr) (info gen.ResultInfo, err error)
|
||||
Updates(value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateColumn(column field.Expr, value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateColumnSimple(columns ...field.AssignExpr) (info gen.ResultInfo, err error)
|
||||
UpdateColumns(value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateFrom(q gen.SubQuery) gen.Dao
|
||||
Attrs(attrs ...field.AssignExpr) IAgentToDatabaseDo
|
||||
Assign(attrs ...field.AssignExpr) IAgentToDatabaseDo
|
||||
Joins(fields ...field.RelationField) IAgentToDatabaseDo
|
||||
Preload(fields ...field.RelationField) IAgentToDatabaseDo
|
||||
FirstOrInit() (*model.AgentToDatabase, error)
|
||||
FirstOrCreate() (*model.AgentToDatabase, error)
|
||||
FindByPage(offset int, limit int) (result []*model.AgentToDatabase, count int64, err error)
|
||||
ScanByPage(result interface{}, offset int, limit int) (count int64, err error)
|
||||
Scan(result interface{}) (err error)
|
||||
Returning(value interface{}, columns ...string) IAgentToDatabaseDo
|
||||
UnderlyingDB() *gorm.DB
|
||||
schema.Tabler
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Debug() IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Debug())
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) WithContext(ctx context.Context) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.WithContext(ctx))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) ReadDB() IAgentToDatabaseDo {
|
||||
return a.Clauses(dbresolver.Read)
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) WriteDB() IAgentToDatabaseDo {
|
||||
return a.Clauses(dbresolver.Write)
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Session(config *gorm.Session) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Session(config))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Clauses(conds ...clause.Expression) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Clauses(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Returning(value interface{}, columns ...string) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Returning(value, columns...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Not(conds ...gen.Condition) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Not(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Or(conds ...gen.Condition) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Or(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Select(conds ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Select(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Where(conds ...gen.Condition) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Where(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Order(conds ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Order(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Distinct(cols ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Distinct(cols...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Omit(cols ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Omit(cols...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Join(table schema.Tabler, on ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Join(table, on...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) LeftJoin(table schema.Tabler, on ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.LeftJoin(table, on...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) RightJoin(table schema.Tabler, on ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.RightJoin(table, on...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Group(cols ...field.Expr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Group(cols...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Having(conds ...gen.Condition) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Having(conds...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Limit(limit int) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Limit(limit))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Offset(offset int) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Offset(offset))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Scopes(funcs ...func(gen.Dao) gen.Dao) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Scopes(funcs...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Unscoped() IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Unscoped())
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Create(values ...*model.AgentToDatabase) error {
|
||||
if len(values) == 0 {
|
||||
return nil
|
||||
}
|
||||
return a.DO.Create(values)
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) CreateInBatches(values []*model.AgentToDatabase, batchSize int) error {
|
||||
return a.DO.CreateInBatches(values, batchSize)
|
||||
}
|
||||
|
||||
// Save : !!! underlying implementation is different with GORM
|
||||
// The method is equivalent to executing the statement: db.Clauses(clause.OnConflict{UpdateAll: true}).Create(values)
|
||||
func (a agentToDatabaseDo) Save(values ...*model.AgentToDatabase) error {
|
||||
if len(values) == 0 {
|
||||
return nil
|
||||
}
|
||||
return a.DO.Save(values)
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) First() (*model.AgentToDatabase, error) {
|
||||
if result, err := a.DO.First(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.AgentToDatabase), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Take() (*model.AgentToDatabase, error) {
|
||||
if result, err := a.DO.Take(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.AgentToDatabase), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Last() (*model.AgentToDatabase, error) {
|
||||
if result, err := a.DO.Last(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.AgentToDatabase), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Find() ([]*model.AgentToDatabase, error) {
|
||||
result, err := a.DO.Find()
|
||||
return result.([]*model.AgentToDatabase), err
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) FindInBatch(batchSize int, fc func(tx gen.Dao, batch int) error) (results []*model.AgentToDatabase, err error) {
|
||||
buf := make([]*model.AgentToDatabase, 0, batchSize)
|
||||
err = a.DO.FindInBatches(&buf, batchSize, func(tx gen.Dao, batch int) error {
|
||||
defer func() { results = append(results, buf...) }()
|
||||
return fc(tx, batch)
|
||||
})
|
||||
return results, err
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) FindInBatches(result *[]*model.AgentToDatabase, batchSize int, fc func(tx gen.Dao, batch int) error) error {
|
||||
return a.DO.FindInBatches(result, batchSize, fc)
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Attrs(attrs ...field.AssignExpr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Attrs(attrs...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Assign(attrs ...field.AssignExpr) IAgentToDatabaseDo {
|
||||
return a.withDO(a.DO.Assign(attrs...))
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Joins(fields ...field.RelationField) IAgentToDatabaseDo {
|
||||
for _, _f := range fields {
|
||||
a = *a.withDO(a.DO.Joins(_f))
|
||||
}
|
||||
return &a
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Preload(fields ...field.RelationField) IAgentToDatabaseDo {
|
||||
for _, _f := range fields {
|
||||
a = *a.withDO(a.DO.Preload(_f))
|
||||
}
|
||||
return &a
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) FirstOrInit() (*model.AgentToDatabase, error) {
|
||||
if result, err := a.DO.FirstOrInit(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.AgentToDatabase), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) FirstOrCreate() (*model.AgentToDatabase, error) {
|
||||
if result, err := a.DO.FirstOrCreate(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.AgentToDatabase), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) FindByPage(offset int, limit int) (result []*model.AgentToDatabase, count int64, err error) {
|
||||
result, err = a.Offset(offset).Limit(limit).Find()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if size := len(result); 0 < limit && 0 < size && size < limit {
|
||||
count = int64(size + offset)
|
||||
return
|
||||
}
|
||||
|
||||
count, err = a.Offset(-1).Limit(-1).Count()
|
||||
return
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) ScanByPage(result interface{}, offset int, limit int) (count int64, err error) {
|
||||
count, err = a.Count()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
err = a.Offset(offset).Limit(limit).Scan(result)
|
||||
return
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Scan(result interface{}) (err error) {
|
||||
return a.DO.Scan(result)
|
||||
}
|
||||
|
||||
func (a agentToDatabaseDo) Delete(models ...*model.AgentToDatabase) (result gen.ResultInfo, err error) {
|
||||
return a.DO.Delete(models)
|
||||
}
|
||||
|
||||
func (a *agentToDatabaseDo) withDO(do gen.Dao) *agentToDatabaseDo {
|
||||
a.DO = *do.(*gen.DO)
|
||||
return a
|
||||
}
|
||||
@@ -0,0 +1,441 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package query
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"gorm.io/gorm"
|
||||
"gorm.io/gorm/clause"
|
||||
"gorm.io/gorm/schema"
|
||||
|
||||
"gorm.io/gen"
|
||||
"gorm.io/gen/field"
|
||||
|
||||
"gorm.io/plugin/dbresolver"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/model"
|
||||
)
|
||||
|
||||
func newDraftDatabaseInfo(db *gorm.DB, opts ...gen.DOOption) draftDatabaseInfo {
|
||||
_draftDatabaseInfo := draftDatabaseInfo{}
|
||||
|
||||
_draftDatabaseInfo.draftDatabaseInfoDo.UseDB(db, opts...)
|
||||
_draftDatabaseInfo.draftDatabaseInfoDo.UseModel(&model.DraftDatabaseInfo{})
|
||||
|
||||
tableName := _draftDatabaseInfo.draftDatabaseInfoDo.TableName()
|
||||
_draftDatabaseInfo.ALL = field.NewAsterisk(tableName)
|
||||
_draftDatabaseInfo.ID = field.NewInt64(tableName, "id")
|
||||
_draftDatabaseInfo.AppID = field.NewInt64(tableName, "app_id")
|
||||
_draftDatabaseInfo.SpaceID = field.NewInt64(tableName, "space_id")
|
||||
_draftDatabaseInfo.RelatedOnlineID = field.NewInt64(tableName, "related_online_id")
|
||||
_draftDatabaseInfo.IsVisible = field.NewInt32(tableName, "is_visible")
|
||||
_draftDatabaseInfo.PromptDisabled = field.NewInt32(tableName, "prompt_disabled")
|
||||
_draftDatabaseInfo.TableName_ = field.NewString(tableName, "table_name")
|
||||
_draftDatabaseInfo.TableDesc = field.NewString(tableName, "table_desc")
|
||||
_draftDatabaseInfo.TableField = field.NewField(tableName, "table_field")
|
||||
_draftDatabaseInfo.CreatorID = field.NewInt64(tableName, "creator_id")
|
||||
_draftDatabaseInfo.IconURI = field.NewString(tableName, "icon_uri")
|
||||
_draftDatabaseInfo.PhysicalTableName = field.NewString(tableName, "physical_table_name")
|
||||
_draftDatabaseInfo.RwMode = field.NewInt64(tableName, "rw_mode")
|
||||
_draftDatabaseInfo.CreatedAt = field.NewInt64(tableName, "created_at")
|
||||
_draftDatabaseInfo.UpdatedAt = field.NewInt64(tableName, "updated_at")
|
||||
_draftDatabaseInfo.DeletedAt = field.NewField(tableName, "deleted_at")
|
||||
|
||||
_draftDatabaseInfo.fillFieldMap()
|
||||
|
||||
return _draftDatabaseInfo
|
||||
}
|
||||
|
||||
// draftDatabaseInfo draft database info
|
||||
type draftDatabaseInfo struct {
|
||||
draftDatabaseInfoDo
|
||||
|
||||
ALL field.Asterisk
|
||||
ID field.Int64 // ID
|
||||
AppID field.Int64 // App ID
|
||||
SpaceID field.Int64 // Space ID
|
||||
RelatedOnlineID field.Int64 // The primary key ID of online_database_info table
|
||||
IsVisible field.Int32 // Visibility: 0 invisible, 1 visible
|
||||
PromptDisabled field.Int32 // Support prompt calls: 1 not supported, 0 supported
|
||||
TableName_ field.String // Table name
|
||||
TableDesc field.String // Table description
|
||||
TableField field.Field // Table field info
|
||||
CreatorID field.Int64 // Creator ID
|
||||
IconURI field.String // Icon Uri
|
||||
PhysicalTableName field.String // The name of the real physical table
|
||||
RwMode field.Int64 // Read and write permission modes: 1. Limited read and write mode 2. Read-only mode 3. Full read and write mode
|
||||
CreatedAt field.Int64 // Create Time in Milliseconds
|
||||
UpdatedAt field.Int64 // Update Time in Milliseconds
|
||||
DeletedAt field.Field // Delete Time
|
||||
|
||||
fieldMap map[string]field.Expr
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfo) Table(newTableName string) *draftDatabaseInfo {
|
||||
d.draftDatabaseInfoDo.UseTable(newTableName)
|
||||
return d.updateTableName(newTableName)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfo) As(alias string) *draftDatabaseInfo {
|
||||
d.draftDatabaseInfoDo.DO = *(d.draftDatabaseInfoDo.As(alias).(*gen.DO))
|
||||
return d.updateTableName(alias)
|
||||
}
|
||||
|
||||
func (d *draftDatabaseInfo) updateTableName(table string) *draftDatabaseInfo {
|
||||
d.ALL = field.NewAsterisk(table)
|
||||
d.ID = field.NewInt64(table, "id")
|
||||
d.AppID = field.NewInt64(table, "app_id")
|
||||
d.SpaceID = field.NewInt64(table, "space_id")
|
||||
d.RelatedOnlineID = field.NewInt64(table, "related_online_id")
|
||||
d.IsVisible = field.NewInt32(table, "is_visible")
|
||||
d.PromptDisabled = field.NewInt32(table, "prompt_disabled")
|
||||
d.TableName_ = field.NewString(table, "table_name")
|
||||
d.TableDesc = field.NewString(table, "table_desc")
|
||||
d.TableField = field.NewField(table, "table_field")
|
||||
d.CreatorID = field.NewInt64(table, "creator_id")
|
||||
d.IconURI = field.NewString(table, "icon_uri")
|
||||
d.PhysicalTableName = field.NewString(table, "physical_table_name")
|
||||
d.RwMode = field.NewInt64(table, "rw_mode")
|
||||
d.CreatedAt = field.NewInt64(table, "created_at")
|
||||
d.UpdatedAt = field.NewInt64(table, "updated_at")
|
||||
d.DeletedAt = field.NewField(table, "deleted_at")
|
||||
|
||||
d.fillFieldMap()
|
||||
|
||||
return d
|
||||
}
|
||||
|
||||
func (d *draftDatabaseInfo) GetFieldByName(fieldName string) (field.OrderExpr, bool) {
|
||||
_f, ok := d.fieldMap[fieldName]
|
||||
if !ok || _f == nil {
|
||||
return nil, false
|
||||
}
|
||||
_oe, ok := _f.(field.OrderExpr)
|
||||
return _oe, ok
|
||||
}
|
||||
|
||||
func (d *draftDatabaseInfo) fillFieldMap() {
|
||||
d.fieldMap = make(map[string]field.Expr, 16)
|
||||
d.fieldMap["id"] = d.ID
|
||||
d.fieldMap["app_id"] = d.AppID
|
||||
d.fieldMap["space_id"] = d.SpaceID
|
||||
d.fieldMap["related_online_id"] = d.RelatedOnlineID
|
||||
d.fieldMap["is_visible"] = d.IsVisible
|
||||
d.fieldMap["prompt_disabled"] = d.PromptDisabled
|
||||
d.fieldMap["table_name"] = d.TableName_
|
||||
d.fieldMap["table_desc"] = d.TableDesc
|
||||
d.fieldMap["table_field"] = d.TableField
|
||||
d.fieldMap["creator_id"] = d.CreatorID
|
||||
d.fieldMap["icon_uri"] = d.IconURI
|
||||
d.fieldMap["physical_table_name"] = d.PhysicalTableName
|
||||
d.fieldMap["rw_mode"] = d.RwMode
|
||||
d.fieldMap["created_at"] = d.CreatedAt
|
||||
d.fieldMap["updated_at"] = d.UpdatedAt
|
||||
d.fieldMap["deleted_at"] = d.DeletedAt
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfo) clone(db *gorm.DB) draftDatabaseInfo {
|
||||
d.draftDatabaseInfoDo.ReplaceConnPool(db.Statement.ConnPool)
|
||||
return d
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfo) replaceDB(db *gorm.DB) draftDatabaseInfo {
|
||||
d.draftDatabaseInfoDo.ReplaceDB(db)
|
||||
return d
|
||||
}
|
||||
|
||||
type draftDatabaseInfoDo struct{ gen.DO }
|
||||
|
||||
type IDraftDatabaseInfoDo interface {
|
||||
gen.SubQuery
|
||||
Debug() IDraftDatabaseInfoDo
|
||||
WithContext(ctx context.Context) IDraftDatabaseInfoDo
|
||||
WithResult(fc func(tx gen.Dao)) gen.ResultInfo
|
||||
ReplaceDB(db *gorm.DB)
|
||||
ReadDB() IDraftDatabaseInfoDo
|
||||
WriteDB() IDraftDatabaseInfoDo
|
||||
As(alias string) gen.Dao
|
||||
Session(config *gorm.Session) IDraftDatabaseInfoDo
|
||||
Columns(cols ...field.Expr) gen.Columns
|
||||
Clauses(conds ...clause.Expression) IDraftDatabaseInfoDo
|
||||
Not(conds ...gen.Condition) IDraftDatabaseInfoDo
|
||||
Or(conds ...gen.Condition) IDraftDatabaseInfoDo
|
||||
Select(conds ...field.Expr) IDraftDatabaseInfoDo
|
||||
Where(conds ...gen.Condition) IDraftDatabaseInfoDo
|
||||
Order(conds ...field.Expr) IDraftDatabaseInfoDo
|
||||
Distinct(cols ...field.Expr) IDraftDatabaseInfoDo
|
||||
Omit(cols ...field.Expr) IDraftDatabaseInfoDo
|
||||
Join(table schema.Tabler, on ...field.Expr) IDraftDatabaseInfoDo
|
||||
LeftJoin(table schema.Tabler, on ...field.Expr) IDraftDatabaseInfoDo
|
||||
RightJoin(table schema.Tabler, on ...field.Expr) IDraftDatabaseInfoDo
|
||||
Group(cols ...field.Expr) IDraftDatabaseInfoDo
|
||||
Having(conds ...gen.Condition) IDraftDatabaseInfoDo
|
||||
Limit(limit int) IDraftDatabaseInfoDo
|
||||
Offset(offset int) IDraftDatabaseInfoDo
|
||||
Count() (count int64, err error)
|
||||
Scopes(funcs ...func(gen.Dao) gen.Dao) IDraftDatabaseInfoDo
|
||||
Unscoped() IDraftDatabaseInfoDo
|
||||
Create(values ...*model.DraftDatabaseInfo) error
|
||||
CreateInBatches(values []*model.DraftDatabaseInfo, batchSize int) error
|
||||
Save(values ...*model.DraftDatabaseInfo) error
|
||||
First() (*model.DraftDatabaseInfo, error)
|
||||
Take() (*model.DraftDatabaseInfo, error)
|
||||
Last() (*model.DraftDatabaseInfo, error)
|
||||
Find() ([]*model.DraftDatabaseInfo, error)
|
||||
FindInBatch(batchSize int, fc func(tx gen.Dao, batch int) error) (results []*model.DraftDatabaseInfo, err error)
|
||||
FindInBatches(result *[]*model.DraftDatabaseInfo, batchSize int, fc func(tx gen.Dao, batch int) error) error
|
||||
Pluck(column field.Expr, dest interface{}) error
|
||||
Delete(...*model.DraftDatabaseInfo) (info gen.ResultInfo, err error)
|
||||
Update(column field.Expr, value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateSimple(columns ...field.AssignExpr) (info gen.ResultInfo, err error)
|
||||
Updates(value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateColumn(column field.Expr, value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateColumnSimple(columns ...field.AssignExpr) (info gen.ResultInfo, err error)
|
||||
UpdateColumns(value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateFrom(q gen.SubQuery) gen.Dao
|
||||
Attrs(attrs ...field.AssignExpr) IDraftDatabaseInfoDo
|
||||
Assign(attrs ...field.AssignExpr) IDraftDatabaseInfoDo
|
||||
Joins(fields ...field.RelationField) IDraftDatabaseInfoDo
|
||||
Preload(fields ...field.RelationField) IDraftDatabaseInfoDo
|
||||
FirstOrInit() (*model.DraftDatabaseInfo, error)
|
||||
FirstOrCreate() (*model.DraftDatabaseInfo, error)
|
||||
FindByPage(offset int, limit int) (result []*model.DraftDatabaseInfo, count int64, err error)
|
||||
ScanByPage(result interface{}, offset int, limit int) (count int64, err error)
|
||||
Scan(result interface{}) (err error)
|
||||
Returning(value interface{}, columns ...string) IDraftDatabaseInfoDo
|
||||
UnderlyingDB() *gorm.DB
|
||||
schema.Tabler
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Debug() IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Debug())
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) WithContext(ctx context.Context) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.WithContext(ctx))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) ReadDB() IDraftDatabaseInfoDo {
|
||||
return d.Clauses(dbresolver.Read)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) WriteDB() IDraftDatabaseInfoDo {
|
||||
return d.Clauses(dbresolver.Write)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Session(config *gorm.Session) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Session(config))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Clauses(conds ...clause.Expression) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Clauses(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Returning(value interface{}, columns ...string) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Returning(value, columns...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Not(conds ...gen.Condition) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Not(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Or(conds ...gen.Condition) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Or(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Select(conds ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Select(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Where(conds ...gen.Condition) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Where(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Order(conds ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Order(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Distinct(cols ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Distinct(cols...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Omit(cols ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Omit(cols...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Join(table schema.Tabler, on ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Join(table, on...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) LeftJoin(table schema.Tabler, on ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.LeftJoin(table, on...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) RightJoin(table schema.Tabler, on ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.RightJoin(table, on...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Group(cols ...field.Expr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Group(cols...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Having(conds ...gen.Condition) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Having(conds...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Limit(limit int) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Limit(limit))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Offset(offset int) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Offset(offset))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Scopes(funcs ...func(gen.Dao) gen.Dao) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Scopes(funcs...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Unscoped() IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Unscoped())
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Create(values ...*model.DraftDatabaseInfo) error {
|
||||
if len(values) == 0 {
|
||||
return nil
|
||||
}
|
||||
return d.DO.Create(values)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) CreateInBatches(values []*model.DraftDatabaseInfo, batchSize int) error {
|
||||
return d.DO.CreateInBatches(values, batchSize)
|
||||
}
|
||||
|
||||
// Save : !!! underlying implementation is different with GORM
|
||||
// The method is equivalent to executing the statement: db.Clauses(clause.OnConflict{UpdateAll: true}).Create(values)
|
||||
func (d draftDatabaseInfoDo) Save(values ...*model.DraftDatabaseInfo) error {
|
||||
if len(values) == 0 {
|
||||
return nil
|
||||
}
|
||||
return d.DO.Save(values)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) First() (*model.DraftDatabaseInfo, error) {
|
||||
if result, err := d.DO.First(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.DraftDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Take() (*model.DraftDatabaseInfo, error) {
|
||||
if result, err := d.DO.Take(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.DraftDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Last() (*model.DraftDatabaseInfo, error) {
|
||||
if result, err := d.DO.Last(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.DraftDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Find() ([]*model.DraftDatabaseInfo, error) {
|
||||
result, err := d.DO.Find()
|
||||
return result.([]*model.DraftDatabaseInfo), err
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) FindInBatch(batchSize int, fc func(tx gen.Dao, batch int) error) (results []*model.DraftDatabaseInfo, err error) {
|
||||
buf := make([]*model.DraftDatabaseInfo, 0, batchSize)
|
||||
err = d.DO.FindInBatches(&buf, batchSize, func(tx gen.Dao, batch int) error {
|
||||
defer func() { results = append(results, buf...) }()
|
||||
return fc(tx, batch)
|
||||
})
|
||||
return results, err
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) FindInBatches(result *[]*model.DraftDatabaseInfo, batchSize int, fc func(tx gen.Dao, batch int) error) error {
|
||||
return d.DO.FindInBatches(result, batchSize, fc)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Attrs(attrs ...field.AssignExpr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Attrs(attrs...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Assign(attrs ...field.AssignExpr) IDraftDatabaseInfoDo {
|
||||
return d.withDO(d.DO.Assign(attrs...))
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Joins(fields ...field.RelationField) IDraftDatabaseInfoDo {
|
||||
for _, _f := range fields {
|
||||
d = *d.withDO(d.DO.Joins(_f))
|
||||
}
|
||||
return &d
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Preload(fields ...field.RelationField) IDraftDatabaseInfoDo {
|
||||
for _, _f := range fields {
|
||||
d = *d.withDO(d.DO.Preload(_f))
|
||||
}
|
||||
return &d
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) FirstOrInit() (*model.DraftDatabaseInfo, error) {
|
||||
if result, err := d.DO.FirstOrInit(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.DraftDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) FirstOrCreate() (*model.DraftDatabaseInfo, error) {
|
||||
if result, err := d.DO.FirstOrCreate(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.DraftDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) FindByPage(offset int, limit int) (result []*model.DraftDatabaseInfo, count int64, err error) {
|
||||
result, err = d.Offset(offset).Limit(limit).Find()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if size := len(result); 0 < limit && 0 < size && size < limit {
|
||||
count = int64(size + offset)
|
||||
return
|
||||
}
|
||||
|
||||
count, err = d.Offset(-1).Limit(-1).Count()
|
||||
return
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) ScanByPage(result interface{}, offset int, limit int) (count int64, err error) {
|
||||
count, err = d.Count()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
err = d.Offset(offset).Limit(limit).Scan(result)
|
||||
return
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Scan(result interface{}) (err error) {
|
||||
return d.DO.Scan(result)
|
||||
}
|
||||
|
||||
func (d draftDatabaseInfoDo) Delete(models ...*model.DraftDatabaseInfo) (result gen.ResultInfo, err error) {
|
||||
return d.DO.Delete(models)
|
||||
}
|
||||
|
||||
func (d *draftDatabaseInfoDo) withDO(do gen.Dao) *draftDatabaseInfoDo {
|
||||
d.DO = *do.(*gen.DO)
|
||||
return d
|
||||
}
|
||||
119
backend/domain/memory/database/internal/dal/query/gen.go
Normal file
119
backend/domain/memory/database/internal/dal/query/gen.go
Normal file
@@ -0,0 +1,119 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package query
|
||||
|
||||
import (
|
||||
"context"
|
||||
"database/sql"
|
||||
|
||||
"gorm.io/gorm"
|
||||
|
||||
"gorm.io/gen"
|
||||
|
||||
"gorm.io/plugin/dbresolver"
|
||||
)
|
||||
|
||||
var (
|
||||
Q = new(Query)
|
||||
AgentToDatabase *agentToDatabase
|
||||
DraftDatabaseInfo *draftDatabaseInfo
|
||||
OnlineDatabaseInfo *onlineDatabaseInfo
|
||||
)
|
||||
|
||||
func SetDefault(db *gorm.DB, opts ...gen.DOOption) {
|
||||
*Q = *Use(db, opts...)
|
||||
AgentToDatabase = &Q.AgentToDatabase
|
||||
DraftDatabaseInfo = &Q.DraftDatabaseInfo
|
||||
OnlineDatabaseInfo = &Q.OnlineDatabaseInfo
|
||||
}
|
||||
|
||||
func Use(db *gorm.DB, opts ...gen.DOOption) *Query {
|
||||
return &Query{
|
||||
db: db,
|
||||
AgentToDatabase: newAgentToDatabase(db, opts...),
|
||||
DraftDatabaseInfo: newDraftDatabaseInfo(db, opts...),
|
||||
OnlineDatabaseInfo: newOnlineDatabaseInfo(db, opts...),
|
||||
}
|
||||
}
|
||||
|
||||
type Query struct {
|
||||
db *gorm.DB
|
||||
|
||||
AgentToDatabase agentToDatabase
|
||||
DraftDatabaseInfo draftDatabaseInfo
|
||||
OnlineDatabaseInfo onlineDatabaseInfo
|
||||
}
|
||||
|
||||
func (q *Query) Available() bool { return q.db != nil }
|
||||
|
||||
func (q *Query) clone(db *gorm.DB) *Query {
|
||||
return &Query{
|
||||
db: db,
|
||||
AgentToDatabase: q.AgentToDatabase.clone(db),
|
||||
DraftDatabaseInfo: q.DraftDatabaseInfo.clone(db),
|
||||
OnlineDatabaseInfo: q.OnlineDatabaseInfo.clone(db),
|
||||
}
|
||||
}
|
||||
|
||||
func (q *Query) ReadDB() *Query {
|
||||
return q.ReplaceDB(q.db.Clauses(dbresolver.Read))
|
||||
}
|
||||
|
||||
func (q *Query) WriteDB() *Query {
|
||||
return q.ReplaceDB(q.db.Clauses(dbresolver.Write))
|
||||
}
|
||||
|
||||
func (q *Query) ReplaceDB(db *gorm.DB) *Query {
|
||||
return &Query{
|
||||
db: db,
|
||||
AgentToDatabase: q.AgentToDatabase.replaceDB(db),
|
||||
DraftDatabaseInfo: q.DraftDatabaseInfo.replaceDB(db),
|
||||
OnlineDatabaseInfo: q.OnlineDatabaseInfo.replaceDB(db),
|
||||
}
|
||||
}
|
||||
|
||||
type queryCtx struct {
|
||||
AgentToDatabase IAgentToDatabaseDo
|
||||
DraftDatabaseInfo IDraftDatabaseInfoDo
|
||||
OnlineDatabaseInfo IOnlineDatabaseInfoDo
|
||||
}
|
||||
|
||||
func (q *Query) WithContext(ctx context.Context) *queryCtx {
|
||||
return &queryCtx{
|
||||
AgentToDatabase: q.AgentToDatabase.WithContext(ctx),
|
||||
DraftDatabaseInfo: q.DraftDatabaseInfo.WithContext(ctx),
|
||||
OnlineDatabaseInfo: q.OnlineDatabaseInfo.WithContext(ctx),
|
||||
}
|
||||
}
|
||||
|
||||
func (q *Query) Transaction(fc func(tx *Query) error, opts ...*sql.TxOptions) error {
|
||||
return q.db.Transaction(func(tx *gorm.DB) error { return fc(q.clone(tx)) }, opts...)
|
||||
}
|
||||
|
||||
func (q *Query) Begin(opts ...*sql.TxOptions) *QueryTx {
|
||||
tx := q.db.Begin(opts...)
|
||||
return &QueryTx{Query: q.clone(tx), Error: tx.Error}
|
||||
}
|
||||
|
||||
type QueryTx struct {
|
||||
*Query
|
||||
Error error
|
||||
}
|
||||
|
||||
func (q *QueryTx) Commit() error {
|
||||
return q.db.Commit().Error
|
||||
}
|
||||
|
||||
func (q *QueryTx) Rollback() error {
|
||||
return q.db.Rollback().Error
|
||||
}
|
||||
|
||||
func (q *QueryTx) SavePoint(name string) error {
|
||||
return q.db.SavePoint(name).Error
|
||||
}
|
||||
|
||||
func (q *QueryTx) RollbackTo(name string) error {
|
||||
return q.db.RollbackTo(name).Error
|
||||
}
|
||||
@@ -0,0 +1,441 @@
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
// Code generated by gorm.io/gen. DO NOT EDIT.
|
||||
|
||||
package query
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"gorm.io/gorm"
|
||||
"gorm.io/gorm/clause"
|
||||
"gorm.io/gorm/schema"
|
||||
|
||||
"gorm.io/gen"
|
||||
"gorm.io/gen/field"
|
||||
|
||||
"gorm.io/plugin/dbresolver"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/dal/model"
|
||||
)
|
||||
|
||||
func newOnlineDatabaseInfo(db *gorm.DB, opts ...gen.DOOption) onlineDatabaseInfo {
|
||||
_onlineDatabaseInfo := onlineDatabaseInfo{}
|
||||
|
||||
_onlineDatabaseInfo.onlineDatabaseInfoDo.UseDB(db, opts...)
|
||||
_onlineDatabaseInfo.onlineDatabaseInfoDo.UseModel(&model.OnlineDatabaseInfo{})
|
||||
|
||||
tableName := _onlineDatabaseInfo.onlineDatabaseInfoDo.TableName()
|
||||
_onlineDatabaseInfo.ALL = field.NewAsterisk(tableName)
|
||||
_onlineDatabaseInfo.ID = field.NewInt64(tableName, "id")
|
||||
_onlineDatabaseInfo.AppID = field.NewInt64(tableName, "app_id")
|
||||
_onlineDatabaseInfo.SpaceID = field.NewInt64(tableName, "space_id")
|
||||
_onlineDatabaseInfo.RelatedDraftID = field.NewInt64(tableName, "related_draft_id")
|
||||
_onlineDatabaseInfo.IsVisible = field.NewInt32(tableName, "is_visible")
|
||||
_onlineDatabaseInfo.PromptDisabled = field.NewInt32(tableName, "prompt_disabled")
|
||||
_onlineDatabaseInfo.TableName_ = field.NewString(tableName, "table_name")
|
||||
_onlineDatabaseInfo.TableDesc = field.NewString(tableName, "table_desc")
|
||||
_onlineDatabaseInfo.TableField = field.NewField(tableName, "table_field")
|
||||
_onlineDatabaseInfo.CreatorID = field.NewInt64(tableName, "creator_id")
|
||||
_onlineDatabaseInfo.IconURI = field.NewString(tableName, "icon_uri")
|
||||
_onlineDatabaseInfo.PhysicalTableName = field.NewString(tableName, "physical_table_name")
|
||||
_onlineDatabaseInfo.RwMode = field.NewInt64(tableName, "rw_mode")
|
||||
_onlineDatabaseInfo.CreatedAt = field.NewInt64(tableName, "created_at")
|
||||
_onlineDatabaseInfo.UpdatedAt = field.NewInt64(tableName, "updated_at")
|
||||
_onlineDatabaseInfo.DeletedAt = field.NewField(tableName, "deleted_at")
|
||||
|
||||
_onlineDatabaseInfo.fillFieldMap()
|
||||
|
||||
return _onlineDatabaseInfo
|
||||
}
|
||||
|
||||
// onlineDatabaseInfo online database info
|
||||
type onlineDatabaseInfo struct {
|
||||
onlineDatabaseInfoDo
|
||||
|
||||
ALL field.Asterisk
|
||||
ID field.Int64 // ID
|
||||
AppID field.Int64 // App ID
|
||||
SpaceID field.Int64 // Space ID
|
||||
RelatedDraftID field.Int64 // The primary key ID of draft_database_info table
|
||||
IsVisible field.Int32 // Visibility: 0 invisible, 1 visible
|
||||
PromptDisabled field.Int32 // Support prompt calls: 1 not supported, 0 supported
|
||||
TableName_ field.String // Table name
|
||||
TableDesc field.String // Table description
|
||||
TableField field.Field // Table field info
|
||||
CreatorID field.Int64 // Creator ID
|
||||
IconURI field.String // Icon Uri
|
||||
PhysicalTableName field.String // The name of the real physical table
|
||||
RwMode field.Int64 // Read and write permission modes: 1. Limited read and write mode 2. Read-only mode 3. Full read and write mode
|
||||
CreatedAt field.Int64 // Create Time in Milliseconds
|
||||
UpdatedAt field.Int64 // Update Time in Milliseconds
|
||||
DeletedAt field.Field // Delete Time
|
||||
|
||||
fieldMap map[string]field.Expr
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfo) Table(newTableName string) *onlineDatabaseInfo {
|
||||
o.onlineDatabaseInfoDo.UseTable(newTableName)
|
||||
return o.updateTableName(newTableName)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfo) As(alias string) *onlineDatabaseInfo {
|
||||
o.onlineDatabaseInfoDo.DO = *(o.onlineDatabaseInfoDo.As(alias).(*gen.DO))
|
||||
return o.updateTableName(alias)
|
||||
}
|
||||
|
||||
func (o *onlineDatabaseInfo) updateTableName(table string) *onlineDatabaseInfo {
|
||||
o.ALL = field.NewAsterisk(table)
|
||||
o.ID = field.NewInt64(table, "id")
|
||||
o.AppID = field.NewInt64(table, "app_id")
|
||||
o.SpaceID = field.NewInt64(table, "space_id")
|
||||
o.RelatedDraftID = field.NewInt64(table, "related_draft_id")
|
||||
o.IsVisible = field.NewInt32(table, "is_visible")
|
||||
o.PromptDisabled = field.NewInt32(table, "prompt_disabled")
|
||||
o.TableName_ = field.NewString(table, "table_name")
|
||||
o.TableDesc = field.NewString(table, "table_desc")
|
||||
o.TableField = field.NewField(table, "table_field")
|
||||
o.CreatorID = field.NewInt64(table, "creator_id")
|
||||
o.IconURI = field.NewString(table, "icon_uri")
|
||||
o.PhysicalTableName = field.NewString(table, "physical_table_name")
|
||||
o.RwMode = field.NewInt64(table, "rw_mode")
|
||||
o.CreatedAt = field.NewInt64(table, "created_at")
|
||||
o.UpdatedAt = field.NewInt64(table, "updated_at")
|
||||
o.DeletedAt = field.NewField(table, "deleted_at")
|
||||
|
||||
o.fillFieldMap()
|
||||
|
||||
return o
|
||||
}
|
||||
|
||||
func (o *onlineDatabaseInfo) GetFieldByName(fieldName string) (field.OrderExpr, bool) {
|
||||
_f, ok := o.fieldMap[fieldName]
|
||||
if !ok || _f == nil {
|
||||
return nil, false
|
||||
}
|
||||
_oe, ok := _f.(field.OrderExpr)
|
||||
return _oe, ok
|
||||
}
|
||||
|
||||
func (o *onlineDatabaseInfo) fillFieldMap() {
|
||||
o.fieldMap = make(map[string]field.Expr, 16)
|
||||
o.fieldMap["id"] = o.ID
|
||||
o.fieldMap["app_id"] = o.AppID
|
||||
o.fieldMap["space_id"] = o.SpaceID
|
||||
o.fieldMap["related_draft_id"] = o.RelatedDraftID
|
||||
o.fieldMap["is_visible"] = o.IsVisible
|
||||
o.fieldMap["prompt_disabled"] = o.PromptDisabled
|
||||
o.fieldMap["table_name"] = o.TableName_
|
||||
o.fieldMap["table_desc"] = o.TableDesc
|
||||
o.fieldMap["table_field"] = o.TableField
|
||||
o.fieldMap["creator_id"] = o.CreatorID
|
||||
o.fieldMap["icon_uri"] = o.IconURI
|
||||
o.fieldMap["physical_table_name"] = o.PhysicalTableName
|
||||
o.fieldMap["rw_mode"] = o.RwMode
|
||||
o.fieldMap["created_at"] = o.CreatedAt
|
||||
o.fieldMap["updated_at"] = o.UpdatedAt
|
||||
o.fieldMap["deleted_at"] = o.DeletedAt
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfo) clone(db *gorm.DB) onlineDatabaseInfo {
|
||||
o.onlineDatabaseInfoDo.ReplaceConnPool(db.Statement.ConnPool)
|
||||
return o
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfo) replaceDB(db *gorm.DB) onlineDatabaseInfo {
|
||||
o.onlineDatabaseInfoDo.ReplaceDB(db)
|
||||
return o
|
||||
}
|
||||
|
||||
type onlineDatabaseInfoDo struct{ gen.DO }
|
||||
|
||||
type IOnlineDatabaseInfoDo interface {
|
||||
gen.SubQuery
|
||||
Debug() IOnlineDatabaseInfoDo
|
||||
WithContext(ctx context.Context) IOnlineDatabaseInfoDo
|
||||
WithResult(fc func(tx gen.Dao)) gen.ResultInfo
|
||||
ReplaceDB(db *gorm.DB)
|
||||
ReadDB() IOnlineDatabaseInfoDo
|
||||
WriteDB() IOnlineDatabaseInfoDo
|
||||
As(alias string) gen.Dao
|
||||
Session(config *gorm.Session) IOnlineDatabaseInfoDo
|
||||
Columns(cols ...field.Expr) gen.Columns
|
||||
Clauses(conds ...clause.Expression) IOnlineDatabaseInfoDo
|
||||
Not(conds ...gen.Condition) IOnlineDatabaseInfoDo
|
||||
Or(conds ...gen.Condition) IOnlineDatabaseInfoDo
|
||||
Select(conds ...field.Expr) IOnlineDatabaseInfoDo
|
||||
Where(conds ...gen.Condition) IOnlineDatabaseInfoDo
|
||||
Order(conds ...field.Expr) IOnlineDatabaseInfoDo
|
||||
Distinct(cols ...field.Expr) IOnlineDatabaseInfoDo
|
||||
Omit(cols ...field.Expr) IOnlineDatabaseInfoDo
|
||||
Join(table schema.Tabler, on ...field.Expr) IOnlineDatabaseInfoDo
|
||||
LeftJoin(table schema.Tabler, on ...field.Expr) IOnlineDatabaseInfoDo
|
||||
RightJoin(table schema.Tabler, on ...field.Expr) IOnlineDatabaseInfoDo
|
||||
Group(cols ...field.Expr) IOnlineDatabaseInfoDo
|
||||
Having(conds ...gen.Condition) IOnlineDatabaseInfoDo
|
||||
Limit(limit int) IOnlineDatabaseInfoDo
|
||||
Offset(offset int) IOnlineDatabaseInfoDo
|
||||
Count() (count int64, err error)
|
||||
Scopes(funcs ...func(gen.Dao) gen.Dao) IOnlineDatabaseInfoDo
|
||||
Unscoped() IOnlineDatabaseInfoDo
|
||||
Create(values ...*model.OnlineDatabaseInfo) error
|
||||
CreateInBatches(values []*model.OnlineDatabaseInfo, batchSize int) error
|
||||
Save(values ...*model.OnlineDatabaseInfo) error
|
||||
First() (*model.OnlineDatabaseInfo, error)
|
||||
Take() (*model.OnlineDatabaseInfo, error)
|
||||
Last() (*model.OnlineDatabaseInfo, error)
|
||||
Find() ([]*model.OnlineDatabaseInfo, error)
|
||||
FindInBatch(batchSize int, fc func(tx gen.Dao, batch int) error) (results []*model.OnlineDatabaseInfo, err error)
|
||||
FindInBatches(result *[]*model.OnlineDatabaseInfo, batchSize int, fc func(tx gen.Dao, batch int) error) error
|
||||
Pluck(column field.Expr, dest interface{}) error
|
||||
Delete(...*model.OnlineDatabaseInfo) (info gen.ResultInfo, err error)
|
||||
Update(column field.Expr, value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateSimple(columns ...field.AssignExpr) (info gen.ResultInfo, err error)
|
||||
Updates(value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateColumn(column field.Expr, value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateColumnSimple(columns ...field.AssignExpr) (info gen.ResultInfo, err error)
|
||||
UpdateColumns(value interface{}) (info gen.ResultInfo, err error)
|
||||
UpdateFrom(q gen.SubQuery) gen.Dao
|
||||
Attrs(attrs ...field.AssignExpr) IOnlineDatabaseInfoDo
|
||||
Assign(attrs ...field.AssignExpr) IOnlineDatabaseInfoDo
|
||||
Joins(fields ...field.RelationField) IOnlineDatabaseInfoDo
|
||||
Preload(fields ...field.RelationField) IOnlineDatabaseInfoDo
|
||||
FirstOrInit() (*model.OnlineDatabaseInfo, error)
|
||||
FirstOrCreate() (*model.OnlineDatabaseInfo, error)
|
||||
FindByPage(offset int, limit int) (result []*model.OnlineDatabaseInfo, count int64, err error)
|
||||
ScanByPage(result interface{}, offset int, limit int) (count int64, err error)
|
||||
Scan(result interface{}) (err error)
|
||||
Returning(value interface{}, columns ...string) IOnlineDatabaseInfoDo
|
||||
UnderlyingDB() *gorm.DB
|
||||
schema.Tabler
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Debug() IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Debug())
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) WithContext(ctx context.Context) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.WithContext(ctx))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) ReadDB() IOnlineDatabaseInfoDo {
|
||||
return o.Clauses(dbresolver.Read)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) WriteDB() IOnlineDatabaseInfoDo {
|
||||
return o.Clauses(dbresolver.Write)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Session(config *gorm.Session) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Session(config))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Clauses(conds ...clause.Expression) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Clauses(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Returning(value interface{}, columns ...string) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Returning(value, columns...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Not(conds ...gen.Condition) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Not(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Or(conds ...gen.Condition) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Or(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Select(conds ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Select(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Where(conds ...gen.Condition) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Where(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Order(conds ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Order(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Distinct(cols ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Distinct(cols...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Omit(cols ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Omit(cols...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Join(table schema.Tabler, on ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Join(table, on...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) LeftJoin(table schema.Tabler, on ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.LeftJoin(table, on...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) RightJoin(table schema.Tabler, on ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.RightJoin(table, on...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Group(cols ...field.Expr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Group(cols...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Having(conds ...gen.Condition) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Having(conds...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Limit(limit int) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Limit(limit))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Offset(offset int) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Offset(offset))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Scopes(funcs ...func(gen.Dao) gen.Dao) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Scopes(funcs...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Unscoped() IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Unscoped())
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Create(values ...*model.OnlineDatabaseInfo) error {
|
||||
if len(values) == 0 {
|
||||
return nil
|
||||
}
|
||||
return o.DO.Create(values)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) CreateInBatches(values []*model.OnlineDatabaseInfo, batchSize int) error {
|
||||
return o.DO.CreateInBatches(values, batchSize)
|
||||
}
|
||||
|
||||
// Save : !!! underlying implementation is different with GORM
|
||||
// The method is equivalent to executing the statement: db.Clauses(clause.OnConflict{UpdateAll: true}).Create(values)
|
||||
func (o onlineDatabaseInfoDo) Save(values ...*model.OnlineDatabaseInfo) error {
|
||||
if len(values) == 0 {
|
||||
return nil
|
||||
}
|
||||
return o.DO.Save(values)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) First() (*model.OnlineDatabaseInfo, error) {
|
||||
if result, err := o.DO.First(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.OnlineDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Take() (*model.OnlineDatabaseInfo, error) {
|
||||
if result, err := o.DO.Take(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.OnlineDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Last() (*model.OnlineDatabaseInfo, error) {
|
||||
if result, err := o.DO.Last(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.OnlineDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Find() ([]*model.OnlineDatabaseInfo, error) {
|
||||
result, err := o.DO.Find()
|
||||
return result.([]*model.OnlineDatabaseInfo), err
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) FindInBatch(batchSize int, fc func(tx gen.Dao, batch int) error) (results []*model.OnlineDatabaseInfo, err error) {
|
||||
buf := make([]*model.OnlineDatabaseInfo, 0, batchSize)
|
||||
err = o.DO.FindInBatches(&buf, batchSize, func(tx gen.Dao, batch int) error {
|
||||
defer func() { results = append(results, buf...) }()
|
||||
return fc(tx, batch)
|
||||
})
|
||||
return results, err
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) FindInBatches(result *[]*model.OnlineDatabaseInfo, batchSize int, fc func(tx gen.Dao, batch int) error) error {
|
||||
return o.DO.FindInBatches(result, batchSize, fc)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Attrs(attrs ...field.AssignExpr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Attrs(attrs...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Assign(attrs ...field.AssignExpr) IOnlineDatabaseInfoDo {
|
||||
return o.withDO(o.DO.Assign(attrs...))
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Joins(fields ...field.RelationField) IOnlineDatabaseInfoDo {
|
||||
for _, _f := range fields {
|
||||
o = *o.withDO(o.DO.Joins(_f))
|
||||
}
|
||||
return &o
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Preload(fields ...field.RelationField) IOnlineDatabaseInfoDo {
|
||||
for _, _f := range fields {
|
||||
o = *o.withDO(o.DO.Preload(_f))
|
||||
}
|
||||
return &o
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) FirstOrInit() (*model.OnlineDatabaseInfo, error) {
|
||||
if result, err := o.DO.FirstOrInit(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.OnlineDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) FirstOrCreate() (*model.OnlineDatabaseInfo, error) {
|
||||
if result, err := o.DO.FirstOrCreate(); err != nil {
|
||||
return nil, err
|
||||
} else {
|
||||
return result.(*model.OnlineDatabaseInfo), nil
|
||||
}
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) FindByPage(offset int, limit int) (result []*model.OnlineDatabaseInfo, count int64, err error) {
|
||||
result, err = o.Offset(offset).Limit(limit).Find()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if size := len(result); 0 < limit && 0 < size && size < limit {
|
||||
count = int64(size + offset)
|
||||
return
|
||||
}
|
||||
|
||||
count, err = o.Offset(-1).Limit(-1).Count()
|
||||
return
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) ScanByPage(result interface{}, offset int, limit int) (count int64, err error) {
|
||||
count, err = o.Count()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
err = o.Offset(offset).Limit(limit).Scan(result)
|
||||
return
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Scan(result interface{}) (err error) {
|
||||
return o.DO.Scan(result)
|
||||
}
|
||||
|
||||
func (o onlineDatabaseInfoDo) Delete(models ...*model.OnlineDatabaseInfo) (result gen.ResultInfo, err error) {
|
||||
return o.DO.Delete(models)
|
||||
}
|
||||
|
||||
func (o *onlineDatabaseInfoDo) withDO(do gen.Dao) *onlineDatabaseInfoDo {
|
||||
o.DO = *do.(*gen.DO)
|
||||
return o
|
||||
}
|
||||
@@ -0,0 +1,344 @@
|
||||
/*
|
||||
* 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 physicaltable
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
model "github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/table"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/internal/convertor"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/rdb"
|
||||
entity3 "github.com/coze-dev/coze-studio/backend/infra/contract/rdb/entity"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/lang/ptr"
|
||||
)
|
||||
|
||||
func CreatePhysicalTable(ctx context.Context, db rdb.RDB, columns []*entity3.Column) (*rdb.CreateTableResponse, error) {
|
||||
table := &entity3.Table{
|
||||
Columns: columns,
|
||||
}
|
||||
// get indexes
|
||||
indexes := make([]*entity3.Index, 0)
|
||||
indexes = append(indexes, &entity3.Index{
|
||||
Name: "PRIMARY",
|
||||
Type: entity3.PrimaryKey,
|
||||
Columns: []string{database.DefaultIDColName},
|
||||
})
|
||||
indexes = append(indexes, &entity3.Index{
|
||||
Name: "idx_uid",
|
||||
Type: entity3.NormalKey,
|
||||
Columns: []string{database.DefaultUidColName, database.DefaultCidColName},
|
||||
})
|
||||
table.Indexes = indexes
|
||||
|
||||
physicalTableRes, err := db.CreateTable(ctx, &rdb.CreateTableRequest{Table: table})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return physicalTableRes, nil
|
||||
}
|
||||
|
||||
func CreateFieldInfo(fieldItems []*model.FieldItem) ([]*model.FieldItem, []*entity3.Column) {
|
||||
columns := make([]*entity3.Column, len(fieldItems))
|
||||
|
||||
fieldID := int64(1)
|
||||
for i, field := range fieldItems {
|
||||
field.AlterID = fieldID
|
||||
field.PhysicalName = GetFieldPhysicsName(fieldID)
|
||||
|
||||
columns[i] = &entity3.Column{
|
||||
Name: GetFieldPhysicsName(fieldID),
|
||||
DataType: convertor.SwitchToDataType(field.Type),
|
||||
NotNull: field.MustRequired,
|
||||
Comment: &field.Desc,
|
||||
}
|
||||
|
||||
if field.Type == table.FieldItemType_Text && !field.MustRequired {
|
||||
columns[i].DefaultValue = ptr.Of("")
|
||||
}
|
||||
|
||||
fieldID++ // field is incremented begin from 1
|
||||
}
|
||||
|
||||
columns = append(columns, GetDefaultColumns()...)
|
||||
|
||||
return fieldItems, columns
|
||||
}
|
||||
|
||||
func GetDefaultColumns() []*entity3.Column {
|
||||
return getDefaultColumns()
|
||||
}
|
||||
|
||||
func getDefaultColumns() []*entity3.Column {
|
||||
return []*entity3.Column{
|
||||
{
|
||||
Name: database.DefaultIDColName,
|
||||
DataType: entity3.TypeBigInt,
|
||||
NotNull: true,
|
||||
AutoIncrement: true,
|
||||
},
|
||||
{
|
||||
Name: database.DefaultUidColName,
|
||||
DataType: entity3.TypeVarchar,
|
||||
NotNull: true,
|
||||
},
|
||||
{
|
||||
Name: database.DefaultCidColName,
|
||||
DataType: entity3.TypeVarchar,
|
||||
NotNull: true,
|
||||
},
|
||||
{
|
||||
Name: database.DefaultCreateTimeColName,
|
||||
DataType: entity3.TypeTimestamp,
|
||||
NotNull: true,
|
||||
DefaultValue: ptr.Of("CURRENT_TIMESTAMP"),
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func GetTablePhysicsName(tableID int64) string {
|
||||
return fmt.Sprintf("table_%d", tableID)
|
||||
}
|
||||
|
||||
func GetFieldPhysicsName(fieldID int64) string {
|
||||
return fmt.Sprintf("f_%d", fieldID)
|
||||
}
|
||||
|
||||
// UpdateFieldInfo handles field information updates.
|
||||
// 1. If alterID exists, use alterID to update existing fields.
|
||||
// 2. If alterID does not exist, add new fields.
|
||||
// 3. Delete fields that have alterIDs not present in the new list.
|
||||
func UpdateFieldInfo(newFieldItems []*database.FieldItem, existingFieldItems []*database.FieldItem) ([]*database.FieldItem, []*entity3.Column, []string, error) {
|
||||
existingFieldMap := make(map[int64]*database.FieldItem)
|
||||
maxAlterID := int64(-1)
|
||||
for _, field := range existingFieldItems {
|
||||
if field.AlterID > 0 {
|
||||
existingFieldMap[field.AlterID] = field
|
||||
maxAlterID = max(maxAlterID, field.AlterID)
|
||||
}
|
||||
}
|
||||
|
||||
newFieldIDs := make(map[int64]bool)
|
||||
|
||||
updatedColumns := make([]*entity3.Column, 0, len(newFieldItems))
|
||||
updatedFieldItems := make([]*database.FieldItem, 0, len(newFieldItems))
|
||||
|
||||
for _, field := range newFieldItems {
|
||||
if field.AlterID > 0 {
|
||||
// update field
|
||||
newFieldIDs[field.AlterID] = true
|
||||
field.PhysicalName = GetFieldPhysicsName(field.AlterID)
|
||||
updatedFieldItems = append(updatedFieldItems, field)
|
||||
|
||||
updatedColumns = append(updatedColumns, &entity3.Column{
|
||||
Name: GetFieldPhysicsName(field.AlterID),
|
||||
DataType: convertor.SwitchToDataType(field.Type),
|
||||
NotNull: field.MustRequired,
|
||||
Comment: &field.Desc,
|
||||
})
|
||||
} else {
|
||||
fieldID := maxAlterID + 1 // auto increment begin from existing maxAlterID
|
||||
maxAlterID++
|
||||
field.AlterID = fieldID
|
||||
field.PhysicalName = GetFieldPhysicsName(fieldID)
|
||||
updatedFieldItems = append(updatedFieldItems, field)
|
||||
|
||||
updatedColumns = append(updatedColumns, &entity3.Column{
|
||||
Name: GetFieldPhysicsName(fieldID),
|
||||
DataType: convertor.SwitchToDataType(field.Type),
|
||||
NotNull: field.MustRequired,
|
||||
Comment: &field.Desc,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
droppedColumns := make([]string, 0, len(existingFieldMap))
|
||||
// get dropped columns
|
||||
for alterID := range existingFieldMap {
|
||||
if !newFieldIDs[alterID] {
|
||||
droppedColumns = append(droppedColumns, GetFieldPhysicsName(alterID))
|
||||
}
|
||||
}
|
||||
|
||||
return updatedFieldItems, updatedColumns, droppedColumns, nil
|
||||
}
|
||||
|
||||
// UpdatePhysicalTableWithDrops 更新物理表结构,包括显式指定要删除的列
|
||||
func UpdatePhysicalTableWithDrops(ctx context.Context, db rdb.RDB, existingTable *entity3.Table, newColumns []*entity3.Column, droppedColumns []string, tableName string) error {
|
||||
// 创建列名到列的映射
|
||||
existingColumnMap := make(map[string]*entity3.Column)
|
||||
for _, col := range existingTable.Columns {
|
||||
existingColumnMap[col.Name] = col
|
||||
}
|
||||
|
||||
// 收集要添加和修改的列
|
||||
var columnsToAdd, columnsToModify []*entity3.Column
|
||||
|
||||
// 查找要添加和修改的列
|
||||
for _, newCol := range newColumns {
|
||||
if _, exists := existingColumnMap[newCol.Name]; exists {
|
||||
columnsToModify = append(columnsToModify, newCol)
|
||||
} else {
|
||||
columnsToAdd = append(columnsToAdd, newCol)
|
||||
}
|
||||
}
|
||||
|
||||
// 应用变更到物理表
|
||||
if len(columnsToAdd) > 0 || len(columnsToModify) > 0 || len(droppedColumns) > 0 {
|
||||
// build AlterTableRequest
|
||||
alterReq := &rdb.AlterTableRequest{
|
||||
TableName: tableName,
|
||||
Operations: getOperation(columnsToAdd, columnsToModify, droppedColumns),
|
||||
}
|
||||
|
||||
// 执行表结构变更
|
||||
_, err := db.AlterTable(ctx, alterReq)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// getOperation 将列的添加、修改和删除操作转换为 AlterTableOperation 数组
|
||||
func getOperation(columnsToAdd, columnsToModify []*entity3.Column, droppedColumns []string) []*rdb.AlterTableOperation {
|
||||
operations := make([]*rdb.AlterTableOperation, 0)
|
||||
|
||||
// 处理添加列操作
|
||||
for _, column := range columnsToAdd {
|
||||
operations = append(operations, &rdb.AlterTableOperation{
|
||||
Action: entity3.AddColumn,
|
||||
Column: column,
|
||||
})
|
||||
}
|
||||
|
||||
// 处理修改列操作
|
||||
for _, column := range columnsToModify {
|
||||
operations = append(operations, &rdb.AlterTableOperation{
|
||||
Action: entity3.ModifyColumn,
|
||||
Column: column,
|
||||
})
|
||||
}
|
||||
|
||||
// 处理删除列操作
|
||||
for _, columnName := range droppedColumns {
|
||||
operations = append(operations, &rdb.AlterTableOperation{
|
||||
Action: entity3.DropColumn,
|
||||
Column: &entity3.Column{Name: columnName},
|
||||
})
|
||||
}
|
||||
|
||||
return operations
|
||||
}
|
||||
|
||||
func GetTemplateTypeMap() map[table.FieldItemType]string {
|
||||
return map[table.FieldItemType]string{
|
||||
table.FieldItemType_Boolean: "false",
|
||||
table.FieldItemType_Number: "0",
|
||||
table.FieldItemType_Date: "0001-01-01 00:00:00",
|
||||
table.FieldItemType_Text: "",
|
||||
table.FieldItemType_Float: "0",
|
||||
}
|
||||
}
|
||||
|
||||
func GetCreateTimeField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultCreateTimeColName,
|
||||
Desc: "create time",
|
||||
Type: table.FieldItemType_Date,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 103,
|
||||
PhysicalName: database.DefaultCreateTimeColName,
|
||||
}
|
||||
}
|
||||
|
||||
func GetUidField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultUidColName,
|
||||
Desc: "user id",
|
||||
Type: table.FieldItemType_Text,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 101,
|
||||
PhysicalName: database.DefaultUidColName,
|
||||
}
|
||||
}
|
||||
|
||||
func GetConnectIDField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultCidColName,
|
||||
Desc: "connector id",
|
||||
Type: table.FieldItemType_Text,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 104,
|
||||
PhysicalName: database.DefaultCidColName,
|
||||
}
|
||||
}
|
||||
|
||||
func GetIDField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultIDColName,
|
||||
Desc: "primary_key",
|
||||
Type: table.FieldItemType_Number,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 102,
|
||||
PhysicalName: database.DefaultIDColName,
|
||||
}
|
||||
}
|
||||
|
||||
func GetDisplayCreateTimeField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultCreateTimeDisplayColName,
|
||||
Desc: "create time",
|
||||
Type: table.FieldItemType_Date,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 103,
|
||||
PhysicalName: database.DefaultCreateTimeDisplayColName,
|
||||
}
|
||||
}
|
||||
|
||||
func GetDisplayUidField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultUidDisplayColName,
|
||||
Desc: "user id",
|
||||
Type: table.FieldItemType_Text,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 101,
|
||||
PhysicalName: database.DefaultUidDisplayColName,
|
||||
}
|
||||
}
|
||||
|
||||
func GetDisplayIDField() *database.FieldItem {
|
||||
return &database.FieldItem{
|
||||
Name: database.DefaultIDDisplayColName,
|
||||
Desc: "primary_key",
|
||||
Type: table.FieldItemType_Number,
|
||||
MustRequired: false,
|
||||
IsSystemField: true,
|
||||
AlterID: 102,
|
||||
PhysicalName: database.DefaultIDDisplayColName,
|
||||
}
|
||||
}
|
||||
738
backend/domain/memory/database/internal/sheet/sheet.go
Normal file
738
backend/domain/memory/database/internal/sheet/sheet.go
Normal file
@@ -0,0 +1,738 @@
|
||||
/*
|
||||
* 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 sheet
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"encoding/csv"
|
||||
"fmt"
|
||||
"io"
|
||||
"math/rand"
|
||||
"os"
|
||||
"regexp"
|
||||
"runtime/debug"
|
||||
"sort"
|
||||
"strconv"
|
||||
"strings"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/extrame/xls"
|
||||
"github.com/xuri/excelize/v2"
|
||||
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/common"
|
||||
"github.com/coze-dev/coze-studio/backend/api/model/crossdomain/database"
|
||||
"github.com/coze-dev/coze-studio/backend/domain/memory/database/entity"
|
||||
"github.com/coze-dev/coze-studio/backend/infra/contract/storage"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/errorx"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/lang/ptr"
|
||||
"github.com/coze-dev/coze-studio/backend/pkg/logs"
|
||||
"github.com/coze-dev/coze-studio/backend/types/errno"
|
||||
)
|
||||
|
||||
type CellTypeIdentifier struct {
|
||||
Priority int64
|
||||
IdentifyCellType func(cellValue string) *common.ColumnType
|
||||
TargetColumnType common.ColumnType
|
||||
}
|
||||
|
||||
var (
|
||||
identifierChain []CellTypeIdentifier
|
||||
initIdentifierOnce sync.Once
|
||||
dateTimePattern string
|
||||
)
|
||||
|
||||
type TosTableParser struct {
|
||||
UserID int64
|
||||
DocumentSource database.DocumentSourceType
|
||||
TosURI string
|
||||
TosServ storage.Storage
|
||||
}
|
||||
|
||||
func (t *TosTableParser) GetTableDataBySheetIDx(ctx context.Context, rMeta entity.TableReaderMeta) (*entity.TableReaderSheetData, *entity.ExcelExtraInfo, error) {
|
||||
meta, err := t.getLocalSheetMeta(ctx, rMeta.TosMaxLine)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
defer func() {
|
||||
if meta == nil || meta.ExcelFile == nil {
|
||||
return
|
||||
}
|
||||
if err1 := meta.ExcelFile.Close(); err1 != nil {
|
||||
logs.CtxInfof(ctx, "[GetTableDataBySheetIdx] close excel file failed, err: %v", err1)
|
||||
}
|
||||
}()
|
||||
|
||||
if len(meta.SheetsRowCount) == 0 {
|
||||
return nil, nil, errorx.New(errno.ErrMemoryDatabaseNoSheetFound)
|
||||
}
|
||||
|
||||
if int(rMeta.SheetId) >= len(meta.SheetsRowCount) {
|
||||
return nil, nil, errorx.New(errno.ErrMemoryDatabaseSheetIndexExceed)
|
||||
}
|
||||
|
||||
// get execl range: sheetIdx + headerIdx + startLineIdx
|
||||
if rMeta.StartLineIdx > int64(meta.SheetsRowCount[rMeta.SheetId]) {
|
||||
return nil, nil, errorx.New(errno.ErrMemoryDatabaseSheetIndexExceed)
|
||||
}
|
||||
extra := &entity.ExcelExtraInfo{
|
||||
ExtensionName: meta.ExtensionName,
|
||||
FileSize: meta.FileSize,
|
||||
TosURI: t.TosURI,
|
||||
}
|
||||
|
||||
data, ocErr := t.getTableDataBySheetIdx(ctx, rMeta, meta, rMeta.SheetId)
|
||||
if ocErr != nil {
|
||||
return nil, nil, ocErr
|
||||
}
|
||||
for i := range meta.SheetsRowCount {
|
||||
extra.Sheets = append(extra.Sheets, &common.DocTableSheet{
|
||||
ID: int64(i),
|
||||
SheetName: meta.SheetsNameList[i],
|
||||
TotalRow: int64(meta.SheetsRowCount[i]),
|
||||
})
|
||||
}
|
||||
return data, extra, ocErr
|
||||
}
|
||||
|
||||
func (t *TosTableParser) getLocalSheetMeta(ctx context.Context, maxLine int64) (*entity.LocalTableMeta, error) {
|
||||
documentExtension, object, ocErr := t.GetTosTableFile(ctx)
|
||||
if ocErr != nil {
|
||||
return nil, ocErr
|
||||
}
|
||||
|
||||
reader := bytes.NewReader(object)
|
||||
if documentExtension == "csv" { // 处理 csv 文件
|
||||
records, err := csv.NewReader(reader).ReadAll()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if int64(len(records)) > maxLine {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &entity.LocalTableMeta{
|
||||
RawLines: records,
|
||||
SheetsNameList: []string{"default"},
|
||||
SheetsRowCount: []int{len(records)},
|
||||
ExtensionName: documentExtension,
|
||||
FileSize: int64(len(object)),
|
||||
}, nil
|
||||
} else if documentExtension == "xls" {
|
||||
result, err := HandleTmpFile(ctx, reader, "xls", getXlsLocalSheetMetaWithTmpFileCallback, int64(len(object)))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
localTableMeta, ok := result.(*entity.LocalTableMeta)
|
||||
if !ok {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return localTableMeta, nil
|
||||
}
|
||||
|
||||
excelFile, err := excelize.OpenReader(reader)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
meta := &entity.LocalTableMeta{
|
||||
ExcelFile: excelFile,
|
||||
ExtensionName: documentExtension,
|
||||
FileSize: int64(len(object)),
|
||||
}
|
||||
|
||||
for _, sheetName := range excelFile.GetSheetList() {
|
||||
total := 0
|
||||
rows, rowsErr := excelFile.Rows(sheetName)
|
||||
if rowsErr != nil {
|
||||
return nil, rowsErr
|
||||
}
|
||||
for rows.Next() {
|
||||
total++
|
||||
if int64(total) > maxLine {
|
||||
return nil, errorx.New(errno.ErrMemoryDatabaseSheetRowCountExceed, errorx.KVf("msg", "row count exceed limit when database importing excel, limit: %v", maxLine))
|
||||
}
|
||||
}
|
||||
meta.SheetsRowCount = append(meta.SheetsRowCount, total)
|
||||
meta.SheetsNameList = append(meta.SheetsNameList, sheetName)
|
||||
}
|
||||
|
||||
return meta, nil
|
||||
}
|
||||
|
||||
func (t *TosTableParser) GetTosTableFile(ctx context.Context) (string, []byte, error) {
|
||||
names := strings.Split(t.TosURI, "/")
|
||||
objectName := strings.Split(names[len(names)-1], ".")
|
||||
documentExtension := objectName[len(objectName)-1]
|
||||
if documentExtension != "csv" && documentExtension != "xlsx" {
|
||||
return "", nil, errorx.New(errno.ErrMemoryDatabaseUnsupportedFileType)
|
||||
}
|
||||
|
||||
object, err := t.TosServ.GetObject(ctx, t.TosURI)
|
||||
if err != nil {
|
||||
return "", nil, fmt.Errorf("get tos file failed:%+v", err)
|
||||
}
|
||||
|
||||
if len(object) > 104857600 {
|
||||
return "", nil, errorx.New(errno.ErrMemoryDatabaseSheetSizeExceed)
|
||||
}
|
||||
|
||||
return documentExtension, object, nil
|
||||
}
|
||||
|
||||
func (t *TosTableParser) getTableDataBySheetIdx(ctx context.Context, rMeta entity.TableReaderMeta, localMeta *entity.LocalTableMeta, sheetIdx int64) (*entity.TableReaderSheetData, error) {
|
||||
if int(sheetIdx) >= len(localMeta.SheetsRowCount) {
|
||||
return nil, fmt.Errorf("start sheet index out of range")
|
||||
}
|
||||
|
||||
res := &entity.TableReaderSheetData{
|
||||
Columns: make([]*common.DocTableColumn, 0),
|
||||
}
|
||||
defer func() {
|
||||
if localMeta != nil && localMeta.ExcelFile != nil {
|
||||
if err := localMeta.ExcelFile.Close(); err != nil {
|
||||
logs.CtxErrorf(ctx, "[GetTableDataBySheetIdx] close excel file err: %v", err)
|
||||
}
|
||||
}
|
||||
}()
|
||||
|
||||
sheetRowTotal := localMeta.SheetsRowCount[sheetIdx]
|
||||
headLine, sampleData, ocErr := t.parseSchemaInfo(ctx, localMeta, rMeta, int(sheetIdx), sheetRowTotal)
|
||||
if ocErr != nil {
|
||||
return nil, ocErr
|
||||
}
|
||||
|
||||
if len(headLine) == 0 {
|
||||
return res, nil
|
||||
}
|
||||
|
||||
for colIndex, cell := range headLine {
|
||||
res.Columns = append(res.Columns, &common.DocTableColumn{
|
||||
ColumnName: cell,
|
||||
Sequence: int64(colIndex),
|
||||
})
|
||||
}
|
||||
res.SampleData = sampleData
|
||||
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (t *TosTableParser) parseSchemaInfo(ctx context.Context, meta *entity.LocalTableMeta, rMeta entity.TableReaderMeta, sheetIdx, sheetRowTotal int) (header []string, sampleData [][]string, err error) {
|
||||
if len(meta.RawLines) != 0 {
|
||||
if len(meta.RawLines) == 0 {
|
||||
return []string{}, [][]string{}, nil
|
||||
}
|
||||
if rMeta.HeaderLineIdx >= int64(len(meta.RawLines)) {
|
||||
return nil, nil, fmt.Errorf("header idx exceed")
|
||||
}
|
||||
if rMeta.StartLineIdx > int64(len(meta.RawLines)) {
|
||||
return meta.RawLines[rMeta.HeaderLineIdx], [][]string{}, nil
|
||||
}
|
||||
|
||||
switch rMeta.ReaderMethod {
|
||||
case database.TableReadDataMethodHead:
|
||||
end := int(rMeta.StartLineIdx + rMeta.ReadLineCnt)
|
||||
if end > len(meta.RawLines) {
|
||||
end = len(meta.RawLines)
|
||||
}
|
||||
return meta.RawLines[rMeta.HeaderLineIdx], meta.RawLines[rMeta.StartLineIdx:end], nil
|
||||
|
||||
case database.TableReadDataMethodOnlyHeader:
|
||||
if len(meta.RawLines[rMeta.HeaderLineIdx]) >= 50 {
|
||||
return meta.RawLines[rMeta.HeaderLineIdx][:50], [][]string{}, nil
|
||||
}
|
||||
return meta.RawLines[rMeta.HeaderLineIdx], [][]string{}, nil
|
||||
|
||||
case database.TableReadDataMethodAll:
|
||||
return meta.RawLines[rMeta.HeaderLineIdx], meta.RawLines[rMeta.StartLineIdx:], nil
|
||||
default:
|
||||
logs.CtxInfof(ctx, "[parseSchemaInfo] reader method is:%d", rMeta.ReaderMethod)
|
||||
}
|
||||
|
||||
return nil, nil, fmt.Errorf("reader method is:%d", rMeta.ReaderMethod)
|
||||
}
|
||||
|
||||
sampleData, header, err = t.GetExcelToParseTableRange(ctx, meta.ExcelFile, sheetIdx, int64(sheetRowTotal), rMeta)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
return header, sampleData, nil
|
||||
}
|
||||
|
||||
func (t *TosTableParser) GetExcelToParseTableRange(ctx context.Context, file *excelize.File, sheetIdx int, rowCount int64, rMeta entity.TableReaderMeta) ([][]string, []string, error) {
|
||||
selectFunc := func(idx int64) (isContinue, isBreak bool) {
|
||||
return idx < rMeta.StartLineIdx, false
|
||||
}
|
||||
if rMeta.ReaderMethod == database.TableReadDataMethodHead {
|
||||
selectFunc = func(idx int64) (isContinue, isBreak bool) {
|
||||
return idx < rMeta.StartLineIdx, idx-rMeta.StartLineIdx > rMeta.ReadLineCnt
|
||||
}
|
||||
}
|
||||
|
||||
selectedExcelContent := make([][]string, 0)
|
||||
sheetName := file.GetSheetName(sheetIdx)
|
||||
rows, err := file.Rows(sheetName)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
headLineContent := make([]string, 0)
|
||||
var (
|
||||
curRowIndex int64
|
||||
columnCount int
|
||||
)
|
||||
for rows.Next() {
|
||||
if curRowIndex < rMeta.HeaderLineIdx {
|
||||
curRowIndex++
|
||||
continue
|
||||
}
|
||||
|
||||
if curRowIndex == rMeta.HeaderLineIdx {
|
||||
content, rowErr := rows.Columns()
|
||||
if rowErr != nil {
|
||||
return nil, nil, rowErr
|
||||
}
|
||||
if len(content) > 50 {
|
||||
content = content[:50]
|
||||
}
|
||||
headLineContent = content
|
||||
curRowIndex++
|
||||
columnCount = len(headLineContent)
|
||||
if rMeta.ReaderMethod == database.TableReadDataMethodOnlyHeader {
|
||||
return [][]string{}, headLineContent, nil
|
||||
}
|
||||
continue
|
||||
}
|
||||
|
||||
isContinue, isBreak := selectFunc(curRowIndex)
|
||||
if isContinue {
|
||||
curRowIndex++
|
||||
continue
|
||||
}
|
||||
if isBreak {
|
||||
break
|
||||
}
|
||||
curRowIndex++
|
||||
|
||||
columns, err := rows.Columns()
|
||||
if err != nil {
|
||||
continue
|
||||
}
|
||||
|
||||
if len(columns) < columnCount {
|
||||
emptyStrs := make([]string, columnCount-len(columns))
|
||||
columns = append(columns, emptyStrs...)
|
||||
}
|
||||
if len(columns) > 50 {
|
||||
columns = columns[:50]
|
||||
}
|
||||
|
||||
if len(columns) != 0 && getCharCount(columns) > 0 {
|
||||
selectedExcelContent = append(selectedExcelContent, columns)
|
||||
}
|
||||
}
|
||||
|
||||
return selectedExcelContent, headLineContent, nil
|
||||
}
|
||||
|
||||
func getCharCount(strs []string) int {
|
||||
var count int
|
||||
for _, str := range strs {
|
||||
count += len(str)
|
||||
}
|
||||
|
||||
return count
|
||||
}
|
||||
|
||||
type TmpFileCallback func(context.Context, string, ...interface{}) (interface{}, error)
|
||||
|
||||
func getTmpFile(extension string) string {
|
||||
return fmt.Sprintf("%s/%s", "/tmp", getTmpFileName(extension))
|
||||
}
|
||||
|
||||
func getTmpFileName(extension string) string {
|
||||
r := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
name := fmt.Sprintf("%s_%d_%d.%s", "dataset_", time.Now().UnixMilli(), r.Intn(10000), extension)
|
||||
return name
|
||||
}
|
||||
|
||||
func HandleTmpFile(ctx context.Context, reader io.Reader, extension string, callback TmpFileCallback, args ...interface{}) (interface{}, error) {
|
||||
tmpFile := getTmpFile(extension)
|
||||
file, err := os.OpenFile(tmpFile, os.O_RDWR|os.O_CREATE|os.O_TRUNC, 0o755)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if reader != nil {
|
||||
_, err = io.Copy(file, reader)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
if err = file.Close(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
defer func() {
|
||||
if err = os.Remove(tmpFile); err != nil {
|
||||
logs.CtxErrorf(ctx, "[HandleTmpFile]Error removing tmpFile: %v", err)
|
||||
return
|
||||
}
|
||||
}()
|
||||
result, err := callback(ctx, tmpFile, args...)
|
||||
return result, err
|
||||
}
|
||||
|
||||
func getXlsLocalSheetMetaWithTmpFileCallback(ctx context.Context, tmpFile string, args ...interface{}) (interface{}, error) {
|
||||
const prefix = "[getXlsLocalSheetMetaWithTmpFileCallback]"
|
||||
defer func() {
|
||||
if panicErr := recover(); panicErr != nil {
|
||||
s := string(debug.Stack())
|
||||
logs.CtxErrorf(ctx, "%s get recover, stack: %s", prefix, s)
|
||||
return
|
||||
}
|
||||
}()
|
||||
size, _ := args[0].(int64)
|
||||
file, err := os.Open(tmpFile)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
defer func() {
|
||||
if err = file.Close(); err != nil {
|
||||
logs.CtxErrorf(ctx, "%v close excel reader failed:%+v", prefix, err)
|
||||
return
|
||||
}
|
||||
}()
|
||||
xlFile, err := xls.OpenReader(file, "utf-8")
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
sheet := xlFile.GetSheet(0)
|
||||
if sheet == nil {
|
||||
return nil, errorx.New(errno.ErrMemoryDatabaseXlsSheetEmpty)
|
||||
}
|
||||
|
||||
records := make([][]string, 0)
|
||||
if sheet.MaxRow < 1 {
|
||||
return nil, errorx.New(errno.ErrMemoryDatabaseXlsSheetEmpty)
|
||||
}
|
||||
for i := 0; i <= int(sheet.MaxRow); i++ {
|
||||
row := sheet.Row(i)
|
||||
record := make([]string, row.LastCol()-row.FirstCol()+1)
|
||||
for j := row.FirstCol(); j <= row.LastCol(); j++ {
|
||||
record[j-row.FirstCol()] = row.Col(j)
|
||||
}
|
||||
records = append(records, record)
|
||||
}
|
||||
|
||||
return &entity.LocalTableMeta{
|
||||
RawLines: records,
|
||||
SheetsNameList: []string{"default"},
|
||||
SheetsRowCount: []int{len(records)},
|
||||
ExtensionName: "xls",
|
||||
FileSize: size,
|
||||
}, nil
|
||||
}
|
||||
|
||||
func (t *TosTableParser) PredictColumnType(columns []*common.DocTableColumn, sampleData [][]string, sheetIdx, startLineIdx int64) ([]*common.DocTableColumn, error) {
|
||||
if len(sampleData) == 0 {
|
||||
for _, column := range columns {
|
||||
column.ColumnType = common.ColumnTypePtr(common.ColumnType_Text) // 兜底展示
|
||||
column.ContainsEmptyValue = ptr.Of(true)
|
||||
}
|
||||
return columns, nil
|
||||
}
|
||||
|
||||
columnInfos, err := ParseDocTableColumnInfo(sampleData, len(columns))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if len(columns) != len(columnInfos) {
|
||||
return nil, errorx.New(errno.ErrMemoryDatabaseColumnNotMatch, errorx.KVf("msg", "columnType length is not match with column count, column length:%d, predict column length:%d", len(columns), len(columnInfos)))
|
||||
}
|
||||
|
||||
for i := range columns {
|
||||
columns[i].ContainsEmptyValue = &columnInfos[i].ContainsEmptyValue
|
||||
columns[i].ColumnType = &columnInfos[i].ColumnType
|
||||
}
|
||||
return columns, nil
|
||||
}
|
||||
|
||||
func ParseDocTableColumnInfo(selectedExcelContent [][]string, columnCount int) ([]entity.ColumnInfo, error) {
|
||||
columnList := transposeExcelContent(selectedExcelContent, columnCount)
|
||||
columInfoList := make([]entity.ColumnInfo, 0)
|
||||
for _, col := range columnList {
|
||||
columnType, containsEmptyValue := predictColumnType(col)
|
||||
columInfoList = append(columInfoList, entity.ColumnInfo{
|
||||
ColumnType: columnType,
|
||||
ContainsEmptyValue: containsEmptyValue,
|
||||
})
|
||||
}
|
||||
|
||||
return columInfoList, nil
|
||||
}
|
||||
|
||||
func transposeExcelContent(excelContent [][]string, columnCount int) [][]string {
|
||||
if len(excelContent) == 0 {
|
||||
return make([][]string, 0)
|
||||
}
|
||||
|
||||
rowCount := len(excelContent)
|
||||
transposedExcelContent := make([][]string, columnCount)
|
||||
for i := range transposedExcelContent {
|
||||
transposedExcelContent[i] = make([]string, rowCount)
|
||||
}
|
||||
|
||||
for i := range excelContent {
|
||||
for j := range excelContent[i] {
|
||||
if j >= columnCount {
|
||||
continue
|
||||
}
|
||||
transposedExcelContent[j][i] = excelContent[i][j]
|
||||
}
|
||||
}
|
||||
|
||||
return transposedExcelContent
|
||||
}
|
||||
|
||||
func predictColumnType(columnContent []string) (common.ColumnType, bool) {
|
||||
columnType := common.ColumnType_Text
|
||||
containsEmptyValue := false
|
||||
for i, col := range columnContent {
|
||||
if col == "" {
|
||||
containsEmptyValue = true
|
||||
continue
|
||||
}
|
||||
|
||||
cellType := GetCellType(col)
|
||||
if i == 0 {
|
||||
columnType = cellType
|
||||
continue
|
||||
}
|
||||
|
||||
if GetColumnTypeCategory(columnType) != GetColumnTypeCategory(cellType) {
|
||||
return common.ColumnType_Text, containsEmptyValue
|
||||
}
|
||||
|
||||
if GetColumnTypePriority(cellType) < GetColumnTypePriority(columnType) {
|
||||
columnType = cellType
|
||||
}
|
||||
}
|
||||
return columnType, containsEmptyValue
|
||||
}
|
||||
|
||||
func GetColumnTypePriority(columnType common.ColumnType) int64 {
|
||||
for _, identifier := range identifierChain {
|
||||
if identifier.TargetColumnType == columnType {
|
||||
return identifier.Priority
|
||||
}
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
func GetColumnTypeCategory(columnType common.ColumnType) database.ColumnTypeCategory {
|
||||
if columnType == common.ColumnType_Number || columnType == common.ColumnType_Float {
|
||||
return database.ColumnTypeCategoryNumber
|
||||
}
|
||||
return database.ColumnTypeCategoryText
|
||||
}
|
||||
|
||||
func GetCellType(cellValue string) common.ColumnType {
|
||||
InitIdentifier()
|
||||
cellTypeResult := common.ColumnType_Text
|
||||
for _, identifier := range identifierChain {
|
||||
cellType := identifier.IdentifyCellType(cellValue)
|
||||
if cellType != nil {
|
||||
cellTypeResult = *cellType
|
||||
break
|
||||
}
|
||||
}
|
||||
return cellTypeResult
|
||||
}
|
||||
|
||||
func IdentifyNumber(cellValue string) *common.ColumnType {
|
||||
_, err := strconv.ParseInt(cellValue, 10, 64)
|
||||
if err != nil {
|
||||
return nil
|
||||
}
|
||||
return common.ColumnTypePtr(common.ColumnType_Number)
|
||||
}
|
||||
|
||||
func IdentifyFloat(cellValue string) *common.ColumnType {
|
||||
_, err := strconv.ParseFloat(cellValue, 64)
|
||||
if err != nil {
|
||||
return nil
|
||||
}
|
||||
return common.ColumnTypePtr(common.ColumnType_Float)
|
||||
}
|
||||
|
||||
func IdentifyBoolean(cellValue string) *common.ColumnType {
|
||||
lowerCellValue := strings.ToLower(cellValue)
|
||||
if lowerCellValue != "true" && lowerCellValue != "false" {
|
||||
return nil
|
||||
}
|
||||
return common.ColumnTypePtr(common.ColumnType_Boolean)
|
||||
}
|
||||
|
||||
func IdentifyDate(cellValue string) *common.ColumnType {
|
||||
matched, err := regexp.MatchString(dateTimePattern, cellValue)
|
||||
if err != nil || !matched {
|
||||
return nil
|
||||
}
|
||||
return common.ColumnTypePtr(common.ColumnType_Date)
|
||||
}
|
||||
|
||||
func IdentifyText(cellValue string) *common.ColumnType {
|
||||
return common.ColumnTypePtr(common.ColumnType_Text)
|
||||
}
|
||||
|
||||
func InitIdentifier() {
|
||||
initIdentifierOnce.Do(func() {
|
||||
identifierChain = []CellTypeIdentifier{
|
||||
{
|
||||
Priority: 5,
|
||||
IdentifyCellType: IdentifyNumber,
|
||||
TargetColumnType: common.ColumnType_Number,
|
||||
},
|
||||
{
|
||||
Priority: 4,
|
||||
IdentifyCellType: IdentifyFloat,
|
||||
TargetColumnType: common.ColumnType_Float,
|
||||
},
|
||||
{
|
||||
Priority: 3,
|
||||
IdentifyCellType: IdentifyBoolean,
|
||||
TargetColumnType: common.ColumnType_Boolean,
|
||||
},
|
||||
{
|
||||
Priority: 2,
|
||||
IdentifyCellType: IdentifyDate,
|
||||
TargetColumnType: common.ColumnType_Date,
|
||||
},
|
||||
{
|
||||
Priority: 1,
|
||||
IdentifyCellType: IdentifyText,
|
||||
TargetColumnType: common.ColumnType_Text,
|
||||
},
|
||||
}
|
||||
|
||||
sort.SliceStable(identifierChain, func(i, j int) bool {
|
||||
return identifierChain[i].Priority > identifierChain[j].Priority
|
||||
})
|
||||
|
||||
datePatternList := []string{
|
||||
"(\\d{2,4})\\/(0?[1-9]|1[0-2])\\/(0?[1-9]|[1-2]\\d|3[0-1])",
|
||||
"(\\d{2,4})-(0?[1-9]|1[0-2])-(0?[1-9]|[1-2]\\d|3[0-1])",
|
||||
"(\\d{2,4})\\.(0?[1-9]|1[0-2])\\.(0?[1-9]|[1-2]\\d|3[0-1])",
|
||||
"(\\d{2,4})年(0?[1-9]|1[0-2])月(0?[1-9]|[1-2]\\d|3[0-1])日",
|
||||
}
|
||||
|
||||
timePatternList := []string{
|
||||
"([0-1]?\\d|2[0-3]):[0-5]\\d(:[0-5]\\d)?",
|
||||
"([0-1]?\\d|2[0-3])时[0-5]\\d分([0-5]\\d秒)?",
|
||||
"(0?\\d|1[0-2]):[0-5]\\d(:[0-5]\\d)? (am|AM|pm|PM)",
|
||||
"(0?\\d|1[0-2])时[0-5]\\d分([0-5]\\d秒)? (am|AM|pm|PM)",
|
||||
}
|
||||
|
||||
dateTimePattern = getDateTimeRegExp(datePatternList, timePatternList)
|
||||
})
|
||||
}
|
||||
|
||||
func getDateTimeRegExp(datePatternList []string, timePatterList []string) string {
|
||||
var (
|
||||
datePattern string
|
||||
timePattern string
|
||||
)
|
||||
|
||||
for _, p := range datePatternList {
|
||||
p = fmt.Sprintf("(%s)", p)
|
||||
if datePattern == "" {
|
||||
datePattern = p
|
||||
continue
|
||||
}
|
||||
datePattern = fmt.Sprintf("%s|%s", datePattern, p)
|
||||
}
|
||||
|
||||
for _, p := range timePatterList {
|
||||
p = fmt.Sprintf("(%s)", p)
|
||||
if timePattern == "" {
|
||||
timePattern = p
|
||||
continue
|
||||
}
|
||||
timePattern = fmt.Sprintf("%s|%s", timePattern, p)
|
||||
}
|
||||
|
||||
return fmt.Sprintf("^(%s)( +(%s))?$", datePattern, timePattern)
|
||||
}
|
||||
|
||||
func (t *TosTableParser) TransferPreviewData(ctx context.Context, columns []*common.DocTableColumn, sampleData [][]string, previewLine int) (previewData []map[int64]string, err error) {
|
||||
previewData = make([]map[int64]string, 0)
|
||||
|
||||
for idx, line := range sampleData {
|
||||
if idx >= previewLine {
|
||||
break
|
||||
}
|
||||
lineValue := make(map[int64]string)
|
||||
if len(columns) != len(line) {
|
||||
logs.CtxWarnf(ctx, "[TransferPreviewData] sampleData's length:%d is not match with column count:%d", len(line), len(columns))
|
||||
}
|
||||
|
||||
for i, value := range line {
|
||||
if i >= len(columns) {
|
||||
break
|
||||
}
|
||||
lineValue[int64(i)] = value
|
||||
}
|
||||
previewData = append(previewData, lineValue)
|
||||
}
|
||||
|
||||
return previewData, nil
|
||||
}
|
||||
|
||||
func CheckSheetIsValid(fields []*database.FieldItem, parsedColumns []*common.DocTableColumn, sheet *entity.ExcelExtraInfo) (bool, *string) {
|
||||
if len(fields) != len(parsedColumns) {
|
||||
return false, ptr.Of("field number not match")
|
||||
}
|
||||
if len(parsedColumns) > 20 {
|
||||
return false, ptr.Of("field number exceed 20")
|
||||
}
|
||||
if sheet.Sheets[0].TotalRow > 100000 {
|
||||
return false, ptr.Of("data rows exceed 100000")
|
||||
}
|
||||
|
||||
equalColumns := map[string]int{}
|
||||
for _, field := range fields {
|
||||
for _, column := range parsedColumns {
|
||||
if field.Name == column.ColumnName {
|
||||
equalColumns[field.Name] = 1
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if len(equalColumns) != len(fields) {
|
||||
return false, ptr.Of("field name not match")
|
||||
}
|
||||
|
||||
return true, nil
|
||||
}
|
||||
Reference in New Issue
Block a user