fix: restore /hrbeu/ugs/news.js (#11224)

* fix: restore /heu/ugs/news.js

* Update lib/v2/heu/ugs/news.js

* Update lib/v2/heu/ugs/news.js

* Update lib/v2/heu/ugs/news.js

* feat(require): update require

* refactor: mise fixes

* rename namespace to hrbeu
- hrbeu.edu.cn is the primary domain name as it's where the contact us mail hosted on

* increase code readability
- use template literals over .concat()
- use .includes() to check the existence of sth

* remove fake publish time

* remove duplicated title in description

* fix: fetch article from wechat mp

* fix: codeql
This commit is contained in:
Derek
2022-11-09 22:31:19 +08:00
committed by GitHub
parent ba2c3419b6
commit c07c960957
14 changed files with 210 additions and 157 deletions

View File

@@ -1125,7 +1125,7 @@ xskb1 对应 <http://www.auto.uestc.edu.cn/index/xskb1.htm>
### 本科生院工作通知
<Route author="XYenon" example="/heu/ugs/news/jwc/jxap" path="/heu/ugs/news/:author?/:category?" :paramsDesc="['发布部门,默认为 `gztz`', '分类,默认为 `all`']">
<Route author="XYenon" example="/hrbeu/ugs/news/jwc/jxap" path="/hrbeu/ugs/news/:author?/:category?" :paramsDesc="['发布部门,默认为 `gztz`', '分类,默认为 `all`']">
author 列表:
@@ -1181,7 +1181,7 @@ category 列表:
### 研究生院
<Route author="Derekmini XYenon" example="/heu/yjsy/list/2981" path="/heu/yjsy/list/:id" :paramsDesc="['栏目编号,由 `URL` 中获取。']" radar="1" rssbud="1">
<Route author="Derekmini XYenon" example="/hrbeu/yjsy/list/2981" path="/hrbeu/yjsy/list/:id" :paramsDesc="['栏目编号,由 `URL` 中获取。']" radar="1" rssbud="1">
| 通知公告 | 新闻动态 | 学籍注册 | 奖助学金 | 其他 |
| :--: | :--: | :--: | :--: | :-: |
@@ -1191,7 +1191,7 @@ category 列表:
### 就业服务平台
<Route author="Derekmini" example="/heu/job/list/tzgg" path="/heu/job/list/:id" :paramsDesc="['栏目,如下表']" radar="1" rssbud="1">
<Route author="Derekmini" example="/hrbeu/job/list/tzgg" path="/hrbeu/job/list/:id" :paramsDesc="['栏目,如下表']" radar="1" rssbud="1">
| 通知公告 | 热点新闻 |
| :--: | :--: |
@@ -1201,19 +1201,19 @@ category 列表:
#### 大型招聘会
<Route author="Derekmini" example="/heu/job/bigemploy" path="/heu/job/bigemploy" radar="1" rssbud="1">
<Route author="Derekmini" example="/hrbeu/job/bigemploy" path="/hrbeu/job/bigemploy" radar="1" rssbud="1">
</Route>
#### 今日招聘会
<Route author="Derekmini" example="/heu/job/calendar" path="/heu/job/calendar" radar="1" rssbud="1">
<Route author="Derekmini" example="/hrbeu/job/calendar" path="/hrbeu/job/calendar" radar="1" rssbud="1">
</Route>
### 工学新闻
<Route author="Derekmini XYenon" example="/heu/gx/list/xw/yw" path="/heu/gx/:type/:column/:id?" :paramsDesc="['页面类型,如 `新闻 - 要闻` 页面为 `list` 类型,`新闻 - 专题策划` 页面为 `card` 类型,通过直接观察页面来判断;','主栏,如 `新闻xw`,由 `URL` 中获取;','次栏,如 `要闻yw`,如果次栏存在,则为必选,由 `URL` 中获取。']" radar="1" rssbud="1">
<Route author="Derekmini XYenon" example="/hrbeu/gx/list/xw/yw" path="/hrbeu/gx/:type/:column/:id?" :paramsDesc="['页面类型,如 `新闻 - 要闻` 页面为 `list` 类型,`新闻 - 专题策划` 页面为 `card` 类型,通过直接观察页面来判断;','主栏,如 `新闻xw`,由 `URL` 中获取;','次栏,如 `要闻yw`,如果次栏存在,则为必选,由 `URL` 中获取。']" radar="1" rssbud="1">
| 新闻 | 新闻 - 要闻 | 新闻 - 专题策划 | 其他 |
| :------: | :---------: | :-----------: | :-: |
@@ -1223,7 +1223,7 @@ category 列表:
### 水声工程学院
<Route author="Derekmini" example="/heu/uae/list/3751" path="/heu/uae/list/:id" :paramsDesc="['栏目编号,由 `URL` 中获取。']" radar="1" rssbud="1">
<Route author="Derekmini" example="/hrbeu/uae/list/3751" path="/hrbeu/uae/list/:id" :paramsDesc="['栏目编号,由 `URL` 中获取。']" radar="1" rssbud="1">
| 新闻动态 | 通知公告 | 其他 |
| :--: | :--: | :-: |

View File

@@ -8,6 +8,7 @@
* lib/v2/pku/nsd/gd
* lib/v2/sdu/cs
* lib/v2/nua/utils
* lib/v2/hrbeu
*
* If your new route is not in the above folders, please add it to the list.
*

View File

@@ -1,42 +0,0 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
module.exports = async (ctx) => {
const date = new Date();
const hour = date.getHours();
const minute = date.getMinutes();
const response = await got({
method: 'get',
url: 'http://job.hrbeu.edu.cn/HrbeuJY/web',
});
const $ = cheerio.load(response.data);
const list = $('div.articlecontent')
.map((_, item) => {
const link = $(item).find('a.bigTitle').attr('href');
return {
title: $(item).find('a.bigTitle').text(),
pubDate:
$(item)
.text()
.replace(/[ ]|[\r\n]/g, '')
.substr(-10) +
' ' +
hour +
':' +
minute,
description: $(item).find('a.bigTitle').text() + '<br><br>' + '点击标题,登录查看招聘详情',
link,
};
})
.get();
ctx.state.data = {
title: '大型招聘会',
link: 'http://job.hrbeu.edu.cn/HrbeuJY/web',
item: list,
allowEmpty: true,
};
};

View File

@@ -1,24 +1,19 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
const rootUrl = 'http://news.hrbeu.edu.cn';
module.exports = async (ctx) => {
const date = new Date();
const hour = date.getHours();
const minute = date.getMinutes();
const column = ctx.params.column;
const id = ctx.params.id || '';
let toUrl;
if (id !== '') {
toUrl = rootUrl.concat('/', column, '/', id, '.htm');
toUrl = `${rootUrl}/${column}/${id}.htm`;
} else {
toUrl = rootUrl.concat('/', column, '.htm');
toUrl = `${rootUrl}/${column}.htm`;
}
const response = await got({
method: 'get',
url: toUrl,
const response = await got(toUrl, {
headers: {
Referer: rootUrl,
},
@@ -33,7 +28,7 @@ module.exports = async (ctx) => {
const card = $('li.clearfix')
.map((_, item) => ({
title: $(item).find('div.list-right-tt').text(),
pubDate: $(item).find('span').text() + ' ' + hour + ':' + minute,
pubDate: parseDate($(item).find('.news-date-li').text(), 'DDYYYY-MM'),
link: $(item).find('a').attr('href'),
description: $(item).find('div.list-right-p').text(),
}))

View File

@@ -1,24 +1,19 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
const rootUrl = 'http://news.hrbeu.edu.cn';
module.exports = async (ctx) => {
const date = new Date();
const hour = date.getHours();
const minute = date.getMinutes();
const column = ctx.params.column;
const id = ctx.params.id || '';
let toUrl;
if (id !== '') {
toUrl = rootUrl.concat('/', column, '/', id, '.htm');
toUrl = `${rootUrl}/${column}/${id}.htm`;
} else {
toUrl = rootUrl.concat('/', column, '.htm');
toUrl = `${rootUrl}/${column}.htm`;
}
const response = await got({
method: 'get',
url: toUrl,
const response = await got(toUrl, {
headers: {
Referer: rootUrl,
},
@@ -33,15 +28,15 @@ module.exports = async (ctx) => {
const list = $('li.txt-elise')
.map((_, item) => {
let link = $(item).find('a').attr('href');
if (link.indexOf('info') !== -1 && id !== '') {
link = rootUrl.concat(link.substring(2));
if (link.includes('info') && id !== '') {
link = new URL(link, rootUrl).href;
}
if (link.indexOf('info') !== -1 && id === '') {
link = rootUrl.concat('/', link);
if (link.includes('info') && id === '') {
link = `${rootUrl}/${link}`;
}
return {
title: $(item).find('a').attr('title'),
pubDate: $(item).find('span').text() + ' ' + hour + ':' + minute,
pubDate: parseDate($(item).find('span').text()),
link,
};
})
@@ -50,15 +45,12 @@ module.exports = async (ctx) => {
const items = await Promise.all(
list.map((item) =>
ctx.cache.tryGet(item.link, async () => {
if (item.link.indexOf('info') !== -1) {
const detailResponse = await got({
method: 'get',
url: item.link,
});
if (item.link.includes('info')) {
const detailResponse = await got(item.link);
const content = cheerio.load(detailResponse.data);
item.description = content('div.v_news_content').html();
} else {
item.description = item.title + '<br><br>' + '本文需跳转,请点击标题后阅读';
item.description = '本文需跳转,请点击标题后阅读';
}
return item;
})

View File

@@ -0,0 +1,25 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
module.exports = async (ctx) => {
const response = await got('http://job.hrbeu.edu.cn/HrbeuJY/web');
const $ = cheerio.load(response.data);
const list = $('div.articlecontent')
.map((_, item) => ({
title: $(item).find('a.bigTitle').text(),
pubDate: parseDate($(item).find('p').eq(1).text().replace('时间:', '').trim()),
description: '点击标题,登录查看招聘详情',
link: $(item).find('a.bigTitle').attr('href'),
}))
.get();
ctx.state.data = {
title: '大型招聘会',
link: 'http://job.hrbeu.edu.cn/HrbeuJY/web',
item: list,
allowEmpty: true,
};
};

View File

@@ -11,10 +11,8 @@ module.exports = async (ctx) => {
month < 10 ? (strmMonth = '0' + month) : (strmMonth = month);
const day = date.getDate();
const response = await got({
method: 'post',
url: 'http://job.hrbeu.edu.cn/HrbeuJY/Web/Employ/QueryCalendar',
json: {
const response = await got('http://job.hrbeu.edu.cn/HrbeuJY/Web/Employ/QueryCalendar', {
searchParams: {
yearMonth: year + '-' + strmMonth,
},
}).json();
@@ -27,22 +25,16 @@ module.exports = async (ctx) => {
}
}
const todayResponse = await got({
method: 'get',
url: rootUrl.concat(link),
});
const todayResponse = await got(`${rootUrl}${link}`);
const $ = cheerio.load(todayResponse.data);
const list = $('li.clearfix')
.map((_, item) => {
const link = $(item).find('span.news_tit.news_tit_s').find('a').attr('href');
return {
title: $(item).find('span.news_tit.news_tit_s').find('a').attr('title'),
description: $(item).find('span.news_tit.news_tit_s').find('a').attr('title') + '<br><br>' + '点击标题,登录查看招聘详情',
link,
};
})
.map((_, item) => ({
title: $(item).find('span.news_tit.news_tit_s').find('a').attr('title'),
description: '点击标题,登录查看招聘详情',
link: $(item).find('span.news_tit.news_tit_s').find('a').attr('href'),
}))
.get();
ctx.state.data = {

View File

@@ -1,6 +1,7 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
const { finishArticleItem } = require('@/utils/wechat-mp');
const rootUrl = 'http://job.hrbeu.edu.cn';
const idMap = {
@@ -15,14 +16,9 @@ const idMap = {
};
module.exports = async (ctx) => {
const date = new Date();
const hour = date.getHours();
const minute = date.getMinutes();
const id = ctx.params.id;
const response = await got({
method: 'get',
url: idMap[id].url,
const response = await got(idMap[id].url, {
headers: {
Referer: rootUrl,
},
@@ -33,12 +29,12 @@ module.exports = async (ctx) => {
const list = $('li.list_item.i1')
.map((_, item) => {
let link = $(item).find('a').attr('href');
if (link.indexOf('HrbeuJY') !== -1) {
link = rootUrl.concat(link);
if (link.includes('HrbeuJY')) {
link = `${rootUrl}${link}`;
}
return {
title: $(item).find('a').attr('title'),
pubDate: $(item).find('.Article_PublishDate').text() + ' ' + hour + ':' + minute,
pubDate: parseDate($(item).find('.Article_PublishDate').text()),
link,
};
})
@@ -47,15 +43,14 @@ module.exports = async (ctx) => {
const items = await Promise.all(
list.map((item) =>
ctx.cache.tryGet(item.link, async () => {
if (item.link.indexOf('HrbeuJY') !== -1) {
const detailResponse = await got({
method: 'get',
url: item.link,
});
if (item.link.includes('HrbeuJY')) {
const detailResponse = await got(item.link);
const content = cheerio.load(detailResponse.data);
item.description = content('.article').html();
} else if (new URL(item.link).hostname === 'mp.weixin.qq.com') {
await finishArticleItem(ctx, item);
} else {
item.description = item.title + '<br><br>' + '本文需跳转,请点击标题后阅读';
item.description = '本文需跳转,请点击标题后阅读';
}
return item;
})

View File

@@ -1,8 +1,9 @@
module.exports = {
'/yjsy/list/:id': ['Derekmini'],
'/job/bigemploy': ['Derekmini'],
'/job/calendar': ['Derekmini'],
'/job/list/:id': ['Derekmini'],
'/gx/:type/:colume/:id?': ['Derekmini'],
'/uae/list/:id': ['Derekmini'],
'/ugs/news/:author?/:category?': ['XYenon'],
'/yjsy/list/:id': ['Derekmini'],
};

View File

@@ -6,7 +6,7 @@ module.exports = {
title: '研究生院',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:id/list.htm',
target: '/heu/yjsy/list/:id',
target: '/hrbeu/yjsy/list/:id',
},
],
job: [
@@ -14,25 +14,25 @@ module.exports = {
title: '大型招聘会',
docs: 'https://docs.rsshub.app/journal.html#ha-er-bin-gong-cheng-da-xue',
source: '/*',
target: '/heu/job/bigemploy',
target: '/hrbeu/job/bigemploy',
},
{
title: '今日招聘会',
docs: 'https://docs.rsshub.app/journal.html#ha-er-bin-gong-cheng-da-xue',
source: '/*',
target: '/heu/job/calendar',
target: '/hrbeu/job/calendar',
},
{
title: '就业服务平台-通知公告',
docs: 'https://docs.rsshub.app/journal.html#ha-er-bin-gong-cheng-da-xue',
source: '/*',
target: '/heu/job/list/tzgg',
target: '/hrbeu/job/list/tzgg',
},
{
title: '就业服务平台-热点新闻',
docs: 'https://docs.rsshub.app/journal.html#ha-er-bin-gong-cheng-da-xue',
source: '/*',
target: '/heu/job/list/rdxw',
target: '/hrbeu/job/list/rdxw',
},
],
news: [
@@ -40,25 +40,25 @@ module.exports = {
title: '工学',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:column',
target: (params) => `/heu/gx/list/${params.column.replace('.htm', '')}`,
target: (params) => `/hrbeu/gx/list/${params.column.replace('.htm', '')}`,
},
{
title: '工学',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:column/:id',
target: (params) => `/heu/gx/list/${params.column}/${params.id.replace('.htm', '')}`,
target: (params) => `/hrbeu/gx/list/${params.column}/${params.id.replace('.htm', '')}`,
},
{
title: '工学-card',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:column',
target: (params) => `/heu/gx/card/${params.column.replace('.htm', '')}`,
target: (params) => `/hrbeu/gx/card/${params.column.replace('.htm', '')}`,
},
{
title: '工学-card',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:column/:id',
target: (params) => `/heu/gx/card/${params.column}/${params.id.replace('.htm', '')}`,
target: (params) => `/hrbeu/gx/card/${params.column}/${params.id.replace('.htm', '')}`,
},
],
uae: [
@@ -66,7 +66,15 @@ module.exports = {
title: '水声学院',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:id/list.htm',
target: '/heu/uae/list/:id',
target: '/hrbeu/uae/list/:id',
},
],
ugs: [
{
title: '本科生院工作通知',
docs: 'https://docs.rsshub.app/university.html#ha-er-bin-gong-cheng-da-xue',
source: '/:author/list.htm',
target: '/hrbeu/ugs/news/:author',
},
],
},

View File

@@ -1,9 +1,10 @@
module.exports = function (router) {
router.get('/yjsy/list/:id', require('./yjsy/list'));
router.get('/job/bigemploy', require('./job/bigemploy'));
router.get('/job/calendar', require('./job/calendar'));
router.get('/job/list/:id', require('./job/list'));
router.get('/gx/list/:column/:id?', require('./gx/list'));
router.get('/gx/card/:column/:id?', require('./gx/card'));
router.get('/gx/list/:column/:id?', require('./gx/list'));
router.get('/uae/list/:id', require('./uae/list'));
router.get('/ugs/news/:author?/:category?', require('./ugs/news'));
router.get('/yjsy/list/:id', require('./yjsy/list'));
};

View File

@@ -1,17 +1,13 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
const { finishArticleItem } = require('@/utils/wechat-mp');
const rootUrl = 'http://uae.hrbeu.edu.cn';
module.exports = async (ctx) => {
const date = new Date();
const hour = date.getHours();
const minute = date.getMinutes();
const id = ctx.params.id;
const response = await got({
method: 'get',
url: rootUrl.concat('/', id, '/list.htm'),
const response = await got(`${rootUrl}/${id}/list.htm`, {
headers: {
Referer: rootUrl,
},
@@ -24,12 +20,12 @@ module.exports = async (ctx) => {
const list = $('a.column-news-item')
.map((_, item) => {
let link = $(item).attr('href');
if (link.indexOf('page.htm') !== -1) {
link = rootUrl.concat(link);
if (link.includes('page.htm')) {
link = `${rootUrl}${link}`;
}
return {
title: $(item).find('span.column-news-title').text(),
pubDate: $(item).find('span.column-news-date').text() + ' ' + hour + ':' + minute,
pubDate: parseDate($(item).find('span.column-news-date').text()),
link,
};
})
@@ -38,16 +34,15 @@ module.exports = async (ctx) => {
const items = await Promise.all(
list.map((item) =>
ctx.cache.tryGet(item.link, async () => {
if (item.link.indexOf('page.htm') !== -1) {
const detailResponse = await got({
method: 'get',
url: item.link,
});
if (item.link.includes('page.htm')) {
const detailResponse = await got(item.link);
const content = cheerio.load(detailResponse.data);
item.description = content('div.wp_articlecontent').html();
item.title = content('h1.arti-title').text();
} else if (new URL(item.link).hostname === 'mp.weixin.qq.com') {
await finishArticleItem(ctx, item);
} else {
item.description = item.title + '<br><br>' + '本文需跳转,请点击标题后阅读';
item.description = '本文需跳转,请点击标题后阅读';
}
return item;
})
@@ -56,7 +51,7 @@ module.exports = async (ctx) => {
ctx.state.data = {
title: '水声学院-' + bigTitle,
link: rootUrl.concat('/', id, '/list.htm'),
link: `${rootUrl}/${id}/list.htm`,
item: items,
};
};

98
lib/v2/hrbeu/ugs/news.js Normal file
View File

@@ -0,0 +1,98 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
const baseUrl = 'http://ugs.hrbeu.edu.cn';
const authorMap = {
gztz: {
all: '/2821',
},
jwc: {
all: '/jwc',
jxap: '/2847',
ksgl: '/2895',
xjgl: '/2902',
wytk: '/2897',
cjgl: '/2901',
},
sjjxyjlc: {
all: '/3206',
syjx: '/2847',
sysjs: '/sysjs',
xwsx: '/2909',
xwlw: '/2910',
kcsj: '/2911',
cxcy: '/2913',
xjjl: '/xjjl',
},
jypgc: {
all: '/3207',
jxyjyjxcg: '/2916',
zljk: '/2917',
},
zyjsc: {
all: '/3208',
zyyjcjs: '/2914',
cgsyb: '/2925',
jxmsyyxzjjs: '/2918',
ktjs: '/2919',
syjx: '/2920',
},
gjdxswhszjd: {
all: '/3209',
},
jsjxfzzx: {
all: '/3210',
jspx: '/2915',
},
zhbgs: {
all: '/3211',
lxkc: '/lxkc',
},
};
module.exports = async (ctx) => {
const author = ctx.params.author || 'gztz';
const category = ctx.params.category || 'all';
const link = baseUrl + authorMap[author][category] + '/list.htm';
const response = await got(link, {
headers: {
Referer: baseUrl,
},
});
const $ = cheerio.load(response.data);
const list = $('.wp_article_list_table .border9')
.toArray()
.map((e) => {
e = $(e);
return {
title: e.find('a').attr('title'),
link: new URL(e.find('a').attr('href'), baseUrl).href,
pubDate: parseDate(e.find('.date').text()),
};
});
const out = await Promise.all(
list.map((item) =>
ctx.cache.tryGet(item.link, async () => {
if (item.link.includes('.htm')) {
const response = await got(item.link);
const $ = cheerio.load(response.data);
item.description = $('.wp_articlecontent').html().trim();
} else {
item.description = '此链接为文件,请点击下载';
}
return item;
})
)
);
ctx.state.data = {
title: '哈尔滨工程大学本科生院工作通知',
link,
item: out,
};
};

View File

@@ -1,17 +1,12 @@
const got = require('@/utils/got');
const cheerio = require('cheerio');
const { parseDate } = require('@/utils/parse-date');
const rootUrl = 'http://yjsy.hrbeu.edu.cn';
module.exports = async (ctx) => {
const date = new Date();
const hour = date.getHours();
const minute = date.getMinutes();
const id = ctx.params.id;
const response = await got({
method: 'get',
url: rootUrl.concat('/', id, '/list.htm'),
const response = await got(`${rootUrl}/${id}/list.htm`, {
headers: {
Referer: rootUrl,
},
@@ -28,12 +23,12 @@ module.exports = async (ctx) => {
const list = $('li.list_item')
.map((_, item) => {
let link = $(item).find('a').attr('href');
if (link.indexOf('page.htm') !== -1) {
link = rootUrl.concat(link);
if (link.includes('page.htm')) {
link = `${rootUrl}${link}`;
}
return {
title: $(item).find('a').attr('title'),
pubDate: $(item).find('span.Article_PublishDate').text() + ' ' + hour + ':' + minute,
pubDate: parseDate($(item).find('span.Article_PublishDate').text()),
link,
};
})
@@ -42,15 +37,12 @@ module.exports = async (ctx) => {
const items = await Promise.all(
list.map((item) =>
ctx.cache.tryGet(item.link, async () => {
if (item.link.indexOf('page.htm') !== -1) {
const detailResponse = await got({
method: 'get',
url: item.link,
});
if (item.link.includes('page.htm')) {
const detailResponse = await got(item.link);
const content = cheerio.load(detailResponse.data);
item.description = content('div.wp_articlecontent').html();
} else {
item.description = item.title + '<br><br>' + '本文需跳转,请点击标题后阅读';
item.description = '本文需跳转,请点击标题后阅读';
}
return item;
})