Merge remote-tracking branch 'origin/glms/feature/1.4.2' into glms/feature/1.4.2-margin

This commit is contained in:
锦麟 王
2026-08-17 10:20:04 +08:00
105 changed files with 4044 additions and 1588 deletions
@@ -109,9 +109,52 @@ const vueTradeType = function () {
};
};
//标的选择组件
//标的选择组件(EQD-7049:改为服务端搜索,不再依赖全量 ylotc.underlyings,避免十几万标的整段下载卡死)
const vueUnderlying = function () {
const _suggestionTpl = _.template($('#underlyingSuggestionTpl').html());
// 标的缓存:按 品种|关键词 隔离;乱序响应由 token 丢弃(helper 收在函数内,避免全局绑定冲突)
const _cache = {};
const _tokens = {};
function _fetch(varietyId, query, cb) {
var key = (varietyId || 0) + '|' + (query || '');
var token = (_tokens[key] = (_tokens[key] || 0) + 1);
var postData = {
FilterCode: (query || '').toUpperCase(),
VarietyId: varietyId || 0,
MaxShowLength: 20,
BlackLimit: 1,
UseForTrading: true,
IncludeMatured: true,
CheckLaunch: true
};
main.post('/frontdata/AjaxGetUnderlyingSelect', postData).done(function (res) {
if (_tokens[key] !== token) return; // 丢弃过期响应
var arr = (res && (res.obj || res.data)) || [];
var norm = arr.map(function (x) {
return {
Code: x.Code,
Name: x.Name,
InstrumentType: x.InstrumentType,
VarietyId: x.VarietyId,
Disallow: !!x.Disallow,
IsCombined: !!x.IsSynthetic || !!x.IsBasket,
BlackWhiteState: x.BlackWhiteState || 0,
PinYin: x.PinYin || ''
};
});
cb && cb(norm);
});
}
function _filter(list, query, varietyId) {
if (!query) return (list || []).slice(0, 20);
query = query.toUpperCase();
return (list || []).filter(function (x) {
if (varietyId && x.VarietyId !== varietyId) return false;
if (x.IsCombined) return false; // 与原逻辑一致:搜索时排除组合标的
return (x.Code && x.Code.toUpperCase().indexOf(query) !== -1)
|| (x.PinYin && x.PinYin.toUpperCase().indexOf(query) !== -1);
}).slice(0, 20);
}
return {
props: ['underlying'],
data() {
@@ -120,27 +163,24 @@ const vueUnderlying = function () {
mounted() {
var self = this;
this.jqInput = $(this.$el).children(0);
// EQD-7049:预拉默认20条(当前品种),避免下拉空白
_fetch(self.underlying.VarietyId, '', function (list) {
_cache[self.underlying.VarietyId || 0] = list;
try { $(self.jqInput).autocomplete('search', ''); } catch (e) {}
});
this.autoctrl = FastVue.autocomplete(this.jqInput, {
valueField: 'Code',
lookup(query, callback) {
var arr = [];
if (!query) {
var varietyId = self.underlying.VarietyId;
ylotc.underlyings.forEach(x => {
(!varietyId || x.VarietyId === varietyId) && arr.push(x);
});
} else {
query = query.toUpperCase();
ylotc.underlyings.forEach(x => {
if (x.Code.toUpperCase().indexOf(query) !== -1 || x.PinYin && x.PinYin.indexOf(query) !== -1 && !x.IsCombined) {
arr.push(x);
}
var varietyId = self.underlying.VarietyId;
var cached = _cache[varietyId || 0] || [];
var immediate = _filter(cached, query, varietyId);
if (query) {
// 有输入时异步向服务端搜索并刷新缓存(乱序响应由 token 丢弃)
_fetch(varietyId, query, function (list) {
_cache[varietyId || 0] = list;
});
}
if (arr.length < 30) {
arr = _.sortBy(arr, x => x.Code);
}
return arr;
return immediate;
},
onSelect(data) {
if (self.underlying !== data) {
@@ -1430,6 +1470,12 @@ const vueTrade = function () {
//更新标的
updateUnderlying(reqData, fromSelect) {
let self = this;
// EQD-7049:新建空白页未选标的/品种/类型时,跳过必然失败的后端默认标的查询,避免报“标的信息缺失”
var hasQueryKey = !!(reqData.UnderlyingCode || reqData.InstrumentType || reqData.VarietyId > 0);
if (!hasQueryKey) {
!fromSelect && (self.viewState.underlying = tradeHelper.getEmptyUnderlying());
return;
}
var instTypeChanged = !!reqData.InstrumentType;
!fromSelect && (self.viewState.underlying = tradeHelper.getEmptyUnderlying());
main.post("/pricing/AjaxGetUnderlying", reqData).done(function (resp) {
@@ -108,9 +108,52 @@ const vueTradeType = function () {
};
};
//标的选择组件
//标的选择组件(EQD-7049:改为服务端搜索,不再依赖全量 ylotc.underlyings,避免十几万标的整段下载卡死)
const vueUnderlying = function () {
const _suggestionTpl = _.template($('#underlyingSuggestionTpl').html());
// 标的缓存:按 品种|关键词 隔离;乱序响应由 token 丢弃(helper 收在函数内,避免全局绑定冲突)
const _cache = {};
const _tokens = {};
function _fetch(varietyId, query, cb) {
var key = (varietyId || 0) + '|' + (query || '');
var token = (_tokens[key] = (_tokens[key] || 0) + 1);
var postData = {
FilterCode: (query || '').toUpperCase(),
VarietyId: varietyId || 0,
MaxShowLength: 20,
BlackLimit: 1,
UseForTrading: true,
IncludeMatured: true,
CheckLaunch: true
};
main.post('/frontdata/AjaxGetUnderlyingSelect', postData).done(function (res) {
if (_tokens[key] !== token) return; // 丢弃过期响应
var arr = (res && (res.obj || res.data)) || [];
var norm = arr.map(function (x) {
return {
Code: x.Code,
Name: x.Name,
InstrumentType: x.InstrumentType,
VarietyId: x.VarietyId,
Disallow: !!x.Disallow,
IsCombined: !!x.IsSynthetic || !!x.IsBasket,
BlackWhiteState: x.BlackWhiteState || 0,
PinYin: x.PinYin || ''
};
});
cb && cb(norm);
});
}
function _filter(list, query, varietyId) {
if (!query) return (list || []).slice(0, 20);
query = query.toUpperCase();
return (list || []).filter(function (x) {
if (varietyId && x.VarietyId !== varietyId) return false;
if (x.IsCombined) return false; // 与原逻辑一致:搜索时排除组合标的
return (x.Code && x.Code.toUpperCase().indexOf(query) !== -1)
|| (x.PinYin && x.PinYin.toUpperCase().indexOf(query) !== -1);
}).slice(0, 20);
}
return {
props: ['underlying'],
data() {
@@ -119,27 +162,24 @@ const vueUnderlying = function () {
mounted() {
var self = this;
this.jqInput = $(this.$el).children(0);
// EQD-7049:预拉默认20条(当前品种),避免下拉空白
_fetch(self.underlying.VarietyId, '', function (list) {
_cache[self.underlying.VarietyId || 0] = list;
try { $(self.jqInput).autocomplete('search', ''); } catch (e) {}
});
this.autoctrl = FastVue.autocomplete(this.jqInput, {
valueField: 'Code',
lookup(query, callback) {
var arr = [];
if (!query) {
var varietyId = self.underlying.VarietyId;
ylotc.underlyings.forEach(x => {
(!varietyId || x.VarietyId === varietyId) && arr.push(x);
});
} else {
query = query.toUpperCase();
ylotc.underlyings.forEach(x => {
if (x.Code.toUpperCase().indexOf(query) !== -1 || x.PinYin && x.PinYin.indexOf(query) !== -1 && !x.IsCombined) {
arr.push(x);
}
var varietyId = self.underlying.VarietyId;
var cached = _cache[varietyId || 0] || [];
var immediate = _filter(cached, query, varietyId);
if (query) {
// 有输入时异步向服务端搜索并刷新缓存(乱序响应由 token 丢弃)
_fetch(varietyId, query, function (list) {
_cache[varietyId || 0] = list;
});
}
if (arr.length < 30) {
arr = _.sortBy(arr, x => x.Code);
}
return arr;
return immediate;
},
onSelect(data) {
if (self.underlying !== data) {
@@ -1044,6 +1084,12 @@ const vueTrade = function () {
//更新标的
updateUnderlying(reqData, fromSelect) {
let self = this;
// EQD-7049:新建空白页未选标的/品种/类型时,跳过必然失败的后端默认标的查询,避免报“标的信息缺失”
var hasQueryKey = !!(reqData.UnderlyingCode || reqData.InstrumentType || reqData.VarietyId > 0);
if (!hasQueryKey) {
!fromSelect && (self.viewState.underlying = tradeHelper.getEmptyUnderlying());
return;
}
var instTypeChanged = !!reqData.InstrumentType;
!fromSelect && (self.viewState.underlying = tradeHelper.getEmptyUnderlying());
main.post("/pricing/AjaxGetUnderlying", reqData).done(function (resp) {
@@ -53,7 +53,8 @@ var app = new Vue({
{ text: '交易新增与修改', value: '2' },
{ text: '交易了结', value: '6' },
/* { text: '资信与授信', value: '3' },*/
{ text: '出金', value: '4' }
{ text: '出金', value: '4' },
{ text: '黑名单', value: '7' }
],
isOpen: false,
@@ -62,12 +63,14 @@ var app = new Vue({
isCredit: false,
isOutCash: false,
isClient: false,
isClientBlack: false,
openItems: [],
clientItems: [],
tradeItems: [],
closeItems: [],
creditItems: [],
outCashItems: [],
clientBlackItems: [],
openCounter: 0,
tradeCounter: 0,
creditCounter: 0,
@@ -140,6 +143,7 @@ var app = new Vue({
thisObj.isCredit = false;
thisObj.isOutCash = false;
thisObj.isClient = false;
thisObj.isClientBlack = false;
} else if (thisObj.selected === '2') {
thisObj.isOpen = false;
thisObj.isTrade = true;
@@ -147,6 +151,7 @@ var app = new Vue({
thisObj.isCredit = false;
thisObj.isOutCash = false;
thisObj.isClient = false;
thisObj.isClientBlack = false;
} else if (thisObj.selected === '6') { // 需求②:交易了结流程
thisObj.isOpen = false;
thisObj.isTrade = false;
@@ -154,6 +159,7 @@ var app = new Vue({
thisObj.isCredit = false;
thisObj.isOutCash = false;
thisObj.isClient = false;
thisObj.isClientBlack = false;
} else if (thisObj.selected === '3') {
thisObj.isOpen = false;
thisObj.isTrade = false;
@@ -161,6 +167,7 @@ var app = new Vue({
thisObj.isCredit = true;
thisObj.isOutCash = false;
thisObj.isClient = false;
thisObj.isClientBlack = false;
}
else if (thisObj.selected === '4') {
thisObj.isOpen = false;
@@ -169,6 +176,7 @@ var app = new Vue({
thisObj.isCredit = false;
thisObj.isOutCash = true;
thisObj.isClient = false;
thisObj.isClientBlack = false;
}
else if (thisObj.selected === '5') {
thisObj.isOpen = false;
@@ -177,6 +185,16 @@ var app = new Vue({
thisObj.isCredit = false;
thisObj.isOutCash = false;
thisObj.isClient = true;
thisObj.isClientBlack = false;
}
else if (thisObj.selected === '7') {
thisObj.isOpen = false;
thisObj.isTrade = false;
thisObj.isClose = false;
thisObj.isCredit = false;
thisObj.isOutCash = false;
thisObj.isClient = false;
thisObj.isClientBlack = true;
}
else {
thisObj.isOpen = false;
@@ -185,6 +203,7 @@ var app = new Vue({
thisObj.isCredit = false;
thisObj.isOutCash = false;
thisObj.isClient = false;
thisObj.isClientBlack = false;
}
thisObj.getProcess();
},
@@ -385,6 +404,18 @@ var app = new Vue({
thisObj.addCloseNode(index, child, node);
return;
}
else if (selectType === "7") { //黑名单
var item = {
Type: 'ClientBlackProcess',
Index: index + 1,
SelectValue: 0
};
thisObj.clientBlackItems.splice(index, 0, item);
thisObj.clientBlackItems.forEach(function (x, itemIndex) {
x.Index = itemIndex + 1;
});
return;
}
},
delProcess: function (openItem) {
@@ -417,6 +448,14 @@ var app = new Vue({
});
return;
}
else if (selectType === "7") {//黑名单
var index = thisObj.clientBlackItems.indexOf(openItem);
thisObj.clientBlackItems.splice(index, 1);
thisObj.clientBlackItems.forEach(function (x, itemIndex) {
x.Index = itemIndex + 1;
});
return;
}
},
addOpenProcess(index, child, node) {
var thisObj = this;
@@ -528,6 +567,10 @@ var app = new Vue({
thisObj.saveCloseProcess();
return;
}
else if (selectType === "7") { //黑名单
thisObj.clientBlackOk();
return;
}
},
openOk() {
var thisObj = this;
@@ -857,6 +900,38 @@ var app = new Vue({
});
}
},
clientBlackOk() {
var thisObj = this;
var items = thisObj.clientBlackItems;
for (var i = 0; i < items.length; i++) {
if (items[i].SelectValue === "" || items[i].SelectValue === 0) {
main.message('流程中断,请重新选择');
return;
}
for (var j = i + 1; j < items.length; j++) {
if (parseInt(items[i].SelectValue) === parseInt(items[j].SelectValue)) {
main.message('流程包含重复项,请重新选择');
return;
}
}
}
if (items.length > 0) {
main.confirm("确认修改黑名单审批流程?", function () {
main.post("/AccountOpeningProcess/AddProcess",
{ type: "ClientBlackProcess", data: items },
{ async: false }).done(function () {
thisObj.getProcess();
});
});
} else {
main.confirm("删除审批流程后,黑名单变更会直接生效,确认删除?", function () {
main.post("/AccountOpeningProcess/AddProcess",
{ type: "ClientBlackProcess" },
{ async: false });
});
}
},
getProcess() {
var thisObj = this;
thisObj.openItems = [];
@@ -865,6 +940,7 @@ var app = new Vue({
thisObj.creditItems = [];
thisObj.outCashItems = [];
thisObj.clientItems = [];
thisObj.clientBlackItems = [];
main.post("/AccountOpeningProcess/GetProcess",
{},
{ async: false }).done(
@@ -945,6 +1021,14 @@ var app = new Vue({
triggerCondition: value.triggerCondition
});
});
(res.ClientBlackProcess || []).forEach(function (value) {
thisObj.clientBlackItems.push({
id: value.id,
Type: value.processType,
Index: value.order,
SelectValue: value.roleId
});
});
// 需求①:加载后把 triggerCondition(JSON)解析为结构化对象供 UI 编辑
['openItems', 'tradeItems', 'closeItems', 'clientItems'].forEach(function (arr) {
thisObj[arr].forEach(function (item) {
@@ -28,10 +28,13 @@ function saveInfo(dataId, rowId) {
g_grid.jqGrid('saveRow', rowId,
{
successfunc: function (response) {
var msg = response.responseJSON.msg;
var result = response.responseJSON || {};
var msg = result.msg || "保存失败";
main.message(msg);
$("#systemTip").text(new Date().toLocaleString() + " " + msg);
if (!result.success) return false;
g_grid.trigger('reloadGrid');
return true;
},
"url": "/ex_dividend_info/SaveDividend",
"extraparam": data,
@@ -150,4 +153,4 @@ $(function () {
onPaging: onJqgridPaging
};
g_grid = jQuery('#listGrid').jqGrid(obj);
});
});
@@ -164,7 +164,7 @@ $(function () {
//设置除权
function SetDividEnd(cellValue, options, rowObject) {
if (rowObject.UnderlyingInstrumentType !== "Stock" || rowObject.CommodityCode === "篮子标的" || !g_dividend) return "";
if (["Stock", "Fund"].indexOf(rowObject.UnderlyingInstrumentType) < 0 || rowObject.CommodityCode === "篮子标的" || !g_dividend) return "";
var imageHtml = "<input type=\"button\" value=\"除权\" class=\"wentiEdit btn-info\" onclick=\"openDividEnd('" + rowObject.EncryptId + "');\" />";
return imageHtml;
}