Skip to content

Commit 42b44b8

Browse files
committed
Add dependency installation step and update AtCoder statistics fetching logic
1 parent 6a4c0b6 commit 42b44b8

4 files changed

Lines changed: 56 additions & 23 deletions

File tree

.github/workflows/update-stats.yml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,11 @@ jobs:
2020
uses: actions/setup-python@v5
2121
with:
2222
python-version: '3.12'
23+
24+
- name: Install dependencies
25+
run: |
26+
python3 -m pip install --upgrade pip
27+
pip install -r requirements.txt
2328
2429
- name: Fetch latest statistics and update README
2530
id: fetch_stats

README.md

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
# 🏆 Problem Solving Statistics
44

55
[![Last Updated](https://img.shields.io/badge/Last%20Updated-15%20January%202026-blue?style=for-the-badge)](https://github.com/MishkatIT/ProblemSolvingStats)
6-
[![Total Problems](https://img.shields.io/badge/Total%20Solved-4063-success?style=for-the-badge&logo=leetcode)](https://github.com/MishkatIT/ProblemSolvingStats)
6+
[![Total Problems](https://img.shields.io/badge/Total%20Solved-4220-success?style=for-the-badge&logo=leetcode)](https://github.com/MishkatIT/ProblemSolvingStats)
77
[![Platforms](https://img.shields.io/badge/Platforms-12-orange?style=for-the-badge)](https://github.com/MishkatIT/ProblemSolvingStats)
88

99
<!-- UPDATE_METADATA_START -->
@@ -36,49 +36,49 @@
3636
<td><strong>🔴 Codeforces</strong></td>
3737
<td><a href="https://codeforces.com/profile/MishkatIT">MishkatIT</a></td>
3838
<td align="center"><strong>2386 <br/><small>(last updated: 15 January 2026)</small></strong></td>
39-
<td><img src="https://img.shields.io/badge/Progress-58.7%25-red?style=flat-square" alt="Codeforces Progress"/></td>
39+
<td><img src="https://img.shields.io/badge/Progress-56.5%25-red?style=flat-square" alt="Codeforces Progress"/></td>
4040
</tr>
4141
<tr>
4242
<td><strong>🟢 LeetCode</strong></td>
4343
<td><a href="https://leetcode.com/MishkatIT/">MishkatIT</a></td>
4444
<td align="center"><strong>412 <br/><small>(last updated: 15 January 2026)</small></strong></td>
45-
<td><img src="https://img.shields.io/badge/Progress-10.1%25-yellow?style=flat-square" alt="LeetCode Progress"/></td>
45+
<td><img src="https://img.shields.io/badge/Progress-9.8%25-yellow?style=flat-square" alt="LeetCode Progress"/></td>
4646
</tr>
4747
<tr>
4848
<td><strong>🟣 Vjudge</strong></td>
4949
<td><a href="https://vjudge.net/user/MishkatIT">MishkatIT</a></td>
5050
<td align="center"><strong>400 <br/><small>(last updated: 15 January 2026)</small></strong></td>
51-
<td><img src="https://img.shields.io/badge/Progress-9.8%25-blueviolet?style=flat-square" alt="Vjudge Progress"/></td>
51+
<td><img src="https://img.shields.io/badge/Progress-9.5%25-blueviolet?style=flat-square" alt="Vjudge Progress"/></td>
5252
</tr>
5353
<tr>
5454
<td><strong>🟠 AtCoder</strong></td>
5555
<td><a href="https://atcoder.jp/users/MishkatIT">MishkatIT</a></td>
56-
<td align="center"><strong>0 <br/><small>(last updated: 15 January 2026)</small></strong></td>
57-
<td><img src="https://img.shields.io/badge/Progress-0.0%25-orange?style=flat-square" alt="AtCoder Progress"/></td>
56+
<td align="center"><strong>157 <br/><small>(last updated: 15 January 2026)</small></strong></td>
57+
<td><img src="https://img.shields.io/badge/Progress-3.7%25-orange?style=flat-square" alt="AtCoder Progress"/></td>
5858
</tr>
5959
<tr>
6060
<td><strong>🟤 CodeChef</strong></td>
6161
<td><a href="https://www.codechef.com/users/MishkatIT">MishkatIT</a></td>
6262
<td align="center"><strong>124 <br/><small>(last updated: 15 January 2026)</small></strong></td>
63-
<td><img src="https://img.shields.io/badge/Progress-3.1%25-brown?style=flat-square" alt="CodeChef Progress"/></td>
63+
<td><img src="https://img.shields.io/badge/Progress-2.9%25-brown?style=flat-square" alt="CodeChef Progress"/></td>
6464
</tr>
6565
<tr>
6666
<td><strong>⚪ CSES</strong></td>
6767
<td><a href="https://cses.fi/user/165802/">MishkatIT</a></td>
6868
<td align="center"><strong>121 <br/><small>(last updated: 15 January 2026)</small></strong></td>
69-
<td><img src="https://img.shields.io/badge/Progress-3.0%25-lightgray?style=flat-square" alt="CSES Progress"/></td>
69+
<td><img src="https://img.shields.io/badge/Progress-2.9%25-lightgray?style=flat-square" alt="CSES Progress"/></td>
7070
</tr>
7171
<tr>
7272
<td><strong>🔵 Toph</strong></td>
7373
<td><a href="https://toph.co/u/MishkatIT">MishkatIT</a></td>
7474
<td align="center"><strong>543 <br/><small>(last updated: 15 January 2026)</small></strong></td>
75-
<td><img src="https://img.shields.io/badge/Progress-13.4%25-blue?style=flat-square" alt="Toph Progress"/></td>
75+
<td><img src="https://img.shields.io/badge/Progress-12.9%25-blue?style=flat-square" alt="Toph Progress"/></td>
7676
</tr>
7777
<tr>
7878
<td><strong>🟡 LightOJ</strong></td>
7979
<td><a href="https://lightoj.com/user/mishkatit">MishkatIT</a></td>
8080
<td align="center"><strong>31 <br/><small>(last updated: 15 January 2026)</small></strong></td>
81-
<td><img src="https://img.shields.io/badge/Progress-0.8%25-yellow?style=flat-square" alt="LightOJ Progress"/></td>
81+
<td><img src="https://img.shields.io/badge/Progress-0.7%25-yellow?style=flat-square" alt="LightOJ Progress"/></td>
8282
</tr>
8383
<tr>
8484
<td><strong>🟩 SPOJ</strong></td>
@@ -108,7 +108,7 @@
108108
<tfoot>
109109
<tr>
110110
<td colspan="2" align="center"><strong>🎖️ TOTAL</strong></td>
111-
<td align="center"><strong style="font-size: 1.2em;">4063</strong></td>
111+
<td align="center"><strong style="font-size: 1.2em;">4220</strong></td>
112112
<td align="center"><strong>100%</strong></td>
113113
</tr>
114114
</tfoot>

requirements.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
requests>=2.31.0

update_stats.py

Lines changed: 39 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -236,20 +236,47 @@ def get_vjudge(self):
236236
def get_atcoder(self):
237237
"""Fetch AtCoder statistics."""
238238
try:
239-
# Try API first
240-
# Note: API uses lowercase username as shown in the API documentation
241-
url = "https://kenkoooo.com/atcoder/atcoder-api/v3/user/submissions?user=mishkatit&from_second=0"
242-
data = self.fetch_url(url, use_api=True)
243-
244-
if data and isinstance(data, list):
245-
# Count unique problems with AC (Accepted) result
239+
# Try API first (requests handles gzip/deflate reliably)
240+
# Note: API expects lowercase username
241+
try:
242+
import requests
243+
244+
url = "https://kenkoooo.com/atcoder/atcoder-api/v3/user/submissions"
245+
user = "mishkatit"
246+
246247
solved = set()
247-
for sub in data:
248-
if isinstance(sub, dict) and sub.get('result') == 'AC' and sub.get('problem_id'):
249-
solved.add(sub['problem_id'])
248+
from_second = 0
249+
250+
# The API supports incremental fetching via from_second.
251+
# Some environments may get truncated responses; loop defensively.
252+
with requests.Session() as session:
253+
for _ in range(50):
254+
res = session.get(url, params={"user": user, "from_second": from_second}, timeout=30)
255+
res.raise_for_status()
256+
batch = res.json()
257+
258+
if not isinstance(batch, list) or not batch:
259+
break
260+
261+
max_epoch = None
262+
for sub in batch:
263+
if not isinstance(sub, dict):
264+
continue
265+
if sub.get('result') == 'AC' and sub.get('problem_id'):
266+
solved.add(sub['problem_id'])
267+
epoch = sub.get('epoch_second')
268+
if isinstance(epoch, int):
269+
max_epoch = epoch if max_epoch is None else max(max_epoch, epoch)
270+
271+
if max_epoch is None or max_epoch < from_second:
272+
break
273+
from_second = max_epoch + 1
274+
250275
count = len(solved)
251-
if 0 < count < self.MAX_REASONABLE_COUNT:
276+
if 0 <= count < self.MAX_REASONABLE_COUNT:
252277
return count
278+
except Exception as e:
279+
print(f" AtCoder requests API failed: {e}")
253280

254281
# Fallback to web scraping profile page
255282
print(" API failed, trying web scraping...")
@@ -269,7 +296,7 @@ def get_atcoder(self):
269296
match = re.search(pattern, html, re.IGNORECASE)
270297
if match:
271298
count = int(match.group(1))
272-
if 0 < count < self.MAX_REASONABLE_COUNT:
299+
if 0 <= count < self.MAX_REASONABLE_COUNT:
273300
return count
274301
except Exception as e:
275302
print(f" Error getting AtCoder stats: {e}")

0 commit comments

Comments
 (0)