mirror of
https://github.com/DIYgod/RSSHub.git
synced 2026-09-24 23:12:34 +08:00
feat: add air quality content in qweather 3days forecast feed (#14136)
* feat: add air quality content in qweather 3days report feed * chore: title enhancement * fix: resolve no needed lines * fix: add guard for api key config
This commit is contained in:
+47
-20
@@ -2,45 +2,72 @@ const got = require('@/utils/got');
|
||||
const { art } = require('@/utils/render');
|
||||
const path = require('path');
|
||||
const config = require('@/config').value;
|
||||
const rootUrl = 'https://devapi.qweather.com/v7/weather/3d?';
|
||||
|
||||
const WEATHER_API = 'https://devapi.qweather.com/v7/weather/3d';
|
||||
const AIR_QUALITY_API = 'https://devapi.qweather.com/v7/air/5d';
|
||||
const CIRY_LOOKUP_API = 'https://geoapi.qweather.com/v2/city/lookup';
|
||||
const author = 'QWeather';
|
||||
|
||||
module.exports = async (ctx) => {
|
||||
if (!config.hefeng.key) {
|
||||
throw Error('QWeather RSS is disabled due to the lack of <a href="https://docs.rsshub.app/zh/install/config#%E5%92%8C%E9%A3%8E%E5%A4%A9%E6%B0%94">relevant config</a>');
|
||||
}
|
||||
const id = await ctx.cache.tryGet(ctx.params.location + '_id', async () => {
|
||||
const response = await got(`https://geoapi.qweather.com/v2/city/lookup?location=${ctx.params.location}&key=${config.hefeng.key}`);
|
||||
const data = [];
|
||||
for (const i in response.data.location) {
|
||||
data.push(response.data.location[i]);
|
||||
}
|
||||
return data[0].id;
|
||||
const response = await got(`${CIRY_LOOKUP_API}?location=${ctx.params.location}&key=${config.hefeng.key}`);
|
||||
return response.data.location[0].id;
|
||||
});
|
||||
const requestUrl = rootUrl + 'key=' + config.hefeng.key + '&location=' + id;
|
||||
const responseData = await ctx.cache.tryGet(
|
||||
const weatherData = await ctx.cache.tryGet(
|
||||
ctx.params.location,
|
||||
async () => {
|
||||
const response = await got(requestUrl);
|
||||
const response = await got(`${WEATHER_API}?key=${config.hefeng.key}&location=${id}`);
|
||||
return response.data;
|
||||
},
|
||||
config.cache.contentExpire,
|
||||
false
|
||||
);
|
||||
const data = [];
|
||||
for (const i in responseData.daily) {
|
||||
data.push(responseData.daily[i]);
|
||||
}
|
||||
const items = data.map((item) => ({
|
||||
title: `${item.fxDate}: ${item.textDay === item.textNight ? item.textDay : item.textDay + '转' + item.textNight}`,
|
||||
const airQualityData = await ctx.cache.tryGet(
|
||||
`qweather:air:${ctx.params.location}`,
|
||||
async () => {
|
||||
const airQualityResponse = await got(`${AIR_QUALITY_API}?location=${id}&key=${config.hefeng.key}`);
|
||||
return airQualityResponse.data;
|
||||
},
|
||||
config.cache.contentExpire,
|
||||
false
|
||||
);
|
||||
// merge weather data with air quality data
|
||||
const combined = {
|
||||
updateTime: weatherData.updateTime,
|
||||
fxLink: weatherData.fxLink,
|
||||
daily: weatherData.daily.map((weatherItem) => {
|
||||
const dailyAirQuality = airQualityData.daily.find((airQualityItem) => airQualityItem.fxDate === weatherItem.fxDate);
|
||||
if (dailyAirQuality) {
|
||||
return {
|
||||
...weatherItem,
|
||||
aqi: dailyAirQuality.aqi,
|
||||
aqiLevel: dailyAirQuality.level,
|
||||
aqiCategory: dailyAirQuality.category,
|
||||
aqiPrimary: dailyAirQuality.primary,
|
||||
};
|
||||
}
|
||||
return weatherItem;
|
||||
}),
|
||||
};
|
||||
const items = combined.daily.map((item) => ({
|
||||
title: `${item.fxDate}: ${item.textDay === item.textNight ? item.textDay : item.textDay + '转' + item.textNight} ${item.tempMin}~${item.tempMax}℃`,
|
||||
description: art(path.join(__dirname, 'templates/3days.art'), {
|
||||
item,
|
||||
}),
|
||||
pubDate: responseData.updateTime,
|
||||
pubDate: combined.updateTime,
|
||||
guid: '位置:' + ctx.params.location + '--日期:' + item.fxDate,
|
||||
link: responseData.fxLink,
|
||||
link: combined.fxLink,
|
||||
author,
|
||||
}));
|
||||
|
||||
ctx.state.data = {
|
||||
title: ctx.params.location + '未来三天天气',
|
||||
description: ctx.params.location + '未来三天天气情况,使用和风彩云api',
|
||||
description: ctx.params.location + '未来三天天气情况,使用和风彩云 API (包括空气质量)',
|
||||
item: items,
|
||||
link: responseData.fxLink,
|
||||
link: combined.fxLink,
|
||||
author,
|
||||
};
|
||||
};
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
module.exports = {
|
||||
'/3days/:location': ['Rein-Ou'],
|
||||
'/3days/:location': ['Rein-Ou', 'la3rence'],
|
||||
'/now/:location': ['Rein-Ou'],
|
||||
};
|
||||
|
||||
@@ -4,6 +4,8 @@
|
||||
<br>
|
||||
<text>相对湿度:{{item.humidity}}%</text>
|
||||
<br>
|
||||
<text>空气质量指数:{{item.aqi}} ({{item.aqiCategory}})</text>
|
||||
<br>
|
||||
<text>大气压强:{{item.pressure}}百帕</text>
|
||||
<br>
|
||||
<text>紫外线强度:{{item.uvIndex}}</text>
|
||||
|
||||
Reference in New Issue
Block a user