| @@ -29,51 +29,22 @@ | |||||
| } | } | ||||
| .rotation3D__item .scale{ position: absolute; top: 0; width: 100%; height: 100%; } | .rotation3D__item .scale{ position: absolute; top: 0; width: 100%; height: 100%; } | ||||
| .rotation3D__item .cont{ position: relative; z-index: 2; } | .rotation3D__item .cont{ position: relative; z-index: 2; } | ||||
| .rotation3D__item .cont .iconfont { font-size: 28px; margin-top: 30px; margin-bottom: 96px; display: block; } | |||||
| .rotation3D__item .cont .iconfont { font-size: 28px; margin-top: 30px; margin-bottom: 96px; display: block; height: 35px;} | |||||
| .rotation3D__item .cont p{ color: #101010; } | .rotation3D__item .cont p{ color: #101010; } | ||||
| .itemList .rotation3D__item .cont p::after{ | |||||
| font-size: 12px; | |||||
| content: ''; | |||||
| position: absolute; | |||||
| left: 0; | |||||
| right: 0; | |||||
| margin-top: 60px; | |||||
| color: #101010; | |||||
| } | |||||
| .itemList .rotation3D__item:nth-child(1) .cont p::after{ | |||||
| content: "鹏城云脑一号"; | |||||
| } | |||||
| .itemList .rotation3D__item:nth-child(2) .cont p::after{ | |||||
| content: "鹏城云脑二号"; | |||||
| } | |||||
| .itemList .rotation3D__item:nth-child(3) .cont p::after{ | |||||
| content: "北大人工智能集群系统"; | |||||
| } | |||||
| .itemList .rotation3D__item:nth-child(4) .cont p::after{ | |||||
| content: "合肥类脑智能开放平台"; | |||||
| .lineList .rotation3D__line:nth-child(5n+0) .dot{ | |||||
| } | } | ||||
| .itemList .rotation3D__item:nth-child(5) .cont p::after{ | |||||
| content: "武汉人工智能计算中心"; | |||||
| .lineList .rotation3D__line:nth-child(5n+1) .dot{ | |||||
| animation-delay: 1s; | |||||
| } | } | ||||
| .itemList .rotation3D__item:nth-child(6) .cont p::after{ | |||||
| content: "西安未来人工智能计算中心"; | |||||
| .lineList .rotation3D__line:nth-child(5n+2) .dot{ | |||||
| animation-delay: 3s; | |||||
| } | } | ||||
| .itemList .rotation3D__item:nth-child(7) .cont p::after{ | |||||
| content: "更多接入中…"; | |||||
| .lineList .rotation3D__line:nth-child(5n+3) .dot{ | |||||
| animation-delay: 2s; | |||||
| } | } | ||||
| .itemList .rotation3D__item:nth-child(8) .cont p::after{ | |||||
| content: "中原人工智能计算中心"; | |||||
| .lineList .rotation3D__line:nth-child(5n+3) .dot{ | |||||
| animation-delay: 4s; | |||||
| } | } | ||||
| .itemList .rotation3D__item:nth-child(9) .cont p::after{ | |||||
| content: "成都人工智能计算中心"; | |||||
| } | |||||
| .itemList .rotation3D__item:nth-child(10) .cont p::after{ | |||||
| content: "横琴先进智能计算中心"; | |||||
| } | |||||
| .itemList .rotation3D__item:nth-child(11) .cont p::after{ | |||||
| content: "国家超级计算济南中心"; | |||||
| } | |||||
| .rotation3D__item.blue{ color: #01e9fc; } | .rotation3D__item.blue{ color: #01e9fc; } | ||||
| .rotation3D__item.green{ color: #b4b3ca; } | .rotation3D__item.green{ color: #b4b3ca; } | ||||
| .rotation3D__item.yellow{ color: #ffd200; } | .rotation3D__item.yellow{ color: #ffd200; } | ||||
| @@ -90,14 +61,17 @@ | |||||
| ---------------------------*/ | ---------------------------*/ | ||||
| .rotation3D__line{ | .rotation3D__line{ | ||||
| position: absolute; left: 50%; top: 50%; | position: absolute; left: 50%; top: 50%; | ||||
| display: block; width: 1px; height: 50%; | |||||
| display: block; | |||||
| width: 30px; | |||||
| height: 50%; | |||||
| padding-top: 60px; color: #fff; font-size: 50px; | padding-top: 60px; color: #fff; font-size: 50px; | ||||
| /*background: #fff;*/ | /*background: #fff;*/ | ||||
| /*原点设置在中间*/ | /*原点设置在中间*/ | ||||
| transform-origin: 50% 0; | transform-origin: 50% 0; | ||||
| transform-style: preserve-3d; | transform-style: preserve-3d; | ||||
| } | |||||
| .rotation3D__line .pos{ position: absolute; top: 0; } | |||||
| overflow: hidden; | |||||
| } | |||||
| .rotation3D__line .pos{ position: absolute; top: 0; left: 15px;} | |||||
| .rotation3D__line svg { position: absolute; top: 0; } | .rotation3D__line svg { position: absolute; top: 0; } | ||||
| .rotation3D__line svg path { | .rotation3D__line svg path { | ||||
| stroke: #fff; fill: none; | stroke: #fff; fill: none; | ||||
| @@ -139,8 +113,10 @@ | |||||
| position: absolute; | position: absolute; | ||||
| font-size: 12px; | font-size: 12px; | ||||
| color: #888; | color: #888; | ||||
| transform: rotate(180deg)scale(0.80); | |||||
| } | |||||
| transform:scale(0.80); | |||||
| transform-origin:left; | |||||
| white-space: nowrap; | |||||
| } | |||||
| /*颜色*/ | /*颜色*/ | ||||
| .rotation3D__line.blue { color: #07b2f9; } | .rotation3D__line.blue { color: #07b2f9; } | ||||
| @@ -134,7 +134,7 @@ type Cloudbrain struct { | |||||
| CanDebug bool `xorm:"-"` | CanDebug bool `xorm:"-"` | ||||
| CanDel bool `xorm:"-"` | CanDel bool `xorm:"-"` | ||||
| CanModify bool `xorm:"-"` | CanModify bool `xorm:"-"` | ||||
| Type int | |||||
| Type int `xorm:"INDEX"` | |||||
| BenchmarkTypeID int | BenchmarkTypeID int | ||||
| BenchmarkChildTypeID int | BenchmarkChildTypeID int | ||||
| @@ -2046,3 +2046,30 @@ func GetDatasetInfo(uuidStr string) (map[string]DatasetInfo, string, error) { | |||||
| return datasetInfos, datasetNames, nil | return datasetInfos, datasetNames, nil | ||||
| } | } | ||||
| func GetNewestJobsByAiCenter() ([]int64, error) { | |||||
| ids := make([]int64, 0) | |||||
| return ids, x. | |||||
| Select("max(id) as id"). | |||||
| Where("type=? and ai_center!='' and ai_center is not null", TypeC2Net). | |||||
| GroupBy("ai_center"). | |||||
| Table(Cloudbrain{}). | |||||
| Find(&ids) | |||||
| } | |||||
| func GetNewestJobsByType() ([]int64, error) { | |||||
| ids := make([]int64, 0) | |||||
| return ids, x. | |||||
| Select("max(id) as id"). | |||||
| In("type", TypeCloudBrainOne, TypeCloudBrainTwo). | |||||
| GroupBy("type"). | |||||
| Table(Cloudbrain{}). | |||||
| Find(&ids) | |||||
| } | |||||
| func GetCloudbrainByIDs(ids []int64) ([]*Cloudbrain, error) { | |||||
| cloudbrains := make([]*Cloudbrain, 0) | |||||
| return cloudbrains, x. | |||||
| In("id", ids). | |||||
| Find(&cloudbrains) | |||||
| } | |||||
| @@ -7,6 +7,7 @@ package setting | |||||
| import ( | import ( | ||||
| "encoding/base64" | "encoding/base64" | ||||
| "encoding/json" | |||||
| "fmt" | "fmt" | ||||
| "io" | "io" | ||||
| "io/ioutil" | "io/ioutil" | ||||
| @@ -64,7 +65,16 @@ const ( | |||||
| ReCaptcha = "recaptcha" | ReCaptcha = "recaptcha" | ||||
| ) | ) | ||||
| // settings | |||||
| type C2NetSequenceInfo struct { | |||||
| ID int `json:"id"` | |||||
| Name string `json:"name"` | |||||
| Content string `json:"content"` | |||||
| } | |||||
| type C2NetSqInfos struct { | |||||
| C2NetSqInfo []*C2NetSequenceInfo `json:"sequence"` | |||||
| } | |||||
| var ( | var ( | ||||
| // AppVer settings | // AppVer settings | ||||
| AppVer string | AppVer string | ||||
| @@ -537,13 +547,16 @@ var ( | |||||
| //grampus config | //grampus config | ||||
| Grampus = struct { | Grampus = struct { | ||||
| Env string | |||||
| Host string | |||||
| UserName string | |||||
| Password string | |||||
| SpecialPools string | |||||
| Env string | |||||
| Host string | |||||
| UserName string | |||||
| Password string | |||||
| SpecialPools string | |||||
| C2NetSequence string | |||||
| }{} | }{} | ||||
| C2NetInfos *C2NetSqInfos | |||||
| //elk config | //elk config | ||||
| ElkUrl string | ElkUrl string | ||||
| ElkUser string | ElkUser string | ||||
| @@ -1428,7 +1441,12 @@ func GetGrampusConfig() { | |||||
| Grampus.UserName = sec.Key("USERNAME").MustString("") | Grampus.UserName = sec.Key("USERNAME").MustString("") | ||||
| Grampus.Password = sec.Key("PASSWORD").MustString("") | Grampus.Password = sec.Key("PASSWORD").MustString("") | ||||
| Grampus.SpecialPools = sec.Key("SPECIAL_POOL").MustString("") | Grampus.SpecialPools = sec.Key("SPECIAL_POOL").MustString("") | ||||
| Grampus.C2NetSequence = sec.Key("C2NET_SEQUENCE").MustString("{\"sequence\":[{\"id\":1,\"name\":\"cloudbrain_one\",\"content\":\"鹏城云脑一号\"},{\"id\":2,\"name\":\"cloudbrain_two\",\"content\":\"鹏城云脑二号\"},{\"id\":3,\"name\":\"beida\",\"content\":\"北大人工智能集群系统\"},{\"id\":4,\"name\":\"hefei\",\"content\":\"合肥类脑智能开放平台\"},{\"id\":5,\"name\":\"wuhan\",\"content\":\"武汉人工智能计算中心\"},{\"id\":6,\"name\":\"xian\",\"content\":\"西安未来人工智能计算中心\"},{\"id\":7,\"pclcci\":\"more\",\"content\":\"鹏城云计算所\"},{\"id\":8,\"name\":\"xuchang\",\"content\":\"中原人工智能计算中心\"},{\"id\":9,\"name\":\"chengdu\",\"content\":\"成都人工智能计算中心\"},{\"id\":10,\"name\":\"more\",\"content\":\"横琴先进智能计算中心\"},{\"id\":11,\"name\":\"more\",\"content\":\"国家超级计算济南中心\"}]}") | |||||
| if Grampus.C2NetSequence != "" { | |||||
| if err := json.Unmarshal([]byte(Grampus.C2NetSequence), &C2NetInfos); err != nil { | |||||
| log.Error("Unmarshal(C2NetSequence) failed:%v", err) | |||||
| } | |||||
| } | |||||
| } | } | ||||
| func SetRadarMapConfig() { | func SetRadarMapConfig() { | ||||
| @@ -575,6 +575,8 @@ func GetObsLogFileName(prefix string) (string, error) { | |||||
| log.Error("PutObject failed:", err.Error()) | log.Error("PutObject failed:", err.Error()) | ||||
| return "", err | return "", err | ||||
| } | } | ||||
| if output == nil || len(output.Contents) == 0 { | |||||
| return "", errors.New("obs log files not exist") | |||||
| } | |||||
| return output.Contents[0].Key, nil | return output.Contents[0].Key, nil | ||||
| } | } | ||||
| @@ -119,7 +119,6 @@ document.onreadystatechange = function () { | |||||
| continue; | continue; | ||||
| } | } | ||||
| } | } | ||||
| refresh3DInfo(record); | |||||
| var recordPrefix = getMsg(record); | var recordPrefix = getMsg(record); | ||||
| if(record.OpType == "6" || record.OpType == "10" || record.OpType == "12" || record.OpType == "13"){ | if(record.OpType == "6" || record.OpType == "10" || record.OpType == "12" || record.OpType == "13"){ | ||||
| html += recordPrefix + actionName; | html += recordPrefix + actionName; | ||||
| @@ -208,29 +207,6 @@ function getTaskLink(record){ | |||||
| return re; | return re; | ||||
| } | } | ||||
| function refresh3DInfo(record){ | |||||
| if(record.OpType == "25" || record.OpType == "29" || record.OpType == "31"){ | |||||
| //cloudbrain one | |||||
| var lines = $('.rotation3D__line'); | |||||
| var span = $('.rotation3D__line').find("span")[0]; | |||||
| //console.log(span); | |||||
| span.innerText =record.RefName; | |||||
| //$('.rotation3D__line').find("span").eq(0).text(record.RefName) | |||||
| //console.log("cloudbrain one line length=" + lines.length); | |||||
| //lines[0].find("span").text(record.RefName); | |||||
| }else if(record.OpType == "26" || record.OpType == "27" || record.OpType == "28"){ | |||||
| //cloudbrain two | |||||
| var lines = $('.rotation3D__line'); | |||||
| //console.log("cloudbrain two line length=" + lines.length); | |||||
| var span = $('.rotation3D__line').find("span")[1]; | |||||
| //console.log(span); | |||||
| if(span != null){ | |||||
| span.innerText =record.RefName; | |||||
| } | |||||
| } | |||||
| } | |||||
| function getMsg(record){ | function getMsg(record){ | ||||
| var html =""; | var html =""; | ||||
| html += "<div class=\"swiper-slide item\">"; | html += "<div class=\"swiper-slide item\">"; | ||||
| @@ -1064,6 +1064,8 @@ func RegisterRoutes(m *macaron.Macaron) { | |||||
| m.Post("/prd/event", authentication.AcceptWechatEvent) | m.Post("/prd/event", authentication.AcceptWechatEvent) | ||||
| }) | }) | ||||
| m.Get("/wechat/material", authentication.GetMaterial) | m.Get("/wechat/material", authentication.GetMaterial) | ||||
| m.Get("/cloudbrain/get_newest_job", repo.GetNewestJobs) | |||||
| m.Get("/cloudbrain/get_center_info", repo.GetAICenterInfo) | |||||
| }, securityHeaders(), context.APIContexter(), sudo()) | }, securityHeaders(), context.APIContexter(), sudo()) | ||||
| } | } | ||||
| @@ -6,6 +6,7 @@ | |||||
| package repo | package repo | ||||
| import ( | import ( | ||||
| "code.gitea.io/gitea/modules/setting" | |||||
| "encoding/json" | "encoding/json" | ||||
| "net/http" | "net/http" | ||||
| "sort" | "sort" | ||||
| @@ -323,3 +324,94 @@ func CloudBrainModelList(ctx *context.APIContext) { | |||||
| "PageIsCloudBrain": true, | "PageIsCloudBrain": true, | ||||
| }) | }) | ||||
| } | } | ||||
| type JobInfo struct { | |||||
| JobName string `json:"job_name"` | |||||
| AiCenterId int `json:"ai_center_id"` | |||||
| } | |||||
| func GetNewestJobs(ctx *context.APIContext) { | |||||
| idsC2Net, err := models.GetNewestJobsByAiCenter() | |||||
| if err != nil { | |||||
| log.Error("GetNewestJobsByAiCenter(%s) failed:%v", err.Error()) | |||||
| return | |||||
| } | |||||
| idsCloudbrain, err := models.GetNewestJobsByType() | |||||
| if err != nil { | |||||
| log.Error("GetNewestJobsByType(%s) failed:%v", err.Error()) | |||||
| return | |||||
| } | |||||
| ids := make([]int64, len(idsC2Net), cap(idsC2Net)*2) | |||||
| copy(ids, idsC2Net) | |||||
| for _, id := range idsCloudbrain { | |||||
| ids = append(ids, id) | |||||
| } | |||||
| jobs, err := models.GetCloudbrainByIDs(ids) | |||||
| if err != nil { | |||||
| log.Error("GetCloudbrainByIDs(%s) failed:%v", err.Error()) | |||||
| return | |||||
| } | |||||
| jobInfos := make([]JobInfo, 0) | |||||
| for _, job := range jobs { | |||||
| var id int | |||||
| var content string | |||||
| switch job.Type { | |||||
| case models.TypeCloudBrainOne: | |||||
| id, content = getAICenterID("cloudbrain_one") | |||||
| if content == "" { | |||||
| log.Error("job(%s) has no match config info", job.DisplayJobName) | |||||
| continue | |||||
| } | |||||
| case models.TypeCloudBrainTwo: | |||||
| id, content = getAICenterID("cloudbrain_two") | |||||
| if content == "" { | |||||
| log.Error("job(%s) has no match config info", job.DisplayJobName) | |||||
| continue | |||||
| } | |||||
| case models.TypeC2Net: | |||||
| centerInfo := strings.Split(job.AiCenter, "+") | |||||
| if len(centerInfo) != 2 { | |||||
| log.Error("job(%s):ai_center(%s) is wrong", job.DisplayJobName, job.AiCenter) | |||||
| continue | |||||
| } | |||||
| id, content = getAICenterID(centerInfo[0]) | |||||
| if content == "" { | |||||
| log.Error("job(%s) has no match config info", job.DisplayJobName) | |||||
| continue | |||||
| } | |||||
| default: | |||||
| log.Error("no match info") | |||||
| continue | |||||
| } | |||||
| jobInfos = append(jobInfos, JobInfo{ | |||||
| JobName: job.DisplayJobName, | |||||
| AiCenterId: id, | |||||
| }) | |||||
| } | |||||
| ctx.JSON(http.StatusOK, jobInfos) | |||||
| } | |||||
| func GetAICenterInfo(ctx *context.APIContext) { | |||||
| if setting.C2NetInfos == nil { | |||||
| log.Error("C2NET_SEQUENCE is incorrect") | |||||
| return | |||||
| } | |||||
| ctx.JSON(http.StatusOK, setting.C2NetInfos.C2NetSqInfo) | |||||
| } | |||||
| func getAICenterID(name string) (int, string) { | |||||
| for _, info := range setting.C2NetInfos.C2NetSqInfo { | |||||
| if name == info.Name { | |||||
| return info.ID, info.Content | |||||
| } | |||||
| } | |||||
| return 0, "" | |||||
| } | |||||
| @@ -51,23 +51,63 @@ | |||||
| <script src="/rotation3D/vue-2.6.10.min.js"></script> | <script src="/rotation3D/vue-2.6.10.min.js"></script> | ||||
| <script src="/rotation3D/rotation3D.js?v={{MD5 AppVer}}"></script> | <script src="/rotation3D/rotation3D.js?v={{MD5 AppVer}}"></script> | ||||
| <script> | <script> | ||||
| var jobTask={}; | |||||
| function queryAiCenterInfo(){ | |||||
| $.ajax({ | |||||
| type:"GET", | |||||
| url:"/api/v1/cloudbrain/get_newest_job", | |||||
| headers: { | |||||
| authorization:token, | |||||
| }, | |||||
| dataType:"json", | |||||
| async:false, | |||||
| success:function(json){ | |||||
| for(var i=0;i < json.length;i++){ | |||||
| jobTask[json[i].ai_center_id] =json[i].job_name; | |||||
| } | |||||
| }, | |||||
| error:function(response) { | |||||
| console.log("query task info error."); | |||||
| } | |||||
| }); | |||||
| $.ajax({ | |||||
| type:"GET", | |||||
| url:"/api/v1/cloudbrain/get_center_info", | |||||
| headers: { | |||||
| authorization:token, | |||||
| }, | |||||
| dataType:"json", | |||||
| async:false, | |||||
| success:function(json){ | |||||
| displayAiCenterInfo(json); | |||||
| }, | |||||
| error:function(response) { | |||||
| } | |||||
| }); | |||||
| } | |||||
| function displayAiCenterInfo(json){ | |||||
| for(var i=0;i<json.length;i++){ | |||||
| var tmp ={}; | |||||
| tmp["name"]=json[i].name; | |||||
| if(jobTask[json[i].id] != null){ | |||||
| tmp["type"]="blue"; | |||||
| }else{ | |||||
| tmp["type"]="green"; | |||||
| } | |||||
| tmp["icon"]=""; | |||||
| tmp["content"]=json[i].content; | |||||
| serverItemList.push(tmp); | |||||
| } | |||||
| } | |||||
| var serverItemList=[]; | |||||
| queryAiCenterInfo(); | |||||
| var app = new Vue({ | var app = new Vue({ | ||||
| el: "#app", | el: "#app", | ||||
| //数据 blue, green, yellow | //数据 blue, green, yellow | ||||
| data: { | data: { | ||||
| itemList: [ | |||||
| { name:'鹏城云脑一号', type:'blue', icon:'', }, | |||||
| { name:'鹏城云脑二号', type:'blue', icon:'', }, | |||||
| { name:'北大人工智能集群系统', type:'green', icon:'', }, | |||||
| { name:'合肥类脑智能开放平台', type:'green', icon:'', }, | |||||
| { name:'武汉人工智能计算中心', type:'green', icon:'', }, | |||||
| { name:'西安未来人工智能计算中心', type:'green', icon:'', }, | |||||
| { name:'……', type:'yellow', icon:'', }, | |||||
| { name:'中原人工智能计算中心', type:'green', icon:'', }, | |||||
| { name:'成都人工智能计算中心', type:'green', icon:'', }, | |||||
| { name:'横琴先进智能计算中心', type:'green', icon:'', }, | |||||
| { name:'国家超级计算济南中心', type:'green', icon:'', }, | |||||
| ], | |||||
| itemList:serverItemList, | |||||
| }, | }, | ||||
| mounted: function () { | mounted: function () { | ||||
| new Rotation3D({ | new Rotation3D({ | ||||
| @@ -84,6 +124,19 @@ | |||||
| }, | }, | ||||
| methods: {}, | methods: {}, | ||||
| }); | }); | ||||
| $(document).ready(function(){ | |||||
| var pArrays=$('.itemList').find("p"); | |||||
| for(var i=0;i<pArrays.length;i++){ | |||||
| var p = pArrays[i]; | |||||
| p.innerText=serverItemList[i].content; | |||||
| } | |||||
| var lines=$('.lineList').find("span"); | |||||
| for(var i=0; i< lines.length;i++){ | |||||
| if(jobTask[i+1] != null){ | |||||
| lines[i].innerText = jobTask[i+1]; | |||||
| } | |||||
| } | |||||
| }); | |||||
| </script> | </script> | ||||
| {{end}} | {{end}} | ||||
| @@ -94,12 +94,6 @@ | |||||
| </div> | </div> | ||||
| <div id="app" v-cloak> | <div id="app" v-cloak> | ||||
| <!--数据 | |||||
| <div class="aiData"> | |||||
| <p>完成AI任务<br><strong id="completed_task">1716</strong></p> | |||||
| <p>运行AI任务<br><strong id="running_task">120</strong></p> | |||||
| <p>等待AI任务<br><strong id="wait_task">80</strong></p> | |||||
| </div>--> | |||||
| <!--底座--> | <!--底座--> | ||||
| <div class="rotation3D-baseMap"></div> | <div class="rotation3D-baseMap"></div> | ||||
| <!--旋转3D--> | <!--旋转3D--> | ||||
| @@ -129,13 +123,13 @@ | |||||
| <svg width="10" height="400"> | <svg width="10" height="400"> | ||||
| <path id="path2" d="M0 400, 0 0" stroke-dasharray="5,10"/> | <path id="path2" d="M0 400, 0 0" stroke-dasharray="5,10"/> | ||||
| </svg> | </svg> | ||||
| <div class="dot dot2"><i class="el-icon-close"></i></div> | |||||
| <div class="dot dot2"><i class="el-icon-close"></i><span></span></div> | |||||
| </div> | </div> | ||||
| <div v-if="item.type=='green'" class="pos"> | <div v-if="item.type=='green'" class="pos"> | ||||
| <svg width="50" height="400"> | <svg width="50" height="400"> | ||||
| <path id="path1" d="M0 400, 0 0" stroke-dasharray="5,10"/> | <path id="path1" d="M0 400, 0 0" stroke-dasharray="5,10"/> | ||||
| </svg> | </svg> | ||||
| <div class="dot dot1 ri-arrow-left-s-line"></div> | |||||
| <div class="dot dot1 ri-arrow-left-s-line"><span></span></div> | |||||
| </div> | </div> | ||||
| </div> | </div> | ||||
| </div> | </div> | ||||
| @@ -213,7 +213,7 @@ td, th { | |||||
| <div class="ui pointing secondary menu" style="border-bottom: 1px solid rgba(34,36,38,.15);"> | <div class="ui pointing secondary menu" style="border-bottom: 1px solid rgba(34,36,38,.15);"> | ||||
| <a class="active item" data-tab="first">{{$.i18n.Tr "repo.modelarts.train_job.config"}}</a> | <a class="active item" data-tab="first">{{$.i18n.Tr "repo.modelarts.train_job.config"}}</a> | ||||
| <a class="item" data-tab="second" onclick="loadLog({{.VersionName}})">{{$.i18n.Tr "repo.modelarts.log"}}</a> | |||||
| <a class="item log_bottom" data-tab="second" data-version="{{.VersionName}}">{{$.i18n.Tr "repo.modelarts.log"}}</a> | |||||
| <a class="item load-model-file" data-tab="third" data-path="{{$.RepoLink}}/modelarts/inference-job/{{.JobID}}/result_list" data-version="{{.VersionName}}" data-parents="" data-filename="" data-init="init" >{{$.i18n.Tr "repo.model_download"}}</a> | <a class="item load-model-file" data-tab="third" data-path="{{$.RepoLink}}/modelarts/inference-job/{{.JobID}}/result_list" data-version="{{.VersionName}}" data-parents="" data-filename="" data-init="init" >{{$.i18n.Tr "repo.model_download"}}</a> | ||||
| </div> | </div> | ||||
| @@ -451,10 +451,10 @@ td, th { | |||||
| <div class="ui tab" data-tab="second"> | <div class="ui tab" data-tab="second"> | ||||
| <div> | <div> | ||||
| <a id="{{.VersionName}}-log-down" | <a id="{{.VersionName}}-log-down" | ||||
| class='{{if 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}}' | |||||
| href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}"> | href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}"> | ||||
| <i class="ri-download-cloud-2-line"></i> | <i class="ri-download-cloud-2-line"></i> | ||||
| <span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span> | |||||
| <span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span>{{.CanModify}} | |||||
| </a> | </a> | ||||
| </div> | </div> | ||||
| @@ -507,6 +507,7 @@ td, th { | |||||
| </div> | </div> | ||||
| {{template "base/footer" .}} | {{template "base/footer" .}} | ||||
| <script> | <script> | ||||
| console.log('{{.CanModify}}') | |||||
| $(document).ready(function(){ | $(document).ready(function(){ | ||||
| $('.secondary.menu .item').tab(); | $('.secondary.menu .item').tab(); | ||||
| }); | }); | ||||
| @@ -521,13 +522,5 @@ $(document).ready(function(){ | |||||
| repoPath = urlArr.slice(-4)[0] | repoPath = urlArr.slice(-4)[0] | ||||
| jobID = urlArr.slice(-1)[0] | jobID = urlArr.slice(-1)[0] | ||||
| }) | }) | ||||
| function loadLog(version_name){ | |||||
| $.get(`/api/v1/repos/${userName}/${repoPath}/modelarts/inference-job/${jobID}/log?version_name=${version_name}&lines=50&order=asc`, (data) => { | |||||
| $('input[name=end_line]').val(data.EndLine) | |||||
| $('input[name=start_line]').val(data.StartLine) | |||||
| $(`#log_file${version_name}`).text(data.Content) | |||||
| }).fail(function(err) { | |||||
| console.log(err); | |||||
| }); | |||||
| } | |||||
| </script> | </script> | ||||
| @@ -487,7 +487,7 @@ | |||||
| <div class="ui tab" data-tab="second{{$k}}"> | <div class="ui tab" data-tab="second{{$k}}"> | ||||
| <div> | <div> | ||||
| <a id="{{.VersionName}}-log-down" | <a id="{{.VersionName}}-log-down" | ||||
| class='{{if and ($.CanLogDownload) (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}}' | |||||
| href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}"> | href="{{$.RepoLink}}/modelarts/train-job/{{.JobID}}/download_log_file?version_name={{.VersionName}}"> | ||||
| <i class="ri-download-cloud-2-line"></i> | <i class="ri-download-cloud-2-line"></i> | ||||
| <span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span> | <span style="margin-left: 0.3rem;">{{$.i18n.Tr "repo.modelarts.download_log"}}</span> | ||||
| @@ -508,7 +508,7 @@ | |||||
| <div class="ui message message{{.VersionName}}" style="display: none;"> | <div class="ui message message{{.VersionName}}" style="display: none;"> | ||||
| <div id="header"></div> | <div id="header"></div> | ||||
| </div> | </div> | ||||
| <div class="ui attached log log-scroll" id="log{{.VersionName}}" | |||||
| <div class="ui attached log log-scroll" id="log{{.VersionName}}" data-version="{{.VersionName}}" | |||||
| style="height: 300px !important; overflow: auto;"> | style="height: 300px !important; overflow: auto;"> | ||||
| <input type="hidden" name="end_line" value> | <input type="hidden" name="end_line" value> | ||||
| <input type="hidden" name="start_line" value> | <input type="hidden" name="start_line" value> | ||||
| @@ -739,7 +739,6 @@ | |||||
| $('#' + version_name + '-status').text(data.JobStatus) | $('#' + version_name + '-status').text(data.JobStatus) | ||||
| console.log(data) | console.log(data) | ||||
| if (["KILLED", "FAILED", "START_FAILED", "STOPPED", "COMPLETED"].includes(data.JobStatus)) { | if (["KILLED", "FAILED", "START_FAILED", "STOPPED", "COMPLETED"].includes(data.JobStatus)) { | ||||
| $(`#${version_name}-log-down`).removeClass('disabled').addClass('ti-download-file') | |||||
| $('#' + version_name + '-stop').addClass('disabled') | $('#' + version_name + '-stop').addClass('disabled') | ||||
| } | } | ||||
| @@ -796,6 +795,9 @@ | |||||
| $('input[name=end_line]').val(data.EndLine) | $('input[name=end_line]').val(data.EndLine) | ||||
| $('input[name=start_line]').val(data.StartLine) | $('input[name=start_line]').val(data.StartLine) | ||||
| $(`#log_file${version_name}`).text(data.Content) | $(`#log_file${version_name}`).text(data.Content) | ||||
| if(!data.CanLogDownload){ | |||||
| $(`#${version_name}-log-down`).removeClass('ti-download-file').addClass('disabled') | |||||
| } | |||||
| }).fail(function (err) { | }).fail(function (err) { | ||||
| console.log(err); | console.log(err); | ||||
| }); | }); | ||||
| @@ -16,6 +16,7 @@ export default async function initCloudrainSow() { | |||||
| function logScroll(version_name) { | function logScroll(version_name) { | ||||
| let container = document.querySelector(`#log${version_name}`); | let container = document.querySelector(`#log${version_name}`); | ||||
| console.log(container); | |||||
| let scrollTop = container.scrollTop; | let scrollTop = container.scrollTop; | ||||
| let scrollHeight = container.scrollHeight; | let scrollHeight = container.scrollHeight; | ||||
| let clientHeight = container.clientHeight; | let clientHeight = container.clientHeight; | ||||