Browse Source

Merge remote-tracking branch 'origin/V20221102' into npu-model-upload

tags/v1.22.11.1^2
chenshihai 2 years ago
parent
commit
e66a1c10df
63 changed files with 1744 additions and 372 deletions
  1. +1
    -1
      models/ai_model_manage.go
  2. +24
    -3
      models/cloudbrain.go
  3. +2
    -2
      models/cloudbrain_spec.go
  4. +173
    -0
      models/cloudbrain_static.go
  5. +1
    -0
      models/models.go
  6. +20
    -19
      models/reward_operate_record.go
  7. +13
    -1
      modules/cron/tasks_basic.go
  8. +46
    -19
      modules/modelarts/modelarts.go
  9. +60
    -0
      modules/modelarts/resty.go
  10. +13
    -0
      modules/setting/setting.go
  11. +9
    -4
      options/locale/locale_en-US.ini
  12. +9
    -3
      options/locale/locale_zh-CN.ini
  13. +5
    -0
      routers/api/v1/api.go
  14. +8
    -3
      routers/api/v1/repo/cloudbrain.go
  15. +476
    -50
      routers/api/v1/repo/cloudbrain_dashboard.go
  16. +17
    -1
      routers/repo/ai_model_convert.go
  17. +5
    -7
      routers/repo/ai_model_manage.go
  18. +7
    -0
      routers/repo/aisafety.go
  19. +34
    -33
      routers/repo/cloudbrain.go
  20. +169
    -0
      routers/repo/cloudbrain_statistic.go
  21. +2
    -0
      routers/repo/dataset.go
  22. +2
    -4
      routers/repo/grampus.go
  23. +34
    -0
      routers/repo/modelarts.go
  24. +6
    -5
      routers/routes/routes.go
  25. +33
    -0
      services/cloudbrain/util.go
  26. +11
    -0
      templates/admin/cloudbrain/list.tmpl
  27. +1
    -1
      templates/base/footer_content.tmpl
  28. +3
    -4
      templates/custom/alert_cb.tmpl
  29. +47
    -0
      templates/custom/max_log.tmpl
  30. +1
    -1
      templates/repo/badge.tmpl
  31. +6
    -4
      templates/repo/cloudbrain/benchmark/new.tmpl
  32. +22
    -11
      templates/repo/cloudbrain/benchmark/show.tmpl
  33. +4
    -2
      templates/repo/cloudbrain/inference/new.tmpl
  34. +22
    -12
      templates/repo/cloudbrain/inference/show.tmpl
  35. +4
    -2
      templates/repo/cloudbrain/new.tmpl
  36. +4
    -2
      templates/repo/cloudbrain/trainjob/new.tmpl
  37. +16
    -5
      templates/repo/cloudbrain/trainjob/show.tmpl
  38. +12
    -0
      templates/repo/debugjob/index.tmpl
  39. +4
    -2
      templates/repo/grampus/trainjob/gpu/new.tmpl
  40. +4
    -2
      templates/repo/grampus/trainjob/npu/new.tmpl
  41. +15
    -4
      templates/repo/grampus/trainjob/show.tmpl
  42. +4
    -2
      templates/repo/modelarts/inferencejob/new.tmpl
  43. +18
    -12
      templates/repo/modelarts/inferencejob/show.tmpl
  44. +5
    -4
      templates/repo/modelarts/notebook/new.tmpl
  45. +4
    -2
      templates/repo/modelarts/trainjob/new.tmpl
  46. +15
    -3
      templates/repo/modelarts/trainjob/show.tmpl
  47. +5
    -2
      templates/repo/modelarts/trainjob/version_new.tmpl
  48. +4
    -2
      templates/repo/modelmanage/convertIndex.tmpl
  49. +1
    -1
      templates/repo/modelmanage/convertshowinfo.tmpl
  50. +1
    -0
      templates/repo/modelmanage/index.tmpl
  51. +1
    -1
      templates/repo/modelmanage/showinfo.tmpl
  52. +4
    -2
      templates/repo/modelsafety/new.tmpl
  53. +23
    -11
      templates/repo/modelsafety/show.tmpl
  54. +1
    -1
      templates/resource_desc.tmpl
  55. +13
    -1
      templates/user/dashboard/cloudbrains.tmpl
  56. +1
    -1
      templates/user/profile.tmpl
  57. +239
    -62
      web_src/js/features/cloudbrainShow.js
  58. +1
    -7
      web_src/js/features/cloudrbanin.js
  59. +1
    -1
      web_src/js/standalone/phoneverify.js
  60. +0
    -10
      web_src/less/_user.less
  61. +1
    -0
      web_src/vuepages/langs/config/en-US.js
  62. +1
    -0
      web_src/vuepages/langs/config/zh-CN.js
  63. +56
    -40
      web_src/vuepages/pages/reward/point/utils.js

+ 1
- 1
models/ai_model_manage.go View File

@@ -88,7 +88,7 @@ type AiModelQueryOptions struct {
}

func (a *AiModelConvert) IsGpuTrainTask() bool {
if a.SrcEngine == 0 || a.SrcEngine == 1 {
if a.SrcEngine == 0 || a.SrcEngine == 1 || a.SrcEngine == 4 || a.SrcEngine == 6 {
return true
}
return false


+ 24
- 3
models/cloudbrain.go View File

@@ -1072,6 +1072,12 @@ type CreateInferenceJobParams struct {
InfConfig InfConfig `json:"config"`
WorkspaceID string `json:"workspace_id"`
}
type CreateInfUserImageParams struct {
JobName string `json:"job_name"`
Description string `json:"job_desc"`
Config InfUserImageConfig `json:"config"`
WorkspaceID string `json:"workspace_id"`
}

type InfConfig struct {
WorkServerNum int `json:"worker_server_num"`
@@ -1086,6 +1092,21 @@ type InfConfig struct {
PoolID string `json:"pool_id"`
}

type InfUserImageConfig struct {
WorkServerNum int `json:"worker_server_num"`
AppUrl string `json:"app_url"` //训练作业的代码目录
BootFileUrl string `json:"boot_file_url"` //训练作业的代码启动文件,需要在代码目录下
Parameter []Parameter `json:"parameter"`
DataUrl string `json:"data_url"` //训练作业需要的数据集OBS路径URL
EngineID int64 `json:"engine_id"`
LogUrl string `json:"log_url"`
CreateVersion bool `json:"create_version"`
Flavor Flavor `json:"flavor"`
PoolID string `json:"pool_id"`
UserImageUrl string `json:"user_image_url"`
UserCommand string `json:"user_command"`
}

type CreateTrainJobVersionParams struct {
Description string `json:"job_desc"`
Config TrainJobVersionConfig `json:"config"`
@@ -2026,7 +2047,7 @@ func GetCloudbrainRunCountByRepoID(repoID int64) (int, error) {
}

func GetModelSafetyCountByUserID(userID int64) (int, error) {
count, err := x.In("status", JobWaiting, JobRunning,ModelArtsTrainJobInit,ModelArtsTrainJobImageCreating,ModelArtsTrainJobSubmitTrying,ModelArtsTrainJobScaling,ModelArtsTrainJobCheckInit,ModelArtsTrainJobCheckRunning,ModelArtsTrainJobCheckRunningCompleted).And("job_type = ? and user_id = ?", string(JobTypeModelSafety), userID).Count(new(Cloudbrain))
count, err := x.In("status", JobWaiting, JobRunning, ModelArtsTrainJobInit, ModelArtsTrainJobImageCreating, ModelArtsTrainJobSubmitTrying, ModelArtsTrainJobScaling, ModelArtsTrainJobCheckInit, ModelArtsTrainJobCheckRunning, ModelArtsTrainJobCheckRunningCompleted).And("job_type = ? and user_id = ?", string(JobTypeModelSafety), userID).Count(new(Cloudbrain))
return int(count), err
}

@@ -2262,9 +2283,9 @@ func CloudbrainAllStatic(opts *CloudbrainsOptions) ([]*CloudbrainInfo, int64, er
}
sess.Limit(opts.PageSize, start)
}
sess.OrderBy("cloudbrain.created_unix DESC")
// sess.OrderBy("cloudbrain.created_unix DESC")
cloudbrains := make([]*CloudbrainInfo, 0, setting.UI.IssuePagingNum)
if err := sess.Table(&Cloudbrain{}).Unscoped().Where(cond).
if err := sess.Cols("status", "type", "job_type", "train_job_duration", "duration", "compute_resource", "created_unix", "start_time", "end_time", "work_server_number").Table(&Cloudbrain{}).Unscoped().Where(cond).
Find(&cloudbrains); err != nil {
return nil, 0, fmt.Errorf("Find: %v", err)
}


+ 2
- 2
models/cloudbrain_spec.go View File

@@ -9,7 +9,7 @@ type CloudbrainSpec struct {
SpecId int64 `xorm:"index"`
SourceSpecId string
AccCardsNum int
AccCardType string
AccCardType string `xorm:"index"`
CpuCores int
MemGiB float32
GPUMemGiB float32
@@ -19,7 +19,7 @@ type CloudbrainSpec struct {
QueueId int64
QueueCode string
Cluster string
AiCenterCode string
AiCenterCode string `xorm:"index"`
AiCenterName string
IsExclusive bool
ExclusiveOrg string


+ 173
- 0
models/cloudbrain_static.go View File

@@ -1,6 +1,7 @@
package models

import (
"fmt"
"strconv"
"time"

@@ -38,6 +39,60 @@ type TaskDetail struct {
Spec *Specification `json:"Spec"`
}

type CloudbrainDurationStatistic struct {
ID int64 `xorm:"pk autoincr"`
Cluster string
AiCenterCode string
AiCenterName string
ComputeResource string
AccCardType string

DateTime string
DayTime string
HourTime int
CardsUseDuration int
CardsTotalDuration int
CardsTotalNum int

DeletedUnix timeutil.TimeStamp `xorm:"deleted"`
CreatedUnix timeutil.TimeStamp `xorm:"created"`
UpdatedUnix timeutil.TimeStamp `xorm:"updated"`
}
type DurationStatisticOptions struct {
BeginTime time.Time
EndTime time.Time
AiCenterCode string
}

type DurationRateStatistic struct {
AiCenterTotalDurationStat map[string]int `json:"aiCenterTotalDurationStat"`
AiCenterUsageDurationStat map[string]int `json:"aiCenterUsageDurationStat"`
UsageRate map[string]float64 `json:"UsageRate"`
}
type ResourceDetail struct {
QueueCode string
Cluster string `xorm:"notnull"`
AiCenterCode string
AiCenterName string
ComputeResource string
AccCardType string
CardsTotalNum int
IsAutomaticSync bool
}

type DateUsageStatistic struct {
Date string `json:"date"`
UsageDuration int `json:"usageDuration"`
TotalDuration int `json:"totalDuration"`
UsageRate float64 `json:"usageRate"`
}

type HourTimeStatistic struct {
HourTimeUsageDuration map[string]int `json:"hourTimeUsageDuration"`
HourTimeTotalDuration map[string]int `json:"hourTimeTotalDuration"`
HourTimeUsageRate map[string]float64 `json:"hourTimeUsageRate"`
}

func GetTodayCreatorCount(beginTime time.Time, endTime time.Time) (int64, error) {
countSql := "SELECT count(distinct user_id) FROM " +
"public.cloudbrain where created_unix >=" + strconv.FormatInt(beginTime.Unix(), 10) +
@@ -199,3 +254,121 @@ func GetRunHourPeriodCount(dateBeginTime string, dateEndTime string) (map[string
}
return dateHourMap, nil
}

func GetCloudbrainRunning() ([]*CloudbrainInfo, error) {
sess := x.NewSession()
defer sess.Close()
var cond = builder.NewCond()
cond = cond.And(
builder.Eq{"cloudbrain.status": string(JobRunning)},
)
sess.OrderBy("cloudbrain.created_unix ASC")
cloudbrains := make([]*CloudbrainInfo, 0, 10)
if err := sess.Table(&Cloudbrain{}).Where(cond).
Find(&cloudbrains); err != nil {
log.Info("find error.")
}
return cloudbrains, nil
}

func GetCloudbrainByTime(beginTime int64, endTime int64) ([]*CloudbrainInfo, error) {
sess := x.NewSession()
defer sess.Close()
var cond = builder.NewCond()
cond = cond.And(
builder.And(builder.Gte{"cloudbrain.end_time": beginTime}, builder.Lte{"cloudbrain.end_time": endTime}),
)
cond = cond.Or(
builder.Eq{"cloudbrain.status": string(JobRunning)},
)
sess.OrderBy("cloudbrain.created_unix ASC")
cloudbrains := make([]*CloudbrainInfo, 0, 10)
if err := sess.Table(&Cloudbrain{}).Unscoped().Where(cond).
Find(&cloudbrains); err != nil {
log.Info("find error.")
}
return cloudbrains, nil
}

func GetSpecByAiCenterCodeAndType(aiCenterCode string, accCardType string) ([]*CloudbrainSpec, error) {
sess := x.NewSession()
defer sess.Close()
var cond = builder.NewCond()
cond = cond.And(
builder.And(builder.Eq{"cloudbrain_spec.ai_center_code": aiCenterCode}, builder.Eq{"cloudbrain_spec.acc_card_type": accCardType}),
)
cloudbrainSpecs := make([]*CloudbrainSpec, 0, 10)
if err := sess.Table(&CloudbrainSpec{}).Where(cond).
Find(&cloudbrainSpecs); err != nil {
log.Info("find error.")
}
return cloudbrainSpecs, nil
}

func InsertCloudbrainDurationStatistic(cloudbrainDurationStatistic *CloudbrainDurationStatistic) (int64, error) {
return xStatistic.Insert(cloudbrainDurationStatistic)
}

func DeleteCloudbrainDurationStatisticHour(date string, hour int, aiCenterCode string, accCardType string) error {
sess := xStatistic.NewSession()
defer sess.Close()
if err := sess.Begin(); err != nil {
return fmt.Errorf("Begin: %v", err)
}

if _, err := sess.Where("day_time = ? AND hour_time = ? AND ai_center_code = ? AND acc_card_type = ?", date, hour, aiCenterCode, accCardType).Delete(&CloudbrainDurationStatistic{}); err != nil {
return fmt.Errorf("Delete: %v", err)
}

if err := sess.Commit(); err != nil {
sess.Close()
return fmt.Errorf("Commit: %v", err)
}

sess.Close()
return nil
}

func GetCanUseCardInfo() ([]*ResourceQueue, error) {
sess := x.NewSession()
defer sess.Close()
sess.OrderBy("resource_queue.id ASC")
ResourceQueues := make([]*ResourceQueue, 0, 10)
if err := sess.Table(&ResourceQueue{}).Find(&ResourceQueues); err != nil {
log.Info("find error.")
}
return ResourceQueues, nil
}

func GetCardDurationStatistics(opts *DurationStatisticOptions) ([]*CloudbrainDurationStatistic, error) {
sess := xStatistic.NewSession()
defer sess.Close()
var cond = builder.NewCond()
if opts.BeginTime.Unix() > 0 && opts.EndTime.Unix() > 0 {
cond = cond.And(
builder.And(builder.Gte{"cloudbrain_duration_statistic.created_unix": opts.BeginTime.Unix()}, builder.Lte{"cloudbrain_duration_statistic.created_unix": opts.EndTime.Unix()}),
)
}
if opts.AiCenterCode != "" {
cond = cond.And(
builder.Eq{"cloudbrain_duration_statistic.ai_center_code": opts.AiCenterCode},
)
}
CloudbrainDurationStatistics := make([]*CloudbrainDurationStatistic, 0, 10)
if err := sess.Table(&CloudbrainDurationStatistic{}).Where(cond).
Find(&CloudbrainDurationStatistics); err != nil {
log.Info("find error.")
}
return CloudbrainDurationStatistics, nil
}

func GetDurationRecordBeginTime() ([]*CloudbrainDurationStatistic, error) {
sess := xStatistic.NewSession()
defer sess.Close()
sess.OrderBy("cloudbrain_duration_statistic.id ASC limit 1")
CloudbrainDurationStatistics := make([]*CloudbrainDurationStatistic, 0)
if err := sess.Table(&CloudbrainDurationStatistic{}).Find(&CloudbrainDurationStatistics); err != nil {
log.Info("find error.")
}
return CloudbrainDurationStatistics, nil
}

+ 1
- 0
models/models.go View File

@@ -184,6 +184,7 @@ func init() {
new(UserMetrics),
new(UserAnalysisPara),
new(Invitation),
new(CloudbrainDurationStatistic),
)

gonicNames := []string{"SSL", "UID"}


+ 20
- 19
models/reward_operate_record.go View File

@@ -249,22 +249,23 @@ type AdminRewardOperateReq struct {
}

type RewardOperateRecordShow struct {
SerialNo string
Status string
OperateType string
SourceId string
Amount int64
LossAmount int64
BalanceAfter int64
Remark string
SourceType string
UserName string
LastOperateDate timeutil.TimeStamp
UnitPrice int64
SuccessCount int
Action *ActionShow
Cloudbrain *CloudbrainShow
AdminLog *RewardAdminLogShow
SerialNo string
Status string
OperateType string
SourceId string
Amount int64
LossAmount int64
BalanceAfter int64
Remark string
SourceType string
SourceTemplateId string
UserName string
LastOperateDate timeutil.TimeStamp
UnitPrice int64
SuccessCount int
Action *ActionShow
Cloudbrain *CloudbrainShow
AdminLog *RewardAdminLogShow
}

func getPointOperateRecord(tl *RewardOperateRecord) (*RewardOperateRecord, error) {
@@ -419,7 +420,7 @@ func GetRewardRecordShowList(opts *RewardRecordListOpts) (RewardRecordShowList,
r := make([]*RewardOperateRecordShow, 0)
err = x.Table("reward_operate_record").Cols("reward_operate_record.source_id", "reward_operate_record.serial_no",
"reward_operate_record.status", "reward_operate_record.operate_type", "reward_operate_record.amount",
"reward_operate_record.loss_amount", "reward_operate_record.remark", "reward_operate_record.source_type",
"reward_operate_record.loss_amount", "reward_operate_record.remark", "reward_operate_record.source_type", "reward_operate_record.source_template_id",
"reward_operate_record.last_operate_unix as last_operate_date").
Where(cond).Limit(opts.PageSize, (opts.Page-1)*opts.PageSize).OrderBy(string(opts.OrderBy)).Find(&r)

@@ -441,7 +442,7 @@ func GetAdminRewardRecordShowList(opts *RewardRecordListOpts) (RewardRecordShowL
case OperateTypeIncrease:
err = x.Table("reward_operate_record").Cols("reward_operate_record.source_id", "reward_operate_record.serial_no",
"reward_operate_record.status", "reward_operate_record.operate_type", "reward_operate_record.amount",
"reward_operate_record.loss_amount", "reward_operate_record.remark", "reward_operate_record.source_type",
"reward_operate_record.loss_amount", "reward_operate_record.remark", "reward_operate_record.source_type", "reward_operate_record.source_template_id",
"reward_operate_record.last_operate_unix as last_operate_date", "public.user.name as user_name",
"point_account_log.balance_after").
Join("LEFT", "public.user", "reward_operate_record.user_id = public.user.id").
@@ -450,7 +451,7 @@ func GetAdminRewardRecordShowList(opts *RewardRecordListOpts) (RewardRecordShowL
case OperateTypeDecrease:
err = x.Table("reward_operate_record").Cols("reward_operate_record.source_id", "reward_operate_record.serial_no",
"reward_operate_record.status", "reward_operate_record.operate_type", "reward_operate_record.amount",
"reward_operate_record.loss_amount", "reward_operate_record.remark", "reward_operate_record.source_type",
"reward_operate_record.loss_amount", "reward_operate_record.remark", "reward_operate_record.source_type", "reward_operate_record.source_template_id",
"reward_operate_record.last_operate_unix as last_operate_date", "public.user.name as user_name",
"reward_periodic_task.amount as unit_price", "reward_periodic_task.success_count").
Join("LEFT", "public.user", "reward_operate_record.user_id = public.user.id").


+ 13
- 1
modules/cron/tasks_basic.go View File

@@ -278,6 +278,17 @@ func registerSyncModelArtsTempJobs() {
})
}

func registerHandleCloudbrainDurationStatistic() {
RegisterTaskFatal("handle_cloudbrain_duration_statistic", &BaseConfig{
Enabled: true,
RunAtStart: false,
Schedule: "1 0 * * * ?",
}, func(ctx context.Context, _ *models.User, _ Config) error {
repo.CloudbrainDurationStatisticHour()
return nil
})
}

func initBasicTasks() {
registerUpdateMirrorTask()
registerRepoHealthCheck()
@@ -306,5 +317,6 @@ func initBasicTasks() {

registerHandleModelSafetyTask()

registerHandleScheduleRecord()
registerHandleScheduleRecord()
registerHandleCloudbrainDurationStatistic()
}

+ 46
- 19
modules/modelarts/modelarts.go View File

@@ -143,6 +143,8 @@ type GenerateInferenceJobReq struct {
Spec *models.Specification
DatasetName string
JobType string
UserImageUrl string
UserCommand string
}

type VersionInfo struct {
@@ -682,26 +684,51 @@ func GetOutputPathByCount(TotalVersionCount int) (VersionOutputPath string) {

func GenerateInferenceJob(ctx *context.Context, req *GenerateInferenceJobReq) (err error) {
createTime := timeutil.TimeStampNow()
jobResult, err := createInferenceJob(models.CreateInferenceJobParams{
JobName: req.JobName,
Description: req.Description,
InfConfig: models.InfConfig{
WorkServerNum: req.WorkServerNumber,
AppUrl: req.CodeObsPath,
BootFileUrl: req.BootFileUrl,
DataUrl: req.DataUrl,
EngineID: req.EngineID,
// TrainUrl: req.TrainUrl,
LogUrl: req.LogUrl,
PoolID: req.PoolID,
CreateVersion: true,
Flavor: models.Flavor{
Code: req.Spec.SourceSpecId,
var jobResult *models.CreateTrainJobResult
var createErr error
if req.EngineID < 0 {
jobResult, createErr = createInferenceJobUserImage(models.CreateInfUserImageParams{
JobName: req.JobName,
Description: req.Description,
Config: models.InfUserImageConfig{
WorkServerNum: req.WorkServerNumber,
AppUrl: req.CodeObsPath,
BootFileUrl: req.BootFileUrl,
DataUrl: req.DataUrl,
// TrainUrl: req.TrainUrl,
LogUrl: req.LogUrl,
PoolID: req.PoolID,
CreateVersion: true,
Flavor: models.Flavor{
Code: req.Spec.SourceSpecId,
},
Parameter: req.Parameters,
UserImageUrl: req.UserImageUrl,
UserCommand: req.UserCommand,
},
Parameter: req.Parameters,
},
})
if err != nil {
})
} else {
jobResult, createErr = createInferenceJob(models.CreateInferenceJobParams{
JobName: req.JobName,
Description: req.Description,
InfConfig: models.InfConfig{
WorkServerNum: req.WorkServerNumber,
AppUrl: req.CodeObsPath,
BootFileUrl: req.BootFileUrl,
DataUrl: req.DataUrl,
EngineID: req.EngineID,
// TrainUrl: req.TrainUrl,
LogUrl: req.LogUrl,
PoolID: req.PoolID,
CreateVersion: true,
Flavor: models.Flavor{
Code: req.Spec.SourceSpecId,
},
Parameter: req.Parameters,
},
})
}
if createErr != nil {
log.Error("createInferenceJob failed: %v", err.Error())
if strings.HasPrefix(err.Error(), UnknownErrorPrefix) {
log.Info("(%s)unknown error, set temp status", req.DisplayJobName)


+ 60
- 0
modules/modelarts/resty.go View File

@@ -1197,6 +1197,66 @@ sendjob:
return &result, nil
}

func createInferenceJobUserImage(createJobParams models.CreateInfUserImageParams) (*models.CreateTrainJobResult, error) {
checkSetting()
client := getRestyClient()
var result models.CreateTrainJobResult

retry := 0

sendjob:
res, err := client.R().
SetHeader("Content-Type", "application/json").
SetAuthToken(TOKEN).
SetBody(createJobParams).
SetResult(&result).
Post(HOST + "/v1/" + setting.ProjectID + urlTrainJob)

if err != nil {
return nil, fmt.Errorf("resty create train-job: %s", err)
}

req, _ := json.Marshal(createJobParams)
log.Info("%s", req)

if res.StatusCode() == http.StatusUnauthorized && retry < 1 {
retry++
_ = getToken()
goto sendjob
}

if res.StatusCode() != http.StatusOK {
var temp models.ErrorResult
if err = json.Unmarshal([]byte(res.String()), &temp); err != nil {
log.Error("json.Unmarshal failed(%s): %v", res.String(), err.Error())
return &result, fmt.Errorf("json.Unmarshal failed(%s): %v", res.String(), err.Error())
}
log.Error("createInferenceJobUserImage failed(%d):%s(%s)", res.StatusCode(), temp.ErrorCode, temp.ErrorMsg)
bootFileErrorMsg := "Invalid OBS path '" + createJobParams.Config.BootFileUrl + "'."
dataSetErrorMsg := "Invalid OBS path '" + createJobParams.Config.DataUrl + "'."
if temp.ErrorMsg == bootFileErrorMsg {
log.Error("启动文件错误!createInferenceJobUserImage failed(%d):%s(%s)", res.StatusCode(), temp.ErrorCode, temp.ErrorMsg)
return &result, fmt.Errorf("启动文件错误!")
}
if temp.ErrorMsg == dataSetErrorMsg {
log.Error("数据集错误!createInferenceJobUserImage failed(%d):%s(%s)", res.StatusCode(), temp.ErrorCode, temp.ErrorMsg)
return &result, fmt.Errorf("数据集错误!")
}
if res.StatusCode() == http.StatusBadGateway {
return &result, fmt.Errorf(UnknownErrorPrefix+"createInferenceJobUserImage failed(%d):%s(%s)", res.StatusCode(), temp.ErrorCode, temp.ErrorMsg)
} else {
return &result, fmt.Errorf("createInferenceJobUserImage failed(%d):%s(%s)", res.StatusCode(), temp.ErrorCode, temp.ErrorMsg)
}
}

if !result.IsSuccess {
log.Error("createInferenceJobUserImage failed(%s): %s", result.ErrorCode, result.ErrorMsg)
return &result, fmt.Errorf("createInferenceJobUserImage failed(%s): %s", result.ErrorCode, result.ErrorMsg)
}

return &result, nil
}

func createNotebook2(createJobParams models.CreateNotebook2Params) (*models.CreateNotebookResult, error) {
checkSetting()
client := getRestyClient()


+ 13
- 0
modules/setting/setting.go View File

@@ -611,6 +611,7 @@ var (

C2NetInfos *C2NetSqInfos
CenterInfos *AiCenterInfos
C2NetMapInfo map[string]*C2NetSequenceInfo

//elk config
ElkUrl string
@@ -715,8 +716,12 @@ var (
GPU_PYTORCH_IMAGE string
GpuQueue string
GPU_TENSORFLOW_IMAGE string
GPU_PADDLE_IMAGE string
GPU_MXNET_IMAGE string
NPU_MINDSPORE_16_IMAGE string
PytorchOnnxBootFile string
PaddleOnnxBootFile string
MXnetOnnxBootFile string
PytorchTrTBootFile string
MindsporeBootFile string
TensorFlowNpuBootFile string
@@ -1610,6 +1615,10 @@ func getModelConvertConfig() {
ModelConvert.NPU_PoolID = sec.Key("NPU_PoolID").MustString("pool7908321a")
ModelConvert.NPU_MINDSPORE_IMAGE_ID = sec.Key("NPU_MINDSPORE_IMAGE_ID").MustInt(121)
ModelConvert.NPU_TENSORFLOW_IMAGE_ID = sec.Key("NPU_TENSORFLOW_IMAGE_ID").MustInt(35)
ModelConvert.GPU_PADDLE_IMAGE = sec.Key("GPU_PADDLE_IMAGE").MustString("dockerhub.pcl.ac.cn:5000/user-images/openi:paddle2.3.0_gpu_cuda11.2_cudnn8")
ModelConvert.GPU_MXNET_IMAGE = sec.Key("GPU_MXNET_IMAGE").MustString("dockerhub.pcl.ac.cn:5000/user-images/openi:mxnet191cu_cuda102_py37")
ModelConvert.PaddleOnnxBootFile = sec.Key("PaddleOnnxBootFile").MustString("convert_paddle.py")
ModelConvert.MXnetOnnxBootFile = sec.Key("MXnetOnnxBootFile").MustString("convert_mxnet.py")
}

func getModelAppConfig() {
@@ -1646,6 +1655,10 @@ func getGrampusConfig() {
if err := json.Unmarshal([]byte(Grampus.C2NetSequence), &C2NetInfos); err != nil {
log.Error("Unmarshal(C2NetSequence) failed:%v", err)
}
C2NetMapInfo=make(map[string]*C2NetSequenceInfo)
for _,value :=range C2NetInfos.C2NetSqInfo{
C2NetMapInfo[value.Name]=value
}
}
Grampus.SyncScriptProject = sec.Key("SYNC_SCRIPT_PROJECT").MustString("script_for_grampus")
Grampus.LocalCenterID = sec.Key("LOCAL_CENTER_ID").MustString("cloudbrain2")


+ 9
- 4
options/locale/locale_en-US.ini View File

@@ -265,8 +265,8 @@ page_dev_yunlao_desc3=China computing power network (C²NET) phase I can realize
page_dev_yunlao_desc4=Developers can freely select the corresponding computing resources according to the use needs, and can test the adaptability, performance, stability, etc. of the model in different hardware environments.
page_dev_yunlao_desc5=If your model requires more computing resources, you can also apply for it separately.
page_dev_yunlao_apply=Apply Separately
c2net_title=China Computing Network
c2net_desc=Extensive access to intelligent computing centers and supercomputing centers across the country to provide users with free computing resources.
c2net_title=China Computing NET(C²NET)
c2net_desc=Extensive access to intelligent computing centers, supercomputing centers and big data centers across the country to provide users with free computing resources.
c2net_center=Center
search=Search
search_repo=Repository
@@ -289,6 +289,7 @@ provide_resoure = Computing resources of CPU/GPU/NPU are provided freely for var
activity = Activity
no_events = There are no events related
or_t = or
powerdby=Powered_by Pengcheng CloudBrain、China Computing NET(C²NET)、

[explore]
repos = Repositories
@@ -1216,7 +1217,8 @@ cloudbrain.benchmark.evaluate_train=Train Script
cloudbrain.benchmark.evaluate_test=Test Script
cloudbrain.benchmark.types={"type":[{"id":1,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=detection","first":"Target detection","second":[{"id":1,"value":"None","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"yangzhx","repo_name":"detection_benchmark_script"}]},{"id":2,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=reid","first":"Target re-identification","second":[{"id":1,"value":"Vehicle re-identification","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"JiahongXu","repo_name":"benchmark_reID_script"},{"id":2,"value":"Image-based person re-identification","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"JiahongXu","repo_name":"benchmark_reID_script"}]},{"id":3,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=tracking","first":"Multi-target tracking","second":[{"id":1,"value":"None","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"lix07","repo_name":"MOT_benchmark_script"}]}]}
cloudbrain.morethanonejob=You already have a running or waiting task, create it after that task is over.

cloudbrain.morethanonejob1=You have created a <span style="color:rgba(242, 113, 28, 1);"> equivalent task </span> that is waiting or running, please wait for the task to finish before creating it.
cloudbrain.morethanonejob2=You can view all your Cloud Brain tasks in <a href="/cloudbrains" target="_blank"> Home > Cloudbrain Task </a>.

modelarts.infer_job_model = Model
modelarts.infer_job_model_file = Model File
@@ -1226,6 +1228,9 @@ modelarts.infer_job.select_model = Select Model
modelarts.infer_job.boot_file_helper=The startup file is the entry file for your program execution and must end in.py.Such as inference.py, main.py, example/inference.py, case/main.py.
modelarts.infer_job.tooltip = The model has been deleted and cannot be viewed.
modelarts.download_log=Download log file
modelarts.log_file = Log file
modelarts.fullscreen_log_file = View in full screen
modelarts.exit_full_screen = Exit fullscreen
modelarts.no_node_right = The value of 'Amount of Compute Node' is wrong, you have no right to use the current value of 'Amount of Compute Node'.


@@ -3217,7 +3222,7 @@ view_sample = View sample
inference_output_path_rule = The inference output path is stored in the run parameter result_url.
model_file_path_rule=The model file location is stored in the run parameter ckpt_url
model_file_postfix_rule = The supported format of the model file is [ckpt, pb, h5, json, pkl, pth, t7, pdparams, onnx, pbtxt, keras, mlmodel, cfg, pt]
model_convert_postfix_rule = The supported format of the model file is [.pth, .pkl, .onnx, .mindir, .ckpt, .pb]
model_convert_postfix_rule = The supported format of the model file is [.pth, .pkl, .onnx, .mindir, .ckpt, .pb, .pdmodel, .pdiparams, .params, .json]
delete_task = Delete task
task_delete_confirm = Are you sure you want to delete this task? Once this task is deleted, it cannot be recovered.
operate_confirm = confirm


+ 9
- 3
options/locale/locale_zh-CN.ini View File

@@ -267,8 +267,8 @@ page_dev_yunlao_desc3=中国算力网(C²NET)一期可实现不同人工智
page_dev_yunlao_desc4=开发者可以根据使用需求,自由选择相应计算资源,可以测试模型在不同硬件环境下的适配能力、性能、稳定性等。
page_dev_yunlao_desc5=如果您的模型需要更多的计算资源,也可以单独申请。
page_dev_yunlao_apply=单独申请
c2net_title=中国算力网
c2net_desc=广泛接入全国各地智算中心、超算中心,为用户提供免费算力资源
c2net_title=中国算力网(C²NET)
c2net_desc=广泛接入全国各地智算中心、超算中心与大数据中心等,为用户提供免费算力资源
c2net_center=中心
search=搜索
search_repo=项目
@@ -292,6 +292,7 @@ create_pro = 创建项目
activity = 活动
no_events = 还没有与您相关的活动
or_t = 或
powerdby=Powered_by 鹏城实验室云脑、中国算力网(C²NET)、


[explore]
@@ -1230,6 +1231,8 @@ cloudbrain.benchmark.evaluate_test=测试程序
cloudbrain.benchmark.types={"type":[{"id":1,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=detection","first":"目标检测","second":[{"id":1,"value":"无","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"yangzhx","repo_name":"detection_benchmark_script"}]},{"id":2,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=reid","first":"目标重识别","second":[{"id":1,"value":"车辆重识别","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"JiahongXu","repo_name":"benchmark_reID_script"},{"id":2,"value":"基于图像的行人重识别","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"JiahongXu","repo_name":"benchmark_reID_script"}]},{"id":3,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=tracking","first":"多目标跟踪","second":[{"id":1,"value":"无","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"lix07","repo_name":"MOT_benchmark_script"}]}]}
cloudbrain.benchmark.model.types={"type":[{"id":1,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=detection","first":"目标检测","second":[{"id":1,"value":"无","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"yangzhx","repo_name":"detection_benchmark_script"}]},{"id":2,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=reid","first":"目标重识别","second":[{"id":1,"value":"车辆重识别","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"JiahongXu","repo_name":"benchmark_reID_script"},{"id":2,"value":"基于图像的行人重识别","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"JiahongXu","repo_name":"benchmark_reID_script"}]},{"id":3,"rank_link":"https://git.openi.org.cn/benchmark/?username=admin&algType=tracking","first":"多目标跟踪","second":[{"id":1,"value":"无","attachment":"84cf39c4-d8bc-41aa-aaa3-182ce289b105","owner":"lix07","repo_name":"MOT_benchmark_script"}]}]}
cloudbrain.morethanonejob=您已经创建了一个正在等待或运行中的同类任务,请等待任务结束再创建。
cloudbrain.morethanonejob1=您已经有 <span style="color:rgba(242, 113, 28, 1);">同类任务</span> 正在等待或运行中,请等待任务结束再创建;
cloudbrain.morethanonejob2=可以在 “<a href="/cloudbrains" target="_blank" >个人中心 > 云脑任务</a>” 查看您所有的云脑任务。

modelarts.infer_job_model = 模型名称
modelarts.infer_job_model_file = 模型文件
@@ -1239,6 +1242,9 @@ modelarts.infer_job.select_model = 选择模型
modelarts.infer_job.boot_file_helper=启动文件是您程序执行的入口文件,必须是以.py结尾的文件。比如inference.py、main.py、example/inference.py、case/main.py。
modelarts.infer_job.tooltip = 该模型已删除,无法查看。
modelarts.download_log=下载日志文件
modelarts.log_file=日志文件
modelarts.fullscreen_log_file=全屏查看
modelarts.exit_full_screen=退出全屏
modelarts.no_node_right = 计算节点数的值配置错误,您没有权限使用当前配置的计算节点数。


@@ -3236,7 +3242,7 @@ view_sample = 查看样例
inference_output_path_rule = 推理输出路径存储在运行参数 result_url 中。
model_file_path_rule = 模型文件位置存储在运行参数 ckpt_url 中。
model_file_postfix_rule = 模型文件支持的格式为 [ckpt, pb, h5, json, pkl, pth, t7, pdparams, onnx, pbtxt, keras, mlmodel, cfg, pt]
model_convert_postfix_rule = 模型文件支持的格式为 [.pth, .pkl, .onnx, .mindir, .ckpt, .pb]
model_convert_postfix_rule = 模型文件支持的格式为 [.pth, .pkl, .onnx, .mindir, .ckpt, .pb, .pdmodel, .pdiparams, .params, .json]
delete_task = 删除任务
task_delete_confirm = 你确认删除该任务么?此任务一旦删除不可恢复。
operate_confirm = 确定操作


+ 5
- 0
routers/api/v1/api.go View File

@@ -599,6 +599,11 @@ func RegisterRoutes(m *macaron.Macaron) {
m.Get("/hours_data", repo.GetCloudbrainsCreateHoursData)
m.Get("/waitting_top_data", repo.GetWaittingTop)
m.Get("/running_top_data", repo.GetRunningTop)

m.Get("/overview_resource", repo.GetCloudbrainResourceOverview)
m.Get("/resource_usage_statistic", repo.GetDurationRateStatistic)
m.Get("/resource_usage_rate_detail", repo.GetCloudbrainResourceUsageDetail)
m.Get("/apitest_for_statistic", repo.CloudbrainDurationStatisticForTest)
})
}, operationReq)



+ 8
- 3
routers/api/v1/repo/cloudbrain.go View File

@@ -574,7 +574,13 @@ func CloudbrainGetLog(ctx *context.APIContext) {
startLine = 0
}
}
} else {
if startLine > 0 {
startLine += 1
endLine += 1
}
}
result = getLogFromModelDir(job.JobName, startLine, endLine, resultPath)
if result == nil {
log.Error("GetJobLog failed: %v", err, ctx.Data["MsgID"])
@@ -722,10 +728,10 @@ func getLogFromModelDir(jobName string, startLine int, endLine int, resultPath s
line, error := r.ReadString('\n')
if error == io.EOF {
if i >= startLine {
fileEndLine = i
re = re + line
count++
}
fileEndLine = i + 1
log.Info("read file completed.")
break
}
@@ -735,13 +741,12 @@ func getLogFromModelDir(jobName string, startLine int, endLine int, resultPath s
}
if error == nil {
if i >= startLine {
fileEndLine = i
fileEndLine = i + 1
re = re + line
count++
}
}
}
fileEndLine = fileEndLine + 1
} else {
log.Info("error:" + err.Error())
}


+ 476
- 50
routers/api/v1/repo/cloudbrain_dashboard.go View File

@@ -4,6 +4,7 @@ import (
"fmt"
"net/http"
"net/url"
"strconv"
"strings"
"time"

@@ -120,9 +121,6 @@ func GetOverviewDuration(ctx *context.Context) {
recordBeginTime := recordCloudbrain[0].Cloudbrain.CreatedUnix
now := time.Now()
endTime := now
page := 1
pagesize := 1000
count := pagesize
worker_server_num := 1
cardNum := 1
durationAllSum := int64(0)
@@ -138,54 +136,46 @@ func GetOverviewDuration(ctx *context.Context) {
c2NetDuration := int64(0)
cDCenterDuration := int64(0)

for count == pagesize && count != 0 {
cloudbrains, _, err := models.CloudbrainAllStatic(&models.CloudbrainsOptions{
ListOptions: models.ListOptions{
Page: page,
PageSize: pagesize,
},
Type: models.TypeCloudBrainAll,
BeginTimeUnix: int64(recordBeginTime),
EndTimeUnix: endTime.Unix(),
})
if err != nil {
ctx.ServerError("Get cloudbrains failed:", err)
return
}
models.LoadSpecs4CloudbrainInfo(cloudbrains)

for _, cloudbrain := range cloudbrains {
if cloudbrain.Cloudbrain.WorkServerNumber >= 1 {
worker_server_num = cloudbrain.Cloudbrain.WorkServerNumber
} else {
worker_server_num = 1
}
if cloudbrain.Cloudbrain.Spec == nil {
cardNum = 1
} else {
cardNum = cloudbrain.Cloudbrain.Spec.AccCardsNum
}
duration := cloudbrain.Duration
durationSum := cloudbrain.Duration * int64(worker_server_num) * int64(cardNum)
if cloudbrain.Cloudbrain.Type == models.TypeCloudBrainOne {
cloudBrainOneDuration += duration
cloudBrainOneCardDuSum += durationSum
} else if cloudbrain.Cloudbrain.Type == models.TypeCloudBrainTwo {
cloudBrainTwoDuration += duration
cloudBrainTwoCardDuSum += durationSum
} else if cloudbrain.Cloudbrain.Type == models.TypeC2Net {
c2NetDuration += duration
c2NetCardDuSum += durationSum
} else if cloudbrain.Cloudbrain.Type == models.TypeCDCenter {
cDCenterDuration += duration
cDNetCardDuSum += durationSum
}
cloudbrains, _, err := models.CloudbrainAllStatic(&models.CloudbrainsOptions{
Type: models.TypeCloudBrainAll,
BeginTimeUnix: int64(recordBeginTime),
EndTimeUnix: endTime.Unix(),
})
if err != nil {
ctx.ServerError("Get cloudbrains failed:", err)
return
}
models.LoadSpecs4CloudbrainInfo(cloudbrains)

durationAllSum += duration
cardDuSum += durationSum
count = len(cloudbrains)
page += 1
for _, cloudbrain := range cloudbrains {
if cloudbrain.Cloudbrain.WorkServerNumber >= 1 {
worker_server_num = cloudbrain.Cloudbrain.WorkServerNumber
} else {
worker_server_num = 1
}
if cloudbrain.Cloudbrain.Spec == nil {
cardNum = 1
} else {
cardNum = cloudbrain.Cloudbrain.Spec.AccCardsNum
}
duration := cloudbrain.Duration
durationSum := cloudbrain.Duration * int64(worker_server_num) * int64(cardNum)
if cloudbrain.Cloudbrain.Type == models.TypeCloudBrainOne {
cloudBrainOneDuration += duration
cloudBrainOneCardDuSum += durationSum
} else if cloudbrain.Cloudbrain.Type == models.TypeCloudBrainTwo {
cloudBrainTwoDuration += duration
cloudBrainTwoCardDuSum += durationSum
} else if cloudbrain.Cloudbrain.Type == models.TypeC2Net {
c2NetDuration += duration
c2NetCardDuSum += durationSum
} else if cloudbrain.Cloudbrain.Type == models.TypeCDCenter {
cDCenterDuration += duration
cDNetCardDuSum += durationSum
}

durationAllSum += duration
cardDuSum += durationSum
}
ctx.JSON(http.StatusOK, map[string]interface{}{
"cloudBrainOneCardDuSum": cloudBrainOneCardDuSum,
@@ -532,6 +522,21 @@ func getPageDateCloudbrainInfo(dateCloudbrainInfo []DateCloudbrainInfo, page int

}

func getPageDateCloudbrainDuration(dateUsageStatistic []models.DateUsageStatistic, page int, pagesize int) []models.DateUsageStatistic {
begin := (page - 1) * pagesize
end := (page) * pagesize

if begin > len(dateUsageStatistic)-1 {
return nil
}
if end > len(dateUsageStatistic)-1 {
return dateUsageStatistic[begin:]
} else {
return dateUsageStatistic[begin:end]
}

}

func GetAllCloudbrainsPeriodDistribution(ctx *context.Context) {
queryType := ctx.QueryTrim("type")
beginTimeStr := ctx.QueryTrim("beginTime")
@@ -545,7 +550,7 @@ func GetAllCloudbrainsPeriodDistribution(ctx *context.Context) {
recordBeginTime := time.Unix(int64(recordCloudbrain[0].Cloudbrain.CreatedUnix), 0)
beginTime, endTime, err := getCloudbrainTimePeroid(ctx, recordBeginTime)
if err != nil {
log.Error("Parameter is wrong", err)
log.Error("getCloudbrainTimePeroid error:", err)
ctx.Error(http.StatusBadRequest, ctx.Tr("repo.parameter_is_wrong"))
return
}
@@ -1403,3 +1408,424 @@ func getCloudbrainTimePeroid(ctx *context.Context, recordBeginTime time.Time) (t

return beginTime, endTime, nil
}

func GetCloudbrainResourceOverview(ctx *context.Context) {
recordCloudbrainDuration, err := models.GetDurationRecordBeginTime()
if err != nil {
log.Error("Can not get GetDurationRecordBeginTime", err)
return
}
recordBeginTime := recordCloudbrainDuration[0].CreatedUnix
recordUpdateTime := time.Now().Unix()
resourceQueues, err := models.GetCanUseCardInfo()
if err != nil {
log.Info("GetCanUseCardInfo err: %v", err)
return
}
OpenIResourceDetail := []models.ResourceDetail{}
C2NetResourceDetail := []models.ResourceDetail{}
for _, resourceQueue := range resourceQueues {
if resourceQueue.Cluster == models.OpenICluster {
var resourceDetail models.ResourceDetail
resourceDetail.QueueCode = resourceQueue.QueueCode
resourceDetail.Cluster = resourceQueue.Cluster
resourceDetail.AiCenterCode = resourceQueue.AiCenterCode
resourceDetail.AiCenterName = resourceQueue.AiCenterName + "/" + resourceQueue.AiCenterCode
resourceDetail.ComputeResource = resourceQueue.ComputeResource
resourceDetail.AccCardType = resourceQueue.AccCardType + "(" + resourceQueue.ComputeResource + ")"
resourceDetail.CardsTotalNum = resourceQueue.CardsTotalNum
resourceDetail.IsAutomaticSync = resourceQueue.IsAutomaticSync
OpenIResourceDetail = append(OpenIResourceDetail, resourceDetail)
}
if resourceQueue.Cluster == models.C2NetCluster {
var resourceDetail models.ResourceDetail
resourceDetail.QueueCode = resourceQueue.QueueCode
resourceDetail.Cluster = resourceQueue.Cluster
resourceDetail.AiCenterCode = resourceQueue.AiCenterCode
resourceDetail.AiCenterName = resourceQueue.AiCenterName + "/" + resourceQueue.AiCenterCode
resourceDetail.ComputeResource = resourceQueue.ComputeResource
resourceDetail.AccCardType = resourceQueue.AccCardType + "(" + resourceQueue.ComputeResource + ")"
resourceDetail.CardsTotalNum = resourceQueue.CardsTotalNum
resourceDetail.IsAutomaticSync = resourceQueue.IsAutomaticSync
C2NetResourceDetail = append(C2NetResourceDetail, resourceDetail)
}
}
openIResourceNum := make(map[string]map[string]int)

for _, openIResourceDetail := range OpenIResourceDetail {
if _, ok := openIResourceNum[openIResourceDetail.AiCenterName]; !ok {
openIResourceNum[openIResourceDetail.AiCenterName] = make(map[string]int)
}
if _, ok := openIResourceNum[openIResourceDetail.AiCenterName][openIResourceDetail.AccCardType]; !ok {
openIResourceNum[openIResourceDetail.AiCenterName][openIResourceDetail.AccCardType] = openIResourceDetail.CardsTotalNum
} else {
openIResourceNum[openIResourceDetail.AiCenterName][openIResourceDetail.AccCardType] += openIResourceDetail.CardsTotalNum
}
}

c2NetResourceNum := make(map[string]map[string]int)
for _, c2NetResourceDetail := range C2NetResourceDetail {
if _, ok := c2NetResourceNum[c2NetResourceDetail.AiCenterName]; !ok {
c2NetResourceNum[c2NetResourceDetail.AiCenterName] = make(map[string]int)
}
if _, ok := c2NetResourceNum[c2NetResourceDetail.AiCenterName][c2NetResourceDetail.AccCardType]; !ok {
c2NetResourceNum[c2NetResourceDetail.AiCenterName][c2NetResourceDetail.AccCardType] = c2NetResourceDetail.CardsTotalNum
} else {
c2NetResourceNum[c2NetResourceDetail.AiCenterName][c2NetResourceDetail.AccCardType] += c2NetResourceDetail.CardsTotalNum
}

}

ctx.JSON(http.StatusOK, map[string]interface{}{
"openI": openIResourceNum,
"c2Net": c2NetResourceNum,
"recordUpdateTime": recordUpdateTime,
"recordBeginTime": recordBeginTime,
})
}

func GetCloudbrainResourceUsageDetail(ctx *context.Context) {
aiCenterCode := ctx.QueryTrim("aiCenterCode")
if aiCenterCode == "" {
aiCenterCode = models.AICenterOfCloudBrainOne
}
beginTime, endTime := getBeginAndEndTime(ctx)
dayCloudbrainDuration, count, err := getDayCloudbrainDuration(beginTime, endTime, aiCenterCode)
if err != nil {
log.Error("Can not query dayCloudbrainDuration.", err)
return
}
hourCloudbrainDuration, err := getHourCloudbrainDuration(beginTime, endTime, aiCenterCode)
if err != nil {
log.Error("Can not query hourCloudbrainDuration.", err)
return
}
page := ctx.QueryInt("page")
if page <= 0 {
page = 1
}
pagesize := ctx.QueryInt("pagesize")
if pagesize <= 0 {
pagesize = 36500
}
pageDateCloudbrainDuration := getPageDateCloudbrainDuration(dayCloudbrainDuration, page, pagesize)
ctx.JSON(http.StatusOK, map[string]interface{}{
"totalCount": count,
"pageDateCloudbrainDuration": pageDateCloudbrainDuration,
"hourCloudbrainDuration": hourCloudbrainDuration,
})
}

func GetDurationRateStatistic(ctx *context.Context) {
beginTime, endTime := getBeginAndEndTime(ctx)
OpenIDurationRate, C2NetDurationRate, totalUsageRate := getDurationStatistic(beginTime, endTime)

ctx.JSON(http.StatusOK, map[string]interface{}{
"openIDurationRate": OpenIDurationRate,
"c2NetDurationRate": C2NetDurationRate,
"totalUsageRate": totalUsageRate,
})

}

func CloudbrainDurationStatisticForTest(ctx *context.Context) {
repo.CloudbrainDurationStatisticHour()
ctx.JSON(http.StatusOK, map[string]interface{}{
"message": 0,
})
}

func getBeginAndEndTime(ctx *context.Context) (time.Time, time.Time) {
queryType := ctx.QueryTrim("type")
now := time.Now()
beginTimeStr := ctx.QueryTrim("beginTime")
endTimeStr := ctx.QueryTrim("endTime")

var beginTime time.Time
var endTime time.Time
var err error
if queryType != "" {
if queryType == "all" {
recordCloudbrainDuration, err := models.GetDurationRecordBeginTime()
if err != nil {
log.Error("Can not get GetDurationRecordBeginTime", err)
ctx.Error(http.StatusBadRequest, ctx.Tr("repo.record_begintime_get_err"))
return beginTime, endTime
}
brainRecordBeginTime := recordCloudbrainDuration[0].CreatedUnix.AsTime()
beginTime = brainRecordBeginTime
endTime = now
} else if queryType == "today" {
beginTime = now.AddDate(0, 0, 0)
beginTime = time.Date(beginTime.Year(), beginTime.Month(), beginTime.Day(), 0, 0, 0, 0, now.Location())
endTime = now

} else if queryType == "yesterday" {
beginTime = now.AddDate(0, 0, -1)
beginTime = time.Date(beginTime.Year(), beginTime.Month(), beginTime.Day(), 0, 0, 0, 0, now.Location())
endTime = time.Date(now.Year(), now.Month(), now.Day(), 0, 0, 0, 0, now.Location())
} else if queryType == "last_7day" {
beginTime = now.AddDate(0, 0, -6)
beginTime = time.Date(beginTime.Year(), beginTime.Month(), beginTime.Day(), 0, 0, 0, 0, now.Location())
endTime = now
} else if queryType == "last_30day" {
beginTime = now.AddDate(0, 0, -29)
beginTime = time.Date(beginTime.Year(), beginTime.Month(), beginTime.Day(), 0, 0, 0, 0, now.Location())
endTime = now
} else if queryType == "current_month" {
endTime = now
beginTime = time.Date(endTime.Year(), endTime.Month(), 1, 0, 0, 0, 0, now.Location())

} else if queryType == "current_year" {
endTime = now
beginTime = time.Date(endTime.Year(), 1, 1, 0, 0, 0, 0, now.Location())
} else if queryType == "last_month" {
lastMonthTime := now.AddDate(0, -1, 0)
beginTime = time.Date(lastMonthTime.Year(), lastMonthTime.Month(), 1, 0, 0, 0, 0, now.Location())
endTime = time.Date(now.Year(), now.Month(), 1, 0, 0, 0, 0, now.Location())
}

} else {
if beginTimeStr == "" || endTimeStr == "" {
//如果查询类型和开始时间结束时间都未设置,按queryType=all处理
recordCloudbrainDuration, err := models.GetDurationRecordBeginTime()
if err != nil {
log.Error("Can not get recordCloudbrain", err)
ctx.Error(http.StatusBadRequest, ctx.Tr("repo.record_begintime_get_err"))
return beginTime, endTime
}
brainRecordBeginTime := recordCloudbrainDuration[0].CreatedUnix.AsTime()
beginTime = brainRecordBeginTime
endTime = now
} else {
beginTime, err = time.ParseInLocation("2006-01-02", beginTimeStr, time.Local)
if err != nil {
log.Error("Can not ParseInLocation.", err)
ctx.Error(http.StatusBadRequest, ctx.Tr("ParseInLocation_get_error"))
return beginTime, endTime
}
endTime, err = time.ParseInLocation("2006-01-02", endTimeStr, time.Local)
if err != nil {
log.Error("Can not ParseInLocation.", err)
ctx.Error(http.StatusBadRequest, ctx.Tr("ParseInLocation_get_error"))
return beginTime, endTime
}
if endTime.After(time.Now()) {
endTime = time.Now()
}
}

}
return beginTime, endTime
}

func getAiCenterUsageDuration(beginTime time.Time, endTime time.Time, cloudbrainStatistics []*models.CloudbrainDurationStatistic) (int, int, float64) {
totalDuration := int(0)
usageDuration := int(0)
usageRate := float64(0)

for _, cloudbrainStatistic := range cloudbrainStatistics {
if int64(cloudbrainStatistic.CreatedUnix) >= beginTime.Unix() && int64(cloudbrainStatistic.CreatedUnix) < endTime.Unix() {
totalDuration += cloudbrainStatistic.CardsTotalDuration
usageDuration += cloudbrainStatistic.CardsUseDuration
}
}
if totalDuration == 0 || usageDuration == 0 {
usageRate = 0
} else {
usageRate = float64(usageDuration) / float64(totalDuration)
}

return totalDuration, usageDuration, usageRate
}

func getDurationStatistic(beginTime time.Time, endTime time.Time) (models.DurationRateStatistic, models.DurationRateStatistic, float64) {
OpenITotalDuration := make(map[string]int)
OpenIUsageDuration := make(map[string]int)
OpenIUsageRate := make(map[string]float64)

C2NetTotalDuration := make(map[string]int)
C2NetUsageDuration := make(map[string]int)
OpenIDurationRate := models.DurationRateStatistic{}
C2NetDurationRate := models.DurationRateStatistic{}
cardDurationStatistics, err := models.GetCardDurationStatistics(&models.DurationStatisticOptions{
BeginTime: beginTime,
EndTime: endTime,
})
if err != nil {
log.Error("GetCardDurationStatistics error:", err)
return OpenIDurationRate, C2NetDurationRate, 0
}
for _, cloudbrainStatistic := range cardDurationStatistics {
if cloudbrainStatistic.Cluster == models.OpenICluster {
if _, ok := OpenITotalDuration[cloudbrainStatistic.AiCenterName]; !ok {
OpenITotalDuration[cloudbrainStatistic.AiCenterName] = cloudbrainStatistic.CardsTotalDuration
} else {
OpenITotalDuration[cloudbrainStatistic.AiCenterName] += cloudbrainStatistic.CardsTotalDuration
}
if _, ok := OpenIUsageDuration[cloudbrainStatistic.AiCenterName]; !ok {
OpenIUsageDuration[cloudbrainStatistic.AiCenterName] = cloudbrainStatistic.CardsUseDuration
} else {
OpenIUsageDuration[cloudbrainStatistic.AiCenterName] += cloudbrainStatistic.CardsUseDuration
}
}
if cloudbrainStatistic.Cluster == models.C2NetCluster {
if _, ok := C2NetTotalDuration[cloudbrainStatistic.AiCenterName]; !ok {
C2NetTotalDuration[cloudbrainStatistic.AiCenterName] = cloudbrainStatistic.CardsTotalDuration
} else {
C2NetTotalDuration[cloudbrainStatistic.AiCenterName] += cloudbrainStatistic.CardsTotalDuration
}
if _, ok := C2NetUsageDuration[cloudbrainStatistic.AiCenterName]; !ok {
C2NetUsageDuration[cloudbrainStatistic.AiCenterName] = cloudbrainStatistic.CardsUseDuration
} else {
C2NetUsageDuration[cloudbrainStatistic.AiCenterName] += cloudbrainStatistic.CardsUseDuration
}
}
}
ResourceAiCenterRes, err := models.GetResourceAiCenters()
if err != nil {
log.Error("Can not get ResourceAiCenterRes.", err)
return OpenIDurationRate, C2NetDurationRate, 0
}
for _, v := range ResourceAiCenterRes {
if cutString(v.AiCenterCode, 4) == cutString(models.AICenterOfCloudBrainOne, 4) {
if _, ok := OpenIUsageDuration[v.AiCenterName]; !ok {
OpenIUsageDuration[v.AiCenterName] = 0
}
if _, ok := OpenITotalDuration[v.AiCenterName]; !ok {
OpenITotalDuration[v.AiCenterName] = 0
}
} else {
if _, ok := C2NetUsageDuration[v.AiCenterName]; !ok {
C2NetUsageDuration[v.AiCenterName] = 0
}
}
}
totalCanUse := float64(0)
totalUse := float64(0)
totalUsageRate := float64(0)
for k, v := range OpenITotalDuration {
for i, j := range OpenIUsageDuration {
if k == i {
OpenIUsageRate[k] = float64(j) / float64(v)
}
}
}
for _, v := range OpenITotalDuration {
totalCanUse += float64(v)
}
for _, v := range OpenIUsageRate {
totalUse += float64(v)
}
if totalCanUse == 0 || totalUse == 0 {
totalUsageRate = 0
} else {
totalUsageRate = totalUse / totalCanUse
}

OpenIDurationRate.AiCenterTotalDurationStat = OpenITotalDuration
OpenIDurationRate.AiCenterUsageDurationStat = OpenIUsageDuration
OpenIDurationRate.UsageRate = OpenIUsageRate
C2NetDurationRate.AiCenterTotalDurationStat = C2NetTotalDuration
C2NetDurationRate.AiCenterUsageDurationStat = C2NetUsageDuration
return OpenIDurationRate, C2NetDurationRate, totalUsageRate
}

func cutString(str string, lens int) string {
if len(str) < lens {
return str
}
return str[:lens]
}

func getDayCloudbrainDuration(beginTime time.Time, endTime time.Time, aiCenterCode string) ([]models.DateUsageStatistic, int, error) {
now := time.Now()
endTimeTemp := time.Date(endTime.Year(), endTime.Month(), endTime.Day(), 0, 0, 0, 0, now.Location())
if endTimeTemp.Equal(endTime) {
endTimeTemp = endTimeTemp.AddDate(0, 0, -1)
}
cardDurationStatistics, err := models.GetCardDurationStatistics(&models.DurationStatisticOptions{
BeginTime: beginTime,
EndTime: endTime,
AiCenterCode: aiCenterCode,
})
if err != nil {
log.Error("GetCardDurationStatistics error:", err)
return nil, 0, err
}

dayCloudbrainInfo := make([]models.DateUsageStatistic, 0)
count := 0
for beginTime.Before(endTimeTemp) || beginTime.Equal(endTimeTemp) {
TotalDuration, UsageDuration, UsageRate := getAiCenterUsageDuration(endTimeTemp, endTime, cardDurationStatistics)
dayCloudbrainInfo = append(dayCloudbrainInfo, models.DateUsageStatistic{
Date: endTimeTemp.Format("2006/01/02"),
UsageDuration: UsageDuration,
TotalDuration: TotalDuration,
UsageRate: UsageRate,
})
endTime = endTimeTemp
endTimeTemp = endTimeTemp.AddDate(0, 0, -1)
if endTimeTemp.Before(beginTime) && beginTime.Before(endTime) {
endTimeTemp = beginTime
}
count += 1
}
return dayCloudbrainInfo, count, nil
}

func getHourCloudbrainDuration(beginTime time.Time, endTime time.Time, aiCenterCode string) (models.HourTimeStatistic, error) {
hourTimeTotalDuration := make(map[string]int)
hourTimeUsageDuration := make(map[string]int)
hourTimeUsageRate := make(map[string]float64)
hourTimeStatistic := models.HourTimeStatistic{}

cardDurationStatistics, err := models.GetCardDurationStatistics(&models.DurationStatisticOptions{
BeginTime: beginTime,
EndTime: endTime,
})
if err != nil {
log.Error("GetCardDurationStatistics error:", err)
return hourTimeStatistic, err
}
for _, cloudbrainStatistic := range cardDurationStatistics {
if cloudbrainStatistic.AiCenterCode == aiCenterCode {
if _, ok := hourTimeTotalDuration[strconv.Itoa(cloudbrainStatistic.HourTime)]; !ok {
hourTimeTotalDuration[strconv.Itoa(cloudbrainStatistic.HourTime)] = cloudbrainStatistic.CardsTotalDuration
} else {
hourTimeTotalDuration[strconv.Itoa(cloudbrainStatistic.HourTime)] += cloudbrainStatistic.CardsTotalDuration
}
if _, ok := hourTimeUsageDuration[strconv.Itoa(cloudbrainStatistic.HourTime)]; !ok {
hourTimeUsageDuration[strconv.Itoa(cloudbrainStatistic.HourTime)] = cloudbrainStatistic.CardsUseDuration
} else {
hourTimeUsageDuration[strconv.Itoa(cloudbrainStatistic.HourTime)] += cloudbrainStatistic.CardsUseDuration
}
}
}
hourTimeList := []string{"0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15", "16", "17", "18", "19", "20", "21", "22", "23"}
for _, v := range hourTimeList {
if _, ok := hourTimeUsageDuration[v]; !ok {
hourTimeUsageDuration[v] = 0
}
if _, ok := hourTimeTotalDuration[v]; !ok {
hourTimeTotalDuration[v] = 0
}
}

for k, v := range hourTimeTotalDuration {
for i, j := range hourTimeUsageDuration {
if k == i {
if v == 0 || j == 0 {
hourTimeUsageRate[k] = 0
} else {
hourTimeUsageRate[k] = float64(j) / float64(v)
}
}
}
}

hourTimeStatistic.HourTimeTotalDuration = hourTimeTotalDuration
hourTimeStatistic.HourTimeUsageDuration = hourTimeUsageDuration
hourTimeStatistic.HourTimeUsageRate = hourTimeUsageRate
return hourTimeStatistic, nil
}

+ 17
- 1
routers/repo/ai_model_convert.go View File

@@ -29,7 +29,9 @@ const (
tplModelConvertInfo = "repo/modelmanage/convertshowinfo"
PYTORCH_ENGINE = 0
TENSORFLOW_ENGINE = 1
MINDSPORE_ENGIN = 2
MINDSPORE_ENGINE = 2
PADDLE_ENGINE = 4
MXNET_ENGINE = 6
ModelMountPath = "/model"
CodeMountPath = "/code"
DataSetMountPath = "/dataset"
@@ -395,6 +397,20 @@ func createGpuTrainJob(modelConvert *models.AiModelConvert, ctx *context.Context
deleteLocalDir(relatetiveModelPath)
dataActualPath = setting.Attachment.Minio.RealPath + setting.Attachment.Minio.Bucket + "/" + setting.CBCodePathPrefix + modelConvert.ID + "/dataset"
}
} else if modelConvert.SrcEngine == PADDLE_ENGINE {
IMAGE_URL = setting.ModelConvert.GPU_PADDLE_IMAGE
if modelConvert.DestFormat == CONVERT_FORMAT_ONNX {
command = getGpuModelConvertCommand(modelConvert.ID, modelConvert.ModelPath, modelConvert, setting.ModelConvert.PaddleOnnxBootFile)
} else {
return errors.New("Not support the format.")
}
} else if modelConvert.SrcEngine == MXNET_ENGINE {
IMAGE_URL = setting.ModelConvert.GPU_MXNET_IMAGE
if modelConvert.DestFormat == CONVERT_FORMAT_ONNX {
command = getGpuModelConvertCommand(modelConvert.ID, modelConvert.ModelPath, modelConvert, setting.ModelConvert.MXnetOnnxBootFile)
} else {
return errors.New("Not support the format.")
}
}
log.Info("dataActualPath=" + dataActualPath)



+ 5
- 7
routers/repo/ai_model_manage.go View File

@@ -17,6 +17,7 @@ import (
"code.gitea.io/gitea/modules/notification"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/storage"
"code.gitea.io/gitea/services/cloudbrain/resource"
uuid "github.com/satori/go.uuid"
)

@@ -69,13 +70,10 @@ func saveModelByParameters(jobId string, versionName string, name string, versio
cloudType = models.TypeCloudBrainTwo
} else if aiTask.ComputeResource == models.GPUResource {
cloudType = models.TypeCloudBrainOne
var ResourceSpecs *models.ResourceSpecs
json.Unmarshal([]byte(setting.ResourceSpecs), &ResourceSpecs)
for _, tmp := range ResourceSpecs.ResourceSpec {
if tmp.Id == aiTask.ResourceSpecId {
flaverName := ctx.Tr("cloudbrain.gpu_num") + ": " + fmt.Sprint(tmp.GpuNum) + " " + ctx.Tr("cloudbrain.cpu_num") + ": " + fmt.Sprint(tmp.CpuNum) + " " + ctx.Tr("cloudbrain.memory") + "(MB): " + fmt.Sprint(tmp.MemMiB) + " " + ctx.Tr("cloudbrain.shared_memory") + "(MB): " + fmt.Sprint(tmp.ShareMemMiB)
aiTask.FlavorName = flaverName
}
spec, err := resource.GetCloudbrainSpec(aiTask.ID)
if err == nil {
flaverName := "GPU: " + fmt.Sprint(spec.AccCardsNum) + "*" + spec.AccCardType + ",CPU: " + fmt.Sprint(spec.CpuCores) + "," + ctx.Tr("cloudbrain.memory") + ": " + fmt.Sprint(spec.MemGiB) + "GB," + ctx.Tr("cloudbrain.shared_memory") + ": " + fmt.Sprint(spec.ShareMemGiB) + "GB"
aiTask.FlavorName = flaverName
}
}



+ 7
- 0
routers/repo/aisafety.go View File

@@ -291,6 +291,7 @@ func queryTaskStatusFromCloudbrain(job *models.Cloudbrain) {
} else {
//
job.Status = string(models.ModelSafetyTesting)
job.EndTime = 0
err = models.UpdateJob(job)
if err != nil {
log.Error("UpdateJob failed:", err)
@@ -307,6 +308,9 @@ func queryTaskStatusFromModelSafetyTestServer(job *models.Cloudbrain) {
if result.Data.Status == 1 {
log.Info("The task is running....")
} else {
job.EndTime = timeutil.TimeStampNow()
job.Duration = (job.EndTime.AsTime().Unix() - job.StartTime.AsTime().Unix()) / 1000
job.TrainJobDuration = models.ConvertDurationToStr(job.Duration)
if result.Data.Code == 0 {
job.ResultJson = result.Data.StandardJson
job.Status = string(models.JobSucceeded)
@@ -440,6 +444,9 @@ func updateJobFailed(job *models.Cloudbrain, msg string) {
//update task failed.
job.Status = string(models.ModelArtsTrainJobFailed)
job.ResultJson = msg
job.EndTime = timeutil.TimeStampNow()
job.Duration = (job.EndTime.AsTime().Unix() - job.StartTime.AsTime().Unix()) / 1000
job.TrainJobDuration = models.ConvertDurationToStr(job.Duration)
err := models.UpdateJob(job)
if err != nil {
log.Error("UpdateJob failed:", err)


+ 34
- 33
routers/repo/cloudbrain.go View File

@@ -753,47 +753,48 @@ func cloudBrainShow(ctx *context.Context, tpName base.TplName, jobType models.Jo
ctx.NotFound(ctx.Req.URL.RequestURI(), nil)
return
}

result, err := cloudbrain.GetJob(task.JobID)
if err != nil {
log.Info("error:" + err.Error())
ctx.NotFound(ctx.Req.URL.RequestURI(), nil)
return
}
prepareSpec4Show(ctx, task)
if ctx.Written() {
return
}
if task.Status==string(models.JobWaiting) || task.Status==string(models.JobRunning) {
result, err := cloudbrain.GetJob(task.JobID)
if err != nil {
log.Info("error:" + err.Error())
ctx.NotFound(ctx.Req.URL.RequestURI(), nil)
return
}

if result != nil {
jobRes, _ := models.ConvertToJobResultPayload(result.Payload)
taskRoles := jobRes.TaskRoles
taskRes, _ := models.ConvertToTaskPod(taskRoles[cloudbrain.SubTaskName].(map[string]interface{}))
ctx.Data["taskRes"] = taskRes
ctx.Data["ExitDiagnostics"] = taskRes.TaskStatuses[0].ExitDiagnostics
oldStatus := task.Status
task.Status = taskRes.TaskStatuses[0].State
task.ContainerIp = ""
task.ContainerID = taskRes.TaskStatuses[0].ContainerID
models.ParseAndSetDurationFromCloudBrainOne(jobRes, task)

if task.DeletedAt.IsZero() { //normal record
if oldStatus != task.Status {
notification.NotifyChangeCloudbrainStatus(task, oldStatus)
}
err = models.UpdateJob(task)
if err != nil {
ctx.Data["error"] = err.Error()
return
}
} else { //deleted record

if result != nil {
jobRes, _ := models.ConvertToJobResultPayload(result.Payload)
taskRoles := jobRes.TaskRoles
taskRes, _ := models.ConvertToTaskPod(taskRoles[cloudbrain.SubTaskName].(map[string]interface{}))
ctx.Data["taskRes"] = taskRes
ctx.Data["ExitDiagnostics"] = taskRes.TaskStatuses[0].ExitDiagnostics
oldStatus := task.Status
task.Status = taskRes.TaskStatuses[0].State
task.ContainerIp = ""
task.ContainerID = taskRes.TaskStatuses[0].ContainerID
models.ParseAndSetDurationFromCloudBrainOne(jobRes, task)

if task.DeletedAt.IsZero() { //normal record
if oldStatus != task.Status {
notification.NotifyChangeCloudbrainStatus(task, oldStatus)
}
err = models.UpdateJob(task)
if err != nil {
ctx.Data["error"] = err.Error()
return
}
} else { //deleted record

ctx.Data["result"] = jobRes
} else {
log.Info("error:" + err.Error())
return
}

ctx.Data["result"] = jobRes
} else {
log.Info("error:" + err.Error())
return
}

user, err := models.GetUserByID(task.UserID)


+ 169
- 0
routers/repo/cloudbrain_statistic.go View File

@@ -0,0 +1,169 @@
package repo

import (
"strings"
"time"

"code.gitea.io/gitea/models"
"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/timeutil"
)

func CloudbrainDurationStatisticHour() {

dateTime := time.Now().Format("2006-01-02 15:04:05")
dayTime := time.Now().Format("2006-01-02")
now := time.Now()

currentTime := time.Date(now.Year(), now.Month(), now.Day(), now.Hour(), 0, 0, 0, now.Location())

m, _ := time.ParseDuration("-1h")
beginTime := currentTime.Add(m).Unix()
endTime := currentTime.Unix()
hourTime := currentTime.Add(m).Hour()

ciTasks, err := models.GetCloudbrainByTime(beginTime, endTime)
if err != nil {
log.Info("GetCloudbrainByTime err: %v", err)
return
}
specMap := make(map[string]*models.Specification)
models.LoadSpecs4CloudbrainInfo(ciTasks)
for _, cloudbrain := range ciTasks {
if _, ok := specMap[cloudbrain.Cloudbrain.Spec.AiCenterCode+"/"+cloudbrain.Cloudbrain.Spec.AccCardType]; !ok {
if cloudbrain.Cloudbrain.Spec != nil {
specMap[cloudbrain.Cloudbrain.Spec.AiCenterCode+"/"+cloudbrain.Cloudbrain.Spec.AccCardType] = cloudbrain.Cloudbrain.Spec
}
}
}

cloudBrainCenterCodeAndCardTypeInfo := getcloudBrainCenterCodeAndCardTypeInfo(ciTasks, beginTime, endTime)

resourceQueues, err := models.GetCanUseCardInfo()
if err != nil {
log.Info("GetCanUseCardInfo err: %v", err)
return
}
cardsTotalDurationMap := make(map[string]int)
for _, resourceQueue := range resourceQueues {
cardsTotalDurationMap[resourceQueue.Cluster+"/"+resourceQueue.AiCenterName+"/"+resourceQueue.AiCenterCode+"/"+resourceQueue.AccCardType+"/"+resourceQueue.ComputeResource] = resourceQueue.CardsTotalNum * 1 * 60 * 60
}

for centerCode, CardTypeInfo := range cloudBrainCenterCodeAndCardTypeInfo {
for cardType, cardDuration := range CardTypeInfo {
spec := specMap[centerCode+"/"+cardType]
if spec != nil {
if err := models.DeleteCloudbrainDurationStatisticHour(dayTime, hourTime, centerCode, cardType); err != nil {
log.Error("DeleteCloudbrainDurationStatisticHour failed: %v", err.Error())
return
}
if _, ok := cardsTotalDurationMap[spec.Cluster+"/"+spec.AiCenterName+"/"+centerCode+"/"+cardType+"/"+spec.ComputeResource]; !ok {
cardsTotalDurationMap[spec.Cluster+"/"+spec.AiCenterName+"/"+centerCode+"/"+cardType+"/"+spec.ComputeResource] = 0
}
cloudbrainDurationStat := models.CloudbrainDurationStatistic{
DateTime: dateTime,
DayTime: dayTime,
HourTime: hourTime,
Cluster: spec.Cluster,
AiCenterName: spec.AiCenterName,
AiCenterCode: centerCode,
AccCardType: cardType,
ComputeResource: spec.ComputeResource,
CardsUseDuration: cardDuration,
CardsTotalDuration: cardsTotalDurationMap[spec.Cluster+"/"+spec.AiCenterName+"/"+centerCode+"/"+cardType+"/"+spec.ComputeResource],
CreatedUnix: timeutil.TimeStampNow(),
}
if _, err = models.InsertCloudbrainDurationStatistic(&cloudbrainDurationStat); err != nil {
log.Error("Insert cloudbrainDurationStat failed: %v", err.Error())
}
delete(cardsTotalDurationMap, spec.Cluster+"/"+spec.AiCenterName+"/"+centerCode+"/"+cardType+"/"+spec.ComputeResource)
}
}
}

for key, cardsTotalDuration := range cardsTotalDurationMap {
if err := models.DeleteCloudbrainDurationStatisticHour(dayTime, hourTime, strings.Split(key, "/")[2], strings.Split(key, "/")[3]); err != nil {
log.Error("DeleteCloudbrainDurationStatisticHour failed: %v", err.Error())
return
}
cloudbrainDurationStat := models.CloudbrainDurationStatistic{
DateTime: dateTime,
DayTime: dayTime,
HourTime: hourTime,
Cluster: strings.Split(key, "/")[0],
AiCenterName: strings.Split(key, "/")[1],
AiCenterCode: strings.Split(key, "/")[2],
AccCardType: strings.Split(key, "/")[3],
ComputeResource: strings.Split(key, "/")[4],
CardsUseDuration: 0,
CardsTotalDuration: cardsTotalDuration,
CreatedUnix: timeutil.TimeStampNow(),
}
if _, err = models.InsertCloudbrainDurationStatistic(&cloudbrainDurationStat); err != nil {
log.Error("Insert cloudbrainDurationStat failed: %v", err.Error())
}
}

log.Info("finish summary cloudbrainDurationStat")
}

func getcloudBrainCenterCodeAndCardTypeInfo(ciTasks []*models.CloudbrainInfo, beginTime int64, endTime int64) map[string]map[string]int {
var WorkServerNumber int
var AccCardsNum int
cloudBrainCenterCodeAndCardType := make(map[string]map[string]int)
for _, cloudbrain := range ciTasks {

if cloudbrain.Cloudbrain.StartTime == 0 {
cloudbrain.Cloudbrain.StartTime = cloudbrain.Cloudbrain.CreatedUnix
}
if cloudbrain.Cloudbrain.EndTime == 0 {
cloudbrain.Cloudbrain.EndTime = cloudbrain.Cloudbrain.UpdatedUnix
}
if cloudbrain.Cloudbrain.WorkServerNumber >= 1 {
WorkServerNumber = cloudbrain.Cloudbrain.WorkServerNumber
} else {
WorkServerNumber = 1
}
if cloudbrain.Cloudbrain.Spec == nil {
AccCardsNum = 1
} else {
AccCardsNum = cloudbrain.Cloudbrain.Spec.AccCardsNum
}
if _, ok := cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode]; !ok {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode] = make(map[string]int)
}

if cloudbrain.Cloudbrain.Status == string(models.ModelArtsRunning) {
if _, ok := cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType]; !ok {
if int64(cloudbrain.Cloudbrain.StartTime) < beginTime {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] = AccCardsNum * WorkServerNumber * (int(endTime) - int(beginTime))
} else {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] = AccCardsNum * WorkServerNumber * (int(endTime) - int(cloudbrain.Cloudbrain.StartTime))
}
} else {
if int64(cloudbrain.Cloudbrain.StartTime) < beginTime {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] += AccCardsNum * WorkServerNumber * (int(endTime) - int(beginTime))
} else {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] += AccCardsNum * WorkServerNumber * (int(endTime) - int(cloudbrain.Cloudbrain.StartTime))
}
}
} else {
if _, ok := cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType]; !ok {
if int64(cloudbrain.Cloudbrain.StartTime) < beginTime {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] = AccCardsNum * WorkServerNumber * (int(cloudbrain.Cloudbrain.EndTime) - int(beginTime))
} else {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] = AccCardsNum * WorkServerNumber * (int(cloudbrain.Cloudbrain.EndTime) - int(cloudbrain.Cloudbrain.StartTime))
}
} else {
if int64(cloudbrain.Cloudbrain.StartTime) < beginTime {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] += AccCardsNum * WorkServerNumber * (int(cloudbrain.Cloudbrain.EndTime) - int(beginTime))
} else {
cloudBrainCenterCodeAndCardType[cloudbrain.Cloudbrain.Spec.AiCenterCode][cloudbrain.Cloudbrain.Spec.AccCardType] += AccCardsNum * WorkServerNumber * (int(cloudbrain.Cloudbrain.EndTime) - int(cloudbrain.Cloudbrain.StartTime))
}
}

}
}

return cloudBrainCenterCodeAndCardType
}

+ 2
- 0
routers/repo/dataset.go View File

@@ -523,6 +523,7 @@ func ReferenceDatasetAvailable(ctx *context.Context) {
PublicOnly: true,
NeedAttachment: false,
CloudBrainType: models.TypeCloudBrainAll,
SearchOrderBy: models.SearchOrderByDefault,
}
dataset, _ := models.GetDatasetByRepo(&models.Repository{ID: ctx.Repo.Repository.ID})
if dataset != nil {
@@ -538,6 +539,7 @@ func PublicDatasetMultiple(ctx *context.Context) {
PublicOnly: true,
NeedAttachment: true,
CloudBrainType: ctx.QueryInt("type"),
SearchOrderBy: models.SearchOrderByDefault,
}
datasetMultiple(ctx, opts)



+ 2
- 4
routers/repo/grampus.go View File

@@ -38,6 +38,7 @@ import (
"code.gitea.io/gitea/modules/context"
"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/setting"
cloudbrainService "code.gitea.io/gitea/services/cloudbrain"
)

const (
@@ -921,10 +922,7 @@ func GrampusTrainJobShow(ctx *context.Context) {
ctx.Data["canDownload"] = cloudbrain.CanModifyJob(ctx, task)
ctx.Data["displayJobName"] = task.DisplayJobName

aiCenterInfo := strings.Split(task.AiCenter, "+")
if len(aiCenterInfo) == 2 {
ctx.Data["ai_center"] = aiCenterInfo[1]
}
ctx.Data["ai_center"] = cloudbrainService.GetAiCenterShow(task.AiCenter,ctx)

ctx.HTML(http.StatusOK, tplGrampusTrainJobShow)
}


+ 34
- 0
routers/repo/modelarts.go View File

@@ -1312,6 +1312,36 @@ func getUserCommand(engineId int, req *modelarts.GenerateTrainJobReq) (string, s
return userCommand, userImageUrl
}

func getInfJobUserCommand(engineId int, req *modelarts.GenerateInferenceJobReq) (string, string) {
userImageUrl := ""
userCommand := ""
if engineId < 0 {
tmpCodeObsPath := strings.Trim(req.CodeObsPath, "/")
tmpCodeObsPaths := strings.Split(tmpCodeObsPath, "/")
lastCodeDir := "code"
if len(tmpCodeObsPaths) > 0 {
lastCodeDir = tmpCodeObsPaths[len(tmpCodeObsPaths)-1]
}
userCommand = "/bin/bash /home/work/run_train.sh 's3://" + req.CodeObsPath + "' '" + lastCodeDir + "/" + req.BootFile + "' '/tmp/log/train.log' --'data_url'='s3://" + req.DataUrl + "' --'train_url'='s3://" + req.TrainUrl + "'"
var versionInfos modelarts.VersionInfo
if err := json.Unmarshal([]byte(setting.EngineVersions), &versionInfos); err != nil {
log.Info("json parse err." + err.Error())
} else {
for _, engine := range versionInfos.Version {
if engine.ID == engineId {
userImageUrl = engine.Url
break
}
}
}
for _, param := range req.Parameters {
userCommand += " --'" + param.Label + "'='" + param.Value + "'"
}
return userCommand, userImageUrl
}
return userCommand, userImageUrl
}

func TrainJobCreateVersion(ctx *context.Context, form auth.CreateModelArtsTrainJobForm) {
ctx.Data["PageIsTrainJob"] = true
var jobID = ctx.Params(":jobid")
@@ -2171,6 +2201,10 @@ func InferenceJobCreate(ctx *context.Context, form auth.CreateModelArtsInference
JobType: string(models.JobTypeInference),
}

userCommand, userImageUrl := getInfJobUserCommand(engineID, req)
req.UserCommand = userCommand
req.UserImageUrl = userImageUrl

err = modelarts.GenerateInferenceJob(ctx, req)
if err != nil {
log.Error("GenerateTrainJob failed:%v", err.Error())


+ 6
- 5
routers/routes/routes.go View File

@@ -6,17 +6,18 @@ package routes

import (
"bytes"
"code.gitea.io/gitea/routers/badge"
"code.gitea.io/gitea/routers/reward/point"
"code.gitea.io/gitea/routers/task"
badge_service "code.gitea.io/gitea/services/badge"
"code.gitea.io/gitea/services/reward"
"encoding/gob"
"net/http"
"path"
"text/template"
"time"

"code.gitea.io/gitea/routers/badge"
"code.gitea.io/gitea/routers/reward/point"
"code.gitea.io/gitea/routers/task"
badge_service "code.gitea.io/gitea/services/badge"
"code.gitea.io/gitea/services/reward"

"code.gitea.io/gitea/routers/modelapp"

"code.gitea.io/gitea/modules/slideimage"


+ 33
- 0
services/cloudbrain/util.go View File

@@ -0,0 +1,33 @@
package cloudbrain

import (
"code.gitea.io/gitea/modules/context"
"code.gitea.io/gitea/modules/setting"
"strings"
)

func GetAiCenterShow(aiCenter string,ctx *context.Context) string{
aiCenterInfo := strings.Split(aiCenter, "+")

if len(aiCenterInfo) == 2{
if setting.C2NetMapInfo!=nil {
if info,ok:=setting.C2NetMapInfo[aiCenterInfo[0]];ok {
if ctx.Language() == "zh-CN" {
return info.Content
} else {
return info.ContentEN
}
}else{
return aiCenterInfo[1]
}

}else{
return aiCenterInfo[1]
}

}

return ""


}

+ 11
- 0
templates/admin/cloudbrain/list.tmpl View File

@@ -497,6 +497,17 @@
</div>
</div>
</div>
<div class="ui modal debug-again-alert">
<div class="ui message" style="background-color: rgba(242, 113, 28, 0.05);border: 1px solid rgba(242, 113, 28, 1);border-radius: 5px;">
<div style="display: flex;align-items: center;">
<i class="ri-information-line" style="font-size: 35px;color: rgba(242, 113, 28, 1);;"></i>
<div style="text-align: left;margin-left: 1rem;">
<div style="font-weight: 600;line-height: 2;">{{.i18n.Tr "repo.cloudbrain.morethanonejob1" | Safe }}</div>
<div style="color:#939393">{{.i18n.Tr "repo.cloudbrain.morethanonejob2" | Safe}}</div>
</div>
</div>
</div>
</div>
</div>
<script>
document.addEventListener('DOMContentLoaded', function() {


+ 1
- 1
templates/base/footer_content.tmpl View File

@@ -45,7 +45,7 @@
<div class="sixteen wide mobile eight wide tablet eight wide computer column" style=" margin:2.0rem 0">
{{.i18n.Tr "custom.foot.copyright"}} <a href="http://beian.miit.gov.cn/" target="_blank">京ICP备18004880号</a>
<br>
{{.i18n.Tr "Powered_by 鹏城实验室云脑、"}}<a href="https://www.trustie.net/" target="_blank">Trustie确实</a>{{.i18n.Tr "、gitea"}}
{{.i18n.Tr "home.powerdby"}}<a href="https://www.trustie.net/" target="_blank">Trustie确实</a>{{.i18n.Tr "、Gitea"}}
<br>
</div>
</div>


+ 3
- 4
templates/custom/alert_cb.tmpl View File

@@ -1,11 +1,10 @@
{{if .NotStopTaskCount}}
<div class="ui message" style="background-color: rgba(242, 113, 28, 0.05);border: 1px solid rgba(242, 113, 28, 1);border-radius: 5px;">
<i class="close icon"></i>
<div class="ui message" style="background-color: rgba(242, 113, 28, 0.05);border: 1px solid rgba(242, 113, 28, 1);border-radius: 5px;">
<div style="display: flex;align-items: center;">
<i class="ri-information-line" style="font-size: 35px;color: rgba(242, 113, 28, 1);;"></i>
<div style="text-align: left;margin-left: 1rem;">
<div style="font-weight: 600;line-height: 2;">您已经有 <span style="color:rgba(242, 113, 28, 1);">同类任务</span> 正在等待或运行中,请等待任务结束再创建</div>
<div style="color:#939393">可以在 “<a href="/cloudbrains" >个人中心 > 云脑任务</a>” 查看您所有的云脑任务</div>
<div style="font-weight: 600;line-height: 2;">{{.i18n.Tr "repo.cloudbrain.morethanonejob1" | Safe }}</div>
<div style="color:#939393">{{.i18n.Tr "repo.cloudbrain.morethanonejob2" | Safe}}</div>
</div>
</div>
</div>

+ 47
- 0
templates/custom/max_log.tmpl View File

@@ -0,0 +1,47 @@
<div>
<div class="ui modal max-full-log{{.VersionName}} container" style="height: 90%;margin: 3rem auto;">
<div class="file-info" style="padding: 2rem;justify-content: space-between;">
<div id="log-file-title" style="font-size: 16px;font-weight:600"></div>
<div class="file-info">
<a class="file-info" id="{{.VersionName}}-log-down" href="">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;" class="log-file-down"></span>
</a>
<div class="file-info close-log-dialog" data-version="{{.VersionName}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;">
<i class="ri-fullscreen-exit-fill" style="font-size: 16px;"></i>
<span id="log-file-exit" style="margin-left: 0.3rem;font-size: 12px;"></span>
</div>
</div>
</div>
<div style="margin: 0 2.5rem;border: 1px solid #e8e8e8;height: 88%;position: relative;">
<span>
<a style="position: absolute; right: -32px;cursor: pointer;"
class="log_top-max" data-version="{{.VersionName}}" data-max="-max"><i class="icon-to-top"></i></a>
</span>
<span class="log-info-{{.VersionName}}">
<a style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
class="log_bottom-max" data-version="{{.VersionName}}" data-max="-max"><i
class="icon-to-bottom"></i></a>
</span>
<div class="ui message message-max{{.VersionName}}" style="display: none;">
<div id="header"></div>
</div>
<div class="log-scroll-max" id="log-max{{.VersionName}}" data-version="{{.VersionName}}" style="overflow: auto;max-height: 100%;">
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<pre id="log_file-max{{.VersionName}}"></pre>
</div>
</div>
</div>
</div>
<script>
$(".ui.modal .close-log-dialog").click(function () {
let version_name = $(this).data("version");
$(`.ui.modal.max-full-log${version_name}`).modal("hide");
});
</script>

+ 1
- 1
templates/repo/badge.tmpl View File

@@ -1,7 +1,7 @@
<div class="badge-achive">
{{range .AllBadges }}
<div class="bagde-section">
<div class="badge-section-title">{{.CategoryName}} &nbsp; (已点亮{{.LightedNum}}个)</div>
<div class="badge-section-title">{{.CategoryName}} &nbsp; (已点亮 {{.LightedNum}} 个)</div>
<div class="badge-section-children">
<div class="badge-honor-badge">
<div class="badge-honor-badge-basic">


+ 6
- 4
templates/repo/cloudbrain/benchmark/new.tmpl View File

@@ -32,7 +32,9 @@
<div class="repository">
{{template "repo/header" .}}
<div class="ui container">
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.evaluate_job.new_job"}}
@@ -151,7 +153,7 @@
</div>
<div class="inline min_title field">
<label class="label-fix-width" style="font-weight: normal;"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="/">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>
@@ -283,7 +285,7 @@

<div class="inline unite min_title field">
<label class="label-fix-width" style="font-weight: normal;"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="/">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>
@@ -354,7 +356,7 @@

<div class="inline unite min_title field">
<label class="label-fix-width" style="font-weight: normal;"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="/">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 22
- 11
templates/repo/cloudbrain/benchmark/show.tmpl View File

@@ -524,23 +524,29 @@
</div>
</div>
<div class="ui tab" data-tab="second{{$k}}">
<div>
<div class="file-info">
<a id="{{.VersionName}}-log-down"
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}}'
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}} file-info'
href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain/{{.ID}}/download_log_file">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>
<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain/{{.ID}}/download_log_file"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div
style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
<span>
<a title="滚动到顶部" style="position: absolute; right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_start"}}" style="position: absolute; right: -32px;cursor: pointer;"
class="log_top" data-version="{{.VersionName}}"><i class="icon-to-top"></i></a>
</span>
<span class="log-info-{{.VersionName}}">
<a title="滚动到底部" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_end"}}" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
class="log_bottom" data-version="{{.VersionName}}"><i
class="icon-to-bottom"></i></a>
</span>
@@ -549,12 +555,16 @@
</div>
<div class="ui attached log log-scroll" id="log{{.VersionName}}" data-version="{{.VersionName}}"
style="height: 300px !important; overflow: auto;">
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="start_line" value>
<pre id="log_file{{.VersionName}}"></pre>
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>
</div>
@@ -565,6 +575,7 @@
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{end}} {{template "base/paginate" .}}
</div>
<!-- 确认模态框 -->


+ 4
- 2
templates/repo/cloudbrain/inference/new.tmpl View File

@@ -40,7 +40,9 @@
<div class="repository">
{{template "repo/header" .}}
<div class="ui container">
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-queue="{{.QueuesDetail}}" data-queue-start="{{.i18n.Tr "repo.wait_count_start"}}" data-queue-end="{{.i18n.Tr "repo.wait_count_end"}}"></div>
<h4 class="ui top attached header">
@@ -272,7 +274,7 @@
<!-- 表单操作 -->
<div class="inline min_title field">
<label class="label-fix-width" style="font-weight: normal;"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="{{.RepoLink}}/modelarts/inference-job">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 22
- 12
templates/repo/cloudbrain/inference/show.tmpl View File

@@ -535,23 +535,29 @@
</div>

<div class="ui tab" data-tab="third">
<div>
<div class="file-info">
<a id="{{.VersionName}}-log-down"
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}}'
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}} file-info'
href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain/{{.ID}}/download_log_file">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>
<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain/{{.ID}}/download_log_file"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div
style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
<span>
<a title="滚动到顶部" style="position: absolute; right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_start"}}" style="position: absolute; right: -32px;cursor: pointer;"
class="log_top" data-version="{{.VersionName}}"><i class="icon-to-top"></i></a>
</span>
<span class="log-info-{{.VersionName}}">
<a title="滚动到底部" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_end"}}" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
class="log_bottom" data-version="{{.VersionName}}"><i
class="icon-to-bottom"></i></a>
</span>
@@ -559,13 +565,17 @@
<div id="header"></div>
</div>
<div class="ui attached log log-scroll" id="log{{.VersionName}}" data-version="{{.VersionName}}"
style="height: 300px !important; overflow: auto;">
<div class="ui inverted active dimmer">
style="height: 300px !important; overflow: auto;">
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="start_line" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>
</div>
@@ -589,7 +599,7 @@
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{end}}
</div>



+ 4
- 2
templates/repo/cloudbrain/new.tmpl View File

@@ -24,7 +24,9 @@
<div class="repository new repo ui middle very relaxed page grid">
<div class="column">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-queue="{{.QueuesDetail}}" data-queue-start="{{.i18n.Tr "repo.wait_count_start"}}" data-queue-end="{{.i18n.Tr "repo.wait_count_end"}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
<div class="ui negative message" id="messageInfo" style="display:none;">
<p></p>
</div>
@@ -200,7 +202,7 @@

<div class="inline field">
<label></label>
<button class="ui green button">
<button class="ui green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button cancel"


+ 4
- 2
templates/repo/cloudbrain/trainjob/new.tmpl View File

@@ -71,7 +71,9 @@
{{template "repo/header" .}}
<div class="ui container">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-flag-model="true" data-dataset-uuid="{{.attachment}}" data-dataset-name="{{.dataset_name}}" data-queue="{{.QueuesDetail}}" data-queue-start="{{.i18n.Tr "repo.wait_count_start"}}" data-queue-end="{{.i18n.Tr "repo.wait_count_end"}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.train_job.new"}}
@@ -232,7 +234,7 @@

<div class="inline field" style="padding: 1rem 0;">
<label class="label-fix-width"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button __btn-cancel-back__"


+ 16
- 5
templates/repo/cloudbrain/trainjob/show.tmpl View File

@@ -524,22 +524,28 @@
</div>

<div class="ui tab" data-tab="third{{$k}}">
<div>
<div class="file-info">
<a id="{{.VersionName}}-log-down"
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}}'
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}} file-info'
href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain/{{.ID}}/download_log_file">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>

<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain/{{.ID}}/download_log_file"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
<span>
<a title="滚动到顶部" style="position: absolute; right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_start"}}" style="position: absolute; right: -32px;cursor: pointer;"
class="log_top" data-version="{{.VersionName}}"><i class="icon-to-top"></i></a>
</span>
<span class="log-info-{{.VersionName}}">
<a title="滚动到底部" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_end"}}" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
class="log_bottom" data-version="{{.VersionName}}"><i
class="icon-to-bottom"></i></a>
</span>
@@ -552,7 +558,11 @@
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>

@@ -581,6 +591,7 @@
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{end}} {{template "base/paginate" .}}
</div>
<!-- 确认模态框 -->


+ 12
- 0
templates/repo/debugjob/index.tmpl View File

@@ -419,6 +419,18 @@
</div>
</div>
</div>

<div class="ui modal debug-again-alert">
<div class="ui message" style="background-color: rgba(242, 113, 28, 0.05);border: 1px solid rgba(242, 113, 28, 1);border-radius: 5px;">
<div style="display: flex;align-items: center;">
<i class="ri-information-line" style="font-size: 35px;color: rgba(242, 113, 28, 1);;"></i>
<div style="text-align: left;margin-left: 1rem;">
<div style="font-weight: 600;line-height: 2;">{{.i18n.Tr "repo.cloudbrain.morethanonejob1" | Safe }}</div>
<div style="color:#939393">{{.i18n.Tr "repo.cloudbrain.morethanonejob2" | Safe}}</div>
</div>
</div>
</div>
</div>
{{template "base/footer" .}}
<script>
// 调试和评分新开窗口


+ 4
- 2
templates/repo/grampus/trainjob/gpu/new.tmpl View File

@@ -63,7 +63,9 @@
{{template "repo/header" .}}
<div class="ui container">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-flag-model="true" data-dataset-uuid="{{.attachment}}" data-dataset-name="{{.dataset_name}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.train_job.new"}}
@@ -205,7 +207,7 @@

<div class="inline min_title field">
<label class="label-fix-width"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button __btn-cancel-back__" href="{{.RepoLink}}/modelarts/train-job">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 4
- 2
templates/repo/grampus/trainjob/npu/new.tmpl View File

@@ -58,7 +58,9 @@
{{template "repo/header" .}}
<div class="ui container">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-flag-model="true" data-dataset-uuid="{{.attachment}}" data-dataset-name="{{.dataset_name}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.train_job.new"}}
@@ -229,7 +231,7 @@

<div class="inline min_title field">
<label class="label-fix-width"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button __btn-cancel-back__" href="{{.RepoLink}}/modelarts/train-job">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 15
- 4
templates/repo/grampus/trainjob/show.tmpl View File

@@ -520,14 +520,20 @@
</div>
</div>
<div class="ui tab" data-tab="second{{$k}}">
<div>
<div class="file-info">
<a id="{{.VersionName}}-log-down"
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}}'
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}} file-info'
href="/api/v1/repos/{{$.RepoRelPath}}/grampus/train-job/{{.JobID}}/download_log">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>

<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="/api/v1/repos/{{$.RepoRelPath}}/grampus/train-job/{{.JobID}}/download_log"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
<span>
@@ -548,7 +554,11 @@
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>

@@ -576,6 +586,7 @@
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{end}} {{template "base/paginate" .}}
</div>
<!-- 确认模态框 -->


+ 4
- 2
templates/repo/modelarts/inferencejob/new.tmpl View File

@@ -39,7 +39,9 @@
<div class="repository">
{{template "repo/header" .}}
<div class="ui container">
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="1" data-repo-link="{{.RepoLink}}"></div>
<h4 class="ui top attached header">
@@ -300,7 +302,7 @@
<!-- 表单操作 -->
<div class="inline min_title field">
<label class="label-fix-width" style="font-weight: normal;"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="/">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 18
- 12
templates/repo/modelarts/inferencejob/show.tmpl View File

@@ -460,22 +460,28 @@ td, th {
</div>

<div class="ui tab" data-tab="second">
<div>
<div class="file-info">
<a id="{{.VersionName}}-log-down"
class='{{if and ($.canDownload) (eq .Status "KILLED" "FAILED" "START_FAILED" "STOPPED" "COMPLETED") }}ti-download-file{{else}}disabled{{end}}'
class='{{if and ($.canDownload) (eq .Status "KILLED" "FAILED" "START_FAILED" "STOPPED" "COMPLETED") }}ti-download-file{{else}}disabled{{end}} file-info'
href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>

<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
<span>
<a title="滚动到顶部" style="position: absolute; right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_start"}}" style="position: absolute; right: -32px;cursor: pointer;"
class="log_top" data-version="{{.VersionName}}"><i class="icon-to-top"></i></a>
</span>
<span class="log-info-{{.VersionName}}">
<a title="滚动到底部" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_end"}}" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
class="log_bottom" data-version="{{.VersionName}}"><i
class="icon-to-bottom"></i></a>
</span>
@@ -486,8 +492,12 @@ td, th {
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="end_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>

@@ -510,12 +520,8 @@ td, th {
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{end}}





</div>
<!-- 确认模态框 -->
</div>


+ 5
- 4
templates/repo/modelarts/notebook/new.tmpl View File

@@ -11,11 +11,12 @@
<div class="repository new repo ui middle very relaxed page grid">
<div class="column">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}"></div>
{{template "base/alert" .}}
<div class="ui negative message" id="messageInfo">
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
<div class="ui negative message" id="messageInfo" style="display: none;">
<p></p>
</div>

{{template "custom/alert_cb" .}}
<form class="ui form" id="form_id" action="{{.Link}}" method="post">
{{.CsrfTokenHtml}}
@@ -106,7 +107,7 @@
</div>
<div class="inline field">
<label></label>
<button class="ui green button">
<button class="ui green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button cancel" href="{{.RepoLink}}/debugjob?debugListType=all">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 4
- 2
templates/repo/modelarts/trainjob/new.tmpl View File

@@ -63,7 +63,9 @@
{{template "repo/header" .}}
<div class="ui container">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-flag-model="true" data-dataset-uuid="{{.attachment}}" data-dataset-name="{{.dataset_name}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.train_job.new"}}
@@ -291,7 +293,7 @@

<div class="inline field" style="padding: 1rem 0;">
<label class="label-fix-width"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="{{.RepoLink}}/modelarts/train-job">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 15
- 3
templates/repo/modelarts/trainjob/show.tmpl View File

@@ -548,14 +548,20 @@
</div>
</div>
<div class="ui tab" data-tab="second{{$k}}">
<div>
<div class="file-info">
<a id="{{.VersionName}}-log-down"
class='{{if and (.CanModify) (eq .Status "KILLED" "FAILED" "START_FAILED" "STOPPED" "COMPLETED") }}ti-download-file{{else}}disabled{{end}}'
class='{{if and (.CanModify) (eq .Status "KILLED" "FAILED" "START_FAILED" "STOPPED" "COMPLETED") }}ti-download-file{{else}}disabled{{end}} file-info'
href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>

<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div
style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
@@ -577,7 +583,11 @@
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file{{.VersionName}}"></pre>
</div>

@@ -609,6 +619,7 @@
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{end}} {{template "base/paginate" .}}
</div>
<!-- 确认模态框 -->
@@ -715,6 +726,7 @@

</div>
</div>
</div>
{{template "base/footer" .}}



+ 5
- 2
templates/repo/modelarts/trainjob/version_new.tmpl View File

@@ -56,7 +56,10 @@
{{template "repo/header" .}}
<div class="ui container">
<div class="cloudbrain-type" style="display: none;" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-flag-model="true" data-dataset-uuid="{{.attachment}}" data-dataset-name="{{.dataset_name}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.train_job.new"}}
</h4>
@@ -260,7 +263,7 @@
</div>

<div class="inline unite min_title field">
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button cancel" href="{{.RepoLink}}/modelarts/train-job">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 4
- 2
templates/repo/modelmanage/convertIndex.tmpl View File

@@ -103,7 +103,7 @@
</span>
</div>
<div class="two wide column center padding0">
<span style="font-size: 12px;">{{if eq .SrcEngine 0}}PyTorch {{else if eq .SrcEngine 1}}TensorFlow{{else if eq .SrcEngine 2}}MindSpore {{end}}</span>
<span style="font-size: 12px;">{{if eq .SrcEngine 0}}PyTorch {{else if eq .SrcEngine 1}}TensorFlow {{else if eq .SrcEngine 2}}MindSpore {{else if eq .SrcEngine 4}}PaddlePaddle {{else if eq .SrcEngine 6}}MXNet {{end}}</span>
</div>
<div class="two wide column center padding0">
<span style="font-size: 12px;">{{if eq .DestFormat 0}}ONNX {{else if eq .DestFormat 1}}TensorRT {{end}}</span>
@@ -532,7 +532,7 @@
}
}
function isModel(filename){
var postfix=[".pth",".pkl",".onnx",".mindir",".ckpt",".pb"];
var postfix=[".pth",".pkl",".onnx",".mindir",".ckpt",".pb",".pdmodel",".pdiparams",".params",".json"];
for(var i =0; i<postfix.length;i++){
if(filename.substring(filename.length-postfix[i].length)==postfix[i]){
return true;
@@ -568,6 +568,8 @@
html +="<option name=\"PyTorch\" " + getSelected(0,value) + " value=\"0\">PyTorch</option>";
html +="<option name=\"TensorFlow\" " + getSelected(1,value) + " value=\"1\">TensorFlow</option>";
html +="<option name=\"MindSpore\" " + getSelected(2,value) + " value=\"2\">MindSpore</option>";
html +="<option name=\"PaddlePaddle\" " + getSelected(4,value) + " value=\"4\">PaddlePaddle</option>";
html +="<option name=\"MXNet\" " + getSelected(6,value) + " value=\"6\">MXNet</option>";
$('#SrcEngine').html(html);
srcEngineChanged();
}


+ 1
- 1
templates/repo/modelmanage/convertshowinfo.tmpl View File

@@ -355,7 +355,7 @@ td, th {

<td class="ti-text-form-content">
<div class="text-span text-span-w">
{{if eq .SrcEngine 0}}PyTorch {{else if eq .SrcEngine 1}}Tensorflow{{else if eq .SrcEngine 2}}MindSpore {{end}}
{{if eq .SrcEngine 0}}PyTorch {{else if eq .SrcEngine 1}}Tensorflow{{else if eq .SrcEngine 2}}MindSpore {{else if eq .SrcEngine 4}}PaddlePaddle{{else if eq .SrcEngine 6}} MXNet{{end}}
</div>
</td>
</tr>


+ 1
- 0
templates/repo/modelmanage/index.tmpl View File

@@ -565,4 +565,5 @@
$("#choice_Engine").removeClass('disabled');
}
}
</script>

+ 1
- 1
templates/repo/modelmanage/showinfo.tmpl View File

@@ -285,7 +285,7 @@ function transObj(data){
DatasetName:TrainTaskInfo.DatasetName || '--',
Parameters:TrainTaskInfo.Parameters || '--',
FlavorName:TrainTaskInfo.FlavorName || '--',
WorkServerNumber:TrainTaskInfo.WorkServerNumber || '--',
WorkServerNumber:TrainTaskInfo.WorkServerNumber || '1',
Parameters:Parameters,
EngineName:EngineName,
DisplayJobName:TrainTaskInfo.DisplayJobName || '--',


+ 4
- 2
templates/repo/modelsafety/new.tmpl View File

@@ -55,7 +55,9 @@
<div class="ui container">
{{$Grampus := (or (eq (index (SubJumpablePath .Link) 1) "create_grampus_gpu") (eq (index (SubJumpablePath .Link) 1) "create_grampus_npu"))}}
<div class="cloudbrain-type" style="display: none;" data-grampus="{{$Grampus}}" data-cloudbrain-type="{{.datasetType}}" data-repo-link="{{.RepoLink}}" data-flag-model="true" data-dataset-uuid="{{.attachment}}" data-dataset-name="{{.dataset_name}}" data-queue="{{.QueuesDetail}}" data-queue-start="{{.i18n.Tr "repo.wait_count_start"}}" data-queue-end="{{.i18n.Tr "repo.wait_count_end"}}"></div>
{{template "base/alert" .}}
{{if eq .NotStopTaskCount 0}}
{{template "base/alert" .}}
{{end}}
{{template "custom/alert_cb" .}}
<h4 class="ui top attached header">
{{.i18n.Tr "repo.modelarts.evaluate_job.new_job"}}
@@ -314,7 +316,7 @@
</div>
<div class="inline unite min_title field">
<label class="label-fix-width" style="font-weight: normal;"></label>
<button class="ui create_train_job green button">
<button class="ui create_train_job green button {{if eq .NotStopTaskCount 1}}disabled{{end}}">
{{.i18n.Tr "repo.cloudbrain.new"}}
</button>
<a class="ui button" href="{{.RepoLink}}/cloudbrain/benchmark">{{.i18n.Tr "repo.cloudbrain.cancel"}}</a>


+ 23
- 11
templates/repo/modelsafety/show.tmpl View File

@@ -467,22 +467,29 @@
</div>
</div>
<div class="ui tab" data-tab="second0">
<div>
<div class="file-info">
<a id="-log-down"
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}}'
class='{{if $.canDownload}}ti-download-file{{else}}disabled{{end}} file-info'
href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain">
<i class="ri-download-cloud-2-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>
</a>
<div class="file-info full-log-dialog" data-version="{{.VersionName}}" data-log="{{$.i18n.Tr "repo.modelarts.log_file"}}"
data-exit="{{$.i18n.Tr "repo.modelarts.exit_full_screen"}}" style="margin-left: 1rem;color:#0366d6;cursor: pointer;"
data-log-down="{{$.i18n.Tr "repo.modelarts.download_log"}}" data-href="/api/v1/repos/{{$.RepoRelPath}}/cloudbrain"
data-scroll-top="{{$.i18n.Tr "repo.log_scroll_start"}}" data-scroll-bottom="{{$.i18n.Tr "repo.log_scroll_end"}}">
<i class="ri-aspect-ratio-line"></i>
<span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.fullscreen_log_file"}}</span>
</div>
</div>
<div
style="position: relative;border: 1px solid rgba(0,0,0,.2);padding: 0 10px;margin-top: 10px;">
<span>
<a title="滚动到顶部" style="position: absolute; right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_start"}}" style="position: absolute; right: -32px;cursor: pointer;"
class="log_top" data-version=""><i class="icon-to-top"></i></a>
</span>
<span class="log-info-">
<a title="滚动到底部" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
<a title="{{$.i18n.Tr "repo.log_scroll_end"}}" style="position: absolute; bottom: 10px;right: -32px;cursor: pointer;"
class="log_bottom" data-version=""><i
class="icon-to-bottom"></i></a>
</span>
@@ -490,13 +497,17 @@
<div id="header"></div>
</div>
<div class="ui attached log log-scroll" id="log" data-version=""
style="height: 300px !important; overflow: auto;">
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="start_line" value>
<pre id="log_file"></pre>
style="height: 300px !important; overflow: auto;">
<div class="ui inverted active dimmer">
<div class="ui loader"></div>
</div>
<input type="hidden" name="end_line" value>
<input type="hidden" name="end_line-max" value>
<input type="hidden" name="start_line-max" value>
<input type="hidden" name="start_line-max-copy" value>
<input type="hidden" name="start_line" value>
<input type="hidden" name="init_log" value>
<pre id="log_file"></pre>
</div>
</div>
</div>
@@ -571,6 +582,7 @@
</div>
</div>
</div>
{{template "custom/max_log" .}}
{{template "base/paginate" .}}
</div>
<!-- 确认模态框 -->


+ 1
- 1
templates/resource_desc.tmpl View File

@@ -65,7 +65,7 @@
<td>
${el.dockerDir}
</td>
<td><a> ${el.example_repo}</a></td>
<td><a href="${el.example_repo}">${el.example_repo}</a></td>
<td>${el.note}</td></tr>`;
});
html2 = html2.replace(


+ 13
- 1
templates/user/dashboard/cloudbrains.tmpl View File

@@ -1,7 +1,7 @@
{{template "base/head" .}}
<!-- 提示框 -->
<script src="{{StaticUrlPrefix}}/js/specsuse.js?v={{MD5 AppVer}}" type="text/javascript"></script>
<div class="alert"></div>
<script src="{{StaticUrlPrefix}}/js/specsuse.js?v={{MD5 AppVer}}" type="text/javascript"></script>
<div class="explore users">
<div class="cloudbrain_debug" style="display: none;" data-debug="{{$.i18n.Tr "repo.debug"}}"
data-debug-again="{{$.i18n.Tr "repo.debug_again"}}" data-debug-task="{{$.i18n.Tr "cloudbrain.DEBUG"}}"
@@ -445,6 +445,18 @@
</div>
</div>
</div>

<div class="ui modal debug-again-alert">
<div class="ui message" style="background-color: rgba(242, 113, 28, 0.05);border: 1px solid rgba(242, 113, 28, 1);border-radius: 5px;">
<div style="display: flex;align-items: center;">
<i class="ri-information-line" style="font-size: 35px;color: rgba(242, 113, 28, 1);;"></i>
<div style="text-align: left;margin-left: 1rem;">
<div style="font-weight: 600;line-height: 2;">{{.i18n.Tr "repo.cloudbrain.morethanonejob1" | Safe }}</div>
<div style="color:#939393">{{.i18n.Tr "repo.cloudbrain.morethanonejob2" | Safe}}</div>
</div>
</div>
</div>
</div>
</div>

<script>


+ 1
- 1
templates/user/profile.tmpl View File

@@ -21,7 +21,7 @@
<div class="badge-wrap">
{{range $k,$v :=.RecentBadges}}
{{if le $k 3}}
<div class="badge-img-avatar" title="{{.Name}}"><img style="width: 100%;height: 100%;" src="{{.LightedIcon}}" class="ui poping up" data-content="{{.Name}}" data-position="top center" data-variation="tiny inverted"></div>
<div class="badge-img-avatar"><img style="width: 100%;height: 100%;" src="{{.LightedIcon}}" class="ui poping up" data-content="{{.Name}}" data-position="top center" data-variation="tiny inverted"></div>
{{else}}
<a class="badge-more-icon" href="{{$.Owner.HomeLink}}?tab=badge"><i class="ri-more-fill"></i></a>
{{end}}


+ 239
- 62
web_src/js/features/cloudbrainShow.js View File

@@ -26,8 +26,8 @@ export default async function initCloudrainSow() {
return `${date.getFullYear()}-${paddingZeros(date.getMonth() + 1, 2)}-${paddingZeros(date.getDate(), 2)} ${paddingZeros(date.getHours(), 2)}:${paddingZeros(date.getMinutes(), 2)}:${paddingZeros(date.getSeconds(), 2)}`;
}

function logScroll(version_name, repoPath, ID) {
let container = document.querySelector(`#log${version_name}`);
function logScroll(version_name, repoPath, ID, max = "", lines = 60) {
let container = document.querySelector(`#log${max}${version_name}`);
let scrollTop = container.scrollTop;
let scrollHeight = container.scrollHeight;
let clientHeight = container.clientHeight;
@@ -38,46 +38,88 @@ export default async function initCloudrainSow() {
parseInt(scrollTop) + clientHeight - 1 == scrollHeight) &&
scrollLeft === 0
) {
let end_line = $(`#log${version_name} input[name=end_line]`).val();
let end_line = $(`#log${version_name} input[name=end_line${max}]`).val();
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css({
"background-color": "#fff",
display: "block",
});
$.get(
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=${end_line}&lines=50&order=desc`,
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=${end_line}&lines=${lines}&order=desc`,
(data) => {
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
if (data.Lines == 0) {
$(`.message${version_name} #header`).text("您已翻阅至日志底部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
if (max) {
$("body").toast({
message: `您已翻阅至日志底部,请稍后再试!`,
});
} else {
$(`.message${version_name} #header`).text("您已翻阅至日志底部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
}
} else {
if (end_line === data.EndLine) {
return;
} else {
$(`#log${version_name} input[name=end_line]`).val(data.EndLine);
$(`#log${version_name}`).append("<pre>" + data.Content);
$(`#log${version_name} input[name=end_line${max}]`).val(
data.EndLine
);
$(`#log${max}${version_name}`).append("<pre>" + data.Content);
}
}
}
).fail(function (err) {
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
console.log(err);
});
}
if (scrollTop == 0 && scrollLeft == 0) {
let start_line = $(`#log${version_name} input[name=start_line]`).val();
let start_line = $(
`#log${version_name} input[name=start_line${max}]`
).val();
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css({
"background-color": "#fff",
display: "block",
});
$.get(
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=${start_line}&lines=50&order=asc`,
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=${start_line}&lines=${lines}&order=asc`,
(data) => {
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
if (data.Lines == 0) {
$(`.message${version_name} #header`).text("您已翻阅至日志顶部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
if (max) {
$("body").toast({
message: `您已翻阅至日志顶部,请稍后再试!`,
});
} else {
$(`.message${version_name} #header`).text("您已翻阅至日志顶部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
}
} else {
$(`#log${version_name} input[name=start_line]`).val(data.StartLine); //如果变动就改变所对应的值
$(`#log${version_name}`).prepend("<pre>" + data.Content);
$(`#log${version_name} input[name=start_line${max}]`).val(
data.StartLine
); //如果变动就改变所对应的值
$(`#log${max}${version_name}`).prepend("<pre>" + data.Content);
}
}
).fail(function (err) {
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
console.log(err);
});
}
@@ -108,51 +150,70 @@ export default async function initCloudrainSow() {
}, 1);
}

$(".log_top").click(function () {
// let logContentDom = document.querySelector('.log')
// if(!logContentDom)
// return
// let version_name = $('.log_top').data('version')
function logTop(e) {
let max = e.currentTarget.getAttribute("data-max") || "";
let lines = !!max ? 100 : 60;
let version_name = $(this).data("version");
let logContentDom = document.querySelector(`#log${version_name}`);
let logContentDom = document.querySelector(`#log${max}${version_name}`);
let ID = $(`#accordion${version_name}`).data("jobid");
let repoPath = $(`#accordion${version_name}`).data("repopath");
$(`#log_file${version_name}`).siblings("pre").remove();
$(`#log${version_name} .ui.inverted.active.dimmer`).css("display", "block");
$(`#log_file${max}${version_name}`).siblings("pre").remove();
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css({
"background-color": "#fff",
display: "block",
});
$.get(
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=&lines=50&order=asc`,
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=&lines=${lines}&order=asc`,
(data) => {
$(".ui.inverted.active.dimmer").css("display", "none");
$(`#log${version_name} input[name=end_line]`).val(data.EndLine); //如果变动就改变所对应的值
$(`#log${version_name} input[name=start_line]`).val(data.StartLine);
$(`#log${version_name}`).prepend("<pre>" + data.Content);
$(`.message${version_name} #header`).text("您已翻阅至日志顶部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
$(`#log${version_name} input[name=end_line${max}]`).val(data.EndLine); //如果变动就改变所对应的值
$(`#log${version_name} input[name=start_line${max}]`).val(
data.StartLine
);
$(`#log${max}${version_name}`).prepend("<pre>" + data.Content);
if (data.Lines == 0) {
if (max) {
$("body").toast({
message: `您已翻阅至日志顶部,请稍后再试!`,
});
} else {
$(`.message${version_name} #header`).text("您已翻阅至日志顶部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
}
}
scrollAnimation(logContentDom, logContentDom.scrollTop, 0);
}
).fail((err) => {
$(`#log${version_name} .ui.inverted.active.dimmer`).css(
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
throw err;
});
});
$(".log_bottom").click(function (e) {
}
function logBottom(e) {
let max = e.currentTarget.getAttribute("data-max") || "";
let lines = !!max ? 100 : 60;
let version_name = $(this).data("version");
let logContentDom = document.querySelector(`#log${version_name}`);
let logContentDom = document.querySelector(`#log${max}${version_name}`);
let ID = $(`#accordion${version_name}`).data("jobid");
let repoPath = $(`#accordion${version_name}`).data("repopath");
$(`#log_file${version_name}`).siblings("pre").remove();
let end_line = $(`#log${version_name} input[name=end_line]`).val();
$(`#log${version_name} .ui.inverted.active.dimmer`).css("display", "block");
$(`#log_file${max}${version_name}`).siblings("pre").remove();
let end_line = $(`#log${version_name} input[name=end_line${max}]`).val();
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css({
"background-color": "#fff",
display: "block",
});
$.get(
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=&lines=50&order=desc`,
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=&lines=${lines}&order=desc`,
(data) => {
$(`#log${version_name} .ui.inverted.active.dimmer`).css(
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
@@ -160,44 +221,81 @@ export default async function initCloudrainSow() {
$(`#${version_name}-log-down`)
.removeClass("ti-download-file")
.addClass("disabled");
$(`.max-full-log${version_name} #${version_name}-log-down`)
.removeClass("ti-download-file")
.addClass("disabled");
} else {
$(`#${version_name}-log-down`)
.addClass("ti-download-file")
.removeClass("disabled");
$(`.max-full-log${version_name} #${version_name}-log-down`)
.addClass("ti-download-file")
.removeClass("disabled");
}
$(`#log${version_name} input[name=end_line${max}]`).val(data.EndLine); //如果变动就改变所对应的值
if ($(this)[0].hasAttribute("data-tab")) {
$(`#log${version_name} input[name=end_line-max]`).val(data.EndLine);
$(`#log${version_name} input[name=start_line-max]`).val(
data.StartLine
);
$(`#log${version_name} input[name=start_line-max-copy]`).val(
data.StartLine
);
}
$(`#log${version_name} input[name=end_line]`).val(data.EndLine); //如果变动就改变所对应的值
$(`#log${version_name} input[name=start_line]`).val(data.StartLine);
$(`#log${version_name}`).append("<pre>" + data.Content);
$(`#log${version_name} input[name=start_line${max}]`).val(
data.StartLine
);
$(`#log${max}${version_name}`).append("<pre>" + data.Content);
$.get(
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=${data.EndLine}&lines=50&order=desc`,
`/api/v1/repos/${repoPath}/${ID}/log?version_name=${version_name}&base_line=${data.EndLine}&lines=${lines}&order=desc`,
(data) => {
$(".ui.inverted.active.dimmer").css("display", "none");
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
if (data.Lines == 0) {
$(`.message${version_name} #header`).text("您已翻阅至日志底部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
if (max) {
$("body").toast({
message: `您已翻阅至日志底部,请稍后再试!`,
});
} else {
$(`.message${version_name} #header`).text("您已翻阅至日志底部");
$(`.message${version_name}`).css("display", "block");
setTimeout(function () {
$(`.message${version_name}`).css("display", "none");
}, 1000);
}
} else {
if (end_line === data.EndLine || end_line === "") {
return;
} else {
$(`#log${version_name} input[name=end_line]`).val(data.EndLine);
$(`#log${version_name}`).append("<pre>" + data.Content);
$(`#log${version_name} input[name=end_line${max}]`).val(
data.EndLine
);
if ($(this)[0].hasAttribute("data-tab")) {
$(`#log${version_name} input[name=end_line-max]`).val(
data.EndLine
);
}
$(`#log${max}${version_name}`).append("<pre>" + data.Content);
}
}
}
).fail(function (err) {
$(`#log${version_name} .ui.inverted.active.dimmer`).css(
$(`#log${max}${version_name} .ui.inverted.active.dimmer`).css(
"display",
"none"
);
console.log(err);
});

let test = $(`#log_file${version_name}`).nextAll();
$(`#log${version_name} input[name=init_log]`).val(test[0].innerHTML);

scrollAnimation(
logContentDom,
logContentDom.scrollTop + 1,
logContentDom.scrollHeight - logContentDom.clientHeight
logContentDom.scrollHeight - logContentDom.clientHeight - 10
);
}
).fail((err) => {
@@ -207,6 +305,86 @@ export default async function initCloudrainSow() {
);
throw err;
});
}
$(".log_top").click(logTop);
$(".log_bottom").click(logBottom);

// $(".log-scroll-max").scroll();

$(".full-log-dialog").click(function () {
let version_name = $(this).data("version");
let log_type = $(this).data("log-type") || "";
let logContentDom = document.querySelector(`#log-max${version_name}`);
$(`.ui.modal.max-full-log${version_name}`)
.modal({
closable: false,
onShow: function () {
$(".ui.dimmer.modals").css({
"background-color": "rgb(136, 136, 136,0.7)",
});
$(".log-scroll-max .ui.inverted.active.dimmer").css(
"display",
"none"
);
$(".file-info #log-file-title").text(
$(".full-log-dialog").data("log")
);
$(".file-info #log-file-exit").text(
$(".full-log-dialog").data("exit")
);
$(".file-info .log-file-down").text(
$(".full-log-dialog").data("log-down")
);
$(".file-info .log-file-down").text(
$(".full-log-dialog").data("log-down")
);
$(`.max-full-log${version_name} #${version_name}-log-down`).attr(
"href",
$(".full-log-dialog").data("href")
);
$(`.max-full-log${version_name} .log_top-max`).attr(
"title",
$(".full-log-dialog").data("scroll-top")
);
$(`.max-full-log${version_name} .log_bottom-max`).attr(
"title",
$(".full-log-dialog").data("scroll-bottom")
);
},
onVisible: function () {
$(`#log-max${version_name}`).append(
"<pre>" + $(`#log${version_name} input[name=init_log]`).val()
);
scrollAnimation(
logContentDom,
logContentDom.scrollTop + 1,
logContentDom.scrollHeight - logContentDom.clientHeight
);
if (log_type !== "c2Net") {
$(".log-scroll-max").bind("scroll", function () {
let version_name = $(this).data("version");
let ID = $(`#accordion${version_name}`).data("jobid");
let repoPath = $(`#accordion${version_name}`).data("repopath");
fn(version_name, repoPath, ID, "-max", 100);
});
}

$(".log_bottom-max").bind("click", logBottom);
$(".log_top-max").bind("click", logTop);
},
onHide: function () {
let startLine = $(
`#log${version_name} input[name=start_line-max-copy]`
).val();
$(`#log_file-max${version_name}`).siblings("pre").remove();
$(`#log${version_name} input[name=start_line-max]`).val(startLine);

$(".log-scroll-max").unbind("scroll");
$(".log_bottom-max").unbind("click");
$(".log_top-max").unbind("click");
},
})
.modal("show");
});

function loadLog(version_name) {
@@ -256,7 +434,6 @@ export default async function initCloudrainSow() {
.modal({
onApprove: function () {
$.post(url, { version_name: version_name }, (data) => {
console.log(data);
if (data.StatusOK === 0) {
if (data.VersionListCount === 0) {
location.href = `/${repoPath}`;


+ 1
- 7
web_src/js/features/cloudrbanin.js View File

@@ -446,13 +446,7 @@ export default async function initCloudrain() {
.css("margin", "0 1rem");
}
} else {
$(".alert")
.html(res.error_msg)
.removeClass("alert-success")
.addClass("alert-danger")
.show()
.delay(2000)
.fadeOut();
$(".ui.modal.debug-again-alert").modal("show");
}
},
error: function (res) {


+ 1
- 1
web_src/js/standalone/phoneverify.js View File

@@ -55,7 +55,7 @@
if (!this.dom) return;
var self = this;
var clientX = 0, oLeft = 0, imgHideTimer = null;
this.dom.find('.slide-bar-bg').on('mouseenter', function (e) {
this.dom.find('.slide-bar-bg').on('mouseenter touchstart', function (e) {
if (self.verifySucess) return;
imgHideTimer && clearTimeout(imgHideTimer);
self.dom.find('.slide-image-big').slideDown();


+ 0
- 10
web_src/less/_user.less View File

@@ -233,14 +233,4 @@
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
}
.badge-section-title:before {
content: "";
position: absolute;
top: 50%;
left: 0;
transform: translateY(-50%);
width: 3px;
height: 1em;
background-color: #000;
}
}

+ 1
- 0
web_src/vuepages/langs/config/en-US.js View File

@@ -54,6 +54,7 @@ const en = {
taskName: 'Task Name',

createdRepository: 'created repository ',
repositoryWasDel: 'repository was deleted',
openedIssue: 'opened issue ',
createdPullRequest: 'created pull request ',
commentedOnIssue: 'commented on issue ',


+ 1
- 0
web_src/vuepages/langs/config/zh-CN.js View File

@@ -54,6 +54,7 @@ const zh = {
taskName: '任务名称',

createdRepository: '创建了项目',
repositoryWasDel: '项目已删除',
openedIssue: '创建了任务',
createdPullRequest: '创建了合并请求',
commentedOnIssue: '评论了任务',


+ 56
- 40
web_src/vuepages/pages/reward/point/utils.js View File

@@ -25,7 +25,7 @@ const getJobType = (key) => {
};

const getJobTypeLink = (record, type) => {
let link = type === 'INCREASE' ? record.Action.RepoLink : '/' + record.Cloudbrain.RepoFullName;
let link = type === 'INCREASE' ? record.Action?.RepoLink : '/' + record.Cloudbrain?.RepoFullName;
const cloudbrain = type === 'INCREASE' ? record.Action?.Cloudbrain : record.Cloudbrain;
switch (cloudbrain?.JobType) {
case 'DEBUG':
@@ -61,7 +61,7 @@ const renderSpecStr = (spec, showPoint) => {
var gpuMemStr = spec.GPUMemGiB != 0 ? `${i18n.t('resourcesManagement.gpuMem')}: ${spec.GPUMemGiB}GB, ` : '';
var sharedMemStr = spec.ShareMemGiB != 0 ? `, ${i18n.t('resourcesManagement.shareMem')}: ${spec.ShareMemGiB}GB` : '';
var workServerNum = spec.workServerNumber;
var workServerNumStr = showPoint && workServerNum != 1 && spec.UnitPrice != 0 ? '*' + workServerNum + i18n.t('resourcesManagement.node') : '';
var workServerNumStr = showPoint && workServerNum != 1 && spec.UnitPrice != 0 ? '*' + workServerNum + i18n.t('resourcesManagement.node') : '';
var pointStr = showPoint ? `, ${spec.UnitPrice == 0 ? i18n.t('resourcesManagement.free') : spec.UnitPrice + i18n.t('resourcesManagement.point_hr') + workServerNumStr}` : '';
var specStr = `${ngpu}, CPU: ${spec.CpuCores}, ${gpuMemStr}${i18n.t('resourcesManagement.mem')}: ${spec.MemGiB}GB${sharedMemStr}${pointStr}`;
return specStr;
@@ -79,7 +79,7 @@ export const getRewardPointRecordInfo = (record) => {
duration: record?.Cloudbrain?.Duration || '--',
taskName: record?.Cloudbrain?.DisplayJobName || '--',
taskId: record?.Cloudbrain?.ID,
action: record?.Action?.TaskType ? getPointAction(record.Action.TaskType) : '--',
action: record?.SourceTemplateId ? getPointAction(record.SourceTemplateId) : '--',
remark: record.Remark,
amount: record.Amount,
};
@@ -91,33 +91,41 @@ export const getRewardPointRecordInfo = (record) => {
record.Action.Cloudbrain.oJobType = 'MODELSAFETY';
record.Action.Cloudbrain.JobType = 'BENCHMARK';
}
switch (record?.Action?.TaskType) {
switch (record?.SourceTemplateId) {
case 'CreatePublicRepo': // 创建公开项目 - 创建了项目OpenI/aiforge
out.remark = `${i18n.t('createdRepository')}<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`;
out.remark = record.Action ? `${i18n.t('createdRepository')}<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'CreateIssue': // 每日提出任务 - 创建了任务PCL-Platform.Intelligence/AISynergy#19
out.remark = `${i18n.t('openedIssue')}<a href="${record.Action.RepoLink}/issues/${record.Action.IssueInfos[0]}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}#${record.Action.IssueInfos[0]}</a>`;
out.remark = record.Action ? `${i18n.t('openedIssue')}<a href="${record.Action.RepoLink}/issues/${record.Action.IssueInfos[0]}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}#${record.Action.IssueInfos[0]}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'CreatePullRequest': // 每日提出PR - 创建了合并请求OpenI/aiforge#1
out.remark = `${i18n.t('createdPullRequest')}<a href="${record.Action.RepoLink}/pulls/${record.Action.IssueInfos[0]}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}#${record.Action.IssueInfos[0]}</a>`;
out.remark = record.Action ? `${i18n.t('createdPullRequest')}<a href="${record.Action.RepoLink}/pulls/${record.Action.IssueInfos[0]}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}#${record.Action.IssueInfos[0]}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'CommentIssue': // 发表评论 - 评论了任务PCL-Platform.Intelligence/AISynergy#19
out.remark = `${i18n.t('commentedOnIssue')}<a href="${record.Action.CommentLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}#${record.Action.IssueInfos[0]}</a>`;
out.remark = record.Action ? `${i18n.t('commentedOnIssue')}<a href="${record.Action.CommentLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}#${record.Action.IssueInfos[0]}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'UploadAttachment': // 上传数据集文件 - 上传了数据集文件MMISTData.zip
out.remark = `${i18n.t('uploadDataset')}<a href="${record.Action.RepoLink}/datasets" rel="nofollow">${record.Action.RefName}</a>`;
out.remark = record.Action ? `${i18n.t('uploadDataset')}<a href="${record.Action.RepoLink}/datasets" rel="nofollow">${record.Action?.RefName}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'CreateNewModelTask': // 导入新模型 - 导入了新模型resnet50_qx7l
out.remark = `${i18n.t('createdNewModel')}<a href="${record.Action.RepoLink}/modelmanage/show_model_info?name=${record.Action.RefName}" rel="nofollow">${record.Action.RefName}</a>`;
out.remark = record.Action ? `${i18n.t('createdNewModel')}<a href="${record.Action.RepoLink}/modelmanage/show_model_info?name=${record.Action?.RefName}" rel="nofollow">${record.Action?.RefName}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'BindWechat': // 完成微信扫码验证 - 首次绑定微信奖励
out.remark = `${i18n.t('firstBindingWechatRewards')}`;
break;
case 'CreateCloudbrainTask': // 每日运行云脑任务 - 创建了(CPU/GPU/NPU)类型(调试/训练/推理/评测)任务tangl202204131431995
out.remark = `${i18n.t('created')}${record.Action?.Cloudbrain?.ComputeResource}${i18n.t('type')}${getJobType(record.Action?.Cloudbrain?.JobType)} <a href="${getJobTypeLink(record, 'INCREASE')}" rel="nofollow">${record.Action.RefName}</a>`;
out.remark = record.Action ? `${i18n.t('created')}${record.Action?.Cloudbrain?.ComputeResource}${i18n.t('type')}${getJobType(record.Action?.Cloudbrain?.JobType)} <a href="${getJobTypeLink(record, 'INCREASE')}" rel="nofollow">${record.Action.RefName}</a>`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'DatasetRecommended': // 数据集被平台推荐 - 数据集XXX被设置为推荐数据集
out.remark = `${i18n.t('dataset')}<a href="${record.Action.RepoLink}/datasets" rel="nofollow">${record.Action.Content && record.Action.Content.split('|')[1]}</a>${i18n.t('setAsRecommendedDataset')}`;
out.remark = record.Action ? `${i18n.t('dataset')}<a href="${record.Action.RepoLink}/datasets" rel="nofollow">${record.Action.Content && record.Action.Content.split('|')[1]}</a>${i18n.t('setAsRecommendedDataset')}`
: `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
break;
case 'CreateImage': // 提交新公开镜像 - 提交了镜像jiangxiang_ceshi_tang03
out.remark = `${i18n.t('committedImage')}<span style="font-weight:bold;">${record.Action.Content && record.Action.Content.split('|')[1]}</span>`;
@@ -129,33 +137,37 @@ export const getRewardPointRecordInfo = (record) => {
out.remark = `${i18n.t('updatedAvatar')}`;
break;
case 'PushCommits': // 每日commit - 推送了xxxx分支的代码到OpenI/aiforge
const opType = record.Action.OpType;
if (opType == 5) {
const words = record.Action.RefName.split('/');
const branch = words[words.length - 1];
out.remark = `${i18n.t('pushedBranch', {
branch: `<a href="${record.Action.RepoLink}/src/branch/${branch}" rel="nofollow">${branch}</a>`
})}<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`;
} else if (opType == 9) {
const words = record.Action.RefName.split('/');
const tag = words[words.length - 1];
out.remark = `${i18n.t('pushedTag', {
tag: `<a href="${record.Action.RepoLink}/src/tag/${tag}" rel="nofollow">${tag}</a>`
})}<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`;
} else if (opType == 16) {
const words = record.Action.RefName.split('/');
const tag = words[words.length - 1];
out.remark = `${i18n.t('deleteTag', {
repo: `<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`,
tag: tag,
})}`;
} else if (opType == 17) {
const words = record.Action.RefName.split('/');
const branch = words[words.length - 1];
out.remark = `${i18n.t('deleteBranch', {
repo: `<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`,
branch: branch,
})}`;
if (record?.Action) {
const opType = record.Action.OpType;
if (opType == 5) {
const words = record.Action.RefName.split('/');
const branch = words[words.length - 1];
out.remark = `${i18n.t('pushedBranch', {
branch: `<a href="${record.Action.RepoLink}/src/branch/${branch}" rel="nofollow">${branch}</a>`
})}<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`;
} else if (opType == 9) {
const words = record.Action.RefName.split('/');
const tag = words[words.length - 1];
out.remark = `${i18n.t('pushedTag', {
tag: `<a href="${record.Action.RepoLink}/src/tag/${tag}" rel="nofollow">${tag}</a>`
})}<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`;
} else if (opType == 16) {
const words = record.Action.RefName.split('/');
const tag = words[words.length - 1];
out.remark = `${i18n.t('deleteTag', {
repo: `<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`,
tag: tag,
})}`;
} else if (opType == 17) {
const words = record.Action.RefName.split('/');
const branch = words[words.length - 1];
out.remark = `${i18n.t('deleteBranch', {
repo: `<a href="${record.Action.RepoLink}" rel="nofollow">${record.Action.ShortRepoFullDisplayName}</a>`,
branch: branch,
})}`;
}
} else {
out.remark = `${getPointAction(record.SourceTemplateId)}(${i18n.t('repositoryWasDel')})`;
}
break;
default:
@@ -174,7 +186,11 @@ export const getRewardPointRecordInfo = (record) => {
} else if (record.SourceType === 'ACCOMPLISH_TASK') {
//
} else if (record.SourceType === 'RUN_CLOUDBRAIN_TASK') {
out.taskName = `<a href="${getJobTypeLink(record, 'DECREASE')}" rel="nofollow">${record?.Cloudbrain?.DisplayJobName}</a>`;
if (!record.Cloudbrain?.RepoFullName) {
out.taskName = `${record?.Cloudbrain?.DisplayJobName}(${i18n.t('repositoryWasDel')})`;
} else {
out.taskName = `<a href="${getJobTypeLink(record, 'DECREASE')}" rel="nofollow">${record?.Cloudbrain?.DisplayJobName}</a>`;
}
const resourceSpec = record?.Cloudbrain?.ResourceSpec;
if (resourceSpec) {
resourceSpec.workServerNumber = record?.Cloudbrain?.WorkServerNumber || 1;


Loading…
Cancel
Save