500px 打不开了?没事,我用 Python 给自己造了一个“任意门”
有段时间我发现一件很尴尬的事:
想认真看图的时候,500px 经常要么打不开,要么开得很慢。等半天刷出来几张,体验已经没了。
我就想,既然我有一台网络条件更好的服务器,为什么不把“访问问题”从本地挪到服务器端解决?
于是,这个小项目就诞生了:一个用 Python 写的私有画廊网关。
不是很复杂,但很实用。
先说结果
现在我的使用体验是这样的:
- 打开就是纯净作品流,没有干扰项。
- 图片加载稳定,滑动浏览很顺。
- 可直接查看拍摄参数、下载高清图。
- 手机和电脑都能流畅用。
一句话总结: 我没有“修好”500px,我只是给自己做了一扇随时可进出的门。
我到底做了什么
整体思路很简单:
- 前端不再直接请求 500px。
- 所有请求都先到我自己的服务。
- 服务端去拉 500px 数据,清洗后再返回给前端。
技术栈:
- Quart:异步 Web 框架。
- HTTPX:异步请求与流式转发。
- Hypercorn:部署运行。
- Tailwind:前端快速构建。
核心模块有三块:
/api/photos:拉取并整理照片列表。/proxy:代理图片与下载流。- 登录与会话:控制服务仅自己可用。
为什么我选 Quart,而不是 Flask
因为这个场景本质是 I/O 密集型:
- 同时发很多外部请求。
- 同时转发很多图片流。
如果是同步模型,线程很容易被占满; 异步模型可以在等待网络返回时切出去处理别的请求。
说得直白一点: 同样一台机器,异步方案更不容易“卡死”。
这版迭代里,我重点做了什么升级
这个项目不是“一把梭写完”,而是边用边打磨。最近一轮我主要做了三件事。
1) 安全基线补齐
- 会话密钥改为环境变量,不再硬编码。
- 登录改成哈希校验,不再明文比对。
- 图片代理加域名白名单,避免开放代理风险。
- 下载文件名做清洗,减少注入风险。
另外我还做了一个小工具页: 支持把明文账号批量转哈希,直接生成可用的环境变量文本。
对个人项目来说,这一步很“值”。
2) 前端体验重构
我不想做成“工具后台”,而是希望它像一个真的摄影浏览器。
所以我做了:
- 封面式 Hero(首屏更有画面感)。
- 顶部筛选菜单重设计(PC/移动端统一)。
- 灯箱预览与 EXIF 信息面板优化。
- 触控与键盘交互完善(手机滑动、桌面左右切换)。
最终效果是: 更克制、更干净,也更像“看图”而不是“看 UI”。
3) 把官方 API 的坑踩明白了
这里是我觉得最有价值的部分。
我做了多轮对照测试后发现:
popular和highest_rated在官方 v1 API 里几乎同池。quest_winning也和popular高度重合。- 人像分类里,
Portraits经常混入风光,People反而更稳定。
于是我把菜单策略调整成更有区分度的四个:
- 热门
popular - 编辑推荐
editors - 最新
fresh - 即将热门
upcoming
这种“数据驱动的 UI 取舍”,比拍脑袋加按钮靠谱太多。
这个项目最让我满意的点
不是代码行数,也不是炫技。
而是: 我把一个“不稳定依赖外部环境”的使用场景,改成了“自己可控、可维护、可迭代”的系统。
小而完整,能长期用。
这类项目平时不太显眼,但真正需要的时候,它很能打。
如果你也想做一个自己的“任意门”
我给三个建议:
- 先把链路打通,再谈精致。
- 先把安全底线做好,再谈开放给别人用。
- 遇到“看起来像前端问题”的现象,先做接口对照实验。
很多时候,真正的答案在数据,不在猜测。
最后
这个项目的初衷很朴素: 只是想安安静静看图。
结果是顺手把异步网关、流式代理、会话鉴权、前端体验和部署链路都练了一遍。
低调地说一句: 这扇“任意门”是给自己做的,但它的工程含金量,已经不止是一个“看图脚本”了。
体验链接:https://p.wlens.top