Authored by 郝肖肖

'队列数据列表'

... ... @@ -14,6 +14,18 @@ const TYPE_LIST = [
{name: '店铺', type: 'shop', lt: 'ShopId'},
{name: '链接', type: 'url', lt: 'URL'}
];
const JOB_TASK = [
{
k: 'global:yoho:seo:task:minute',
v: '1 */10 * * * *',
info: '每10分钟执行一次'
},
{
k: 'global:yoho:seo:task:day',
v: '30 30 1 * * *',
info: '每天的1点30分30s执行一次'
}
];
const tdk = {
// tdk 列表
... ... @@ -459,7 +471,6 @@ const category = {
}
}
const friendLink = {
index: async(ctx, next) => {
let type = ctx.query.type || 'text';
... ... @@ -624,6 +635,59 @@ const friendLink = {
},
};
const task = {
index: async(ctx, next) => {
let tasks = await ctx.redis.multi(_.map(JOB_TASK, job => ['hvals', job.k])).execAsync().then(rdata => {
let result = [];
_.each(rdata, (items, rk) => {
_.each(items, item => {
result.push(Object.assign(JSON.parse(item), {
job_name: JOB_TASK[rk].info,
type: rk,
}));
})
});
return result;
});
await ctx.render('action/seo_task', {
title: '定时任务管理',
tasks: tasks
});
},
add: async(ctx, next) => {
},
del: async(ctx, next) => {
let params = ctx.request.body || {};
let key_name = JOB_TASK[parseInt(`0${params.type}`)];
let field_name = params.code || '';
return ctx.redis.hdelAsync(key_name.k, field_name).then(status => {
return ctx.body = {
code: 200,
message: 'success',
data: ''
};
});
},
log: async(ctx, next) => {
let key = ctx.query.key || '';
let resData = {
typeList: [
{type: 'text', name: '文字友链'},
{type: 'img', name: '图片友链'},
]
};
await ctx.render('action/seo_task', Object.assign(resData, {
title: '定时任务日志',
}));
},
};
r.get('/', tdk.index);
r.get('/tdk', tdk.index);
r.post('/tdk/add', tdk.add);
... ... @@ -650,4 +714,10 @@ r.post('/friendlink/add', friendLink.add);
r.post('/friendlink/edit', friendLink.edit);
r.post('/friendlink/delete', friendLink.delete);
// 定时任务管理
r.get('/task', task.index);
r.post('/task/add', task.add);
r.post('/task/del', task.del);
r.post('/task/log', task.log);
module.exports = r;
... ...
... ... @@ -196,7 +196,7 @@
{{/each}}
{{#unless linkList}}
<tr>
<td class="text-center" colspan="6">暂无数据</td>
<td class="text-center" colspan="5">暂无数据</td>
</tr>
{{/unless}}
</tbody>
... ...
<div class="pageheader">
<div class="media">
<div class="pageicon pull-left">
<i class="fa fa-th-list"></i>
</div>
<div class="media-body">
<ul class="breadcrumb">
<li><a href="/"><i class="glyphicon glyphicon-home"></i></a></li>
<li>{{title}}</li>
</ul>
<h4>{{title}}</h4>
</div>
</div>
<!-- media -->
</div>
<!-- pageheader -->
<div class="contentpanel" style="padding-bottom:0;">
<div class="panel panel-default">
<div class="panel-body">
<a data-toggle="modal" href="#pop" class="btn btn-default" style="margin-right:10px;">增加</a>
<button class="btn btn-default delete-all" type="submit">删除</button>
</div>
</div><!--/panel-default-->
<div class="panel panel-default">
<div class="panel-body">
<table class="table table-striped table-bordered tab-task">
<thead>
<tr>
<th width="10%">&nbsp;&nbsp;&nbsp;
<label><input type="checkbox" style="vertical-align: text-bottom;" onclick="javascript:$('.tab-task input[type=checkbox]').attr('checked', this.checked);" />&nbsp;全选</label>
</th>
<th class="text-center" width="20%">任务名称</th>
<th class="text-center" width="30%">链接</th>
<th class="text-center" width="10%">延迟时间</th>
<th class="text-center" width="15%">执行频率</th>
<th class="text-center" width="15%">操作</th>
</tr>
</thead>
<tbody>
{{#each tasks}}
<tr data-code="{{code}}" data-type="{{type}}">
<td>&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" /></td>
<td class="text-center" >{{name}}</td>
<td class="text-center" >{{url}}</td>
<td class="text-center" >{{time}}</td>
<td class="text-center" >{{job_name}}</td>
<td class="text-center">
<a href="#pop" class="edit-btn" data-toggle="modal">执行日志</a>
<a href="javascript:;" class="del-btn">删除</a>
</td>
</tr>
{{/each}}
{{#unless tasks}}
<tr>
<td class="text-center" colspan="6">暂无数据</td>
</tr>
{{/unless}}
</tbody>
</table>
{{# pager}}
<div class="text-right">
{{#if pages}}
<ul class="pagination">
{{# prePage}}
<li><a href="{{url}}">上一页</a></li>
{{/ prePage}}
{{# pages}}
<li class="{{#unless url}}disabled {{/unless}}{{#if cur}}active{{/if}}"><a {{#if url}}href="{{url}}"{{^}}href="javascript:;"{{/if}}>{{num}}</a></li>
{{/ pages}}
{{# nextPage}}
<li><a href="{{url}}">下一页</a></li>
{{/ nextPage}}
</ul>
{{/if}}
</div>
{{/ pager}}
</div>
</div><!--/panel-default-->
</div><!--/contentpanel-->
<script>
var tasks = {
init: function() {
var that = this;
this.$base = $('.contentpanel');
this.$popTitle = $('.cover-title', this.$base);
this.$base.on('change', '#select-type', function() {
if ($(this).val() === 'img') {
that.$imgLink.removeClass('hide');
} else {
that.$imgLink.addClass('hide');
}
}).on('click', '.clear-input', function() {
that.clearInput();
}).on('click', '.sure-btn', function() {
var data;
if (that.saving) {
return;
}
data = that.packReqData();
if (!data) {
that.$errTip.text('请填写完整友链信息');
return;
}
that.saving = true;
$.ajax({
url: that.editInfo ? '/seo/friendlink/edit' : '/seo/friendlink/add',
type: 'POST',
data: data,
}).done(function(res) {
if (res.code === 200) {
history.go(0);
}
}).always(function() {
that.saving = false;
});
});
// 单个删除
this.$base.on('click', '.del-btn', function() {
let $tr = $(this).closest('tr');
that.del($tr.data()).then(() => {
$tr.remove();
});
});
},
del: function(data) {
return $.ajax({
url: '/seo/task/del',
type: 'POST',
data: data,
});
}
};
tasks.init();
</script>
... ...
... ... @@ -77,6 +77,7 @@
<li><a href="/seo/tdk"><span>TDK管理</span></a></li>
<li><a href="/seo/category"><span>品类描述管理</span></a></li>
<li><a href="/seo/friendlink"><span>友链管理</span></a></li>
<li><a href="/seo/task"><span>定时任务管理</span></a></li>
</ul>
</li>
... ...