| @@ -473,3 +473,7 @@ func GetAttachmentSizeByDatasetID(datasetID int64) (int64, error) { | |||||
| return total, nil | return total, nil | ||||
| } | } | ||||
| func GetAllAttachmentSize() (int64, error) { | |||||
| return x.SumInt(&Attachment{}, "size") | |||||
| } | |||||
| @@ -27,6 +27,7 @@ const ( | |||||
| JobTypeDebug JobType = "DEBUG" | JobTypeDebug JobType = "DEBUG" | ||||
| JobTypeBenchmark JobType = "BENCHMARK" | JobTypeBenchmark JobType = "BENCHMARK" | ||||
| JobTypeSnn4imagenet JobType = "SNN4IMAGENET" | JobTypeSnn4imagenet JobType = "SNN4IMAGENET" | ||||
| JobTypeBrainScore JobType = "BRAINSCORE" | |||||
| ModelArtsCreateQueue ModelArtsJobStatus = "CREATE_QUEUING" //免费资源创建排队中 | ModelArtsCreateQueue ModelArtsJobStatus = "CREATE_QUEUING" //免费资源创建排队中 | ||||
| ModelArtsCreating ModelArtsJobStatus = "CREATING" //创建中 | ModelArtsCreating ModelArtsJobStatus = "CREATING" //创建中 | ||||
| @@ -150,23 +151,42 @@ type TaskPod struct { | |||||
| TaskRoleStatus struct { | TaskRoleStatus struct { | ||||
| Name string `json:"name"` | Name string `json:"name"` | ||||
| } `json:"taskRoleStatus"` | } `json:"taskRoleStatus"` | ||||
| TaskStatuses []struct { | |||||
| TaskIndex int `json:"taskIndex"` | |||||
| PodUID string `json:"podUid"` | |||||
| PodIP string `json:"podIp"` | |||||
| PodName string `json:"podName"` | |||||
| ContainerID string `json:"containerId"` | |||||
| ContainerIP string `json:"containerIp"` | |||||
| ContainerGpus string `json:"containerGpus"` | |||||
| State string `json:"state"` | |||||
| StartAt time.Time `json:"startAt"` | |||||
| FinishedAt time.Time `json:"finishedAt"` | |||||
| ExitCode int `json:"exitCode"` | |||||
| ExitDiagnostics string `json:"exitDiagnostics"` | |||||
| RetriedCount int `json:"retriedCount"` | |||||
| StartTime string | |||||
| FinishedTime string | |||||
| } `json:"taskStatuses"` | |||||
| //TaskStatuses []struct { | |||||
| // TaskIndex int `json:"taskIndex"` | |||||
| // PodUID string `json:"podUid"` | |||||
| // PodIP string `json:"podIp"` | |||||
| // PodName string `json:"podName"` | |||||
| // ContainerID string `json:"containerId"` | |||||
| // ContainerIP string `json:"containerIp"` | |||||
| // ContainerGpus string `json:"containerGpus"` | |||||
| // State string `json:"state"` | |||||
| // StartAt time.Time `json:"startAt"` | |||||
| // FinishedAt time.Time `json:"finishedAt"` | |||||
| // ExitCode int `json:"exitCode"` | |||||
| // ExitDiagnostics string `json:"exitDiagnostics"` | |||||
| // RetriedCount int `json:"retriedCount"` | |||||
| // StartTime string | |||||
| // FinishedTime string | |||||
| //} `json:"taskStatuses"` | |||||
| TaskStatuses []TaskStatuses `json:"taskStatuses"` | |||||
| } | |||||
| type TaskStatuses struct { | |||||
| TaskIndex int `json:"taskIndex"` | |||||
| PodUID string `json:"podUid"` | |||||
| PodIP string `json:"podIp"` | |||||
| PodName string `json:"podName"` | |||||
| ContainerID string `json:"containerId"` | |||||
| ContainerIP string `json:"containerIp"` | |||||
| ContainerGpus string `json:"containerGpus"` | |||||
| State string `json:"state"` | |||||
| StartAt time.Time `json:"startAt"` | |||||
| FinishedAt time.Time `json:"finishedAt"` | |||||
| ExitCode int `json:"exitCode"` | |||||
| ExitDiagnostics string `json:"exitDiagnostics"` | |||||
| RetriedCount int `json:"retriedCount"` | |||||
| StartTime string | |||||
| FinishedTime string | |||||
| } | } | ||||
| type TaskInfo struct { | type TaskInfo struct { | ||||
| @@ -254,6 +274,11 @@ func ConvertToJobResultPayload(input map[string]interface{}) (JobResultPayload, | |||||
| err := json.Unmarshal(data, &jobResultPayload) | err := json.Unmarshal(data, &jobResultPayload) | ||||
| jobResultPayload.JobStatus.StartTime = time.Unix(jobResultPayload.JobStatus.CreatedTime/1000, 0).Format("2006-01-02 15:04:05") | jobResultPayload.JobStatus.StartTime = time.Unix(jobResultPayload.JobStatus.CreatedTime/1000, 0).Format("2006-01-02 15:04:05") | ||||
| jobResultPayload.JobStatus.EndTime = time.Unix(jobResultPayload.JobStatus.CompletedTime/1000, 0).Format("2006-01-02 15:04:05") | jobResultPayload.JobStatus.EndTime = time.Unix(jobResultPayload.JobStatus.CompletedTime/1000, 0).Format("2006-01-02 15:04:05") | ||||
| if jobResultPayload.JobStatus.State == string(JobWaiting) { | |||||
| jobResultPayload.JobStatus.StartTime = "-" | |||||
| jobResultPayload.JobStatus.EndTime = "-" | |||||
| } | |||||
| return jobResultPayload, err | return jobResultPayload, err | ||||
| } | } | ||||
| @@ -673,7 +698,7 @@ func GetCloudbrainByName(jobName string) (*Cloudbrain, error) { | |||||
| } | } | ||||
| func CanDelJob(isSigned bool, user *User, job *CloudbrainInfo) bool { | func CanDelJob(isSigned bool, user *User, job *CloudbrainInfo) bool { | ||||
| if !isSigned || job.Status != string(JobStopped) { | |||||
| if !isSigned || (job.Status != string(JobStopped) && job.Status != string(JobFailed) && job.Status != string(ModelArtsStartFailed) && job.Status != string(ModelArtsCreateFailed)){ | |||||
| return false | return false | ||||
| } | } | ||||
| repo, err := GetRepositoryByID(job.RepoID) | repo, err := GetRepositoryByID(job.RepoID) | ||||
| @@ -139,7 +139,14 @@ func SearchDatasetCondition(opts *SearchDatasetOptions) builder.Cond { | |||||
| if opts.IncludePublic { | if opts.IncludePublic { | ||||
| cond = cond.And(builder.Eq{"dataset.status": DatasetStatusPublic}) | cond = cond.And(builder.Eq{"dataset.status": DatasetStatusPublic}) | ||||
| if opts.OwnerID > 0 { | if opts.OwnerID > 0 { | ||||
| cond = cond.Or(builder.Eq{"repository.owner_id": opts.OwnerID}) | |||||
| if len(opts.Keyword) == 0 { | |||||
| cond = cond.Or(builder.Eq{"repository.owner_id": opts.OwnerID}) | |||||
| } else { | |||||
| subCon := builder.NewCond() | |||||
| subCon = subCon.And(builder.Eq{"repository.owner_id": opts.OwnerID}, builder.Like{"dataset.title", opts.Keyword}) | |||||
| cond = cond.Or(subCon) | |||||
| } | |||||
| } | } | ||||
| } else if opts.OwnerID > 0 { | } else if opts.OwnerID > 0 { | ||||
| cond = cond.And(builder.Eq{"repository.owner_id": opts.OwnerID}) | cond = cond.And(builder.Eq{"repository.owner_id": opts.OwnerID}) | ||||
| @@ -137,6 +137,7 @@ func init() { | |||||
| tablesStatistic = append(tablesStatistic, | tablesStatistic = append(tablesStatistic, | ||||
| new(RepoStatistic), | new(RepoStatistic), | ||||
| new(SummaryStatistic), | |||||
| new(UserBusinessAnalysis), | new(UserBusinessAnalysis), | ||||
| ) | ) | ||||
| @@ -1430,6 +1430,15 @@ func GetAllRepositoriesByFilterCols(columns ...string) ([]*Repository, error) { | |||||
| } | } | ||||
| func GetAllRepositoriesCount() (int64, error) { | |||||
| repo := new(Repository) | |||||
| return x.Count(repo) | |||||
| } | |||||
| func GetAllRepositoriesSize() (int64, error) { | |||||
| return x.SumInt(&Repository{}, "size") | |||||
| } | |||||
| func updateRepository(e Engine, repo *Repository, visibilityChanged bool) (err error) { | func updateRepository(e Engine, repo *Repository, visibilityChanged bool) (err error) { | ||||
| repo.LowerName = strings.ToLower(repo.Name) | repo.LowerName = strings.ToLower(repo.Name) | ||||
| @@ -0,0 +1,69 @@ | |||||
| package models | |||||
| import ( | |||||
| "fmt" | |||||
| "code.gitea.io/gitea/modules/timeutil" | |||||
| ) | |||||
| var DomainMap = map[string]int{ | |||||
| "大模型": 0, | |||||
| "ai开发工具": 1, | |||||
| "计算机视觉": 2, | |||||
| "自然语言处理": 3, | |||||
| "机器学习": 4, | |||||
| "神经网络": 5, | |||||
| "自动驾驶": 6, | |||||
| "机器人": 7, | |||||
| "联邦学习": 8, | |||||
| "数据挖掘": 9, | |||||
| "risc-v开发": 10, | |||||
| } | |||||
| type SummaryStatistic struct { | |||||
| ID int64 `xorm:"pk autoincr"` | |||||
| Date string `xorm:"unique(s) NOT NULL"` | |||||
| NumUsers int64 `xorm:"NOT NULL DEFAULT 0"` | |||||
| RepoSize int64 `xorm:"NOT NULL DEFAULT 0"` | |||||
| DatasetSize int64 `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumOrganizations int64 `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumModels int64 `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepos int64 `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoBigModel int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoAI int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoVision int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoNLP int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoML int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoNN int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoAutoDrive int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoRobot int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoLeagueLearn int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoDataMining int `xorm:"NOT NULL DEFAULT 0"` | |||||
| NumRepoRISC int `xorm:"NOT NULL DEFAULT 0"` | |||||
| CreatedUnix timeutil.TimeStamp `xorm:"INDEX created"` | |||||
| UpdatedUnix timeutil.TimeStamp `xorm:"INDEX updated"` | |||||
| } | |||||
| func DeleteSummaryStatisticDaily(date string) error { | |||||
| sess := xStatistic.NewSession() | |||||
| defer sess.Close() | |||||
| if err := sess.Begin(); err != nil { | |||||
| return fmt.Errorf("Begin: %v", err) | |||||
| } | |||||
| if _, err := sess.Where("date = ?", date).Delete(&SummaryStatistic{}); 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 InsertSummaryStatistic(summaryStatistic *SummaryStatistic) (int64, error) { | |||||
| return xStatistic.Insert(summaryStatistic) | |||||
| } | |||||
| @@ -98,6 +98,13 @@ func GetTopicByName(name string) (*Topic, error) { | |||||
| return &topic, nil | return &topic, nil | ||||
| } | } | ||||
| func GetAllUsedTopics() ([]*Topic, error) { | |||||
| topics := make([]*Topic, 0) | |||||
| err := x.Where("repo_count > ?", 0).Find(&topics) | |||||
| return topics, err | |||||
| } | |||||
| // addTopicByNameToRepo adds a topic name to a repo and increments the topic count. | // addTopicByNameToRepo adds a topic name to a repo and increments the topic count. | ||||
| // Returns topic after the addition | // Returns topic after the addition | ||||
| func addTopicByNameToRepo(e Engine, repoID int64, topicName string) (*Topic, error) { | func addTopicByNameToRepo(e Engine, repoID int64, topicName string) (*Topic, error) { | ||||
| @@ -178,7 +185,7 @@ func (opts *FindTopicOptions) toConds() builder.Cond { | |||||
| } | } | ||||
| if opts.Keyword != "" { | if opts.Keyword != "" { | ||||
| cond = cond.And(builder.Like{"topic.name", opts.Keyword}) | |||||
| cond = cond.And(builder.Like{"topic.name", strings.ToLower(opts.Keyword)}) | |||||
| } | } | ||||
| return cond | return cond | ||||
| @@ -2071,6 +2071,18 @@ func SyncExternalUsers(ctx context.Context, updateExisting bool) error { | |||||
| return nil | return nil | ||||
| } | } | ||||
| func GetUsersCount() (int64, error) { | |||||
| user := new(User) | |||||
| return x.Where("type=0").Count(user) | |||||
| } | |||||
| func GetOrganizationsCount() (int64, error) { | |||||
| user := new(User) | |||||
| return x.Where("type=1").Count(user) | |||||
| } | |||||
| func GetBlockChainUnSuccessUsers() ([]*User, error) { | func GetBlockChainUnSuccessUsers() ([]*User, error) { | ||||
| users := make([]*User, 0, 10) | users := make([]*User, 0, 10) | ||||
| err := x.Where("public_key = ''"). | err := x.Where("public_key = ''"). | ||||
| @@ -224,7 +224,7 @@ func SizedAvatarLinkWithDomain(email string, size int) string { | |||||
| // FileSize calculates the file size and generate user-friendly string. | // FileSize calculates the file size and generate user-friendly string. | ||||
| func FileSize(s int64) string { | func FileSize(s int64) string { | ||||
| return humanize.IBytes(uint64(s)) | |||||
| return humanize.Bytes(uint64(s)) | |||||
| } | } | ||||
| // PrettyNumber produces a string form of the given number in base 10 with | // PrettyNumber produces a string form of the given number in base 10 with | ||||
| @@ -16,6 +16,7 @@ const ( | |||||
| ModelMountPath = "/model" | ModelMountPath = "/model" | ||||
| BenchMarkMountPath = "/benchmark" | BenchMarkMountPath = "/benchmark" | ||||
| Snn4imagenetMountPath = "/snn4imagenet" | Snn4imagenetMountPath = "/snn4imagenet" | ||||
| BrainScoreMountPath = "/brainscore" | |||||
| TaskInfoName = "/taskInfo" | TaskInfoName = "/taskInfo" | ||||
| SubTaskName = "task1" | SubTaskName = "task1" | ||||
| @@ -174,6 +174,16 @@ func registerHandleRepoStatistic() { | |||||
| }) | }) | ||||
| } | } | ||||
| func registerHandleSummaryStatistic() { | |||||
| RegisterTaskFatal("handle_summary_statistic", &BaseConfig{ | |||||
| Enabled: true, | |||||
| RunAtStart: false, | |||||
| Schedule: "@daily", | |||||
| }, func(ctx context.Context, _ *models.User, _ Config) error { | |||||
| repo.SummaryStatistic() | |||||
| return nil | |||||
| }) | |||||
| } | |||||
| func registerHandleUserStatistic() { | func registerHandleUserStatistic() { | ||||
| RegisterTaskFatal("handle_user_statistic", &BaseConfig{ | RegisterTaskFatal("handle_user_statistic", &BaseConfig{ | ||||
| Enabled: true, | Enabled: true, | ||||
| @@ -202,4 +212,5 @@ func initBasicTasks() { | |||||
| registerHandleRepoStatistic() | registerHandleRepoStatistic() | ||||
| registerHandleUserStatistic() | registerHandleUserStatistic() | ||||
| registerHandleSummaryStatistic() | |||||
| } | } | ||||
| @@ -4,10 +4,10 @@ import ( | |||||
| "bytes" | "bytes" | ||||
| "encoding/base64" | "encoding/base64" | ||||
| "encoding/json" | "encoding/json" | ||||
| "fmt" | |||||
| "io/ioutil" | "io/ioutil" | ||||
| "net/http" | "net/http" | ||||
| "code.gitea.io/gitea/modules/log" | |||||
| "code.gitea.io/gitea/modules/setting" | "code.gitea.io/gitea/modules/setting" | ||||
| ) | ) | ||||
| @@ -99,8 +99,8 @@ type ResultInfo struct { | |||||
| //elk输出的json结构end | //elk输出的json结构end | ||||
| //发送post请求到elk | |||||
| func SendReqToElk(jsonStr []byte) (content string) { | |||||
| //处理返回的elk数据,只保留totalView,即访问量;loaded是分片载入次数,用来判断返回的数据是否准确 | |||||
| func GetResultFromElk(resultInfo ResultInfo, jsonStr []byte) (loaded int, totalView int, err error) { | |||||
| ElkBase64Init := setting.ElkUser + ":" + setting.ElkPassword | ElkBase64Init := setting.ElkUser + ":" + setting.ElkPassword | ||||
| ElkBase64 := base64.StdEncoding.EncodeToString([]byte(ElkBase64Init)) | ElkBase64 := base64.StdEncoding.EncodeToString([]byte(ElkBase64Init)) | ||||
| BasicElkBase64 := "Basic" + " " + ElkBase64 | BasicElkBase64 := "Basic" + " " + ElkBase64 | ||||
| @@ -117,15 +117,11 @@ func SendReqToElk(jsonStr []byte) (content string) { | |||||
| } | } | ||||
| defer resp.Body.Close() | defer resp.Body.Close() | ||||
| body, _ := ioutil.ReadAll(resp.Body) | body, _ := ioutil.ReadAll(resp.Body) | ||||
| return string(body) | |||||
| } | |||||
| //处理返回的elk数据,只保留totalView,即访问量;loaded是分片载入次数,用来判断返回的数据是否准确 | |||||
| func GetResultFromElk(resultinfo ResultInfo, jobResult string) (loaded int, totalView int) { | |||||
| var resultTest ResultInfo | |||||
| errs := json.Unmarshal([]byte(jobResult), &resultTest) | |||||
| fmt.Println(errs) | |||||
| return resultTest.Result.Loaded, resultTest.Result.RawResponse.Hits.Total | |||||
| errs := json.Unmarshal([]byte(string(body)), &resultInfo) | |||||
| log.Info("Get resultJson failed", errs) | |||||
| return resultInfo.Result.Loaded, resultInfo.Result.RawResponse.Hits.Total, err | |||||
| } | } | ||||
| //初始化传给elk的数据结构,给定用户名和项目名,查询的起止时间,返回初始化后的结构 | //初始化传给elk的数据结构,给定用户名和项目名,查询的起止时间,返回初始化后的结构 | ||||
| @@ -211,23 +207,23 @@ func TagNameInit(MessageInfo string, Tagname string, Gte string, Lte string) (pr | |||||
| } | } | ||||
| //向elk发送请求,将获取的结果只保留访问量,输入是初始化后的数据结构,返回访问量 | //向elk发送请求,将获取的结果只保留访问量,输入是初始化后的数据结构,返回访问量 | ||||
| func ViewInfo(viewInfo InputInfo) (totalView int) { | |||||
| func ViewInfo(viewInfo InputInfo) (totalView int, err error) { | |||||
| jsons, errs := json.Marshal(viewInfo) | jsons, errs := json.Marshal(viewInfo) | ||||
| if errs != nil { | if errs != nil { | ||||
| fmt.Println("errs:", errs.Error()) | |||||
| log.Info("errs:", errs) | |||||
| } | } | ||||
| // fmt.Println("viewInfoInit:",string(jsons)) | |||||
| var jsonStr = []byte(jsons) | var jsonStr = []byte(jsons) | ||||
| var resultInfo ResultInfo | var resultInfo ResultInfo | ||||
| loaded, totalView := GetResultFromElk(resultInfo, SendReqToElk(jsonStr)) | |||||
| loaded, totalView, err := GetResultFromElk(resultInfo, jsonStr) | |||||
| time := 0 | time := 0 | ||||
| for { | for { | ||||
| if loaded == 0 { | if loaded == 0 { | ||||
| loaded_next, totalView := GetResultFromElk(resultInfo, SendReqToElk(jsonStr)) | |||||
| loaded_next, totalView, err := GetResultFromElk(resultInfo, jsonStr) | |||||
| time++ | time++ | ||||
| log.Info("time:", time) | |||||
| if loaded_next != 0 && time < 100 { | if loaded_next != 0 && time < 100 { | ||||
| fmt.Println("totalView:", totalView) | |||||
| return totalView | |||||
| return totalView, err | |||||
| } | } | ||||
| if time > 100 { | if time > 100 { | ||||
| break | break | ||||
| @@ -236,20 +232,20 @@ func ViewInfo(viewInfo InputInfo) (totalView int) { | |||||
| break | break | ||||
| } | } | ||||
| } | } | ||||
| fmt.Println("loaded:", loaded) | |||||
| return totalView | |||||
| return totalView, err | |||||
| } | } | ||||
| // @title ProjectView | |||||
| // @title AppointProjectView | |||||
| // @description 获取指定用户和项目的访问量 | // @description 获取指定用户和项目的访问量 | ||||
| // @param User string "用户名" | // @param User string "用户名" | ||||
| // @param Project string "项目名" | // @param Project string "项目名" | ||||
| // @param Gte string "起始时间" 如time.Now().AddDate(0, 0, -1).Format(time.RFC3339) | // @param Gte string "起始时间" 如time.Now().AddDate(0, 0, -1).Format(time.RFC3339) | ||||
| // @param Lte string "结束时间" 如time.Now().Format(time.RFC3339) | // @param Lte string "结束时间" 如time.Now().Format(time.RFC3339) | ||||
| // @return totalView int "访问量" | // @return totalView int "访问量" | ||||
| func AppointProjectView(User string, Project string, Gte string, Lte string) (totalView int) { | |||||
| InitInfo := ProjectViewInit(User, Project, Gte, Lte) | |||||
| return ViewInfo(InitInfo) | |||||
| func AppointProjectView(User string, Project string, Gte string, Lte string) (totalView int, err error) { | |||||
| ProjectViewInitInfo := ProjectViewInit(User, Project, Gte, Lte) | |||||
| ProjectTotalView, err := ViewInfo(ProjectViewInitInfo) | |||||
| return ProjectTotalView, err | |||||
| } | } | ||||
| //统计项目相关页面的访问量 | //统计项目相关页面的访问量 | ||||
| @@ -287,26 +283,44 @@ type ProjectInfo struct { | |||||
| Project_forks int | Project_forks int | ||||
| } | } | ||||
| type ErrorInfo struct { | |||||
| Project_dataset_type_0 error | |||||
| Project_dataset_type_1 error | |||||
| Project_issues error | |||||
| Project_labels error | |||||
| Project_milestones error | |||||
| Project_pulls error | |||||
| Project_release error | |||||
| Project_wiki error | |||||
| Project_activity error | |||||
| Project_cloudbrain error | |||||
| Project_modelarts error | |||||
| Project_blockchain error | |||||
| Project_watchers error | |||||
| Project_stars error | |||||
| Project_forks error | |||||
| } | |||||
| // @title AllProjectView | // @title AllProjectView | ||||
| // @description 获取指定用户和项目的访问量 | // @description 获取指定用户和项目的访问量 | ||||
| // @param Gte string "起始时间" 如time.Now().AddDate(0, 0, -1).Format(time.RFC3339) | // @param Gte string "起始时间" 如time.Now().AddDate(0, 0, -1).Format(time.RFC3339) | ||||
| // @param Lte string "结束时间" | // @param Lte string "结束时间" | ||||
| // @return projectInfo ProjectInfo "统计所有项目中页面的浏览情况,不需要区分项目" | // @return projectInfo ProjectInfo "统计所有项目中页面的浏览情况,不需要区分项目" | ||||
| func AllProjectView(Gte string, Lte string) (projectInfo ProjectInfo) { | |||||
| projectInfo.Project_dataset_type_0 = ViewInfo(AllProjectViewInit("/datasets?type=0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_dataset_type_1 = ViewInfo(AllProjectViewInit("/datasets?type=1", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_issues = ViewInfo(AllProjectViewInit("/issues HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_labels = ViewInfo(TagNameInit("/labels HTTP/2.0", "labels", Gte, Lte)) | |||||
| projectInfo.Project_milestones = ViewInfo(AllProjectViewInit("/milestones HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_pulls = ViewInfo(AllProjectViewInit("/pulls HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_release = ViewInfo(AllProjectViewInit("/release HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_wiki = ViewInfo(AllProjectViewInit("/wiki HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_activity = ViewInfo(AllProjectViewInit("/activity HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_cloudbrain = ViewInfo(AllProjectViewInit("/cloudbrain HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_modelarts = ViewInfo(AllProjectViewInit("/modelarts HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_blockchain = ViewInfo(AllProjectViewInit("/blockchain HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_watchers = ViewInfo(AllProjectViewInit("/watchers HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_stars = ViewInfo(AllProjectViewInit("/stars HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectInfo.Project_forks = ViewInfo(AllProjectViewInit("/forks HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| return projectInfo | |||||
| func AllProjectView(Gte string, Lte string) (projectViewInfo ProjectInfo, errorInfo ErrorInfo) { | |||||
| projectViewInfo.Project_dataset_type_0, errorInfo.Project_dataset_type_0 = ViewInfo(AllProjectViewInit("/datasets?type=0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_dataset_type_1, errorInfo.Project_dataset_type_1 = ViewInfo(AllProjectViewInit("/datasets?type=1", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_issues, errorInfo.Project_issues = ViewInfo(AllProjectViewInit("/issues HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_labels, errorInfo.Project_labels = ViewInfo(TagNameInit("/labels HTTP/2.0", "labels", Gte, Lte)) | |||||
| projectViewInfo.Project_milestones, errorInfo.Project_milestones = ViewInfo(AllProjectViewInit("/milestones HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_pulls, errorInfo.Project_pulls = ViewInfo(AllProjectViewInit("/pulls HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_release, errorInfo.Project_release = ViewInfo(AllProjectViewInit("/release HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_wiki, errorInfo.Project_wiki = ViewInfo(AllProjectViewInit("/wiki HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_activity, errorInfo.Project_activity = ViewInfo(AllProjectViewInit("/activity HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_cloudbrain, errorInfo.Project_cloudbrain = ViewInfo(AllProjectViewInit("/cloudbrain HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_modelarts, errorInfo.Project_modelarts = ViewInfo(AllProjectViewInit("/modelarts HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_blockchain, errorInfo.Project_blockchain = ViewInfo(AllProjectViewInit("/blockchain HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_watchers, errorInfo.Project_watchers = ViewInfo(AllProjectViewInit("/watchers HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_stars, errorInfo.Project_stars = ViewInfo(AllProjectViewInit("/stars HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| projectViewInfo.Project_forks, errorInfo.Project_forks = ViewInfo(AllProjectViewInit("/forks HTTP/2.0", "%{[request][2]}", Gte, Lte)) | |||||
| return projectViewInfo, errorInfo | |||||
| } | } | ||||
| @@ -457,6 +457,11 @@ var ( | |||||
| Snn4imagenetCode string | Snn4imagenetCode string | ||||
| Snn4imagenetServerHost string | Snn4imagenetServerHost string | ||||
| //snn4imagenet config | |||||
| IsBrainScoreEnabled bool | |||||
| BrainScoreCode string | |||||
| BrainScoreServerHost string | |||||
| //blockchain config | //blockchain config | ||||
| BlockChainHost string | BlockChainHost string | ||||
| CommitValidDate string | CommitValidDate string | ||||
| @@ -1184,8 +1189,13 @@ func NewContext() { | |||||
| sec = Cfg.Section("snn4imagenet") | sec = Cfg.Section("snn4imagenet") | ||||
| IsSnn4imagenetEnabled = sec.Key("ENABLED").MustBool(false) | IsSnn4imagenetEnabled = sec.Key("ENABLED").MustBool(false) | ||||
| Snn4imagenetCode = sec.Key("SNN4IMAGENETCODE").MustString("https://yangzhx:justfortest123@git.openi.org.cn/yangzhx/detection_benchmark_script.git") | |||||
| Snn4imagenetServerHost = sec.Key("HOST").MustString("http://192.168.202.90:3366/") | |||||
| Snn4imagenetCode = sec.Key("SNN4IMAGENETCODE").MustString("https://yult:19910821ylt@git.openi.org.cn/yult/snn4imagenet_script.git") | |||||
| Snn4imagenetServerHost = sec.Key("HOST").MustString("http://192.168.207.76:8080/") | |||||
| sec = Cfg.Section("brainscore") | |||||
| IsBrainScoreEnabled = sec.Key("ENABLED").MustBool(false) | |||||
| BrainScoreCode = sec.Key("BRAINSCORECODE").MustString("https://yult:19910821ylt@git.openi.org.cn/yult/brainscore_script.git") | |||||
| BrainScoreServerHost = sec.Key("HOST").MustString("http://192.168.207.76:8080/") | |||||
| sec = Cfg.Section("blockchain") | sec = Cfg.Section("blockchain") | ||||
| BlockChainHost = sec.Key("HOST").MustString("http://192.168.136.66:3302/") | BlockChainHost = sec.Key("HOST").MustString("http://192.168.136.66:3302/") | ||||
| @@ -776,6 +776,7 @@ cloudbrain_creator=创建者 | |||||
| cloudbrain_task=任务名称 | cloudbrain_task=任务名称 | ||||
| cloudbrain_operate=操作 | cloudbrain_operate=操作 | ||||
| cloudbrain_status_createtime=状态/创建时间 | cloudbrain_status_createtime=状态/创建时间 | ||||
| cloudbrain_jobname_err=只能以小写字母或数字开头且只包含小写字母、数字、_和-,不能以_结尾,最长36个字符。 | |||||
| template.items=模板选项 | template.items=模板选项 | ||||
| template.git_content=Git数据(默认分支) | template.git_content=Git数据(默认分支) | ||||
| @@ -65,12 +65,15 @@ func GetCloudbrainTask(ctx *context.APIContext) { | |||||
| return | return | ||||
| } | } | ||||
| taskRoles := result.TaskRoles | |||||
| taskRes, _ := models.ConvertToTaskPod(taskRoles[cloudbrain.SubTaskName].(map[string]interface{})) | |||||
| job.Status = result.JobStatus.State | |||||
| if result.JobStatus.State != string(models.JobWaiting) && result.JobStatus.State != string(models.JobFailed) { | |||||
| taskRoles := result.TaskRoles | |||||
| taskRes, _ := models.ConvertToTaskPod(taskRoles[cloudbrain.SubTaskName].(map[string]interface{})) | |||||
| job.ContainerIp = taskRes.TaskStatuses[0].ContainerIP | |||||
| job.ContainerID = taskRes.TaskStatuses[0].ContainerID | |||||
| job.Status = taskRes.TaskStatuses[0].State | |||||
| job.ContainerIp = taskRes.TaskStatuses[0].ContainerIP | |||||
| job.ContainerID = taskRes.TaskStatuses[0].ContainerID | |||||
| job.Status = taskRes.TaskStatuses[0].State | |||||
| } | |||||
| if result.JobStatus.State != string(models.JobWaiting) { | if result.JobStatus.State != string(models.JobWaiting) { | ||||
| err = models.UpdateJob(job) | err = models.UpdateJob(job) | ||||
| @@ -40,6 +40,8 @@ var ( | |||||
| categories *models.Categories | categories *models.Categories | ||||
| ) | ) | ||||
| var jobNamePattern = regexp.MustCompile(`^[a-z0-9][a-z0-9-_]{1,34}[a-z0-9-]$`) | |||||
| // MustEnableDataset check if repository enable internal cb | // MustEnableDataset check if repository enable internal cb | ||||
| func MustEnableCloudbrain(ctx *context.Context) { | func MustEnableCloudbrain(ctx *context.Context) { | ||||
| if !ctx.Repo.CanRead(models.UnitTypeCloudBrain) { | if !ctx.Repo.CanRead(models.UnitTypeCloudBrain) { | ||||
| @@ -175,6 +177,9 @@ func cloudBrainNewDataPrepare(ctx *context.Context) error{ | |||||
| ctx.Data["snn4imagenet_path"] = cloudbrain.Snn4imagenetMountPath | ctx.Data["snn4imagenet_path"] = cloudbrain.Snn4imagenetMountPath | ||||
| ctx.Data["is_snn4imagenet_enabled"] = setting.IsSnn4imagenetEnabled | ctx.Data["is_snn4imagenet_enabled"] = setting.IsSnn4imagenetEnabled | ||||
| ctx.Data["brainscore_path"] = cloudbrain.BrainScoreMountPath | |||||
| ctx.Data["is_brainscore_enabled"] = setting.IsBrainScoreEnabled | |||||
| return nil | return nil | ||||
| } | } | ||||
| @@ -197,8 +202,13 @@ func CloudBrainCreate(ctx *context.Context, form auth.CreateCloudBrainForm) { | |||||
| gpuQueue := setting.JobType | gpuQueue := setting.JobType | ||||
| codePath := setting.JobPath + jobName + cloudbrain.CodeMountPath | codePath := setting.JobPath + jobName + cloudbrain.CodeMountPath | ||||
| resourceSpecId := form.ResourceSpecId | resourceSpecId := form.ResourceSpecId | ||||
| if !jobNamePattern.MatchString(jobName) { | |||||
| ctx.RenderWithErr(ctx.Tr("repo.cloudbrain_jobname_err"), tplModelArtsNew, &form) | |||||
| return | |||||
| } | |||||
| if jobType != string(models.JobTypeBenchmark) && jobType != string(models.JobTypeDebug) && jobType != string(models.JobTypeSnn4imagenet) { | |||||
| if jobType != string(models.JobTypeBenchmark) && jobType != string(models.JobTypeDebug) && jobType != string(models.JobTypeSnn4imagenet) && jobType != string(models.JobTypeBrainScore) { | |||||
| log.Error("jobtype error:", jobType, ctx.Data["MsgID"]) | log.Error("jobtype error:", jobType, ctx.Data["MsgID"]) | ||||
| cloudBrainNewDataPrepare(ctx) | cloudBrainNewDataPrepare(ctx) | ||||
| ctx.RenderWithErr("jobtype error", tplCloudBrainNew, &form) | ctx.RenderWithErr("jobtype error", tplCloudBrainNew, &form) | ||||
| @@ -247,6 +257,11 @@ func CloudBrainCreate(ctx *context.Context, form auth.CreateCloudBrainForm) { | |||||
| downloadRateCode(repo, jobName, setting.Snn4imagenetCode, snn4imagenetPath, "", "") | downloadRateCode(repo, jobName, setting.Snn4imagenetCode, snn4imagenetPath, "", "") | ||||
| } | } | ||||
| brainScorePath := setting.JobPath + jobName + cloudbrain.BrainScoreMountPath | |||||
| if setting.IsBrainScoreEnabled && jobType == string(models.JobTypeBrainScore) { | |||||
| downloadRateCode(repo, jobName, setting.BrainScoreCode, brainScorePath, "", "") | |||||
| } | |||||
| err = cloudbrain.GenerateTask(ctx, jobName, image, command, uuid, codePath, modelPath, benchmarkPath, snn4imagenetPath, jobType, gpuQueue, resourceSpecId) | err = cloudbrain.GenerateTask(ctx, jobName, image, command, uuid, codePath, modelPath, benchmarkPath, snn4imagenetPath, jobType, gpuQueue, resourceSpecId) | ||||
| if err != nil { | if err != nil { | ||||
| cloudBrainNewDataPrepare(ctx) | cloudBrainNewDataPrepare(ctx) | ||||
| @@ -273,17 +288,30 @@ func CloudBrainShow(ctx *context.Context) { | |||||
| if result != nil { | if result != nil { | ||||
| jobRes, _ := models.ConvertToJobResultPayload(result.Payload) | jobRes, _ := models.ConvertToJobResultPayload(result.Payload) | ||||
| jobRes.Resource.Memory = strings.ReplaceAll(jobRes.Resource.Memory, "Mi", "MB") | jobRes.Resource.Memory = strings.ReplaceAll(jobRes.Resource.Memory, "Mi", "MB") | ||||
| ctx.Data["result"] = jobRes | |||||
| taskRoles := jobRes.TaskRoles | taskRoles := jobRes.TaskRoles | ||||
| taskRes, _ := models.ConvertToTaskPod(taskRoles[cloudbrain.SubTaskName].(map[string]interface{})) | |||||
| ctx.Data["taskRes"] = taskRes | |||||
| task.Status = taskRes.TaskStatuses[0].State | |||||
| task.ContainerID = taskRes.TaskStatuses[0].ContainerID | |||||
| task.ContainerIp = taskRes.TaskStatuses[0].ContainerIP | |||||
| err = models.UpdateJob(task) | |||||
| if err != nil { | |||||
| ctx.Data["error"] = err.Error() | |||||
| if jobRes.JobStatus.State != string(models.JobFailed) { | |||||
| taskRes, _ := models.ConvertToTaskPod(taskRoles[cloudbrain.SubTaskName].(map[string]interface{})) | |||||
| ctx.Data["taskRes"] = taskRes | |||||
| task.Status = taskRes.TaskStatuses[0].State | |||||
| task.ContainerID = taskRes.TaskStatuses[0].ContainerID | |||||
| task.ContainerIp = taskRes.TaskStatuses[0].ContainerIP | |||||
| err = models.UpdateJob(task) | |||||
| if err != nil { | |||||
| ctx.Data["error"] = err.Error() | |||||
| } | |||||
| } else { | |||||
| task.Status = jobRes.JobStatus.State | |||||
| taskRes := models.TaskPod{TaskStatuses: []models.TaskStatuses{ | |||||
| { | |||||
| State: jobRes.JobStatus.State, | |||||
| }, | |||||
| }} | |||||
| ctx.Data["taskRes"] = taskRes | |||||
| jobRes.JobStatus.StartTime = time.Unix(int64(task.CreatedUnix), 0).Format("2006-01-02 15:04:05") | |||||
| jobRes.JobStatus.EndTime = time.Unix(int64(task.UpdatedUnix), 0).Format("2006-01-02 15:04:05") | |||||
| } | } | ||||
| ctx.Data["result"] = jobRes | |||||
| } | } | ||||
| ctx.Data["task"] = task | ctx.Data["task"] = task | ||||
| @@ -343,7 +371,7 @@ func CloudBrainStop(ctx *context.Context) { | |||||
| return | return | ||||
| } | } | ||||
| if task.Status == string(models.JobStopped) { | |||||
| if task.Status == string(models.JobStopped) || task.Status == string(models.JobFailed) { | |||||
| log.Error("the job(%s) has been stopped", task.JobName, ctx.Data["msgID"]) | log.Error("the job(%s) has been stopped", task.JobName, ctx.Data["msgID"]) | ||||
| ctx.ServerError("the job has been stopped", errors.New("the job has been stopped")) | ctx.ServerError("the job has been stopped", errors.New("the job has been stopped")) | ||||
| return | return | ||||
| @@ -568,6 +596,8 @@ func GetRate(ctx *context.Context) { | |||||
| ctx.Redirect(setting.BenchmarkServerHost + "?username=" + ctx.User.Name) | ctx.Redirect(setting.BenchmarkServerHost + "?username=" + ctx.User.Name) | ||||
| } else if job.JobType == string(models.JobTypeSnn4imagenet) { | } else if job.JobType == string(models.JobTypeSnn4imagenet) { | ||||
| ctx.Redirect(setting.Snn4imagenetServerHost) | ctx.Redirect(setting.Snn4imagenetServerHost) | ||||
| } else if job.JobType == string(models.JobTypeBrainScore) { | |||||
| ctx.Redirect(setting.BrainScoreServerHost) | |||||
| } else { | } else { | ||||
| log.Error("JobType error:%s", job.JobType, ctx.Data["msgID"]) | log.Error("JobType error:%s", job.JobType, ctx.Data["msgID"]) | ||||
| } | } | ||||
| @@ -100,7 +100,10 @@ func ModelArtsCreate(ctx *context.Context, form auth.CreateModelArtsForm) { | |||||
| uuid := form.Attachment | uuid := form.Attachment | ||||
| description := form.Description | description := form.Description | ||||
| //repo := ctx.Repo.Repository | //repo := ctx.Repo.Repository | ||||
| if !jobNamePattern.MatchString(jobName) { | |||||
| ctx.RenderWithErr(ctx.Tr("repo.cloudbrain_jobname_err"), tplModelArtsNew, &form) | |||||
| return | |||||
| } | |||||
| err := modelarts.GenerateTask(ctx, jobName, uuid, description) | err := modelarts.GenerateTask(ctx, jobName, uuid, description) | ||||
| if err != nil { | if err != nil { | ||||
| ctx.RenderWithErr(err.Error(), tplModelArtsNew, &form) | ctx.RenderWithErr(err.Error(), tplModelArtsNew, &form) | ||||
| @@ -5,6 +5,7 @@ import ( | |||||
| "code.gitea.io/gitea/models" | "code.gitea.io/gitea/models" | ||||
| "code.gitea.io/gitea/modules/log" | "code.gitea.io/gitea/modules/log" | ||||
| "code.gitea.io/gitea/modules/repository" | |||||
| ) | ) | ||||
| //auto daily or manually | //auto daily or manually | ||||
| @@ -62,9 +63,12 @@ func RepoStatisticDaily(date string) { | |||||
| continue | continue | ||||
| } | } | ||||
| //beginTime, endTime := getStatTime(date) | |||||
| //numVisits := repository.AppointProjectView(repo.OwnerName, repo.Name, beginTime, endTime) | |||||
| numVisits := 0 | |||||
| beginTime, endTime := getStatTime(date) | |||||
| numVisits, err := repository.AppointProjectView(repo.OwnerName, repo.Name, beginTime, endTime) | |||||
| if err != nil { | |||||
| log.Error("Get numVisits failed", err) | |||||
| numVisits = 0 | |||||
| } | |||||
| repoStat := models.RepoStatistic{ | repoStat := models.RepoStatistic{ | ||||
| RepoID: repo.ID, | RepoID: repo.ID, | ||||
| @@ -0,0 +1,94 @@ | |||||
| package repo | |||||
| import ( | |||||
| "time" | |||||
| "code.gitea.io/gitea/models" | |||||
| "code.gitea.io/gitea/modules/log" | |||||
| ) | |||||
| func SummaryStatistic() { | |||||
| log.Info("Generate summary statistic begin") | |||||
| yesterday := time.Now().AddDate(0, 0, -1).Format("2006-01-02") | |||||
| SummaryStatisticDaily(yesterday) | |||||
| log.Info("Generate summary statistic end") | |||||
| } | |||||
| func SummaryStatisticDaily(date string) { | |||||
| log.Info("%s", date) | |||||
| if err := models.DeleteSummaryStatisticDaily(date); err != nil { | |||||
| log.Error("DeleteRepoStatDaily failed: %v", err.Error()) | |||||
| return | |||||
| } | |||||
| //user number | |||||
| userNumber, err := models.GetUsersCount() | |||||
| if err != nil { | |||||
| log.Error("can not get user number", err) | |||||
| userNumber = 0 | |||||
| } | |||||
| //organization number | |||||
| organizationNumber, err := models.GetOrganizationsCount() | |||||
| if err != nil { | |||||
| log.Error("can not get orgnazition number", err) | |||||
| organizationNumber = 0 | |||||
| } | |||||
| // repository number | |||||
| repositoryNumer, err := models.GetAllRepositoriesCount() | |||||
| if err != nil { | |||||
| log.Error("can not get repository number", err) | |||||
| repositoryNumer = 0 | |||||
| } | |||||
| //repository size | |||||
| repositorySize, err := models.GetAllRepositoriesSize() | |||||
| if err != nil { | |||||
| log.Error("can not get repository size", err) | |||||
| repositorySize = 0 | |||||
| } | |||||
| // dataset size | |||||
| allDatasetSize, err := models.GetAllAttachmentSize() | |||||
| if err != nil { | |||||
| log.Error("can not get dataset size", err) | |||||
| allDatasetSize = 0 | |||||
| } | |||||
| //topic repo number | |||||
| topics, err := models.GetAllUsedTopics() | |||||
| if err != nil { | |||||
| log.Error("can not get topics", err) | |||||
| } | |||||
| var topicsCount [11]int | |||||
| for _, topic := range topics { | |||||
| index, exists := models.DomainMap[topic.Name] | |||||
| if exists { | |||||
| topicsCount[index] = topic.RepoCount | |||||
| } | |||||
| } | |||||
| summaryStat := models.SummaryStatistic{ | |||||
| Date: date, | |||||
| NumUsers: userNumber, | |||||
| RepoSize: repositorySize, | |||||
| DatasetSize: allDatasetSize, | |||||
| NumOrganizations: organizationNumber, | |||||
| NumRepos: repositoryNumer, | |||||
| NumRepoBigModel: topicsCount[0], | |||||
| NumRepoAI: topicsCount[1], | |||||
| NumRepoVision: topicsCount[2], | |||||
| NumRepoNLP: topicsCount[3], | |||||
| NumRepoML: topicsCount[4], | |||||
| NumRepoNN: topicsCount[5], | |||||
| NumRepoAutoDrive: topicsCount[6], | |||||
| NumRepoRobot: topicsCount[7], | |||||
| NumRepoLeagueLearn: topicsCount[8], | |||||
| NumRepoDataMining: topicsCount[9], | |||||
| NumRepoRISC: topicsCount[10], | |||||
| } | |||||
| if _, err = models.InsertSummaryStatistic(&summaryStat); err != nil { | |||||
| log.Error("Insert summary Stat failed: %v", err.Error()) | |||||
| } | |||||
| log.Info("finish summary statistic") | |||||
| } | |||||
| @@ -11,8 +11,6 @@ import ( | |||||
| "net/http" | "net/http" | ||||
| "strings" | "strings" | ||||
| "code.gitea.io/gitea/routers/repo" | |||||
| "code.gitea.io/gitea/models" | "code.gitea.io/gitea/models" | ||||
| "code.gitea.io/gitea/modules/auth" | "code.gitea.io/gitea/modules/auth" | ||||
| "code.gitea.io/gitea/modules/auth/oauth2" | "code.gitea.io/gitea/modules/auth/oauth2" | ||||
| @@ -1058,7 +1056,6 @@ func SignOut(ctx *context.Context) { | |||||
| }) | }) | ||||
| } | } | ||||
| HandleSignOut(ctx) | HandleSignOut(ctx) | ||||
| go repo.StopJobsByUserID(ctx.User.ID) | |||||
| ctx.Redirect(setting.AppSubURL + "/") | ctx.Redirect(setting.AppSubURL + "/") | ||||
| } | } | ||||
| @@ -8,6 +8,8 @@ package setting | |||||
| import ( | import ( | ||||
| "errors" | "errors" | ||||
| "code.gitea.io/gitea/routers/repo" | |||||
| "code.gitea.io/gitea/models" | "code.gitea.io/gitea/models" | ||||
| "code.gitea.io/gitea/modules/auth" | "code.gitea.io/gitea/modules/auth" | ||||
| "code.gitea.io/gitea/modules/base" | "code.gitea.io/gitea/modules/base" | ||||
| @@ -240,6 +242,7 @@ func DeleteAccount(ctx *context.Context) { | |||||
| ctx.ServerError("DeleteUser", err) | ctx.ServerError("DeleteUser", err) | ||||
| } | } | ||||
| } else { | } else { | ||||
| go repo.StopJobsByUserID(ctx.User.ID) | |||||
| log.Trace("Account deleted: %s", ctx.User.Name) | log.Trace("Account deleted: %s", ctx.User.Name) | ||||
| ctx.Redirect(setting.AppSubURL + "/") | ctx.Redirect(setting.AppSubURL + "/") | ||||
| } | } | ||||
| @@ -50,6 +50,13 @@ | |||||
| </a> | </a> | ||||
| </div> | </div> | ||||
| </div> | </div> | ||||
| <div class="swiper-slide"> | |||||
| <div class="ui card"> | |||||
| <a class="image" href="https://git.openi.org.cn/JD_Group"> | |||||
| <img src="/img/org-jd@2x-80.jpg" alt="京东" title="京东"> | |||||
| </a> | |||||
| </div> | |||||
| </div> | |||||
| <div class="swiper-slide"> | <div class="swiper-slide"> | ||||
| <div class="ui card"> | <div class="ui card"> | ||||
| <a class="image" href="https://git.openi.org.cn/TensorLayer"> | <a class="image" href="https://git.openi.org.cn/TensorLayer"> | ||||
| @@ -337,9 +337,9 @@ | |||||
| 调试 | 调试 | ||||
| </a> | </a> | ||||
| <form id="stopForm-{{.JobID}}" action="{{if eq .Status "STOPPED"}}javascript:void(0){{else}}{{$.Link}}/{{.JobID}}/stop{{end}}" method="post" style="margin-left:-1px;"> | |||||
| <form id="stopForm-{{.JobID}}" action="{{if or (eq .Status "STOPPED") (eq .Status "FAILED")}}javascript:void(0){{else}}{{$.Link}}/{{.JobID}}/stop{{end}}" method="post" style="margin-left:-1px;"> | |||||
| {{$.CsrfTokenHtml}} | {{$.CsrfTokenHtml}} | ||||
| <a class="ui basic {{if eq .Status "STOPPED"}}disabled {{else}}blue {{end}}button" onclick="document.getElementById('stopForm-{{.JobID}}').submit();"> | |||||
| <a class="ui basic {{if or (eq .Status "STOPPED") (eq .Status "FAILED")}}disabled {{else}}blue {{end}}button" onclick="document.getElementById('stopForm-{{.JobID}}').submit();"> | |||||
| 停止 | 停止 | ||||
| </a> | </a> | ||||
| </form> | </form> | ||||
| @@ -491,7 +491,7 @@ | |||||
| console.log("---------",index,job) | console.log("---------",index,job) | ||||
| const jobID = job.dataset.jobid; | const jobID = job.dataset.jobid; | ||||
| const repoPath = job.dataset.repopath; | const repoPath = job.dataset.repopath; | ||||
| if (job.textContent.trim() == 'STOPPED') { | |||||
| if (job.textContent.trim() == 'STOPPED' || job.textContent.trim() == 'FAILED') { | |||||
| return | return | ||||
| } | } | ||||
| @@ -499,7 +499,6 @@ | |||||
| $.get(`/api/v1/repos/${repoPath}/cloudbrain/${jobID}`, (data) => { | $.get(`/api/v1/repos/${repoPath}/cloudbrain/${jobID}`, (data) => { | ||||
| const jobID = data.JobID | const jobID = data.JobID | ||||
| const status = data.JobStatus | const status = data.JobStatus | ||||
| console.log("status",status) | |||||
| if (status != job.textContent.trim()) { | if (status != job.textContent.trim()) { | ||||
| //$('#' + jobID).text(status) | //$('#' + jobID).text(status) | ||||
| //if (status == 'STOPPED') { | //if (status == 'STOPPED') { | ||||
| @@ -89,6 +89,10 @@ | |||||
| display: none; | display: none; | ||||
| } | } | ||||
| .inline.required.field.cloudbrain_brainscore { | |||||
| display: none; | |||||
| } | |||||
| .select2-container .select2-selection--single{ | .select2-container .select2-selection--single{ | ||||
| height:38px !important; | height:38px !important; | ||||
| } | } | ||||
| @@ -130,12 +134,13 @@ | |||||
| <input name="job_name" id="cloudbrain_job_name" placeholder="任务名称" value="{{.job_name}}" tabindex="3" autofocus required maxlength="255"> | <input name="job_name" id="cloudbrain_job_name" placeholder="任务名称" value="{{.job_name}}" tabindex="3" autofocus required maxlength="255"> | ||||
| </div> | </div> | ||||
| <div class="inline required field" style="{{if .is_benchmark_enabled}}display:block;{{else if .is_snn4imagenet_enabled}}display:block;{{else}}display:none;{{end}}"> | |||||
| <div class="inline required field" style="{{if ((.is_benchmark_enabled) or (.is_snn4imagenet_enabled) or (.is_brainscore_enabled))}}display:block;{{else}}display:none;{{end}}"> | |||||
| <label>任务类型</label> | <label>任务类型</label> | ||||
| <select id="cloudbrain_job_type" class="ui search dropdown" placeholder="选择任务类型" style='width:385px' name="job_type"> | <select id="cloudbrain_job_type" class="ui search dropdown" placeholder="选择任务类型" style='width:385px' name="job_type"> | ||||
| <option name="job_type" value="DEBUG">DEBUG</option> | <option name="job_type" value="DEBUG">DEBUG</option> | ||||
| <option name="job_type" value="BENCHMARK">BENCHMARK</option> | <option name="job_type" value="BENCHMARK">BENCHMARK</option> | ||||
| <option name="job_type" value="SNN4IMAGENET">SNN4IMAGENET</option> | <option name="job_type" value="SNN4IMAGENET">SNN4IMAGENET</option> | ||||
| <option name="job_type" value="BRAINSCORE">BRAINSCORE</option> | |||||
| </select> | </select> | ||||
| </div> | </div> | ||||
| @@ -215,6 +220,10 @@ | |||||
| <label>snn4imagenet脚本存放路径</label> | <label>snn4imagenet脚本存放路径</label> | ||||
| <input name="snn4imagenet_path" id="cloudbrain_snn4imagenet_path" value="{{.snn4imagenet_path}}" tabindex="3" autofocus required maxlength="255" readonly="readonly"> | <input name="snn4imagenet_path" id="cloudbrain_snn4imagenet_path" value="{{.snn4imagenet_path}}" tabindex="3" autofocus required maxlength="255" readonly="readonly"> | ||||
| </div> | </div> | ||||
| <div class="inline required field cloudbrain_brainscore"> | |||||
| <label>brainscore脚本存放路径</label> | |||||
| <input name="brainscore_path" id="cloudbrain_brainscore_path" value="{{.brainscore_path}}" tabindex="3" autofocus required maxlength="255" readonly="readonly"> | |||||
| </div> | |||||
| <div class="inline required field" hidden> | <div class="inline required field" hidden> | ||||
| <label>启动命令</label> | <label>启动命令</label> | ||||
| <textarea name="command" rows="10" readonly="readonly">{{.command}}</textarea> | <textarea name="command" rows="10" readonly="readonly">{{.command}}</textarea> | ||||
| @@ -250,11 +259,11 @@ | |||||
| let value_task = $("input[name='job_name']").val() | let value_task = $("input[name='job_name']").val() | ||||
| let value_image = $("input[name='image']").val() | let value_image = $("input[name='image']").val() | ||||
| let value_data = $("input[name='attachment']").val() | let value_data = $("input[name='attachment']").val() | ||||
| let re = /^[a-z0-9][a-z0-9-_]{1,36}$/ | |||||
| let re = /^[a-z0-9][a-z0-9-_]{1,35}[^_]$/ | |||||
| let flag = re.test(value_task) | let flag = re.test(value_task) | ||||
| if(!flag){ | if(!flag){ | ||||
| $('#messageInfo').css('display','block') | $('#messageInfo').css('display','block') | ||||
| let str = '只能以小写字母或数字开头且只包含小写字母、数字、_和-、最长36个字符。' | |||||
| let str = '只能以小写字母或数字开头且只包含小写字母、数字、_和-、最长36个字符,不能下划线(-)结尾。' | |||||
| $('#messageInfo p').text(str) | $('#messageInfo p').text(str) | ||||
| return false | return false | ||||
| } | } | ||||
| @@ -311,9 +320,12 @@ | |||||
| $(".cloudbrain_benchmark").show(); | $(".cloudbrain_benchmark").show(); | ||||
| } else if ($(this).val() == 'SNN4IMAGENET') { | } else if ($(this).val() == 'SNN4IMAGENET') { | ||||
| $(".cloudbrain_snn4imagenet").show(); | $(".cloudbrain_snn4imagenet").show(); | ||||
| } else if ($(this).val() == 'BRAINSCORE') { | |||||
| $(".cloudbrain_brainscore").show(); | |||||
| } else { | } else { | ||||
| $(".cloudbrain_benchmark").hide(); | $(".cloudbrain_benchmark").hide(); | ||||
| $(".cloudbrain_snn4imagenet").hide(); | $(".cloudbrain_snn4imagenet").hide(); | ||||
| $(".cloudbrain_brainscore").hide(); | |||||
| } | } | ||||
| }) | }) | ||||
| }) | }) | ||||
| @@ -179,7 +179,7 @@ | |||||
| let value_task = $("input[name='job_name']").val() | let value_task = $("input[name='job_name']").val() | ||||
| let re = /^[a-z0-9][a-z0-9-_]{1,36}$/ | |||||
| let re = /^[a-z0-9][a-z0-9-_]{1,35}$/ | |||||
| let flag = re.test(value_task) | let flag = re.test(value_task) | ||||
| if(!flag){ | if(!flag){ | ||||
| $('#messageInfo').css('display','block') | $('#messageInfo').css('display','block') | ||||
| @@ -11,16 +11,16 @@ | |||||
| <div class="icon-wrapper"> | <div class="icon-wrapper"> | ||||
| <i style="line-height: 1.5;color: #303643;font-weight: 900;" v-if="showInitTopic[i]" class="el-icon-check" ></i> | <i style="line-height: 1.5;color: #303643;font-weight: 900;" v-if="showInitTopic[i]" class="el-icon-check" ></i> | ||||
| </div> | </div> | ||||
| <div class="text">{{arr.topic_name}} </div> | |||||
| <div class="text">{{arr.topic_name.toLowerCase()}} </div> | |||||
| </div> | </div> | ||||
| <div v-if="showInputValue" class="addition item-text" @click="postTopic"> | <div v-if="showInputValue" class="addition item-text" @click="postTopic"> | ||||
| 点击或回车添加<b class="user-add-label-text">{{input}}</b>标签 | |||||
| 点击或回车添加<b class="user-add-label-text">{{input.toLowerCase()}}</b>标签 | |||||
| </div> | </div> | ||||
| <div v-if="showAddTopic" class="item-text" @click="addPostTopic"> | <div v-if="showAddTopic" class="item-text" @click="addPostTopic"> | ||||
| <div class="icon-wrapper"> | <div class="icon-wrapper"> | ||||
| <i style="line-height: 1.5;color: #303643;font-weight: 900;" v-if="showAddFlage" class="el-icon-check" ></i> | <i style="line-height: 1.5;color: #303643;font-weight: 900;" v-if="showAddFlage" class="el-icon-check" ></i> | ||||
| </div> | </div> | ||||
| <div class="text">{{input}}</div> | |||||
| <div class="text">{{input.toLowerCase()}}</div> | |||||
| </div> | </div> | ||||
| </div> | </div> | ||||
| @@ -134,7 +134,7 @@ export default { | |||||
| this.showSearchTopic = true | this.showSearchTopic = true | ||||
| } | } | ||||
| else if(this.arrayTopics.indexOf(this.input)>-1){ | |||||
| else if(this.arrayTopics.indexOf(this.input.toLowerCase())>-1){ | |||||
| this.showInputValue = false | this.showInputValue = false | ||||
| this.showSearchTopic = false | this.showSearchTopic = false | ||||
| @@ -142,7 +142,7 @@ export default { | |||||
| this.showInitTopic = [] | this.showInitTopic = [] | ||||
| let timestamp=new Date().getTime() | let timestamp=new Date().getTime() | ||||
| this.params.q = this.input | |||||
| this.params.q = this.input.toLowerCase() | |||||
| this.params._ = timestamp | this.params._ = timestamp | ||||
| this.$axios.get('/api/v1/topics/search',{ | this.$axios.get('/api/v1/topics/search',{ | ||||
| params:this.params | params:this.params | ||||
| @@ -224,11 +224,11 @@ export default { | |||||
| return | return | ||||
| }else{ | }else{ | ||||
| let topic = this.input | let topic = this.input | ||||
| if(this.arrayTopics.includes(topic)){ | |||||
| if(this.arrayTopics.includes(topic.toLowerCase())){ | |||||
| return | return | ||||
| } | } | ||||
| else{ | else{ | ||||
| this.arrayTopics.push(topic) | |||||
| this.arrayTopics.push(topic.toLowerCase()) | |||||
| let topics = this.arrayTopics | let topics = this.arrayTopics | ||||
| let strTopics = topics.join(',') | let strTopics = topics.join(',') | ||||
| @@ -268,7 +268,7 @@ export default { | |||||
| } | } | ||||
| else if(!this.showAddFlage){ | else if(!this.showAddFlage){ | ||||
| let topic = this.input | let topic = this.input | ||||
| this.arrayTopics.push(topic) | |||||
| this.arrayTopics.push(topic.toLowerCase()) | |||||
| let topics = this.arrayTopics | let topics = this.arrayTopics | ||||
| let strTopics = topics.join(',') | let strTopics = topics.join(',') | ||||