From 44d94dace54f7a767994fc5ac1fb3d210a8d12ae Mon Sep 17 00:00:00 2001 From: yumoqing Date: Fri, 29 May 2026 12:07:53 +0800 Subject: [PATCH] refactor: optimize debug output - use debug_params for compact logging, truncate SQL; add CRUD definitions --- wwwroot/llm/add_llm.dspy | 51 ++++ wwwroot/llm/delete_llm.dspy | 47 +++ wwwroot/llm/get_llm.dspy | 135 +++++++++ wwwroot/llm/index.ui | 275 ++++++++++++++++++ wwwroot/llm/update_llm.dspy | 70 +++++ wwwroot/llm_api_map/add_llm_api_map.dspy | 37 +++ wwwroot/llm_api_map/delete_llm_api_map.dspy | 33 +++ wwwroot/llm_api_map/get_llm_api_map.dspy | 98 +++++++ wwwroot/llm_api_map/index.ui | 170 +++++++++++ wwwroot/llm_api_map/update_llm_api_map.dspy | 36 +++ wwwroot/llmcatelog_list/add_llmcatelog.dspy | 37 +++ .../llmcatelog_list/delete_llmcatelog.dspy | 33 +++ wwwroot/llmcatelog_list/get_llmcatelog.dspy | 67 +++++ wwwroot/llmcatelog_list/index.ui | 92 ++++++ .../llmcatelog_list/update_llmcatelog.dspy | 36 +++ wwwroot/llmcost.dspy | 2 +- wwwroot/llminference.dspy | 4 +- wwwroot/llmusage/add_llmusage.dspy | 37 +++ wwwroot/llmusage/delete_llmusage.dspy | 33 +++ wwwroot/llmusage/get_llmusage.dspy | 148 ++++++++++ wwwroot/llmusage/index.ui | 229 +++++++++++++++ wwwroot/llmusage/update_llmusage.dspy | 36 +++ .../add_llmusage_accounting_failed.dspy | 37 +++ .../delete_llmusage_accounting_failed.dspy | 33 +++ .../get_llmusage_accounting_failed.dspy | 136 +++++++++ wwwroot/llmusage_accounting_failed/index.ui | 235 +++++++++++++++ .../update_llmusage_accounting_failed.dspy | 36 +++ .../add_llmusage_history.dspy | 37 +++ .../delete_llmusage_history.dspy | 33 +++ .../get_llmusage_history.dspy | 157 ++++++++++ wwwroot/llmusage_history/index.ui | 242 +++++++++++++++ .../update_llmusage_history.dspy | 36 +++ wwwroot/model_estimate.dspy | 2 +- wwwroot/t2t/index.dspy | 2 +- wwwroot/v1/chat/completions/index.dspy | 4 +- wwwroot/v1/image/generations/index.dspy | 2 +- wwwroot/v1/video/generations/index.dspy | 2 +- wwwroot/vidu_inference.dspy | 2 +- 38 files changed, 2692 insertions(+), 10 deletions(-) create mode 100644 wwwroot/llm/add_llm.dspy create mode 100644 wwwroot/llm/delete_llm.dspy create mode 100644 wwwroot/llm/get_llm.dspy create mode 100644 wwwroot/llm/index.ui create mode 100644 wwwroot/llm/update_llm.dspy create mode 100644 wwwroot/llm_api_map/add_llm_api_map.dspy create mode 100644 wwwroot/llm_api_map/delete_llm_api_map.dspy create mode 100644 wwwroot/llm_api_map/get_llm_api_map.dspy create mode 100644 wwwroot/llm_api_map/index.ui create mode 100644 wwwroot/llm_api_map/update_llm_api_map.dspy create mode 100644 wwwroot/llmcatelog_list/add_llmcatelog.dspy create mode 100644 wwwroot/llmcatelog_list/delete_llmcatelog.dspy create mode 100644 wwwroot/llmcatelog_list/get_llmcatelog.dspy create mode 100644 wwwroot/llmcatelog_list/index.ui create mode 100644 wwwroot/llmcatelog_list/update_llmcatelog.dspy create mode 100644 wwwroot/llmusage/add_llmusage.dspy create mode 100644 wwwroot/llmusage/delete_llmusage.dspy create mode 100644 wwwroot/llmusage/get_llmusage.dspy create mode 100644 wwwroot/llmusage/index.ui create mode 100644 wwwroot/llmusage/update_llmusage.dspy create mode 100644 wwwroot/llmusage_accounting_failed/add_llmusage_accounting_failed.dspy create mode 100644 wwwroot/llmusage_accounting_failed/delete_llmusage_accounting_failed.dspy create mode 100644 wwwroot/llmusage_accounting_failed/get_llmusage_accounting_failed.dspy create mode 100644 wwwroot/llmusage_accounting_failed/index.ui create mode 100644 wwwroot/llmusage_accounting_failed/update_llmusage_accounting_failed.dspy create mode 100644 wwwroot/llmusage_history/add_llmusage_history.dspy create mode 100644 wwwroot/llmusage_history/delete_llmusage_history.dspy create mode 100644 wwwroot/llmusage_history/get_llmusage_history.dspy create mode 100644 wwwroot/llmusage_history/index.ui create mode 100644 wwwroot/llmusage_history/update_llmusage_history.dspy diff --git a/wwwroot/llm/add_llm.dspy b/wwwroot/llm/add_llm.dspy new file mode 100644 index 0000000..73c73b7 --- /dev/null +++ b/wwwroot/llm/add_llm.dspy @@ -0,0 +1,51 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None +id = params_kw.id +if not id or len(id) > 32: + id = uuid() +ns['id'] = id + + + +userorgid = await get_userorgid() +if not userorgid: + return { + "widgettype":"Error", + "options":{ + "title":"Authorization Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"Please login" + } + } +ns['ownerid'] = userorgid + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.C('llm', ns.copy()) + return { + "widgettype":"Message", + "options":{ + "cwidth":16, + "cheight":9, + "title":"Add Success", + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Add Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llm/delete_llm.dspy b/wwwroot/llm/delete_llm.dspy new file mode 100644 index 0000000..5b25a6b --- /dev/null +++ b/wwwroot/llm/delete_llm.dspy @@ -0,0 +1,47 @@ + +ns = { + 'id':params_kw['id'], +} + + +userorgid = await get_userorgid() +if not userorgid: + return { + "widgettype":"Error", + "options":{ + "title":"Authorization Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"Please login" + } + } +ns['ownerid'] = userorgid + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.D('llm', ns) + debug('delete success'); + return { + "widgettype":"Message", + "options":{ + "title":"Delete Success", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"ok" + } + } + +debug('Delete failed'); +return { + "widgettype":"Error", + "options":{ + "title":"Delete Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llm/get_llm.dspy b/wwwroot/llm/get_llm.dspy new file mode 100644 index 0000000..ef70cf8 --- /dev/null +++ b/wwwroot/llm/get_llm.dspy @@ -0,0 +1,135 @@ + +ns = params_kw.copy() + + +userorgid = await get_userorgid() +if not userorgid: + return { + "widgettype":"Error", + "options":{ + "title":"Authorization Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"Please login" + } + } +ns['ownerid'] = userorgid +ns['userorgid'] = userorgid + +debug_params('get_llm', ns) +if not ns.get('page'): + ns['page'] = 1 +if not ns.get('sort'): + + + ns['sort'] = 'name' + + + +sql = '''select a.*, b.providerid_text, c.iconid_text, d.upappid_text, e.ownerid_text +from (select * from llm where 1=1 [[filterstr]]) a left join (select id as providerid, + orgname as providerid_text from organization where 1 = 1) b on a.providerid = b.providerid left join (select id as iconid, + id as iconid_text from svgicon where 1 = 1) c on a.iconid = c.iconid left join (select id as upappid, + name as upappid_text from upapp where 1 = 1) d on a.upappid = d.upappid left join (select id as ownerid, + orgname as ownerid_text from organization where 1 = 1) e on a.ownerid = e.ownerid''' + +filterjson = params_kw.get('data_filter') +fields_str=r'''[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32 + }, + { + "name": "name", + "title": "名称", + "type": "str", + "length": 100 + }, + { + "name": "model", + "title": "识别名", + "type": "str", + "length": 100 + }, + { + "name": "description", + "title": "说明", + "type": "text", + "length": 500 + }, + { + "name": "iconid", + "title": "图标id", + "type": "str", + "length": 32 + }, + { + "name": "upappid", + "title": "上位系统id", + "type": "str", + "length": 32 + }, + { + "name": "providerid", + "title": "供应商id", + "type": "str", + "length": 32 + }, + { + "name": "ownerid", + "title": "所属机构id", + "type": "str", + "length": 32 + }, + { + "name": "enabled_date", + "title": "启用日期", + "type": "date" + }, + { + "name": "expired_date", + "title": "失效日期", + "type": "date" + }, + { + "name": "min_balance", + "title": "最低余额", + "type": "float", + "length": 20, + "default": 10 + } +]''' +ori_fields = json.loads(fields_str) +if not filterjson: + fields = [ f['name'] for f in ori_fields ] + filterjson = default_filterjson(fields, ns) +filterdic = ns.copy() +filterdic['filterstr'] = '' +filterdic['userorgid'] = '${userorgid}$' +filterdic['userid'] = '${userid}$' +if filterjson: + dbf = DBFilter(filterjson) + conds = dbf.gen(ns) + if conds: + ns.update(dbf.consts) + conds = f' and {conds}' + filterdic['filterstr'] = conds +ac = ArgsConvert('[[', ']]') +vars = ac.findAllVariables(sql) +NameSpace = {v:'${' + v + '}$' for v in vars if v != 'filterstr' } +filterdic.update(NameSpace) +sql = ac.convert(sql, filterdic) + +debug(f'sql({len(sql)}ch): {sql[:200]}') +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.sqlPaging(sql, ns) + return r +return { + "total":0, + "rows":[] +} \ No newline at end of file diff --git a/wwwroot/llm/index.ui b/wwwroot/llm/index.ui new file mode 100644 index 0000000..0e4dd8b --- /dev/null +++ b/wwwroot/llm/index.ui @@ -0,0 +1,275 @@ + +{ + "id":"llm_tbl", + "widgettype":"Tabular", + "options":{ + "width":"100%", + "height":"100%", + + + "title":"大语言模型", + + + + + "toolbar":{ + "tools": [ + { + "name": "test", + "label": "体验", + "selected_row": true + }, + { + "selected_row": true, + "name": "llm_api_map", + "icon": "{{entire_url('/imgs/llm_api_map.svg')}}", + "label": "能力映射" + } + ] +}, + + "css":"card", + + + "editable":{ + + "new_data_url":"{{entire_url('add_llm.dspy')}}", + + + "delete_data_url":"{{entire_url('delete_llm.dspy')}}", + + + "update_data_url":"{{entire_url('update_llm.dspy')}}" + + }, + + + "data_url":"{{entire_url('./get_llm.dspy')}}", + + "data_method":"GET", + "data_params":{{json.dumps(params_kw, indent=4, ensure_ascii=False)}}, + "row_options":{ + + + + "browserfields": { + "exclouded": [ + "id", + "ownerid" + ], + "alters": { + "ppid": { + "dataurl": "{{entire_url('/pricing/get_all_pricing_programs.dspy')}}", + "textField": "name", + "valueField": "id" + } + } +}, + + + "editexclouded":[ + "id", + "ownerid" +], + + "fields":[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "id" + }, + { + "name": "name", + "title": "名称", + "type": "str", + "length": 100, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "名称" + }, + { + "name": "model", + "title": "识别名", + "type": "str", + "length": 100, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "识别名" + }, + { + "name": "description", + "title": "说明", + "type": "text", + "length": 500, + "cwidth": 18, + "uitype": "text", + "datatype": "text", + "label": "说明" + }, + { + "name": "iconid", + "title": "图标id", + "type": "str", + "length": 32, + "label": "图标id", + "uitype": "code", + "valueField": "iconid", + "textField": "iconid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "svgicon", + "tblvalue": "id", + "tbltext": "id", + "valueField": "iconid", + "textField": "iconid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "upappid", + "title": "上位系统id", + "type": "str", + "length": 32, + "label": "上位系统id", + "uitype": "code", + "valueField": "upappid", + "textField": "upappid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "upapp", + "tblvalue": "id", + "tbltext": "name", + "valueField": "upappid", + "textField": "upappid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "providerid", + "title": "供应商id", + "type": "str", + "length": 32, + "label": "供应商id", + "uitype": "code", + "valueField": "providerid", + "textField": "providerid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "organization", + "tblvalue": "id", + "tbltext": "orgname", + "valueField": "providerid", + "textField": "providerid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "ownerid", + "title": "所属机构id", + "type": "str", + "length": 32, + "label": "所属机构id", + "uitype": "code", + "valueField": "ownerid", + "textField": "ownerid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "organization", + "tblvalue": "id", + "tbltext": "orgname", + "valueField": "ownerid", + "textField": "ownerid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "enabled_date", + "title": "启用日期", + "type": "date", + "length": 0, + "uitype": "date", + "datatype": "date", + "label": "启用日期" + }, + { + "name": "expired_date", + "title": "失效日期", + "type": "date", + "length": 0, + "uitype": "date", + "datatype": "date", + "label": "失效日期" + }, + { + "name": "min_balance", + "title": "最低余额", + "type": "float", + "length": 20, + "default": 10, + "cwidth": 18, + "uitype": "float", + "datatype": "float", + "label": "最低余额" + } +] + }, + + + + "page_rows":160, + "cache_limit":5 + } + + ,"binds":[ + { + "wid": "self", + "event": "test", + "actiontype": "urlwidget", + "target": "PopupWindow", + "popup_options": { + "title": "model Test", + "cwidth": 22, + "height": "75%" + }, + "options": { + "url": "{{entire_url('./llm_dialog.ui')}}", + "params": { + "id": "${id}" + } + } + }, + { + "wid": "self", + "event": "llm_api_map", + "actiontype": "urlwidget", + "target": "PopupWindow", + "popup_options": { + "title": "能力映射", + "icon": "{{entire_url('/appbase/get_icon.dspy')}}?id=llm_api_map", + "resizable": true, + "height": "70%", + "width": "70%" + }, + "params_mapping": { + "mapping": { + "id": "llmid", + "referer_widget": "referer_widget" + }, + "need_other": false + }, + "options": { + "method": "POST", + "params": {}, + "url": "{{entire_url('../llm_api_map')}}" + } + } +] + +} \ No newline at end of file diff --git a/wwwroot/llm/update_llm.dspy b/wwwroot/llm/update_llm.dspy new file mode 100644 index 0000000..f8d1165 --- /dev/null +++ b/wwwroot/llm/update_llm.dspy @@ -0,0 +1,70 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None + + +userorgid = await get_userorgid() +if not userorgid: + return { + "widgettype":"Error", + "options":{ + "title":"Authorization Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"Please login" + } + } +ns['ownerid'] = userorgid + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + + ns1 = { + + "ownerid": userorgid, + + + "id": params_kw.id + } + recs = await sor.R('llm', ns1) + if len(recs) < 1: + return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"Record no exist or with wrong ownership" + } + } + + r = await sor.U('llm', ns) + debug('update success'); + return { + "widgettype":"Message", + "options":{ + "title":"Update Success", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llm_api_map/add_llm_api_map.dspy b/wwwroot/llm_api_map/add_llm_api_map.dspy new file mode 100644 index 0000000..1ada2a2 --- /dev/null +++ b/wwwroot/llm_api_map/add_llm_api_map.dspy @@ -0,0 +1,37 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None +id = params_kw.id +if not id or len(id) > 32: + id = uuid() +ns['id'] = id + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.C('llm_api_map', ns.copy()) + return { + "widgettype":"Message", + "options":{ + "cwidth":16, + "cheight":9, + "title":"Add Success", + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Add Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llm_api_map/delete_llm_api_map.dspy b/wwwroot/llm_api_map/delete_llm_api_map.dspy new file mode 100644 index 0000000..7b96ec6 --- /dev/null +++ b/wwwroot/llm_api_map/delete_llm_api_map.dspy @@ -0,0 +1,33 @@ + +ns = { + 'id':params_kw['id'], +} + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.D('llm_api_map', ns) + debug('delete success'); + return { + "widgettype":"Message", + "options":{ + "title":"Delete Success", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"ok" + } + } + +debug('Delete failed'); +return { + "widgettype":"Error", + "options":{ + "title":"Delete Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llm_api_map/get_llm_api_map.dspy b/wwwroot/llm_api_map/get_llm_api_map.dspy new file mode 100644 index 0000000..a362ff5 --- /dev/null +++ b/wwwroot/llm_api_map/get_llm_api_map.dspy @@ -0,0 +1,98 @@ + +ns = params_kw.copy() + + +debug_params('get_llm_api_map', ns) +if not ns.get('page'): + ns['page'] = 1 +if not ns.get('sort'): + + ns['sort'] = 'id' + + +sql = '''select a.*, b.llmid_text, c.llmcatelogid_text, d.ppid_text +from (select * from llm_api_map where 1=1 [[filterstr]]) a left join (select id as llmid, + name as llmid_text from llm where 1 = 1) b on a.llmid = b.llmid left join (select id as llmcatelogid, + name as llmcatelogid_text from llmcatelog where 1 = 1) c on a.llmcatelogid = c.llmcatelogid left join (select id as ppid, + name as ppid_text from pricing_program where 1 = 1) d on a.ppid = d.ppid''' + +filterjson = params_kw.get('data_filter') +fields_str=r'''[ + { + "name": "id", + "type": "varchar(32)", + "not_null": true, + "title": "主键ID" + }, + { + "name": "llmid", + "type": "varchar(32)", + "not_null": true, + "title": "模型ID" + }, + { + "name": "llmcatelogid", + "type": "varchar(32)", + "not_null": true, + "title": "模型分类ID" + }, + { + "name": "apiname", + "type": "varchar(100)", + "not_null": true, + "title": "接口名称" + }, + { + "name": "query_apiname", + "type": "varchar(100)", + "title": "任务结果查询接口名称" + }, + { + "name": "query_period", + "type": "bigint", + "default": 30, + "title": "任务查询间隔(秒)" + }, + { + "name": "ppid", + "type": "varchar(32)", + "title": "定价ID" + }, + { + "name": "isdefaultcatelog", + "type": "varchar(1)", + "not_null": true, + "title": "缺省分类" + } +]''' +ori_fields = json.loads(fields_str) +if not filterjson: + fields = [ f['name'] for f in ori_fields ] + filterjson = default_filterjson(fields, ns) +filterdic = ns.copy() +filterdic['filterstr'] = '' +filterdic['userorgid'] = '${userorgid}$' +filterdic['userid'] = '${userid}$' +if filterjson: + dbf = DBFilter(filterjson) + conds = dbf.gen(ns) + if conds: + ns.update(dbf.consts) + conds = f' and {conds}' + filterdic['filterstr'] = conds +ac = ArgsConvert('[[', ']]') +vars = ac.findAllVariables(sql) +NameSpace = {v:'${' + v + '}$' for v in vars if v != 'filterstr' } +filterdic.update(NameSpace) +sql = ac.convert(sql, filterdic) + +debug(f'sql({len(sql)}ch): {sql[:200]}') +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.sqlPaging(sql, ns) + return r +return { + "total":0, + "rows":[] +} \ No newline at end of file diff --git a/wwwroot/llm_api_map/index.ui b/wwwroot/llm_api_map/index.ui new file mode 100644 index 0000000..5b19bbf --- /dev/null +++ b/wwwroot/llm_api_map/index.ui @@ -0,0 +1,170 @@ + +{ + "id":"llm_api_map_tbl", + "widgettype":"Tabular", + "options":{ + "width":"100%", + "height":"100%", + + + "title":"模型API映射表", + + + + + "css":"card", + + + "editable":{ + + "new_data_url":"{{entire_url('add_llm_api_map.dspy')}}", + + + "delete_data_url":"{{entire_url('delete_llm_api_map.dspy')}}", + + + "update_data_url":"{{entire_url('update_llm_api_map.dspy')}}" + + }, + + + "data_url":"{{entire_url('./get_llm_api_map.dspy')}}", + + "data_method":"GET", + "data_params":{{json.dumps(params_kw, indent=4, ensure_ascii=False)}}, + "row_options":{ + + + + "browserfields": { + "exclouded": [ + "id", + "llmid" + ], + "alters": {} +}, + + + "editexclouded":[ + "id", + "llmid" +], + + "fields":[ + { + "name": "id", + "type": "varchar(32)", + "not_null": true, + "title": "主键ID", + "length": 0, + "uitype": "str", + "datatype": "varchar(32)", + "label": "主键ID" + }, + { + "name": "llmid", + "type": "varchar(32)", + "not_null": true, + "title": "模型ID", + "label": "模型ID", + "uitype": "code", + "valueField": "llmid", + "textField": "llmid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "llm", + "tblvalue": "id", + "tbltext": "name", + "valueField": "llmid", + "textField": "llmid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "llmcatelogid", + "type": "varchar(32)", + "not_null": true, + "title": "模型分类ID", + "label": "模型分类ID", + "uitype": "code", + "valueField": "llmcatelogid", + "textField": "llmcatelogid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "llmcatelog", + "tblvalue": "id", + "tbltext": "name", + "valueField": "llmcatelogid", + "textField": "llmcatelogid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "apiname", + "type": "varchar(100)", + "not_null": true, + "title": "接口名称", + "length": 0, + "uitype": "str", + "datatype": "varchar(100)", + "label": "接口名称" + }, + { + "name": "query_apiname", + "type": "varchar(100)", + "title": "任务结果查询接口名称", + "length": 0, + "uitype": "str", + "datatype": "varchar(100)", + "label": "任务结果查询接口名称" + }, + { + "name": "query_period", + "type": "bigint", + "default": 30, + "title": "任务查询间隔(秒)", + "length": 0, + "uitype": "str", + "datatype": "bigint", + "label": "任务查询间隔(秒)" + }, + { + "name": "ppid", + "type": "varchar(32)", + "title": "定价ID", + "label": "定价ID", + "uitype": "code", + "valueField": "ppid", + "textField": "ppid_text", + "params": { + "dbname": "{{get_module_dbname('llm')}}", + "table": "pricing_program", + "tblvalue": "id", + "tbltext": "name", + "valueField": "ppid", + "textField": "ppid_text" + }, + "dataurl": "{{entire_url('/appbase/get_code.dspy')}}" + }, + { + "name": "isdefaultcatelog", + "type": "varchar(1)", + "not_null": true, + "title": "缺省分类", + "length": 0, + "uitype": "str", + "datatype": "varchar(1)", + "label": "缺省分类" + } +] + }, + + + + "page_rows":160, + "cache_limit":5 + } + + ,"binds":[] + +} \ No newline at end of file diff --git a/wwwroot/llm_api_map/update_llm_api_map.dspy b/wwwroot/llm_api_map/update_llm_api_map.dspy new file mode 100644 index 0000000..ef8cf67 --- /dev/null +++ b/wwwroot/llm_api_map/update_llm_api_map.dspy @@ -0,0 +1,36 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None + + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + + r = await sor.U('llm_api_map', ns) + debug('update success'); + return { + "widgettype":"Message", + "options":{ + "title":"Update Success", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmcatelog_list/add_llmcatelog.dspy b/wwwroot/llmcatelog_list/add_llmcatelog.dspy new file mode 100644 index 0000000..e79043f --- /dev/null +++ b/wwwroot/llmcatelog_list/add_llmcatelog.dspy @@ -0,0 +1,37 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None +id = params_kw.id +if not id or len(id) > 32: + id = uuid() +ns['id'] = id + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.C('llmcatelog', ns.copy()) + return { + "widgettype":"Message", + "options":{ + "cwidth":16, + "cheight":9, + "title":"Add Success", + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Add Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmcatelog_list/delete_llmcatelog.dspy b/wwwroot/llmcatelog_list/delete_llmcatelog.dspy new file mode 100644 index 0000000..c938375 --- /dev/null +++ b/wwwroot/llmcatelog_list/delete_llmcatelog.dspy @@ -0,0 +1,33 @@ + +ns = { + 'id':params_kw['id'], +} + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.D('llmcatelog', ns) + debug('delete success'); + return { + "widgettype":"Message", + "options":{ + "title":"Delete Success", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"ok" + } + } + +debug('Delete failed'); +return { + "widgettype":"Error", + "options":{ + "title":"Delete Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmcatelog_list/get_llmcatelog.dspy b/wwwroot/llmcatelog_list/get_llmcatelog.dspy new file mode 100644 index 0000000..367dc1b --- /dev/null +++ b/wwwroot/llmcatelog_list/get_llmcatelog.dspy @@ -0,0 +1,67 @@ + +ns = params_kw.copy() + + +debug_params('get_llmcatelog', ns) +if not ns.get('page'): + ns['page'] = 1 +if not ns.get('sort'): + + + ns['sort'] = ["name"] + + + +sql = '''select * from llmcatelog where 1=1 [[filterstr]]''' + +filterjson = params_kw.get('data_filter') +fields_str=r'''[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32 + }, + { + "name": "name", + "title": "类型名", + "type": "str", + "length": 100 + }, + { + "name": "description", + "title": "类型说明", + "type": "text" + } +]''' +ori_fields = json.loads(fields_str) +if not filterjson: + fields = [ f['name'] for f in ori_fields ] + filterjson = default_filterjson(fields, ns) +filterdic = ns.copy() +filterdic['filterstr'] = '' +filterdic['userorgid'] = '${userorgid}$' +filterdic['userid'] = '${userid}$' +if filterjson: + dbf = DBFilter(filterjson) + conds = dbf.gen(ns) + if conds: + ns.update(dbf.consts) + conds = f' and {conds}' + filterdic['filterstr'] = conds +ac = ArgsConvert('[[', ']]') +vars = ac.findAllVariables(sql) +NameSpace = {v:'${' + v + '}$' for v in vars if v != 'filterstr' } +filterdic.update(NameSpace) +sql = ac.convert(sql, filterdic) + +debug(f'sql({len(sql)}ch): {sql[:200]}') +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.sqlPaging(sql, ns) + return r +return { + "total":0, + "rows":[] +} \ No newline at end of file diff --git a/wwwroot/llmcatelog_list/index.ui b/wwwroot/llmcatelog_list/index.ui new file mode 100644 index 0000000..03b1eb3 --- /dev/null +++ b/wwwroot/llmcatelog_list/index.ui @@ -0,0 +1,92 @@ + +{ + "id":"llmcatelog_tbl", + "widgettype":"Tabular", + "options":{ + "width":"100%", + "height":"100%", + + + "title":"模型类目", + + + + + "css":"card", + + + "editable":{ + + "new_data_url":"{{entire_url('add_llmcatelog.dspy')}}", + + + "delete_data_url":"{{entire_url('delete_llmcatelog.dspy')}}", + + + "update_data_url":"{{entire_url('update_llmcatelog.dspy')}}" + + }, + + + "data_url":"{{entire_url('./get_llmcatelog.dspy')}}", + + "data_method":"GET", + "data_params":{{json.dumps(params_kw, indent=4, ensure_ascii=False)}}, + "row_options":{ + + + + "browserfields": { + "exclouded": [ + "id" + ], + "alters": {} +}, + + + "editexclouded":[ + "id" +], + + "fields":[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "id" + }, + { + "name": "name", + "title": "类型名", + "type": "str", + "length": 100, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "类型名" + }, + { + "name": "description", + "title": "类型说明", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "类型说明" + } +] + }, + + + + "page_rows":160, + "cache_limit":5 + } + + ,"binds":[] + +} \ No newline at end of file diff --git a/wwwroot/llmcatelog_list/update_llmcatelog.dspy b/wwwroot/llmcatelog_list/update_llmcatelog.dspy new file mode 100644 index 0000000..f5748f1 --- /dev/null +++ b/wwwroot/llmcatelog_list/update_llmcatelog.dspy @@ -0,0 +1,36 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None + + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + + r = await sor.U('llmcatelog', ns) + debug('update success'); + return { + "widgettype":"Message", + "options":{ + "title":"Update Success", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmcost.dspy b/wwwroot/llmcost.dspy index 87b77aa..45cbdfc 100644 --- a/wwwroot/llmcost.dspy +++ b/wwwroot/llmcost.dspy @@ -1,4 +1,4 @@ -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) ns = params_kw.copy() if not ns.page: ns.page = 1 diff --git a/wwwroot/llminference.dspy b/wwwroot/llminference.dspy index bd32ebf..fcc6a46 100644 --- a/wwwroot/llminference.dspy +++ b/wwwroot/llminference.dspy @@ -1,4 +1,4 @@ -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) if params_kw.off_peak: off_peak = params_kw.off_peak if off_peak in [True, "Y" "y", 1, "1"]: @@ -25,7 +25,7 @@ if kdbids: ret = await rfexe('fusedsearch', request, params) data.update(ret) params_kw.prompt = await tmpl_engine.renders(tmpl, data) - debug(f'{params=}rag return {data}, {params_kw.prompt=}') + debug_params('rag', {'query': params.get('query',''), 'prompt_len': len(str(params_kw.prompt))}) env = DictObject(**globals()) return await inference(request, env=env) diff --git a/wwwroot/llmusage/add_llmusage.dspy b/wwwroot/llmusage/add_llmusage.dspy new file mode 100644 index 0000000..b8985af --- /dev/null +++ b/wwwroot/llmusage/add_llmusage.dspy @@ -0,0 +1,37 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None +id = params_kw.id +if not id or len(id) > 32: + id = uuid() +ns['id'] = id + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.C('llmusage', ns.copy()) + return { + "widgettype":"Message", + "options":{ + "cwidth":16, + "cheight":9, + "title":"Add Success", + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Add Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage/delete_llmusage.dspy b/wwwroot/llmusage/delete_llmusage.dspy new file mode 100644 index 0000000..3a9a12a --- /dev/null +++ b/wwwroot/llmusage/delete_llmusage.dspy @@ -0,0 +1,33 @@ + +ns = { + 'id':params_kw['id'], +} + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.D('llmusage', ns) + debug('delete success'); + return { + "widgettype":"Message", + "options":{ + "title":"Delete Success", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"ok" + } + } + +debug('Delete failed'); +return { + "widgettype":"Error", + "options":{ + "title":"Delete Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage/get_llmusage.dspy b/wwwroot/llmusage/get_llmusage.dspy new file mode 100644 index 0000000..783f00d --- /dev/null +++ b/wwwroot/llmusage/get_llmusage.dspy @@ -0,0 +1,148 @@ + +ns = params_kw.copy() + + +debug_params('get_llmusage', ns) +if not ns.get('page'): + ns['page'] = 1 +if not ns.get('sort'): + + + ns['sort'] = 'use_time desc' + + + +sql = '''select * from llmusage where 1=1 [[filterstr]]''' + +filterjson = params_kw.get('data_filter') +fields_str=r'''[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32 + }, + { + "name": "llmid", + "title": "模型id", + "type": "str", + "length": 32 + }, + { + "name": "use_date", + "title": "使用日期", + "type": "date" + }, + { + "name": "use_time", + "title": "使用时间", + "type": "timestamp" + }, + { + "name": "userid", + "title": "用户id", + "type": "str", + "length": 32 + }, + { + "name": "usages", + "title": "使用信息", + "type": "text" + }, + { + "name": "ioinfo", + "title": "交互内容", + "type": "text" + }, + { + "name": "transno", + "title": "交易号", + "type": "str", + "length": 32 + }, + { + "name": "responsed_seconds", + "title": "响应时间", + "type": "float", + "length": 18 + }, + { + "name": "finish_seconds", + "title": "结束时间", + "type": "float", + "length": 18 + }, + { + "name": "status", + "title": "状态", + "type": "str", + "length": 32 + }, + { + "name": "taskid", + "title": "任务号", + "type": "str", + "length": 256 + }, + { + "name": "amount", + "title": "交易金额", + "type": "float", + "length": 18 + }, + { + "name": "cost", + "title": "交易成本", + "type": "float", + "length": 18 + }, + { + "name": "userorgid", + "title": "用户机构id", + "type": "str", + "length": 32 + }, + { + "name": "ownerid", + "title": "模型机构id", + "type": "str", + "length": 32 + }, + { + "name": "accounting_status", + "title": "记账状态", + "type": "str", + "length": 32 + } +]''' +ori_fields = json.loads(fields_str) +if not filterjson: + fields = [ f['name'] for f in ori_fields ] + filterjson = default_filterjson(fields, ns) +filterdic = ns.copy() +filterdic['filterstr'] = '' +filterdic['userorgid'] = '${userorgid}$' +filterdic['userid'] = '${userid}$' +if filterjson: + dbf = DBFilter(filterjson) + conds = dbf.gen(ns) + if conds: + ns.update(dbf.consts) + conds = f' and {conds}' + filterdic['filterstr'] = conds +ac = ArgsConvert('[[', ']]') +vars = ac.findAllVariables(sql) +NameSpace = {v:'${' + v + '}$' for v in vars if v != 'filterstr' } +filterdic.update(NameSpace) +sql = ac.convert(sql, filterdic) + +debug(f'sql({len(sql)}ch): {sql[:200]}') +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.sqlPaging(sql, ns) + return r +return { + "total":0, + "rows":[] +} \ No newline at end of file diff --git a/wwwroot/llmusage/index.ui b/wwwroot/llmusage/index.ui new file mode 100644 index 0000000..6ea55fe --- /dev/null +++ b/wwwroot/llmusage/index.ui @@ -0,0 +1,229 @@ + +{ + "id":"llmusage_tbl", + "widgettype":"Tabular", + "options":{ + "width":"100%", + "height":"100%", + + + "title":"模型使用", + + + + + "css":"card", + + + "editable":{ + + "new_data_url":"{{entire_url('add_llmusage.dspy')}}", + + + "delete_data_url":"{{entire_url('delete_llmusage.dspy')}}", + + + "update_data_url":"{{entire_url('update_llmusage.dspy')}}" + + }, + + + "data_url":"{{entire_url('./get_llmusage.dspy')}}", + + "data_method":"GET", + "data_params":{{json.dumps(params_kw, indent=4, ensure_ascii=False)}}, + "row_options":{ + + + + "browserfields": { + "exclouded": [ + "id" + ], + "alters": {} +}, + + + "editexclouded":[ + "id" +], + + "fields":[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "id" + }, + { + "name": "llmid", + "title": "模型id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "模型id" + }, + { + "name": "use_date", + "title": "使用日期", + "type": "date", + "length": 0, + "uitype": "date", + "datatype": "date", + "label": "使用日期" + }, + { + "name": "use_time", + "title": "使用时间", + "type": "timestamp", + "length": 0, + "uitype": "str", + "datatype": "timestamp", + "label": "使用时间" + }, + { + "name": "userid", + "title": "用户id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "用户id" + }, + { + "name": "usages", + "title": "使用信息", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "使用信息" + }, + { + "name": "ioinfo", + "title": "交互内容", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "交互内容" + }, + { + "name": "transno", + "title": "交易号", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "交易号" + }, + { + "name": "responsed_seconds", + "title": "响应时间", + "type": "float", + "length": 18, + "cwidth": 18, + "uitype": "float", + "datatype": "float", + "label": "响应时间" + }, + { + "name": "finish_seconds", + "title": "结束时间", + "type": "float", + "length": 18, + "cwidth": 18, + "uitype": "float", + "datatype": "float", + "label": "结束时间" + }, + { + "name": "status", + "title": "状态", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "状态" + }, + { + "name": "taskid", + "title": "任务号", + "type": "str", + "length": 256, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "任务号" + }, + { + "name": "amount", + "title": "交易金额", + "type": "float", + "length": 18, + "cwidth": 18, + "uitype": "float", + "datatype": "float", + "label": "交易金额" + }, + { + "name": "cost", + "title": "交易成本", + "type": "float", + "length": 18, + "cwidth": 18, + "uitype": "float", + "datatype": "float", + "label": "交易成本" + }, + { + "name": "userorgid", + "title": "用户机构id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "用户机构id" + }, + { + "name": "ownerid", + "title": "模型机构id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "模型机构id" + }, + { + "name": "accounting_status", + "title": "记账状态", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "记账状态" + } +] + }, + + + + "page_rows":160, + "cache_limit":5 + } + + ,"binds":[] + +} \ No newline at end of file diff --git a/wwwroot/llmusage/update_llmusage.dspy b/wwwroot/llmusage/update_llmusage.dspy new file mode 100644 index 0000000..7655334 --- /dev/null +++ b/wwwroot/llmusage/update_llmusage.dspy @@ -0,0 +1,36 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None + + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + + r = await sor.U('llmusage', ns) + debug('update success'); + return { + "widgettype":"Message", + "options":{ + "title":"Update Success", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage_accounting_failed/add_llmusage_accounting_failed.dspy b/wwwroot/llmusage_accounting_failed/add_llmusage_accounting_failed.dspy new file mode 100644 index 0000000..abb1891 --- /dev/null +++ b/wwwroot/llmusage_accounting_failed/add_llmusage_accounting_failed.dspy @@ -0,0 +1,37 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None +id = params_kw.id +if not id or len(id) > 32: + id = uuid() +ns['id'] = id + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.C('llmusage_accounting_failed', ns.copy()) + return { + "widgettype":"Message", + "options":{ + "cwidth":16, + "cheight":9, + "title":"Add Success", + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Add Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage_accounting_failed/delete_llmusage_accounting_failed.dspy b/wwwroot/llmusage_accounting_failed/delete_llmusage_accounting_failed.dspy new file mode 100644 index 0000000..bfddb49 --- /dev/null +++ b/wwwroot/llmusage_accounting_failed/delete_llmusage_accounting_failed.dspy @@ -0,0 +1,33 @@ + +ns = { + 'id':params_kw['id'], +} + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.D('llmusage_accounting_failed', ns) + debug('delete success'); + return { + "widgettype":"Message", + "options":{ + "title":"Delete Success", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"ok" + } + } + +debug('Delete failed'); +return { + "widgettype":"Error", + "options":{ + "title":"Delete Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage_accounting_failed/get_llmusage_accounting_failed.dspy b/wwwroot/llmusage_accounting_failed/get_llmusage_accounting_failed.dspy new file mode 100644 index 0000000..c9fdc21 --- /dev/null +++ b/wwwroot/llmusage_accounting_failed/get_llmusage_accounting_failed.dspy @@ -0,0 +1,136 @@ + +ns = params_kw.copy() + + +debug_params('get_llmusage_accounting_failed', ns) +if not ns.get('page'): + ns['page'] = 1 +if not ns.get('sort'): + + + ns['sort'] = 'failed_time desc' + + + +sql = '''select * from llmusage_accounting_failed where 1=1 [[filterstr]]''' + +filterjson = params_kw.get('data_filter') +fields_str=r'''[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32 + }, + { + "name": "llmusageid", + "title": "使用记录id", + "type": "str", + "length": 32 + }, + { + "name": "llmid", + "title": "模型id", + "type": "str", + "length": 32 + }, + { + "name": "userid", + "title": "用户id", + "type": "str", + "length": 32 + }, + { + "name": "userorgid", + "title": "用户机构id", + "type": "str", + "length": 32 + }, + { + "name": "use_date", + "title": "使用日期", + "type": "date" + }, + { + "name": "use_time", + "title": "使用时间", + "type": "timestamp" + }, + { + "name": "amount", + "title": "交易金额", + "type": "double", + "length": 18, + "dec": 5 + }, + { + "name": "cost", + "title": "交易成本", + "type": "double", + "length": 18, + "dec": 5 + }, + { + "name": "failed_reason", + "title": "失败原因", + "type": "text" + }, + { + "name": "failed_time", + "title": "失败时间", + "type": "timestamp" + }, + { + "name": "retry_count", + "title": "重试次数", + "type": "int" + }, + { + "name": "handled", + "title": "是否已处理", + "type": "str", + "length": 1, + "default": "0" + }, + { + "name": "handled_time", + "title": "处理时间", + "type": "timestamp" + }, + { + "name": "handled_note", + "title": "处理备注", + "type": "text" + } +]''' +ori_fields = json.loads(fields_str) +if not filterjson: + fields = [ f['name'] for f in ori_fields ] + filterjson = default_filterjson(fields, ns) +filterdic = ns.copy() +filterdic['filterstr'] = '' +filterdic['userorgid'] = '${userorgid}$' +filterdic['userid'] = '${userid}$' +if filterjson: + dbf = DBFilter(filterjson) + conds = dbf.gen(ns) + if conds: + ns.update(dbf.consts) + conds = f' and {conds}' + filterdic['filterstr'] = conds +ac = ArgsConvert('[[', ']]') +vars = ac.findAllVariables(sql) +NameSpace = {v:'${' + v + '}$' for v in vars if v != 'filterstr' } +filterdic.update(NameSpace) +sql = ac.convert(sql, filterdic) + +debug(f'sql({len(sql)}ch): {sql[:200]}') +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.sqlPaging(sql, ns) + return r +return { + "total":0, + "rows":[] +} \ No newline at end of file diff --git a/wwwroot/llmusage_accounting_failed/index.ui b/wwwroot/llmusage_accounting_failed/index.ui new file mode 100644 index 0000000..3d14ad9 --- /dev/null +++ b/wwwroot/llmusage_accounting_failed/index.ui @@ -0,0 +1,235 @@ + +{ + "id":"llmusage_accounting_failed_tbl", + "widgettype":"Tabular", + "options":{ + "width":"100%", + "height":"100%", + + + "title":"记账失败记录", + + + + + "css":"card", + + + "editable":{ + + "new_data_url":"{{entire_url('add_llmusage_accounting_failed.dspy')}}", + + + "delete_data_url":"{{entire_url('delete_llmusage_accounting_failed.dspy')}}", + + + "update_data_url":"{{entire_url('update_llmusage_accounting_failed.dspy')}}" + + }, + + + "data_url":"{{entire_url('./get_llmusage_accounting_failed.dspy')}}", + + "data_method":"GET", + "data_params":{{json.dumps(params_kw, indent=4, ensure_ascii=False)}}, + "row_options":{ + + + + "browserfields": { + "exclouded": [ + "id" + ], + "alters": { + "handled": { + "uitype": "code", + "data": [ + { + "value": "0", + "text": "未处理" + }, + { + "value": "1", + "text": "已处理" + } + ] + } + } +}, + + + "editexclouded":[ + "id", + "llmusageid", + "failed_time" +], + + "fields":[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "id" + }, + { + "name": "llmusageid", + "title": "使用记录id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "使用记录id" + }, + { + "name": "llmid", + "title": "模型id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "模型id" + }, + { + "name": "userid", + "title": "用户id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "用户id" + }, + { + "name": "userorgid", + "title": "用户机构id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "用户机构id" + }, + { + "name": "use_date", + "title": "使用日期", + "type": "date", + "length": 0, + "uitype": "date", + "datatype": "date", + "label": "使用日期" + }, + { + "name": "use_time", + "title": "使用时间", + "type": "timestamp", + "length": 0, + "uitype": "str", + "datatype": "timestamp", + "label": "使用时间" + }, + { + "name": "amount", + "title": "交易金额", + "type": "double", + "length": 18, + "dec": 5, + "cwidth": 18, + "uitype": "float", + "datatype": "double", + "label": "交易金额" + }, + { + "name": "cost", + "title": "交易成本", + "type": "double", + "length": 18, + "dec": 5, + "cwidth": 18, + "uitype": "float", + "datatype": "double", + "label": "交易成本" + }, + { + "name": "failed_reason", + "title": "失败原因", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "失败原因" + }, + { + "name": "failed_time", + "title": "失败时间", + "type": "timestamp", + "length": 0, + "uitype": "str", + "datatype": "timestamp", + "label": "失败时间" + }, + { + "name": "retry_count", + "title": "重试次数", + "type": "int", + "length": 0, + "uitype": "int", + "datatype": "int", + "label": "重试次数" + }, + { + "name": "handled", + "title": "是否已处理", + "type": "str", + "length": 1, + "default": "0", + "cwidth": 4, + "uitype": "code", + "datatype": "str", + "label": "是否已处理", + "data": [ + { + "value": "0", + "text": "未处理" + }, + { + "value": "1", + "text": "已处理" + } + ] + }, + { + "name": "handled_time", + "title": "处理时间", + "type": "timestamp", + "length": 0, + "uitype": "str", + "datatype": "timestamp", + "label": "处理时间" + }, + { + "name": "handled_note", + "title": "处理备注", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "处理备注" + } +] + }, + + + + "page_rows":160, + "cache_limit":5 + } + + ,"binds":[] + +} \ No newline at end of file diff --git a/wwwroot/llmusage_accounting_failed/update_llmusage_accounting_failed.dspy b/wwwroot/llmusage_accounting_failed/update_llmusage_accounting_failed.dspy new file mode 100644 index 0000000..6699b0f --- /dev/null +++ b/wwwroot/llmusage_accounting_failed/update_llmusage_accounting_failed.dspy @@ -0,0 +1,36 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None + + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + + r = await sor.U('llmusage_accounting_failed', ns) + debug('update success'); + return { + "widgettype":"Message", + "options":{ + "title":"Update Success", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage_history/add_llmusage_history.dspy b/wwwroot/llmusage_history/add_llmusage_history.dspy new file mode 100644 index 0000000..260105d --- /dev/null +++ b/wwwroot/llmusage_history/add_llmusage_history.dspy @@ -0,0 +1,37 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None +id = params_kw.id +if not id or len(id) > 32: + id = uuid() +ns['id'] = id + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.C('llmusage_history', ns.copy()) + return { + "widgettype":"Message", + "options":{ + "cwidth":16, + "cheight":9, + "title":"Add Success", + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Add Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage_history/delete_llmusage_history.dspy b/wwwroot/llmusage_history/delete_llmusage_history.dspy new file mode 100644 index 0000000..8aa864f --- /dev/null +++ b/wwwroot/llmusage_history/delete_llmusage_history.dspy @@ -0,0 +1,33 @@ + +ns = { + 'id':params_kw['id'], +} + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.D('llmusage_history', ns) + debug('delete success'); + return { + "widgettype":"Message", + "options":{ + "title":"Delete Success", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"ok" + } + } + +debug('Delete failed'); +return { + "widgettype":"Error", + "options":{ + "title":"Delete Error", + "timeout":3, + "cwidth":16, + "cheight":9, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/llmusage_history/get_llmusage_history.dspy b/wwwroot/llmusage_history/get_llmusage_history.dspy new file mode 100644 index 0000000..6541059 --- /dev/null +++ b/wwwroot/llmusage_history/get_llmusage_history.dspy @@ -0,0 +1,157 @@ + +ns = params_kw.copy() + + +debug_params('get_llmusage_history', ns) +if not ns.get('page'): + ns['page'] = 1 +if not ns.get('sort'): + + + ns['sort'] = 'use_time desc' + + + +sql = '''select * from llmusage_history where 1=1 [[filterstr]]''' + +filterjson = params_kw.get('data_filter') +fields_str=r'''[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32 + }, + { + "name": "llmid", + "title": "模型id", + "type": "str", + "length": 32 + }, + { + "name": "use_date", + "title": "使用日期", + "type": "date" + }, + { + "name": "use_time", + "title": "使用时间", + "type": "timestamp" + }, + { + "name": "userid", + "title": "用户id", + "type": "str", + "length": 32 + }, + { + "name": "usages", + "title": "使用信息", + "type": "text" + }, + { + "name": "ioinfo", + "title": "交互内容", + "type": "text" + }, + { + "name": "transno", + "title": "交易号", + "type": "str", + "length": 32 + }, + { + "name": "responsed_seconds", + "title": "响应时间", + "type": "double", + "length": 18, + "dec": 3 + }, + { + "name": "finish_seconds", + "title": "结束时间", + "type": "double", + "length": 18, + "dec": 3 + }, + { + "name": "status", + "title": "状态", + "type": "str", + "length": 32 + }, + { + "name": "taskid", + "title": "任务号", + "type": "str", + "length": 256 + }, + { + "name": "amount", + "title": "交易金额", + "type": "double", + "length": 18, + "dec": 5 + }, + { + "name": "cost", + "title": "交易成本", + "type": "double", + "length": 18, + "dec": 5 + }, + { + "name": "userorgid", + "title": "用户机构id", + "type": "str", + "length": 32 + }, + { + "name": "ownerid", + "title": "模型机构id", + "type": "str", + "length": 32 + }, + { + "name": "accounting_status", + "title": "记账状态", + "type": "str", + "length": 32 + }, + { + "name": "backup_time", + "title": "备份时间", + "type": "timestamp" + } +]''' +ori_fields = json.loads(fields_str) +if not filterjson: + fields = [ f['name'] for f in ori_fields ] + filterjson = default_filterjson(fields, ns) +filterdic = ns.copy() +filterdic['filterstr'] = '' +filterdic['userorgid'] = '${userorgid}$' +filterdic['userid'] = '${userid}$' +if filterjson: + dbf = DBFilter(filterjson) + conds = dbf.gen(ns) + if conds: + ns.update(dbf.consts) + conds = f' and {conds}' + filterdic['filterstr'] = conds +ac = ArgsConvert('[[', ']]') +vars = ac.findAllVariables(sql) +NameSpace = {v:'${' + v + '}$' for v in vars if v != 'filterstr' } +filterdic.update(NameSpace) +sql = ac.convert(sql, filterdic) + +debug(f'sql({len(sql)}ch): {sql[:200]}') +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + r = await sor.sqlPaging(sql, ns) + return r +return { + "total":0, + "rows":[] +} \ No newline at end of file diff --git a/wwwroot/llmusage_history/index.ui b/wwwroot/llmusage_history/index.ui new file mode 100644 index 0000000..22ce578 --- /dev/null +++ b/wwwroot/llmusage_history/index.ui @@ -0,0 +1,242 @@ + +{ + "id":"llmusage_history_tbl", + "widgettype":"Tabular", + "options":{ + "width":"100%", + "height":"100%", + + + "title":"模型使用历史记录", + + + + + "css":"card", + + + "editable":{ + + "new_data_url":"{{entire_url('add_llmusage_history.dspy')}}", + + + "delete_data_url":"{{entire_url('delete_llmusage_history.dspy')}}", + + + "update_data_url":"{{entire_url('update_llmusage_history.dspy')}}" + + }, + + + "data_url":"{{entire_url('./get_llmusage_history.dspy')}}", + + "data_method":"GET", + "data_params":{{json.dumps(params_kw, indent=4, ensure_ascii=False)}}, + "row_options":{ + + + + "browserfields": { + "exclouded": [ + "id" + ], + "alters": {} +}, + + + "editexclouded":[ + "id" +], + + "fields":[ + { + "name": "id", + "title": "id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "id" + }, + { + "name": "llmid", + "title": "模型id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "模型id" + }, + { + "name": "use_date", + "title": "使用日期", + "type": "date", + "length": 0, + "uitype": "date", + "datatype": "date", + "label": "使用日期" + }, + { + "name": "use_time", + "title": "使用时间", + "type": "timestamp", + "length": 0, + "uitype": "str", + "datatype": "timestamp", + "label": "使用时间" + }, + { + "name": "userid", + "title": "用户id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "用户id" + }, + { + "name": "usages", + "title": "使用信息", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "使用信息" + }, + { + "name": "ioinfo", + "title": "交互内容", + "type": "text", + "length": 0, + "uitype": "text", + "datatype": "text", + "label": "交互内容" + }, + { + "name": "transno", + "title": "交易号", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "交易号" + }, + { + "name": "responsed_seconds", + "title": "响应时间", + "type": "double", + "length": 18, + "dec": 3, + "cwidth": 18, + "uitype": "float", + "datatype": "double", + "label": "响应时间" + }, + { + "name": "finish_seconds", + "title": "结束时间", + "type": "double", + "length": 18, + "dec": 3, + "cwidth": 18, + "uitype": "float", + "datatype": "double", + "label": "结束时间" + }, + { + "name": "status", + "title": "状态", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "状态" + }, + { + "name": "taskid", + "title": "任务号", + "type": "str", + "length": 256, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "任务号" + }, + { + "name": "amount", + "title": "交易金额", + "type": "double", + "length": 18, + "dec": 5, + "cwidth": 18, + "uitype": "float", + "datatype": "double", + "label": "交易金额" + }, + { + "name": "cost", + "title": "交易成本", + "type": "double", + "length": 18, + "dec": 5, + "cwidth": 18, + "uitype": "float", + "datatype": "double", + "label": "交易成本" + }, + { + "name": "userorgid", + "title": "用户机构id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "用户机构id" + }, + { + "name": "ownerid", + "title": "模型机构id", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "模型机构id" + }, + { + "name": "accounting_status", + "title": "记账状态", + "type": "str", + "length": 32, + "cwidth": 18, + "uitype": "str", + "datatype": "str", + "label": "记账状态" + }, + { + "name": "backup_time", + "title": "备份时间", + "type": "timestamp", + "length": 0, + "uitype": "str", + "datatype": "timestamp", + "label": "备份时间" + } +] + }, + + + + "page_rows":160, + "cache_limit":5 + } + + ,"binds":[] + +} \ No newline at end of file diff --git a/wwwroot/llmusage_history/update_llmusage_history.dspy b/wwwroot/llmusage_history/update_llmusage_history.dspy new file mode 100644 index 0000000..cf6a4a4 --- /dev/null +++ b/wwwroot/llmusage_history/update_llmusage_history.dspy @@ -0,0 +1,36 @@ + +ns = params_kw.copy() +for k,v in ns.items(): + if v == 'NaN' or v == 'null': + ns[k] = None + + + + +db = DBPools() +dbname = get_module_dbname('llm') +async with db.sqlorContext(dbname) as sor: + + r = await sor.U('llmusage_history', ns) + debug('update success'); + return { + "widgettype":"Message", + "options":{ + "title":"Update Success", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"ok" + } + } + +return { + "widgettype":"Error", + "options":{ + "title":"Update Error", + "cwidth":16, + "cheight":9, + "timeout":3, + "message":"failed" + } +} \ No newline at end of file diff --git a/wwwroot/model_estimate.dspy b/wwwroot/model_estimate.dspy index 0c04aed..f6a4917 100644 --- a/wwwroot/model_estimate.dspy +++ b/wwwroot/model_estimate.dspy @@ -1,5 +1,5 @@ -debug(f'model_estimate.dspy:{params_kw=}') +debug_params('model_estimate', params_kw) db = DBPools() dbname = get_module_dbname('llmage') async with db.sqlorContext(dbname) as sor: diff --git a/wwwroot/t2t/index.dspy b/wwwroot/t2t/index.dspy index 58ad527..61b7a2a 100644 --- a/wwwroot/t2t/index.dspy +++ b/wwwroot/t2t/index.dspy @@ -1,4 +1,4 @@ -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) lctype='文生文' if params_kw.off_peak: off_peak = params_kw.off_peak diff --git a/wwwroot/v1/chat/completions/index.dspy b/wwwroot/v1/chat/completions/index.dspy index 6850c23..46b0ddc 100644 --- a/wwwroot/v1/chat/completions/index.dspy +++ b/wwwroot/v1/chat/completions/index.dspy @@ -9,7 +9,7 @@ async def gen(): async for l in f(): yield l -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) lctype='文生文' if params_kw.off_peak: off_peak = params_kw.off_peak @@ -25,7 +25,7 @@ if userid is None: return openai_403() if not params_kw.prompt and not params_kw.messages: - debug(f'not params_kw.prompt and not params_kw.messages,{params_kw=}') + debug(f'missing prompt and messages, model={params_kw.model}') d = return_error('Missing need data(prompt or messages)') return json_response(d, status=400) env = request._run_ns diff --git a/wwwroot/v1/image/generations/index.dspy b/wwwroot/v1/image/generations/index.dspy index 067c014..a1d68cb 100644 --- a/wwwroot/v1/image/generations/index.dspy +++ b/wwwroot/v1/image/generations/index.dspy @@ -23,7 +23,7 @@ from appPublic.uniqueID import getID from appPublic.timeUtils import curDateString, timestampstr from sqlor.dbpools import get_sor_context -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) userid = await get_user() userorgid = await get_userorgid() diff --git a/wwwroot/v1/video/generations/index.dspy b/wwwroot/v1/video/generations/index.dspy index 29a94c6..e81ff42 100644 --- a/wwwroot/v1/video/generations/index.dspy +++ b/wwwroot/v1/video/generations/index.dspy @@ -31,7 +31,7 @@ from appPublic.uniqueID import getID from appPublic.timeUtils import curDateString, timestampstr from sqlor.dbpools import get_sor_context -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) userid = await get_user() userorgid = await get_userorgid() diff --git a/wwwroot/vidu_inference.dspy b/wwwroot/vidu_inference.dspy index cf0f6da..28d0a73 100644 --- a/wwwroot/vidu_inference.dspy +++ b/wwwroot/vidu_inference.dspy @@ -1,4 +1,4 @@ -debug(f'{params_kw=}') +debug_params('params_kw', params_kw) if params_kw.off_peak: off_peak = params_kw.off_peak if off_peak in [True, "Y" "y", 1, "1"]: