Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 22 additions & 0 deletions .github/workflows/check_status.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
name: Daily Site Check
on:
schedule:
- cron: '0 0,8,16 * * *' # 每天 UTC 0点、8点、16点各运行一次(分钟=0)
workflow_dispatch: # 支持手动触发

jobs:
monitor:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: "3.10"
- name: Install dependencies
run: pip install requests notion-client python-dateutil
- name: Run Check
env:
NOTION_TOKEN: ${{ secrets.NOTION_TOKEN }}
DATABASE_ID: ${{ secrets.DATABASE_ID }}
run: python links_check_status.py
2 changes: 1 addition & 1 deletion conf/post.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ module.exports = {

POST_TITLE_ICON: process.env.NEXT_PUBLIC_POST_TITLE_ICON || true, // 是否显示标题icon
POST_DISABLE_GALLERY_CLICK:
process.env.NEXT_PUBLIC_POST_DISABLE_GALLERY_CLICK || false, // 画册视图禁止点击,方便在友链页面的画册插入链接
process.env.NEXT_PUBLIC_POST_DISABLE_GALLERY_CLICK || true, // 画廊视图禁止点击,方便在友链页面的画廊中插入链接,可参考 https://66619.eu.org/article/auto-links 进行设置
POST_LIST_STYLE: process.env.NEXT_PUBLIC_POST_LIST_STYLE || 'page', // ['page','scroll] 文章列表样式:页码分页、单页滚动加载
POST_LIST_PREVIEW: process.env.NEXT_PUBLIC_POST_PREVIEW || 'false', // 是否在列表加载文章预览
POST_PREVIEW_LINES: process.env.NEXT_PUBLIC_POST_POST_PREVIEW_LINES || 12, // 预览博客行数
Expand Down
96 changes: 96 additions & 0 deletions links_check_status.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
import os
import requests
import time
from datetime import datetime, timedelta
from notion_client import Client

notion = Client(auth=os.environ["NOTION_TOKEN"])
database_id = os.environ["DATABASE_ID"]

def check_site(url):
try:
start_time = time.time()
response = requests.get(url, timeout=15, allow_redirects=True)
end_time = time.time()
open_time_sec = round(end_time - start_time, 2)
# 只要能响应就判正常,且只在有实际响应时显示时间
return (
f"状态:✅正常({open_time_sec}s)" if open_time_sec > 0 else "状态:✅正常",
open_time_sec if open_time_sec > 0 else None
)
except requests.exceptions.Timeout:
return "状态:❓不可用", None
except requests.exceptions.ConnectionError as e:
err_str = str(e).lower()
# 只要是明显的DNS错误或无法建立连接才算不可用
if (
"dns" in err_str
or "name or service not known" in err_str
or "nodename nor servname provided" in err_str
or "failed to establish a new connection" in err_str
or "connection refused" in err_str
):
return "状态:❓不可用", None
# 其它连接问题也报正常,不显示时间
return "状态:✅正常", None
except Exception:
# 其它所有异常都算正常,不显示时间
return "状态:✅正常", None

def update_status():
cursor = None
while True:
query = notion.databases.query(
database_id,
start_cursor=cursor,
page_size=50,
filter={"property": "URL-TEXT", "url": {"is_not_empty": True}}
)
pages = query.get("results")
for page in pages:
page_id = page["id"]
url_property = page["properties"]["URL-TEXT"]["url"]

homepage_cover = page["properties"].get("主页链接", {}).get("url")
avatar_icon = page["properties"].get("头像链接", {}).get("url")

update_payload = {
"properties": {}
}

new_status, open_time_sec = check_site(url_property)

utc_now = datetime.utcnow()
beijing_time = utc_now + timedelta(hours=8)
formatted_time = beijing_time.strftime("%Y-%m-%d %H:%M")
last_check_text = f"于 {formatted_time} 自动检测~"

update_payload["properties"]["Status"] = {"select": {"name": new_status}}
update_payload["properties"]["LAST-CHECK"] = {"rich_text": [{"text": {"content": last_check_text}}]}
if open_time_sec is not None:
update_payload["properties"]["OPEN-TIME"] = {"number": open_time_sec}
else:
update_payload["properties"]["OPEN-TIME"] = {"number": None}

if homepage_cover:
update_payload["cover"] = {
"type": "external",
"external": {"url": homepage_cover}
}
print(f"设置封面: {homepage_cover}")
if avatar_icon:
update_payload["icon"] = {
"type": "external",
"external": {"url": avatar_icon}
}
print(f"设置图标: {avatar_icon}")

notion.pages.update(page_id, **update_payload)
print(f"更新: {url_property} → {new_status} | {last_check_text}")
time.sleep(0.5)
if not query.get("has_more"):
break
cursor = query.get("next_cursor")

if __name__ == "__main__":
update_status()