feat: add a web UI server (#1345)

* update rdagent cmd

* fix log error message

* use multiProcessing.Process instead of subprocess.Popen

* add traces to gitignore

* add user interactor in RDLoop (finance scenarios)

* add interactor (feedback, hypothesis) for quant scens

* fix the test_end in qlib conf

* add features init config, general instruction to qlib scenarios

* set base features for based exp

* fix bug when combine factors

* move traces folder to git_ignore_folder

* fix bug in features init

* fix quant interact bug

* fix logger warning error

* bug fixes

* modify rdagent logger, now it can set file output

* adjust cli functions and fix logger bug

* fix server port transport problem

* update server_ui in cli

* add web code

* fix CI problem

* black fix

* update web ui README

* update README

* update readme
This commit is contained in:
XianBW
2026-03-18 14:04:52 +08:00
committed by GitHub
parent 7cd64a26fd
commit 14395488b9
141 changed files with 12852 additions and 279 deletions
+57
View File
@@ -0,0 +1,57 @@
import request from './request';
export const url = typeof window !== 'undefined' ? `${window.location.origin}/` : '/';
export function uploadFile(data, config = {}) {
return request({
url: url + "upload",
method: 'post',
headers: {
'Content-Type': 'multipart/form-data',
},
// onUploadProgress: progressEvent => {
// // this.uploadPercentage = parseInt(Math.round((progressEvent.loaded / progressEvent.total) * 100));
// console.log(progressEvent)
// },
data: data,
...config
})
}
export function trace(data) {
return request({
url: url + "trace",
method: 'post',
headers: {
'Content-Type': 'application/json'
},
data: data
})
}
export function control(data) {
return request({
url: url + "control",
method: 'post',
headers: {
'Content-Type': 'application/json'
},
data: data
})
}
export function submitUserInteraction(data) {
return request({
url: url + "user_interaction/submit",
method: 'post',
headers: {
'Content-Type': 'application/json'
},
data: data
})
}
export function getStdoutDownloadUrl(traceId) {
const query = new URLSearchParams({ id: traceId });
return url + "stdout?" + query.toString();
}
+29
View File
@@ -0,0 +1,29 @@
//crypto.js文件内容
import CryptoJS from 'crypto-js'
export default { // 加密
/**
* @description: 加密
* @param {*} word
* @param {*} keyStr
*/
set(word, keyStr) {
keyStr = keyStr || 'abcdef0123456789' // 16位的密钥,自己定义,和下面的密钥要相同
var srcs = CryptoJS.enc.Utf8.parse(word) // 字符串到数组转换,解析明文
var key = CryptoJS.enc.Utf8.parse(keyStr) // 字符串到数组转换,解析秘钥
// mode:加密方式;padding:填充方式;iv便宜向量(可选)
var encrypted = CryptoJS.AES.encrypt(srcs, key, { mode: CryptoJS.mode.ECB, padding: CryptoJS.pad.Pkcs7 })
return encrypted.toString() // 加密后的结果是对象,要转换为文本
},
/**
* @description: 解密
* @param {*} word
* @param {*} keyStr
*/
get(word, keyStr) {
keyStr = keyStr || 'abcdef0123456789'
var key = CryptoJS.enc.Utf8.parse(keyStr) // 字符串到数组转换
var decrypt = CryptoJS.AES.decrypt(word, key, { mode: CryptoJS.mode.ECB, padding: CryptoJS.pad.Pkcs7 })
return CryptoJS.enc.Utf8.stringify(decrypt).toString() // 数组到字符串转换
}
}
+5
View File
@@ -0,0 +1,5 @@
// 获取assets静态资源
const getAssetsFile = (url: string) => {
return new URL(`../assets/images/${url}`, import.meta.url).href
}
export default getAssetsFile;
+37
View File
@@ -0,0 +1,37 @@
import axios from 'axios'
axios.defaults.headers.post['Content-Type'] = 'application/json'
const service = axios.create({
baseURL: ''
})
service.defaults.timeout = 5 * 60 * 1000;
// request拦截器
service.interceptors.request.use(
config => {
if (config.data) {}
if (config.params) {
// console.log('request: ', config.params)
}
return config
},
error => {
console.log('error-request: ', error)
return error
}
)
// respone拦截器
service.interceptors.response.use(
response => {
return response.data
},
error => {
console.log('error-response: ', error)
console.log('error-response: ', error.response)
return error.response
}
)
export default service
+21
View File
File diff suppressed because one or more lines are too long