fix: filter task by project (#20195)

Co-authored-by: Qiu Jian <qiujian@yunionyun.com>
This commit is contained in:
Jian Qiu
2024-05-04 11:58:07 +08:00
committed by GitHub
co-authored by Qiu Jian
parent 8b5afbf995
commit 5b80297de2
18 changed files with 724 additions and 229 deletions
+63 -24
View File
@@ -15,41 +15,80 @@
package misc
import (
"fmt"
"yunion.io/x/jsonutils"
"yunion.io/x/onecloud/pkg/apis"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/mcclient/modulebase"
"yunion.io/x/onecloud/pkg/mcclient/modules/compute"
"yunion.io/x/onecloud/pkg/mcclient/modules/devtool"
"yunion.io/x/onecloud/pkg/mcclient/modules/identity"
"yunion.io/x/onecloud/pkg/mcclient/modules/image"
"yunion.io/x/onecloud/pkg/mcclient/modules/k8s"
"yunion.io/x/onecloud/pkg/mcclient/modules/notify"
)
func init() {
type RegionTaskListOptions struct {
ObjName string `help:"object name"`
ObjId string `help:"object id"`
TaskName string `help:"task name"`
cmds := []struct {
service string
manager modulebase.Manager
}{
{
service: "region",
manager: &compute.ComputeTasks,
},
{
service: "devtool",
manager: &devtool.DevtoolTasks,
},
{
service: "image",
manager: &image.Tasks,
},
{
service: "identity",
manager: &identity.Tasks,
},
{
service: "k8s",
manager: k8s.KubeTasks,
},
{
service: "notify",
manager: &notify.Tasks,
},
}
R(&RegionTaskListOptions{}, "region-task-list", "List tasks on region server", func(s *mcclient.ClientSession, args *RegionTaskListOptions) error {
params := jsonutils.Marshal(args)
result, err := compute.ComputeTasks.List(s, params)
if err != nil {
return err
for i := range cmds {
c := cmds[i]
type TaskListOptions struct {
apis.TaskListInput
}
printList(result, compute.ComputeTasks.GetColumns(s))
return nil
})
R(&TaskListOptions{}, fmt.Sprintf("%s-task-list", c.service), "List tasks on region server", func(s *mcclient.ClientSession, args *TaskListOptions) error {
params := jsonutils.Marshal(args)
result, err := c.manager.List(s, params)
if err != nil {
return err
}
printList(result, c.manager.GetColumns(s))
return nil
})
type RegionTaskShowOptions struct {
ID string `help:"ID or name of the task"`
type TaskShowOptions struct {
ID string `help:"ID or name of the task"`
}
R(&TaskShowOptions{}, "region-task-show", "Show details of a region task", func(s *mcclient.ClientSession, args *TaskShowOptions) error {
result, err := c.manager.GetById(s, args.ID, nil)
if err != nil {
return err
}
printObject(result)
return nil
})
}
R(&RegionTaskShowOptions{}, "region-task-show", "Show details of a region task", func(s *mcclient.ClientSession, args *RegionTaskShowOptions) error {
result, err := compute.ComputeTasks.Get(s, args.ID, nil)
if err != nil {
return err
}
printObject(result)
return nil
})
type TaskListOptions struct {
/*type TaskListOptions struct {
ObjName string `help:"object name"`
ObjId string `help:"object id"`
TaskName string `help:"task name"`
@@ -80,6 +119,6 @@ func init() {
}
printObject(result)
return nil
})
})*/
}
@@ -31,8 +31,8 @@ import (
"yunion.io/x/onecloud/pkg/cloudcommon/workmanager"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/mcclient/auth"
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/compute"
"yunion.io/x/onecloud/pkg/mcclient/modules/devtool"
"yunion.io/x/onecloud/pkg/util/ansible"
"yunion.io/x/onecloud/pkg/util/ansiblev2"
)
@@ -216,7 +216,7 @@ var PlaybookWorker *workmanager.SWorkManager
func taskFailed(ctx context.Context, reason string) {
if taskId := ctx.Value(appctx.APP_CONTEXT_KEY_TASK_ID); taskId != nil {
session := auth.GetAdminSessionWithInternal(ctx, "")
modules.TaskFailed(&compute.DevtoolTasks, session, taskId.(string), reason)
devtool.DevtoolTasks.TaskFailed2(session, taskId.(string), reason)
} else {
log.Warningf("Reqeuest task failed missing task id, with reason: %s", reason)
}
@@ -225,7 +225,7 @@ func taskFailed(ctx context.Context, reason string) {
func taskCompleted(ctx context.Context, data jsonutils.JSONObject) {
if taskId := ctx.Value(appctx.APP_CONTEXT_KEY_TASK_ID); taskId != nil {
session := auth.GetAdminSessionWithInternal(ctx, "")
modules.TaskComplete(&compute.DevtoolTasks, session, taskId.(string), data)
devtool.DevtoolTasks.TaskComplete(session, taskId.(string), data)
} else {
log.Warningf("Reqeuest task failed missing task id, with data: %v", data)
}
+64
View File
@@ -0,0 +1,64 @@
// Copyright 2019 Yunion
//
// 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 apis
import (
"time"
"yunion.io/x/jsonutils"
)
type TaskListInput struct {
ModelBaseListInput
ProjectizedResourceListInput
Id []string `json:"id" help:"id filter"`
ObjId []string `json:"obj_id" help:"object id filter"`
ObjName []string `json:"obj_name" help:"object type (in singular form) filter"`
TaskName []string `json:"task_name" help:"task name filter"`
IsMulti *bool `json:"is_multi" negative:"is_single" help:"is multi task"`
IsComplete *bool `json:"is_complete" negative:"not_complete" help:"is task completed, either fail or complete"`
IsInit *bool `json:"is_init" negative:"not_init" help:"is task started?"`
Stage []string `json:"stage" help:"task stage"`
ParentId []string `json:"parent_id" help:"filter tasks by parent_task_id"`
IsRoot *bool `json:"is_root" help:"filter root tasks"`
}
type TaskDetails struct {
ModelBaseDetails
ProjectizedResourceInfo
// 资源创建时间
CreatedAt time.Time `json:"created_at"`
// 资源更新时间
UpdatedAt time.Time `json:"updated_at"`
// 资源被更新次数
UpdateVersion int `json:"update_version"`
// 开始任务时间
StartAt time.Time `json:"start_at"`
// 完成任务时间
EndAt time.Time `json:"end_at"`
DomainId string `json:"domain_id"`
ProjectId string `json:"tenant_id"`
Id string
ObjName string
ObjId string
TaskName string
Params *jsonutils.JSONDict
Stage string
ParentTaskId string
}
+2 -1
View File
@@ -297,7 +297,8 @@ func ValidateProjectizedResourceInput(ctx context.Context, input apis.Projectize
}
func (manager *SProjectizedResourceBaseManager) ListItemExportKeys(ctx context.Context, q *sqlchemy.SQuery, userCred mcclient.TokenCredential, keys stringutils2.SSortedStrings) (*sqlchemy.SQuery, error) {
q, err := manager.SDomainizedResourceBaseManager.ListItemExportKeys(ctx, q, userCred, keys)
var err error
q, err = manager.SDomainizedResourceBaseManager.ListItemExportKeys(ctx, q, userCred, keys)
if err != nil {
return nil, errors.Wrap(err, "SDomainizedResourceBaseManager.ListItemExportKeys")
}
+52
View File
@@ -15,15 +15,24 @@
package taskman
import (
"context"
"database/sql"
"yunion.io/x/jsonutils"
"yunion.io/x/log"
"yunion.io/x/pkg/errors"
"yunion.io/x/pkg/util/rbacscope"
"yunion.io/x/sqlchemy"
"yunion.io/x/onecloud/pkg/cloudcommon/db"
"yunion.io/x/onecloud/pkg/httperrors"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/util/stringutils2"
)
type STaskObjectManager struct {
db.SModelBaseManager
db.SProjectizedResourceBaseManager
}
var TaskObjectManager *STaskObjectManager
@@ -34,6 +43,7 @@ func init() {
type STaskObject struct {
db.SModelBase
db.SProjectizedResourceBase
TaskId string `width:"36" charset:"ascii" nullable:"false" primary:"true" index:"true"` // Column(VARCHAR(36, charset='ascii'), nullable=False, primary_key=True, index=True)
ObjId string `width:"36" charset:"ascii" nullable:"false" primary:"true"` // Column(VARCHAR(36, charset='ascii'), nullable=False, primary_key=True)
@@ -62,3 +72,45 @@ func (manager *STaskObjectManager) GetObjectIds(task *STask) []string {
}
return ret
}
func (manager *STaskObjectManager) FetchOwnerId(ctx context.Context, data jsonutils.JSONObject) (mcclient.IIdentityProvider, error) {
return manager.SProjectizedResourceBaseManager.FetchOwnerId(ctx, data)
}
func (manager *STaskObjectManager) FilterByOwner(ctx context.Context, q *sqlchemy.SQuery, man db.FilterByOwnerProvider, userCred mcclient.TokenCredential, owner mcclient.IIdentityProvider, scope rbacscope.TRbacScope) *sqlchemy.SQuery {
return manager.SProjectizedResourceBaseManager.FilterByOwner(ctx, q, man, userCred, owner, scope)
}
func (manager *STaskObjectManager) ListItemExportKeys(ctx context.Context, q *sqlchemy.SQuery, userCred mcclient.TokenCredential, keys stringutils2.SSortedStrings) (*sqlchemy.SQuery, error) {
var err error
q, err = manager.SModelBaseManager.ListItemExportKeys(ctx, q, userCred, keys)
if err != nil {
return nil, errors.Wrap(err, "SModelBaseManager.ListItemExportKeys")
}
q, err = manager.SProjectizedResourceBaseManager.ListItemExportKeys(ctx, q, userCred, keys)
if err != nil {
return nil, errors.Wrap(err, "SProjectizedResourceBaseManager.ListItemExportKeys")
}
return q, nil
}
func (manager *STaskObjectManager) QueryDistinctExtraField(q *sqlchemy.SQuery, field string) (*sqlchemy.SQuery, error) {
var err error
q, err = manager.SModelBaseManager.QueryDistinctExtraField(q, field)
if err == nil {
return q, nil
}
q, err = manager.SProjectizedResourceBaseManager.QueryDistinctExtraField(q, field)
if err == nil {
return q, nil
}
return q, httperrors.ErrNotFound
}
func (manager *STaskObjectManager) ResourceScope() rbacscope.TRbacScope {
return manager.SProjectizedResourceBaseManager.ResourceScope()
}
func (taskObj *STaskObject) GetOwnerId() mcclient.IIdentityProvider {
return taskObj.SProjectizedResourceBase.GetOwnerId()
}
+265 -48
View File
@@ -49,6 +49,7 @@ import (
"yunion.io/x/onecloud/pkg/mcclient/auth"
"yunion.io/x/onecloud/pkg/mcclient/modules/yunionconf"
"yunion.io/x/onecloud/pkg/util/logclient"
"yunion.io/x/onecloud/pkg/util/stringutils2"
)
const (
@@ -72,31 +73,50 @@ const (
)
type STaskManager struct {
db.SResourceBaseManager
db.SModelBaseManager
db.SProjectizedResourceBaseManager
}
var TaskManager *STaskManager
func init() {
TaskManager = &STaskManager{
SResourceBaseManager: db.NewResourceBaseManager(STask{}, "tasks_tbl", "task", "tasks")}
SModelBaseManager: db.NewModelBaseManager(STask{}, "tasks_tbl", "task", "tasks"),
}
TaskManager.SetVirtualObject(TaskManager)
}
type STask struct {
db.SResourceBase
db.SModelBase
db.SProjectizedResourceBase
// 资源创建时间
CreatedAt time.Time `nullable:"false" created_at:"true" index:"true" get:"user" list:"user" json:"created_at"`
// 资源更新时间
UpdatedAt time.Time `nullable:"false" updated_at:"true" list:"user" json:"updated_at"`
// 资源被更新次数
UpdateVersion int `default:"0" nullable:"false" auto_version:"true" list:"user" json:"update_version"`
// 开始任务时间
StartAt time.Time `nullable:"true" list:"user" json:"start_at"`
// 完成任务时间
EndAt time.Time `nullable:"true" list:"user" json:"end_at"`
Id string `width:"36" charset:"ascii" primary:"true" list:"user"` // Column(VARCHAR(36, charset='ascii'), primary_key=True, default=get_uuid)
ObjName string `width:"128" charset:"utf8" nullable:"false" list:"user"` // Column(VARCHAR(128, charset='utf8'), nullable=False)
ObjId string `width:"128" charset:"ascii" nullable:"false" list:"user" index:"true"` // Column(VARCHAR(ID_LENGTH, charset='ascii'), nullable=False)
TaskName string `width:"64" charset:"ascii" nullable:"false" list:"user"` // Column(VARCHAR(64, charset='ascii'), nullable=False)
UserCred mcclient.TokenCredential `width:"1024" charset:"utf8" nullable:"false" get:"user"` // Column(VARCHAR(1024, charset='ascii'), nullable=False)
ObjName string `width:"128" charset:"utf8" nullable:"false" list:"user"` // Column(VARCHAR(128, charset='utf8'), nullable=False)
ObjId string `width:"128" charset:"ascii" nullable:"false" list:"user" index:"true"` // Column(VARCHAR(ID_LENGTH, charset='ascii'), nullable=False)
TaskName string `width:"64" charset:"ascii" nullable:"false" list:"user"` // Column(VARCHAR(64, charset='ascii'), nullable=False)
UserCred mcclient.TokenCredential `width:"1024" charset:"utf8" nullable:"false" get:"user"` // Column(VARCHAR(1024, charset='ascii'), nullable=False)
// OwnerCred string `width:"512" charset:"ascii" nullable:"true"` // Column(VARCHAR(512, charset='ascii'), nullable=True)
Params *jsonutils.JSONDict `charset:"utf8" length:"medium" nullable:"false" get:"user"` // Column(MEDIUMTEXT(charset='ascii'), nullable=False)
Stage string `width:"64" charset:"ascii" nullable:"false" default:"on_init" list:"user"` // Column(VARCHAR(64, charset='ascii'), nullable=False, default='on_init')
// 父任务时间
ParentTaskId string `width:"36" charset:"ascii" primary:"true" list:"user" index:"true" json:"parent_task_id"`
taskObject db.IStandaloneModel `ignore:"true"`
taskObjects []db.IStandaloneModel `ignore:"true"`
}
@@ -131,7 +151,6 @@ func (manager *STaskManager) PerformAction(ctx context.Context, userCred mcclien
return nil, errors.Wrapf(err, "runTask")
}
resp := jsonutils.NewDict()
// 'result': 'ok'
resp.Add(jsonutils.NewString("ok"), "result")
return resp, nil
}
@@ -143,40 +162,38 @@ func (manager *STask) PreCheckPerformAction(
return nil
}
func (self *STask) GetOwnerId() mcclient.IIdentityProvider {
owner := db.SOwnerId{DomainId: self.UserCred.GetProjectDomainId(), Domain: self.UserCred.GetProjectDomain(),
ProjectId: self.UserCred.GetProjectId(), Project: self.UserCred.GetProjectName()}
return &owner
func (task *STask) GetOwnerId() mcclient.IIdentityProvider {
return task.SProjectizedResourceBase.GetOwnerId()
}
func (manager *STaskManager) FilterByOwner(ctx context.Context, q *sqlchemy.SQuery, man db.FilterByOwnerProvider, userCred mcclient.TokenCredential, owner mcclient.IIdentityProvider, scope rbacscope.TRbacScope) *sqlchemy.SQuery {
if owner != nil {
switch scope {
case rbacscope.ScopeProject:
if len(owner.GetProjectId()) > 0 {
q = q.Contains("user_cred", owner.GetProjectId())
}
case rbacscope.ScopeDomain:
if len(owner.GetProjectDomainId()) > 0 {
q = q.Contains("user_cred", owner.GetProjectDomainId())
}
}
objectQAltered := false
objectQ := TaskObjectManager.Query().Snapshot()
objectQ = TaskObjectManager.SProjectizedResourceBaseManager.FilterByOwner(ctx, objectQ, man, userCred, owner, scope)
objectQAltered = objectQ.IsAltered()
objectQ = objectQ.AppendField(sqlchemy.DISTINCT("task_id", objectQ.Field("task_id")))
singleTaskQAltered := false
singleTaskQ := TaskManager.Query().NotEquals("obj_id", MULTI_OBJECTS_ID).Snapshot()
singleTaskQ = TaskManager.SProjectizedResourceBaseManager.FilterByOwner(ctx, singleTaskQ, man, userCred, owner, scope)
singleTaskQAltered = singleTaskQ.IsAltered()
singleTaskQ = singleTaskQ.AppendField(sqlchemy.DISTINCT("task_id", singleTaskQ.Field("id")))
if objectQAltered || singleTaskQAltered {
subQ := sqlchemy.Union(objectQ, singleTaskQ).Query().SubQuery()
q = q.Join(subQ, sqlchemy.Equals(q.Field("id"), subQ.Field("task_id")))
}
return q
}
func (manager *STaskManager) FetchOwnerId(ctx context.Context, data jsonutils.JSONObject) (mcclient.IIdentityProvider, error) {
return manager.SProjectizedResourceBaseManager.FetchOwnerId(ctx, data)
}
func (manager *STaskManager) FetchTaskById(taskId string) *STask {
return manager.fetchTask(taskId)
}
func (self *STask) AllowUpdateItem(ctx context.Context, userCred mcclient.TokenCredential) bool {
return false
}
func (self *STask) AllowDeleteItem(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, data jsonutils.JSONObject) bool {
return false
}
func (self *STask) ValidateDeleteCondition(ctx context.Context, info jsonutils.JSONObject) error {
return httperrors.NewForbiddenError("forbidden")
}
@@ -199,6 +216,19 @@ func (self *STask) GetName() string {
return self.TaskName
}
func (task *STask) saveStartAt() {
if !task.StartAt.IsZero() {
return
}
_, err := db.Update(task, func() error {
task.StartAt = timeutils.UtcNow()
return nil
})
if err != nil {
log.Errorf("task %s save start_at fail: %s", task.String(), err)
}
}
func fetchTaskParams(
ctx context.Context,
taskName string,
@@ -271,13 +301,21 @@ func (manager *STaskManager) NewTask(
data := fetchTaskParams(ctx, taskName, taskData, parentTaskId, parentTaskNotifyUrl, pendingUsage)
task := &STask{
ObjName: obj.Keyword(),
ObjId: obj.GetId(),
TaskName: taskName,
UserCred: userCred,
Params: data,
Stage: TASK_INIT_STAGE,
ObjName: obj.Keyword(),
ObjId: obj.GetId(),
TaskName: taskName,
UserCred: userCred,
Params: data,
Stage: TASK_INIT_STAGE,
ParentTaskId: parentTaskId,
}
ownerId := obj.GetOwnerId()
if ownerId != nil {
task.DomainId = ownerId.GetProjectDomainId()
task.ProjectId = ownerId.GetProjectId()
}
task.SetModelManager(manager, task)
err := manager.TableSpec().Insert(ctx, task)
if err != nil {
@@ -319,12 +357,13 @@ func (manager *STaskManager) NewParallelTask(
data := fetchTaskParams(ctx, taskName, taskData, parentTaskId, parentTaskNotifyUrl, pendingUsage)
task := &STask{
ObjName: objs[0].Keyword(),
ObjId: MULTI_OBJECTS_ID,
TaskName: taskName,
UserCred: userCred,
Params: data,
Stage: TASK_INIT_STAGE,
ObjName: objs[0].Keyword(),
ObjId: MULTI_OBJECTS_ID,
TaskName: taskName,
UserCred: userCred,
Params: data,
Stage: TASK_INIT_STAGE,
ParentTaskId: parentTaskId,
}
task.SetModelManager(manager, task)
err := manager.TableSpec().Insert(ctx, task)
@@ -333,8 +372,19 @@ func (manager *STaskManager) NewParallelTask(
return nil, err
}
for _, obj := range objs {
to := STaskObject{TaskId: task.Id, ObjId: obj.GetId()}
for i := range objs {
obj := objs[i]
to := STaskObject{
TaskId: task.Id,
ObjId: obj.GetId(),
}
ownerId := obj.GetOwnerId()
if ownerId != nil {
to.DomainId = ownerId.GetProjectDomainId()
to.ProjectId = ownerId.GetProjectId()
}
to.SetModelManager(TaskObjectManager, &to)
to.SetModelManager(TaskObjectManager, &to)
err := TaskObjectManager.TableSpec().Insert(ctx, &to)
if err != nil {
@@ -412,6 +462,8 @@ func execITask(taskValue reflect.Value, task *STask, odata jsonutils.JSONObject,
ctxData := task.GetRequestContext()
ctx := ctxData.GetContext()
task.saveStartAt()
taskFailed := false
var data jsonutils.JSONObject
@@ -589,8 +641,19 @@ func (self *STask) IsSubtask() bool {
return self.HasParentTask()
}
func (self *STask) HasParentTask() bool {
func (self *STask) GetParentTaskId() string {
if len(self.ParentTaskId) > 0 {
return self.ParentTaskId
}
parentTaskId, _ := self.Params.GetString(PARENT_TASK_ID_KEY)
if len(parentTaskId) > 0 {
return parentTaskId
}
return ""
}
func (self *STask) HasParentTask() bool {
parentTaskId := self.GetParentTaskId()
if len(parentTaskId) > 0 {
return true
}
@@ -598,7 +661,7 @@ func (self *STask) HasParentTask() bool {
}
func (self *STask) GetParentTask() *STask {
parentTaskId, _ := self.Params.GetString(PARENT_TASK_ID_KEY)
parentTaskId := self.GetParentTaskId()
if len(parentTaskId) > 0 {
return TaskManager.fetchTask(parentTaskId)
}
@@ -623,6 +686,7 @@ func (self *STask) SaveRequestContext(data *appctx.AppContextData) {
params := self.Params.CopyExcludes(REQUEST_CONTEXT_KEY)
params.Add(jsonData, REQUEST_CONTEXT_KEY)
self.Params = params
self.EndAt = timeutils.UtcNow()
return nil
})
log.Debugf("Params: %s", self.Params)
@@ -715,7 +779,7 @@ func (self *STask) SetStageFailed(ctx context.Context, reason jsonutils.JSONObje
func (self *STask) NotifyParentTaskComplete(ctx context.Context, body *jsonutils.JSONDict, failed bool) {
log.Infof("notify_parent_task_complete: %s params %s", self.TaskName, self.Params)
parentTaskId, _ := self.Params.GetString(PARENT_TASK_ID_KEY)
parentTaskId := self.GetParentTaskId()
parentTaskNotify, _ := self.Params.GetString(PARENT_TASK_NOTIFY_KEY)
if len(parentTaskId) > 0 {
subTask := SubTaskManager.GetSubTask(parentTaskId, self.Id)
@@ -771,6 +835,7 @@ func (self *STask) NotifyParentTaskFailure(ctx context.Context, reason jsonutils
func (self *STask) IsCurrentStageComplete() bool {
totalSubtasks := SubTaskManager.GetTotalSubtasks(self.Id, self.Stage, "")
initSubtasks := SubTaskManager.GetInitSubtasks(self.Id, self.Stage)
log.Debugf("Task %s IsCurrentStageComplete totalSubtasks %d initSubtasks %d ", self.String(), len(totalSubtasks), len(initSubtasks))
if len(totalSubtasks) > 0 && len(initSubtasks) == 0 {
return true
} else {
@@ -862,6 +927,10 @@ func (task *STask) GetTaskRequestHeader() http.Header {
return header
}
func (task *STask) String() string {
return fmt.Sprintf("%s(%s,%s)", task.Id, task.TaskName, task.Stage)
}
var serviceUrl string
func SetServiceUrl(url string) {
@@ -947,3 +1016,151 @@ func (manager *STaskManager) FetchTasksOfObject(obj db.IStandaloneModel, since t
}
return tasks, nil
}
// 操作日志列表
func (manager *STaskManager) ListItemFilter(
ctx context.Context,
q *sqlchemy.SQuery,
userCred mcclient.TokenCredential,
input apis.TaskListInput,
) (*sqlchemy.SQuery, error) {
var err error
q, err = manager.SModelBaseManager.ListItemFilter(ctx, q, userCred, input.ModelBaseListInput)
if err != nil {
return q, errors.Wrap(err, "SResourceBaseManager.ListItemFilter")
}
if len(input.Id) > 0 {
q = q.In("id", input.Id)
}
if len(input.ObjId) > 0 {
taskObjsQ := TaskObjectManager.Query().In("obj_id", input.ObjId)
taskObjsQ = taskObjsQ.AppendField(sqlchemy.DISTINCT("task_id", taskObjsQ.Field("task_id")))
tasksQ := TaskManager.Query().In("obj_id", input.ObjId)
tasksQ = tasksQ.AppendField(tasksQ.Field("id").Label("task_id"))
taskIdQ := sqlchemy.Union(taskObjsQ, tasksQ).Query().SubQuery()
q = q.Join(taskIdQ, sqlchemy.Equals(taskIdQ.Field("task_id"), q.Field("id")))
}
if len(input.ObjName) > 0 {
q = q.In("obj_name", input.ObjName)
}
if len(input.TaskName) > 0 {
q = q.In("task_name", input.TaskName)
}
if len(input.Stage) > 0 {
q = q.In("stage", input.Stage)
}
if len(input.ParentId) > 0 {
q = q.In("parent_task_id", input.ParentId)
}
if input.IsComplete != nil {
if *input.IsComplete {
q = q.In("stage", []string{TASK_STAGE_FAILED, TASK_STAGE_COMPLETE})
} else {
q = q.NotIn("stage", []string{TASK_STAGE_FAILED, TASK_STAGE_COMPLETE})
}
}
if input.IsInit != nil {
if *input.IsInit {
q = q.Equals("stage", TASK_INIT_STAGE)
} else {
q = q.NotEquals("stage", TASK_INIT_STAGE)
}
}
if input.IsMulti != nil {
if *input.IsMulti {
q = q.Equals("obj_id", MULTI_OBJECTS_ID)
} else {
q = q.NotEquals("obj_id", MULTI_OBJECTS_ID)
}
}
if input.IsRoot != nil {
if *input.IsRoot {
q = q.IsNullOrEmpty("parent_task_id")
} else {
q = q.IsNotEmpty("parent_task_id")
}
}
q.DebugQuery2("taskQuery")
return q, nil
}
func (manager *STaskManager) ListItemExportKeys(ctx context.Context, q *sqlchemy.SQuery, userCred mcclient.TokenCredential, keys stringutils2.SSortedStrings) (*sqlchemy.SQuery, error) {
var err error
q, err = manager.SModelBaseManager.ListItemExportKeys(ctx, q, userCred, keys)
if err != nil {
return nil, errors.Wrap(err, "SModelBaseManager.ListItemExportKeys")
}
// q, err = manager.SProjectizedResourceBaseManager.ListItemExportKeys(ctx, q, userCred, keys)
// if err != nil {
// return nil, errors.Wrap(err, "SProjectizedResourceBaseManager.ListItemExportKeys")
// }
return q, nil
}
func (manager *STaskManager) QueryDistinctExtraField(q *sqlchemy.SQuery, field string) (*sqlchemy.SQuery, error) {
var err error
q, err = manager.SModelBaseManager.QueryDistinctExtraField(q, field)
if err == nil {
return q, nil
}
// q, err = manager.SProjectizedResourceBaseManager.QueryDistinctExtraField(q, field)
// if err == nil {
// return q, nil
// }
return q, httperrors.ErrNotFound
}
func (manager *STaskManager) ResourceScope() rbacscope.TRbacScope {
return manager.SProjectizedResourceBaseManager.ResourceScope()
}
func (manager *STaskManager) FetchCustomizeColumns(
ctx context.Context,
userCred mcclient.TokenCredential,
query jsonutils.JSONObject,
objs []interface{},
fields stringutils2.SSortedStrings,
isList bool,
) []apis.TaskDetails {
rows := make([]apis.TaskDetails, len(objs))
bases := manager.SModelBaseManager.FetchCustomizeColumns(ctx, userCred, query, objs, fields, isList)
projs := manager.SProjectizedResourceBaseManager.FetchCustomizeColumns(ctx, userCred, query, objs, fields, isList)
for i := range objs {
rows[i] = apis.TaskDetails{
ModelBaseDetails: bases[i],
ProjectizedResourceInfo: projs[i],
}
}
return rows
}
func (manager *STaskManager) OrderByExtraFields(
ctx context.Context,
q *sqlchemy.SQuery,
userCred mcclient.TokenCredential,
query apis.TaskListInput,
) (*sqlchemy.SQuery, error) {
var err error
q, err = manager.SModelBaseManager.OrderByExtraFields(ctx, q, userCred, query.ModelBaseListInput)
if err != nil {
return q, errors.Wrap(err, "SModelBaseManager.OrderByExtraField")
}
// q, err = manager.SProjectizedResourceBaseManager.OrderByExtraFields(ctx, q, userCred, query.ProjectizedResourceListInput)
// if err != nil {
// return q, errors.Wrap(err, "SProjectizedResourceBaseManager.OrderByExtraField")
// }
return q, nil
}
+1 -1
View File
@@ -119,7 +119,7 @@ func TaskComplete(ctx context.Context, params jsonutils.JSONObject) {
func K8sTaskFailed(ctx context.Context, reason string) {
if taskId := ctx.Value(appctx.APP_CONTEXT_KEY_TASK_ID); taskId != nil {
k8s.KubeTasks.TaskFailed(GetK8sSession(ctx), taskId.(string), reason)
k8s.KubeTasks.TaskFailed2(GetK8sSession(ctx), taskId.(string), reason)
} else {
log.Errorf("Reqeuest k8s task failed missing task id, with reason(%s)", reason)
}
+3 -79
View File
@@ -15,93 +15,17 @@
package compute
import (
"yunion.io/x/jsonutils"
"yunion.io/x/pkg/util/printutils"
"yunion.io/x/onecloud/pkg/apis"
"yunion.io/x/onecloud/pkg/httperrors"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/mcclient/modulebase"
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
)
var (
ComputeTasks TasksManager
DevtoolTasks TasksManager
)
type TasksManager struct {
modulebase.ResourceManager
}
var ComputeTasks tasks.TasksManager
func init() {
ComputeTasks = TasksManager{
ComputeTasks = tasks.TasksManager{
ResourceManager: modules.NewComputeManager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"}),
}
modules.RegisterCompute(&ComputeTasks)
DevtoolTasks = TasksManager{
ResourceManager: modules.NewDevtoolManager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"},
),
}
}
func (man TasksManager) TaskComplete(session *mcclient.ClientSession, taskId string, params jsonutils.JSONObject) {
modules.TaskComplete(&man, session, taskId, params)
}
func (man TasksManager) TaskFailed(session *mcclient.ClientSession, taskId string, err error) {
man.TaskFailed2(session, taskId, err.Error())
}
func (man TasksManager) TaskFailed2(session *mcclient.ClientSession, taskId string, reason string) {
man.TaskFailed3(session, taskId, reason, nil)
}
func (man TasksManager) TaskFailed3(session *mcclient.ClientSession, taskId string, reason string, params *jsonutils.JSONDict) {
if params == nil {
params = jsonutils.NewDict()
}
params.Add(jsonutils.NewString("error"), "__status__")
params.Add(jsonutils.NewString(reason), "__reason__")
man.TaskComplete(session, taskId, params)
}
func (self *TasksManager) getManager(session *mcclient.ClientSession, params jsonutils.JSONObject) (*modulebase.ResourceManager, error) {
serviceType := apis.SERVICE_TYPE_REGION
if params.Contains("service_type") {
serviceType, _ = params.GetString("service_type")
}
version := ""
switch serviceType {
case apis.SERVICE_TYPE_KEYSTONE:
version = "v3"
case apis.SERVICE_TYPE_REGION, apis.SERVICE_TYPE_NOTIFY:
version = "v2"
case apis.SERVICE_TYPE_IMAGE:
version = "v1"
}
_, err := session.GetServiceURL(serviceType, "")
if err != nil {
return nil, httperrors.NewNotFoundError("service %s not found error: %v", serviceType, err)
}
return &modulebase.ResourceManager{
BaseManager: *modulebase.NewBaseManager(serviceType, "", version, []string{}, []string{}),
Keyword: "task", KeywordPlural: "tasks",
}, nil
}
func (this *TasksManager) List(session *mcclient.ClientSession, params jsonutils.JSONObject) (*printutils.ListResult, error) {
man, err := this.getManager(session, params)
if err != nil {
return nil, err
}
return man.List(session, params)
}
+6 -5
View File
@@ -36,7 +36,7 @@ func init() {
[]string{"id", "ansible_playbook_id", "template_id", "server_id", "name", "day", "hour", "min", "sec", "interval", "start", "enabled", "created_at"},
[]string{},
)
modules.RegisterCompute(&DevToolCronjobs)
modules.Register(&DevToolCronjobs)
DevToolTemplates = modules.NewDevtoolManager(
"devtool_template",
@@ -44,7 +44,7 @@ func init() {
[]string{"id", "name", "domain_id", "tenant_id", "day", "hour", "min", "sec", "interval", "start", "enabled", "description"},
[]string{"is_system"},
)
modules.RegisterCompute(&DevToolTemplates)
modules.Register(&DevToolTemplates)
DevToolScripts = modules.NewDevtoolManager(
"script",
@@ -52,14 +52,15 @@ func init() {
[]string{"Id", "Name", "Type", "Playbook_Reference", "Max_Try_Times"},
[]string{},
)
modules.RegisterCompute(&DevToolScripts)
modules.Register(&DevToolScripts)
DevToolScriptApplyRecords = modules.NewDevtoolManager(
"scriptapplyrecord",
"scriptapplyrecords",
[]string{"Script_Id", "Server_Id", "Start_Time", "End_Time", "Reason", "Status"},
[]string{},
)
modules.RegisterCompute(&DevToolScriptApplyRecords)
modules.Register(&DevToolScriptApplyRecords)
DevToolSshInfos = modules.NewDevtoolManager(
"sshinfo",
@@ -67,7 +68,7 @@ func init() {
[]string{"Id", "Server_Id", "Server_Name", "Server_Hypervisor", "Forward_Id", "User", "Host", "Port", "Need_Clean", "Failed_Reason"},
[]string{},
)
modules.RegisterCompute(&DevToolSshInfos)
modules.Register(&DevToolSshInfos)
DevToolServiceUrls = modules.NewDevtoolManager(
"serviceurl",
+31
View File
@@ -0,0 +1,31 @@
// Copyright 2019 Yunion
//
// 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 devtool
import (
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
)
var DevtoolTasks tasks.TasksManager
func init() {
DevtoolTasks = tasks.TasksManager{
ResourceManager: modules.NewDevtoolManager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"},
),
}
}
@@ -0,0 +1,31 @@
// Copyright 2019 Yunion
//
// 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 identity
import (
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
)
var Tasks tasks.TasksManager
func init() {
Tasks = tasks.TasksManager{
ResourceManager: modules.NewIdentityV3Manager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"},
),
}
}
+31
View File
@@ -0,0 +1,31 @@
// Copyright 2019 Yunion
//
// 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 image
import (
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
)
var Tasks tasks.TasksManager
func init() {
Tasks = tasks.TasksManager{
ResourceManager: modules.NewImageManager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"},
),
}
}
+6 -15
View File
@@ -15,14 +15,11 @@
package k8s
import (
"yunion.io/x/jsonutils"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
)
var (
KubeTasks *KubeTasksManager
KubeTasks *tasks.TasksManager
)
type KubeTasksManager struct {
@@ -30,15 +27,9 @@ type KubeTasksManager struct {
}
func init() {
KubeTasks = &KubeTasksManager{
ResourceManager: *NewResourceManager("task", "tasks", NewColumns(), NewColumns("Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at")),
k8sResMan := NewResourceManager("task", "tasks", NewColumns(), NewColumns("Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"))
KubeTasks = &tasks.TasksManager{
ResourceManager: k8sResMan.GetBaseManager(),
}
}
func (m *KubeTasksManager) TaskComplete(session *mcclient.ClientSession, taskId string, params jsonutils.JSONObject) {
modules.TaskComplete(m, session, taskId, params)
}
func (m *KubeTasksManager) TaskFailed(session *mcclient.ClientSession, taskId string, reason string) {
modules.TaskFailed(m, session, taskId, reason)
}
+31
View File
@@ -0,0 +1,31 @@
// Copyright 2019 Yunion
//
// 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 notify
import (
"yunion.io/x/onecloud/pkg/mcclient/modules"
"yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
)
var Tasks tasks.TasksManager
func init() {
Tasks = tasks.TasksManager{
ResourceManager: modules.NewNotifyv2Manager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"},
),
}
}
+6 -6
View File
@@ -163,32 +163,32 @@ func init() {
Quotas = QuotaManager{modules.NewComputeManager("quota", "quotas",
quotaColumns,
[]string{})}
modules.RegisterCompute(&Quotas)
modules.Register(&Quotas)
ProjectQuotas = QuotaManager{modules.NewComputeManager("project_quota", "project_quotas",
quotaColumns,
[]string{})}
modules.RegisterCompute(&ProjectQuotas)
modules.Register(&ProjectQuotas)
RegionQuotas = QuotaManager{modules.NewComputeManager("region_quota", "region_quotas",
quotaColumns,
[]string{})}
modules.RegisterCompute(&RegionQuotas)
modules.Register(&RegionQuotas)
ZoneQuotas = QuotaManager{modules.NewComputeManager("zone_quota", "zone_quotas",
quotaColumns,
[]string{})}
modules.RegisterCompute(&ZoneQuotas)
modules.Register(&ZoneQuotas)
DomainQuotas = QuotaManager{modules.NewComputeManager("domain_quota", "domain_quotas",
quotaColumns,
[]string{})}
modules.RegisterCompute(&DomainQuotas)
modules.Register(&DomainQuotas)
InfrasQuotas = QuotaManager{modules.NewComputeManager("infras_quota", "infras_quotas",
quotaColumns,
[]string{})}
modules.RegisterCompute(&InfrasQuotas)
modules.Register(&InfrasQuotas)
ImageQuotas = QuotaManager{modules.NewImageManager("image_quota", "image_quotas",
quotaColumns,
-47
View File
@@ -1,47 +0,0 @@
// Copyright 2019 Yunion
//
// 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 modules
import (
"time"
"yunion.io/x/jsonutils"
"yunion.io/x/log"
"yunion.io/x/onecloud/pkg/mcclient"
)
type ITaskResourceManager interface {
PerformClassAction(session *mcclient.ClientSession, action string, params jsonutils.JSONObject) (jsonutils.JSONObject, error)
}
func TaskComplete(man ITaskResourceManager, session *mcclient.ClientSession, taskId string, params jsonutils.JSONObject) {
for i := 0; i < 3; i++ {
_, err := man.PerformClassAction(session, taskId, params)
if err == nil {
log.Infof("Sync task %s complete succ", taskId)
break
}
log.Errorf("Sync task %s complete error: %v", taskId, err)
time.Sleep(5 * time.Second)
}
}
func TaskFailed(man ITaskResourceManager, session *mcclient.ClientSession, taskId string, reason string) {
params := jsonutils.NewDict()
params.Add(jsonutils.NewString("error"), "__status__")
params.Add(jsonutils.NewString(reason), "__reason__")
TaskComplete(man, session, taskId, params)
}
+15
View File
@@ -0,0 +1,15 @@
// Copyright 2019 Yunion
//
// 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 tasks // import "yunion.io/x/onecloud/pkg/mcclient/modules/tasks"
+114
View File
@@ -0,0 +1,114 @@
// Copyright 2019 Yunion
//
// 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 tasks
import (
"time"
"yunion.io/x/jsonutils"
"yunion.io/x/log"
"yunion.io/x/onecloud/pkg/mcclient"
"yunion.io/x/onecloud/pkg/mcclient/modulebase"
)
/*var (
ComputeTasks TasksManager
DevtoolTasks TasksManager
)*/
type TasksManager struct {
modulebase.ResourceManager
}
/*func init() {
ComputeTasks = TasksManager{
ResourceManager: modules.NewComputeManager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"}),
}
modules.RegisterCompute(&ComputeTasks)
DevtoolTasks = TasksManager{
ResourceManager: modules.NewDevtoolManager("task", "tasks",
[]string{},
[]string{"Id", "Obj_name", "Obj_Id", "Task_name", "Stage", "Created_at"},
),
}
}*/
func (man *TasksManager) TaskComplete(session *mcclient.ClientSession, taskId string, params jsonutils.JSONObject) {
for i := 0; i < 3; i++ {
_, err := man.PerformClassAction(session, taskId, params)
if err == nil {
log.Infof("Sync task %s complete succ", taskId)
break
}
log.Errorf("Sync task %s complete error: %v", taskId, err)
time.Sleep(5 * time.Second)
}
}
func (man *TasksManager) TaskFailed(session *mcclient.ClientSession, taskId string, err error) {
man.TaskFailed2(session, taskId, err.Error())
}
func (man *TasksManager) TaskFailed2(session *mcclient.ClientSession, taskId string, reason string) {
man.TaskFailed3(session, taskId, reason, nil)
}
func (man *TasksManager) TaskFailed3(session *mcclient.ClientSession, taskId string, reason string, params *jsonutils.JSONDict) {
if params == nil {
params = jsonutils.NewDict()
}
params.Add(jsonutils.NewString("error"), "__status__")
params.Add(jsonutils.NewString(reason), "__reason__")
man.TaskComplete(session, taskId, params)
}
/*func (self *TasksManager) getManager(session *mcclient.ClientSession, params jsonutils.JSONObject) (*modulebase.ResourceManager, error) {
serviceType := apis.SERVICE_TYPE_REGION
if params.Contains("service_type") {
serviceType, _ = params.GetString("service_type")
}
version := ""
switch serviceType {
case apis.SERVICE_TYPE_KEYSTONE:
version = "v3"
case apis.SERVICE_TYPE_REGION, apis.SERVICE_TYPE_NOTIFY:
version = "v2"
case apis.SERVICE_TYPE_IMAGE:
version = "v1"
}
_, err := session.GetServiceURL(serviceType, "")
if err != nil {
return nil, httperrors.NewNotFoundError("service %s not found error: %v", serviceType, err)
}
return &modulebase.ResourceManager{
BaseManager: *modulebase.NewBaseManager(serviceType, "", version, []string{}, []string{}),
Keyword: "task", KeywordPlural: "tasks",
}, nil
}
func (this *TasksManager) List(session *mcclient.ClientSession, params jsonutils.JSONObject) (*printutils.ListResult, error) {
man, err := this.getManager(session, params)
if err != nil {
return nil, err
}
return man.List(session, params)
}*/