【引言】展示的Github贡献日历分为前端和后端

  1. 前端

    【hexo-githubcalendar】

image-20250624211616206

在博客上主页显示的效果是这样的

在hexo文件夹下运行下面代码

npm i hexo-githubcalendar --save
# 或者
cnpm i hexo-githubcalendar --save

注意,一定要加--save,不然本地预览的时候可能不会显示!!!

第二步

修改hexo根目录下的_config.yml文件,这是我的模板,根据需要修改,在文件末尾插入即可

githubcalendar:
enable: true
enable_page: /
user: # 你的GitHub名字
layout:
type: id
name: recent-posts
index: 0
githubcalendar_html: '<div class="recent-post-item" style="width:100%;height:auto;padding:10px;"><div id="github_loading" style="width:10%;height:100%;margin:0 auto;display: block"><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 50 50" style="enable-background:new 0 0 50 50" xml:space="preserve"><path fill="#d0d0d0" d="M25.251,6.461c-10.318,0-18.683,8.365-18.683,18.683h4.068c0-8.071,6.543-14.615,14.615-14.615V6.461z" transform="rotate(275.098 25 25)"><animateTransform attributeType="xml" attributeName="transform" type="rotate" from="0 25 25" to="360 25 25" dur="0.6s" repeatCount="indefinite"></animateTransform></path></svg></div><div id="github_container"></div></div>'
pc_minheight: 280px
mobile_minheight: 0px
# 这里我自己调了几种颜色根据需要修改
# color: "['#ebedf0', '#fdcdec', '#fc9bd9', '#fa6ac5', '#f838b2', '#f5089f', '#c4067e', '#92055e', '#540336', '#48022f', '#30021f']" #基佬紫色
# color: "['#e4dfd7', '#f9f4dc', '#f7e8aa', '#f7e8aa', '#f8df72', '#fcd217', '#fcc515', '#f28e16', '#fb8b05', '#d85916', '#f43e06']" #橘黄色调
# color: "['#ebedf0', '#f0fff4', '#dcffe4', '#bef5cb', '#85e89d', '#34d058', '#28a745', '#22863a', '#176f2c', '#165c26', '#144620']" #翠绿色调
color: "['#ebedf0', '#f1f8ff', '#dbedff', '#c8e1ff', '#79b8ff', '#2188ff', '#0366d6', '#005cc5', '#044289', '#032f62', '#05264c']" #天青色调
api: https://cdn.jsdelivr.net/gh/你的GitHub Action文件路径.json #至于方法请继续阅读文章的后端的配置方法!
#URL 例子 https://cdn.jsdelivr.net/gh/Yeely0162/blog-img/github_contributions_Yeely0162.json
calendar_js: /js/hexo_githubcalendar.js #建议插入本地的js文件防止跑不动
plus_style: ""

[!TIP]

hexo_githubcalendar.js请将该文件保存在本地当中!

路径为 Hexo\themes\你的主题名字(默认landscape)\source\js

  1. 后端

我看了很多关于博主的文章都是说申请个自己的api或者跑云端脚本,但是大家都忽略了一件事!

Github可以跑Action!!!
Github可以跑Action!!!
Github可以跑Action!!!

我们只需要弄一个库就可以跑Action了

开始实践

  1. 首先需要一个Github账号!

  2. 创建一个任意的库!然后git clone 库到本地!

  3. 上传文件

image-20250624213635693

上传图中三个部分的内容

  1. .github/workflows 目录下放main.yml文件

[!NOTE]

请自己创立文件夹和保存相关文件,代码main.yml文件内容如下

name: Update GitHub Contributions #不喜欢这个名字可以自己Custom

on:
workflow_dispatch: # 允许手动触发
schedule:
- cron: '0 12 * * *' # 每天UTC时间12:00运行(北京时间20:00)

permissions:
contents: write # 确保有写入权限

jobs:
build:
runs-on: ubuntu-latest

steps:
- name: Checkout repository
uses: actions/checkout@v2

- name: Set up Python
uses: actions/setup-python@v2
with:
python-version: '3.10'

- name: Install dependencies
run: pip install -r requirements.txt

- name: Run script
run: python Github_contributions.py

- name: add and change
run: |
git config --global user.name 'GitHub Action'
git config --global user.email 'action@github.com'
git add github_contributions_*.json # 添加生成的文件 ,不喜欢此命名请自己修改
git commit -m "Update Github Contribution [action]" || echo "No changes to commit"
continue-on-error: true

- name: Push changes
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: git push origin main

  1. 上传Github_contributions.py 文件

    [!NOTE]

    请自行修改里面的ID参数修改成自己的ID号码

    # -*- coding: UTF-8 -*-
    import requests
    import re
    from http.server import BaseHTTPRequestHandler
    import json

    def list_split(items, n):
    return [items[i:i + n] for i in range(0, len(items), n)]
    def getdata(name):

    # 2024-03-29 定义 headers 请求头
    # 请见 https://github.com/yuhengwei2001/python_github_calendar_api/commit/0f37cfc003f09e99a1892602d8bc2b38137899d2#diff-b014e93fcab9bae29f453d7a616da5eac2f02947f32d02a1a1bf200eeaab5a39L11
    headers = {
    'Referer': 'https://github.com/'+ name,
    'Sec-Ch-Ua': '"Chromium";v="122", "Not(A:Brand";v="24", "Microsoft Edge";v="122"',
    'Sec-Ch-Ua-Mobile': '?0',
    'Sec-Ch-Ua-Platform': '"Windows"',
    'Sec-Fetch-Dest': 'empty',
    'Sec-Fetch-Mode': 'cors',
    'Sec-Fetch-Site': 'same-origin',
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Safari/537.36 Edg/122.0.0.0',
    'X-Requested-With': 'XMLHttpRequest'
    }
    # 发送请求时添加 headers 请求头
    # gitpage = requests.get("https://github.com/" + name)
    gitpage = requests.get("https://github.com/" + name + "?action=show&controller=profiles&tab=contributions&user_id="+ name, headers=headers)
    data = gitpage.text

    # 2023-11-22 更新正则 https://github.com/Zfour/python_github_calendar_api/issues/18
    datadatereg = re.compile(r'data-date="(.*?)" id="contribution-day-component')
    datacountreg = re.compile(r'<tool-tip .*?class="sr-only position-absolute">(.*?) contribution')

    datadate = datadatereg.findall(data)
    datacount = datacountreg.findall(data)
    datacount = list(map(int, [0 if i == "No" else i for i in datacount]))

    # 检查datadate和datacount是否为空
    if not datadate or not datacount:
    # 处理空数据情况
    return {"total": 0, "contributions": []}

    # 将datadate和datacount按照字典序排序
    sorted_data = sorted(zip(datadate, datacount))
    datadate, datacount = zip(*sorted_data)

    contributions = sum(datacount)
    datalist = []
    for index, item in enumerate(datadate):
    itemlist = {"date": item, "count": datacount[index]}
    datalist.append(itemlist)
    datalistsplit = list_split(datalist, 7)
    returndata = {
    "total": contributions,
    "contributions": datalistsplit
    }
    return returndata
    class handler(BaseHTTPRequestHandler):
    def do_GET(self):
    # 2024-03-15 规范接口的传参方式 https://github.com/Zfour/python_github_calendar_api/issues/20#issuecomment-1999115747
    path = self.path
    spl=path.split('?')[1:]
    for kv in spl:
    key,user=kv.split("=")
    if key=="user": break
    data = getdata(user)
    self.send_response(200)
    self.send_header('Access-Control-Allow-Origin', '*')
    self.send_header('Content-type', 'application/json')
    self.end_headers()
    self.wfile.write(json.dumps(data).encode('utf-8'))
    return
    if __name__ == "__main__":
    # 方式1:直接指定用户名 !!!!!!!!!!!!!!!!Custom here!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
    username = "Github user name" # 替换为实际的GitHub用户名
    #!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!Custom here!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

    print(f"正在获取 {username} 的贡献数据...")
    data = getdata(username)

    # 保存到JSON文件
    filename = f"github_contributions_{username}.json"
    with open(filename, 'w', encoding='utf-8') as f:
    json.dump(data, f, ensure_ascii=False, indent=2)

    print(f"数据已保存到 {filename}")
    print(f"总贡献数: {data['total']}")
  2. 还有requirements.txt文件

certifi==2020.12.5
chardet==4.0.0
idna==2.10
requests==2.25.1
urllib3==1.26.2

上述操作完成即可运行Action!

image-20250624214828159

image-20250624214907454

等待运行完成就可以啦!

根据自己的实际路径自定义获取json的URL,然后粘贴到上述配置_config->githubcalendar(函数)->api即可

获取到的内容如下

image-20250624215146382