2026年1月

西班牙当局逮捕了34名个人,据称他们是一个涉及网络欺诈的犯罪网络的一部分,并被认为与在欧洲各地从事非法活动的Black Axe团伙有关。

此次行动是在巴伐利亚州刑事警察局的协助和欧洲刑警组织的支持下进行的。

在对塞维利亚、马德里、马拉加和巴塞罗那的搜查中,警方查获了66,400欧元现金、电子设备、车辆,并冻结了银行账户中的119,350欧元。

这个西班牙网络犯罪团伙由尼日利亚裔的个人领导,他们是Black Axe帮派的成员,专门从事所谓的中间人诈骗,例如商业电子邮件入侵(BEC)。

西班牙国家警察表示:“该组织专门从事被称为‘中间人’(MITM)的诈骗,这是一种犯罪分子介入合法通信以拦截、修改或重定向信息和支付,而受害者毫无察觉的技术。”

“检测到的最常见形式是商业电子邮件入侵(BEC),即企业电子邮件账户被入侵或冒充,使得犯罪分子能够拦截公司之间的真实通信、更改银行信息,并将大额支付转移到该组织控制的账户。”

据调查人员称,这些网络犯罪分子在过去15年中造成的损失超过600万美元,其中350万美元与此行动有关。

该团伙利用了一个遍布欧洲多国的庞大钱骡和前台人员网络,帮助转移非法所得并掩盖踪迹。

被捕人员中有四名主要嫌疑人已被采取审前拘留措施。他们现在面临严重持续性欺诈、参与犯罪组织、洗钱、文件伪造和妨碍司法公正等指控。

西班牙当局强调,调查仍在进行中,可能很快会有更多逮捕行动。

Black Axe于1977年在尼日利亚成立,是世界上影响最广、最危险的网络犯罪集团之一,据信拥有30,000名注册成员以及一个庞大的钱骡和协助者网络。

该团伙从事毒品贩运、人口贩运、卖淫、绑架、武装抢劫、精神诈骗,以及最近的网络犯罪。

两年前,美国判处其一名成员奥卢本加·拉瓦尔十年监禁,因其为Black Axe操作员在该国诈骗所得的数百万美元进行洗钱。

2022年,国际刑警组织在南非开展了一次大规模行动,逮捕了70名Black Axe团伙的疑似成员。

BreachForums黑客论坛数据库泄露,暴露32.4万个账户

                        By

01:17 PM

更新:文末已补充新信息。

臭名昭著的BreachForums黑客论坛最新版本遭遇数据泄露,其用户数据库表已在网上曝光。

BreachForums是一系列黑客论坛的名称,这些论坛被用于交易、出售和泄露被盗数据,以及出售企业网络访问权限和其他非法网络犯罪服务。

该网站在首个同类论坛RaidForums被执法部门查封、其所有者"Omnipotent"被捕后成立。

尽管BreachForums过去曾遭遇数据泄露和警方行动,但它已多次通过新域名重新上线,有人指控其现已成为执法部门的蜜罐。

昨日,一个以ShinyHunters勒索团伙命名的网站发布了一个名为breachedforum.7z的7Zip压缩包。

该压缩包包含三个文件:

shinyhunte.rs-the-story-of-james.txt
databoose.sql
breachedforum-pgp-key.txt.asc

ShinyHunters勒索团伙的代表向BleepingComputer声称,他们与分发此压缩包的网站无关。

压缩包中的"breachedforum-pgp-key.txt.asc"文件是创建于2023年7月25日的PGP私钥,BreachForums曾用其签署管理员的官方消息。虽然该密钥已泄露,但受密码保护,没有密码便无法滥用其签署消息。

受密码保护的BreachForums PGP私钥
来源:BleepingComputer

"databoose.sql"文件是一个MyBB用户数据库表(mybb_users),包含323,988条成员记录,涵盖成员显示名称、注册日期、IP地址及其他内部信息。

BleepingComputer对该表的分析显示,大部分IP地址映射到本地回环IP地址(0x7F000009/127.0.0.9),因此实用价值有限。

然而,有70,296条记录未包含127.0.0.9 IP地址,我们测试的这些记录映射到了公共IP地址。这些公共IP地址可能对相关人士构成操作安全风险,对执法部门和网络安全研究人员则具有价值。

新泄露用户数据库中的最后注册日期为2025年8月11日,这正是前一个BreachForums论坛(breachforums[.]hn)关闭的日期。此次关闭发生在该论坛部分涉嫌运营者被捕之后。

同日,ShinyHunters勒索团伙的一名成员在"Scattered Lapsus$ Hunters" Telegram频道发布消息,声称该论坛是执法部门的蜜罐。BreachForums管理员随后否认了这些指控。

breachforums[.]hn域名后来于2025年10月被执法部门查封,此前该域名被重新用于勒索受ShinyHunters勒索团伙发起的大规模Salesforce数据盗窃攻击影响的企业。

"我们希望就近期关于所谓数据库泄露的讨论进行说明,并清晰解释事件经过,"N/A在BreachForums上写道。

"首先,这不是近期事件。相关数据源自2025年8月的一次旧用户表泄露,当时BreachForums正从.hn域名进行恢复/重建。"

尽管管理员表示BreachForums成员应使用一次性邮箱以降低风险,且多数IP地址映射到本地IP,但该数据库仍包含可能引起执法部门关注的信息。

更新 2026年1月10日 下午04:02(美国东部时间):
本文发布后,网络安全公司Resecurity告知BleepingComputer,该网站现已更新并包含了BreachForums PGP私钥的密码。

另一位安全研究人员向BleepingComputer确认,该密码与此密钥匹配。

微软正在停用一项允许您直接从Microsoft Word将文档发送至Kindle的功能。

在更新支持文档时,微软确认将从Microsoft Word中移除“发送文档至Kindle”的选项。

此项变更将于2026年2月后逐步推行,但具体日期尚未确定,因此可能会分阶段实施。

功能停用后,您将无法再通过导出菜单访问该功能。

微软指出:“我们建议直接通过此发送至Kindle网站发送doc和docx文件。”

对于不了解的用户,“发送至Kindle”功能允许您在几分钟内将Microsoft Word文档直接发送至您的Kindle图书馆。

微软解释道:“传输的文件可以显示为可调整字体大小的Kindle电子书,也可以显示为固定版式的打印文档,以保留您的页面设计格式。”

当您使用“发送至Kindle”时,Word会保留格式样式和页面布局,类似于打印时的显示效果。

使用“发送至Kindle”时仅会丢失批注和修订记录。

遗憾的是,2026年2月后将无法继续使用“发送至Kindle”功能。

加州隐私保护局(CalPrivacy)已对营销公司Datamasters采取行动,该公司在未注册为数据中介的情况下出售了数百万用户的健康和个人数据。

根据《加州删除法案》,买卖消费者信息的企业必须在每年1月31日前注册其数据中介活动。

从2026年开始,消费者将能够访问一个名为“删除请求与退出平台”(DROP)的在线平台,在该平台上他们可以向所有注册的数据中介提交删除个人信息的请求。

对于以Datamasters名义运营的Rickenbacher Data LLC,CalPrivacy因其未能及时注册而处以45,000美元的罚款。

由于持续存在严重违规行为,这家总部位于德克萨斯州的公司还被禁止出售属于加州居民的个人信息。

根据该机构的最终命令,Datamasters购买并转售了数百万患有各种疾病(如阿尔茨海默病、药物成瘾、膀胱失禁)用户的个人信息,用于定向广告。

收集的数据包含数亿条记录,其中包括姓名、电子邮件地址、实际地址和电话号码。

一个加重处罚的因素是该公司对州监管工作的态度,其声称未在加州开展业务或管理加州居民数据,后在证据面前承认了相反事实,并辩称其正在手动筛查数据。

尽管监管机构多次试图强制该公司合规,但据报道Datamasters予以抵制,同时继续以未注册数据中介的身份运营。

根据12月12日签署的决定,该公司还被命令在12月底前删除所有先前购买的加州居民个人信息。

如果Datamasters未来在更大的数据集中收到属于加州居民的信息,该公司必须在收到后24小时内将其删除。

Datamasters还必须在未来五年内保持合规措施,并在一年后提交其相关隐私实践报告。

CalPrivacy还对S&P Global Inc.处以62,600美元的罚款,因其未能在2025年1月31日的截止日期前注册为2024年度的数据中介。然而,此次违规是由于行政错误所致。

该机构在对S&P Global的罚款决定中指出:“尽管S&P Global迅速采取行动注册为数据中介并实施了纠正措施,但该公司仍有313天处于未注册状态。”

Instagram否认数据泄露,尽管声称有1700万账户数据遭窃

                        By

02:13 PM

Instagram表示已修复一个允许威胁行为者批量请求密码重置邮件的漏洞,此前有声称称超过1700万个Instagram账户的数据被爬取并泄露到网上。

Meta发言人告诉BleepingComputer:"我们修复了一个允许外部方为部分Instagram用户请求密码重置邮件的问题。"

"我们希望向所有人保证,我们的系统没有遭到入侵,用户的Instagram账户仍然安全。人们可以忽略这些邮件,对于可能造成的任何困惑,我们深表歉意。"

在Malwarebytes警告其客户网络犯罪分子已窃取1750万个账户的数据后,媒体开始对所谓的Instagram数据泄露事件大肆报道。

据称这些Instagram数据已在多个黑客论坛上免费发布,发帖者声称这些数据是通过未经证实的2024年Instagram API泄露事件收集的。

论坛帖子泄露据称的Instagram数据

共享的数据总共包含17,017,213个Instagram账户资料,包括电话号码、用户名、姓名、实际地址、电子邮件地址和Instagram ID。

该数据集包含以下唯一值的数量:

ID: 17,015,503
Username: 16,553,662
Email: 6,233,162
Phone number: 3,494,383
Name: 12,418,006
Address: 1,335,727

并非每条记录都包含所有这些信息,有些记录仅包含Instagram ID和用户名。

X平台上的网络安全研究人员声称[1, 2],这些被爬取的数据来自2022年的一次API爬取事件,但尚未提供任何明确证据来证实这一点。

此外,Meta告诉BleepingComputer,他们不知道2022年或2024年有任何API事件。

然而,Instagram此前曾遭受API爬取事件,例如2017年一个被利用来爬取并出售据称600万个账户个人信息的漏洞。

目前尚不清楚新泄露的Instagram数据是否是2017年泄露数据与过去几年额外信息的汇编。

BleepingComputer联系了泄露Instagram信息的人以确认数据被盗时间,但未收到回复。

Instagram否认数据泄露

目前没有证据表明该事件代表一次新的Instagram数据泄露。Meta表示他们不知道2022年或2024年有任何API被入侵的情况,也没有发生新的泄露。

此外,研究人员尚未提供证据证明泄露的数据集是通过最近的漏洞获得的。

相反,信息表明这些数据可能是多年来从多个来源爬取的信息汇编。

好消息是,这些泄露的数据不包含密码,因此无需更改密码。

然而,人们确实需要警惕利用这些信息进行的针对性网络钓鱼、短信钓鱼和社会工程攻击。

威胁行为者通常使用泄露的数据来尝试窃取额外信息,例如用户密码。

如果您收到Instagram密码重置邮件或发送到您手机号码的验证码,但您并未发起账户恢复,请直接忽略并删除它们。

如果您的账户未启用双因素身份验证,强烈建议您开启此功能以增强安全性。

更新于26年1月11日:添加了唯一数据值。

基于 Pydantic-Resolve 和 FastAPI-Voyager 的 Clean Architecture 实践

篇幅较长无法粘贴全文,原文链接:
https://github.com/allmonday/A-Python-web-development-methodology-for-complex-business-scenarios/blob/main/README.zh.md

一套面向复杂业务场景的 Python Web 开发方法论

目录


1. 背景与问题

1.1 当前主流做法及其痛点

在 Python Web 开发中,处理复杂业务场景时,开发者通常采用以下几种模式:

模式一:直接使用 ORM (如 SQLAlchemy )

@router.get("/teams/{team_id}", response_model=TeamDetail)
async def get_team(team_id: int, session: AsyncSession = Depends(get_session)):
    # 获取团队基本信息
    team = await session.get(Team, team_id)

    # 获取 Sprint 列表
    sprints = await session.execute(
        select(Sprint).where(Sprint.team_id == team_id)
    )
    team.sprints = sprints.scalars().all()

    # 获取每个 Sprint 的 Story
    for sprint in team.sprints:
        stories = await session.execute(
            select(Story).where(Story.sprint_id == sprint.id)
        )
        sprint.stories = stories.scalars().all()

        # 获取每个 Story 的 Task
        for story in sprint.stories:
            tasks = await session.execute(
                select(Task).where(Task.story_id == story.id)
            )
            story.tasks = tasks.scalars().all()

            # 获取每个 Task 的负责人
            for task in story.tasks:
                task.owner = await session.get(User, task.owner_id)

    return team

这种做法在简单场景下确实很直观,能够快速上手。ORM 的类型安全特性也能在编译时发现一些错误,而且与数据库表结构的一一对应关系让代码容易理解。但当我们面对真正的业务场景时,这种方式的缺陷很快就暴露出来了。

最致命的问题是 N+1 查询。虽然代码看起来很清晰,但执行时会产生大量的数据库查询。每当我们访问一个关联关系时,ORM 就会发起一次新的查询。在深层嵌套的情况下,查询数量会呈指数级增长。更糟糕的是,这种性能问题在开发阶段不容易发现,只有当数据量积累到一定程度后才会显现出来,那时候往往已经太晚了。

代码的组织方式也是个问题。数据获取的逻辑散落在各个嵌套的循环中,业务逻辑和数据获取逻辑混在一起,难以阅读和维护。当需要修改业务规则时,开发者不得不在复杂的嵌套结构中寻找修改点,很容易引入新的 bug 。性能更是不可控,随着数据量的增长,查询效率会急剧下降,而这些性能瓶颈很难在代码层面直接观察到。

此外,相似的数据获取逻辑会在多个 API 中重复出现,导致大量代码冗余。当一个 API 需要获取"团队及其 Sprint",另一个 API 需要"团队及其成员"时,即使它们的查询逻辑非常相似,也不得不重复编写。这违反了 DRY ( Don't Repeat Yourself )原则,增加了维护成本。

模式二:使用 ORM 的 Eager Loading

@router.get("/teams/{team_id}", response_model=TeamDetail)
async def get_team(team_id: int, session: AsyncSession = Depends(get_session)):
    # 使用 joinedload 预加载关联数据
    result = await session.execute(
        select(Team)
        .options(
            joinedload(Team.sprints)
            .joinedload(Sprint.stories)
            .joinedload(Story.tasks)
            .joinedload(Task.owner)
        )
        .where(Team.id == team_id)
    )
    return result.scalar_one()

为了解决 N+1 查询问题,ORM 提供了 Eager Loading 机制,让我们可以通过 joinedloadselectinload 等方式预先加载关联数据。代码变得更简洁了,性能问题也得到了缓解。但这种方案也带来了新的挑战。

最明显的问题是笛卡尔积。当我们使用多层 JOIN 预加载关联数据时,数据库返回的数据量会急剧膨胀。比如一个团队有 10 个 Sprint ,每个 Sprint 有 10 个 Story ,每个 Story 有 10 个 Task ,那么 JOIN 的结果集会包含 1000 行数据,即使每行的数据量不大,也会给网络传输和内存占用带来压力。

更严重的问题是灵活性差。Eager Loading 的策略是在代码中硬编码的,所有使用同一个 Model 的 API 都会执行相同的预加载逻辑。但不同的 API 往往需要不同的数据。比如一个 API 只需要团队的基本信息,另一个 API 需要团队的 Sprint ,还有一个 API 需要团队的成员。如果统一使用 Eager Loading 加载所有关联数据,就会出现过度获取的问题,前端不需要的数据也被查询和传输了,浪费了资源。

配置 Eager Loading 本身就很复杂。开发者需要理解 lazyjoinedloadselectinloadsubquery 等多种加载策略的区别,知道什么时候用哪一种,以及它们各自会有什么副作用。这种配置错误很容易导致性能问题或意外的数据加载行为。而且,这种"一刀切"的配置方式意味着所有 API 都使用相同的加载策略,无法针对特定场景进行优化。

模式三:手动组装数据

@router.get("/teams/{team_id}", response_model=TeamDetail)
async def get_team(team_id: int, session: AsyncSession = Depends(get_session)):
    # 1. 批量获取所有需要的数据
    team = await session.get(Team, team_id)

    sprints_result = await session.execute(
        select(Sprint).where(Sprint.team_id == team_id)
    )
    sprint_ids = [s.id for s in sprints_result.scalars().all()]

    stories_result = await session.execute(
        select(Story).where(Story.sprint_id.in_(sprint_ids))
    )
    story_ids = [s.id for s in stories_result.scalars().all()]

    tasks_result = await session.execute(
        select(Task).where(Story.id.in_(story_ids))
    )
    tasks = tasks_result.scalars().all()

    owner_ids = list(set(t.owner_id for t in tasks))
    owners_result = await session.execute(
        select(User).where(User.id.in_(owner_ids))
    )
    owners = {u.id: u for u in owners_result.scalars().all()}

    # 2. 手动组装数据结构
    sprint_dict = {s.id: s for s in sprints_result.scalars().all()}
    story_dict = {s.id: s for s in stories_result.scalars().all()}

    for story in story_dict.values():
        story.tasks = [t for t in tasks if t.story_id == story.id]
        for task in story.tasks:
            task.owner = owners.get(task.owner_id)

    for sprint in sprint_dict.values():
        sprint.stories = [s for s in story_dict.values() if s.sprint_id == sprint.id]

    team.sprints = list(sprint_dict.values())

    return team

为了获得最优的性能和精确的数据控制,有经验的开发者会选择手动组装数据。这种方式完全掌控查询逻辑,可以精确控制每个查询的 SQL 语句,避免不必要的数据库访问。通过批量查询和智能的数据组装,可以获得最佳的性能,而且没有冗余数据。

但这种方式的代价是代码变得非常冗长。如上面的例子所示,为了获取一个团队的完整信息,我们需要编写多个查询,手动构建数据字典,然后通过嵌套循环组装数据。代码的长度和复杂度都大幅增加,而真正表达业务逻辑的代码反而被淹没在数据组装的细节中。

更容易出错也是个大问题。手动组装数据涉及到大量的索引操作和循环嵌套,很容易出现索引错误、空指针引用等 bug 。而且这些错误往往只有在运行时、特定数据条件下才会暴露,难以在开发阶段发现。

维护成本更是高昂。当业务规则发生变化时(比如需要添加一个新的关联关系),开发者需要在所有相关的 API 中修改数据组装逻辑。如果遗漏了某个地方,就会导致数据不一致。而且,相似的数据组装逻辑会在多个 API 中重复出现,违反了 DRY 原则。

最根本的问题是,这种代码已经变成了纯粹的数据搬运工,看不出任何业务意图。代码中充满了字典操作、循环嵌套、索引查找,而这些都是技术细节,与业务需求毫无关系。新加入的团队成员很难从这些代码中理解业务逻辑,业务知识的传递变得异常困难。

模式四:使用 GraphQL

type Query {
    team(id: ID!): Team
}

type Team {
    id: ID!
    name: String!
    sprints: [Sprint!]!
}

type Sprint {
    id: ID!
    name: String!
    stories: [Story!]!
}

type Story {
    id: ID!
    name: String!
    tasks: [Task!]!
}

type Task {
    id: ID!
    name: String!
    owner: User!
}

GraphQL 确实是一个很有吸引力的方案。前端可以按需获取数据,需要什么字段就查什么字段,不会有过度获取的问题。它提供了类型安全的查询接口,而且通过 DataLoader 可以自动解决 N+1 查询问题。这些特性让 GraphQL 在前端开发中广受欢迎。

但 GraphQL 的学习曲线非常陡峭。开发者需要学习全新的查询语言、Schema 定义、Resolver 编写、DataLoader 配置等一堆概念,这与 REST API 的直观性形成了鲜明对比。更麻烦的是,GraphQL 的过度灵活性给后端带来了巨大的挑战。前端可以构造任意复杂的查询,有些查询甚至可能是开发者没有想到过的,这导致后端很难进行针对性的优化。当一个查询嵌套了 10 层,返回了数百万条数据时,数据库和服务器都会面临巨大的压力。

调试 GraphQL API 也比调试 REST API 复杂得多。当一个 GraphQL 查询出错时,错误信息往往很难定位到具体的问题源头。而且 GraphQL 需要额外的服务器和工具链支持,无法直接利用现有的 FastAPI 生态系统。比如 FastAPI 的依赖注入、中间件、自动文档生成等特性,在 GraphQL 中都无法直接使用。

还有一个更深层次的问题是 ERD 和用例的界限模糊。GraphQL 的 Schema 同时扮演了实体模型和查询接口两个角色。当我们设计一个 GraphQL Schema 时,很难确定应该按照实体来组织(一个 Type 对应一个数据库表),还是按照用例来组织(不同的业务场景需要不同的字段)。这导致最佳实践不清晰,不同的项目、不同的开发者可能有完全不同的组织方式。

而且随着业务增长,所有的用例都会堆砌在同一个 Schema 中,导致 Schema 膨胀,难以维护。权限控制也变得异常复杂。不同的 API 端点可能有不同的权限要求,但它们可能都查询同一个实体(比如 User ),在 GraphQL 中很难针对不同的查询场景应用不同的权限规则。

1.2 问题根源分析

上面我们探讨的所有模式,虽然表面上的问题各不相同,但它们的核心困境其实是一致的。

问题 1:业务模型与数据模型混淆

# SQLAlchemy ORM 同时扮演两个角色:
# 1. 数据模型(如何存储)
# 2. 业务模型(业务概念)

class Team(Base):
    __tablename__ = 'teams'

    id = Column(Integer, primary_key=True)
    name = Column(String)

    # 这是数据库的外键关系,还是业务关系?
    sprints = relationship("Sprint", back_populates="team")

在传统的 ORM 开发中,业务模型和数据模型是混在一起的。看看这个例子,Team 类既表达了业务概念(团队是什么),又承载了数据模型的细节(如何在数据库中存储)。当我们在 sprints 字段上定义 relationship 时,这到底是在描述一个业务关系(团队有多个 Sprint ),还是在声明一个数据库外键约束?这种模糊性会导致很多问题。

数据库的设计约束会直接影响我们的业务建模。比如,如果数据库中的 teams 表没有直接到 users 的外键,而是通过中间表 team_members 关联,那么在 ORM 中我们也必须通过这个中间表来定义关系。这意味着业务模型被迫适应数据库的实现细节,而不是反过来。

更严重的是,这种方式无法表达跨库、跨服务的业务关系。现代系统中,数据可能分布在不同的数据库中,甚至存储在外部服务里。比如用户的基本信息在 PostgreSQL ,而用户的偏好设置在 MongoDB ,用户的实时状态在 Redis 中。ORM 的 relationship 无法跨越这些边界,业务模型因此被限制在了单一数据库的范围内。

问题 2:依赖方向错误

传统架构的依赖方向:
┌─────────────┐
│   API Layer │  ← 依赖于
└──────┬──────┘
       │
       ↓
┌─────────────┐
│ ORM Models  │  ← 依赖于
└──────┬──────┘
       │
       ↓
┌─────────────┐
│  Database   │
└─────────────┘

问题:业务规则依赖于数据库实现!

这违反了 Clean Architecture 的依赖规则。正确的依赖关系应该是:业务规则最稳定,不依赖任何外层;数据库是实现细节,应该依赖业务规则;当数据库变化时,业务规则不应该受影响。但传统架构的依赖方向恰恰相反,业务规则被数据库的实现细节所绑架。

问题 3:缺少业务关系的显式声明

# 传统方式:业务关系隐藏在查询中
async def get_team_tasks(team_id: int):
    # "团队的任务"这个业务概念隐藏在 SQL WHERE 中
    result = await session.execute(
        select(Task)
        .join(Sprint, Sprint.id == Task.sprint_id)
        .where(Sprint.team_id == team_id)
    )
    return result.scalars().all()

业务关系没有被显式声明出来,这是个很隐蔽但危害很大的问题。看看这个例子,"团队的任务"是一个清晰的业务概念,但这个概念被隐藏在 SQL 的 JOIN 和 WHERE 子句中。新加入团队的成员需要阅读大量代码才能理解系统中有哪些业务关系,这些关系是如何定义的。更糟糕的是,没有自动化的方式来检查业务关系的一致性。当需求变化需要修改某个关系时,开发者很难找到所有相关的代码,很容易遗漏某个地方,导致业务逻辑的不一致。

问题 4:中间表的技术暴露

在 SQLAlchemy ORM 中,多对多关系需要显式定义中间表,这导致技术细节泄漏到业务层。

# SQLAlchemy ORM:必须定义中间表
class Team(Base):
    __tablename__ = 'teams'
    id = Column(Integer, primary_key=True)
    name = Column(String)

    # ORM relationship 需要指定中间表
    members = relationship("User",
                          secondary="team_members",  # 必须指定中间表
                          back_populates="teams")

class User(Base):
    __tablename__ = 'users'
    id = Column(Integer, primary_key=True)
    name = Column(String)

    teams = relationship("Team",
                        secondary="team_members",  # 必须指定中间表
                        back_populates="members")

# 中间表(技术实现细节)
class TeamMember(Base):
    __tablename__ = 'team_members'
    team_id = Column(Integer, ForeignKey('teams.id'), primary_key=True)
    user_id = Column(Integer, ForeignKey('users.id'), primary_key=True)
    role = Column(String)  # 可能还有额外字段

# 查询时需要关心中间表的存在
@router.get("/teams/{team_id}")
async def get_team_members(team_id: int, session: AsyncSession):
    # 必须通过中间表查询
    result = await session.execute(
        select(User)
        .join(TeamMember, TeamMember.user_id == User.id)  # 中间表暴露
        .where(TeamMember.team_id == team_id)
    )
    return result.scalars().all()

这个问题的根源在于,ORM 的多对多关系需要显式定义中间表,这导致技术细节直接泄漏到业务层代码中。业务代码必须知道 team_members 中间表的存在,查询时也需要显式地 join 这个中间表。这增加了代码复杂度,更重要的是,业务逻辑被数据库的实现细节所绑架。

更深层的问题是业务语义变得模糊。TeamMember 到底是一个有意义的业务概念,还是纯粹的技术实现?如果中间表还有额外的字段(比如 role 表示用户在团队中的角色,joined_at 表示加入时间),这些字段应该被建模为独立的实体吗?不同的开发者可能给出不同的答案,缺乏统一的指导原则。

数据组装也因此变得复杂。查询"团队的所有成员"需要 join 中间表,查询"用户所属的团队"也需要 join 中间表。所有涉及多对多关系的查询都变得冗长和难以理解。当业务规则要求"获取用户在所有团队中的角色"时,情况就更加复杂了。这些技术细节让业务逻辑的实现变得异常沉重。

对比:Pydantic-Resolve ERD 的方式

# ERD:业务概念清晰,无需关心中间表
class TeamEntity(BaseModel, BaseEntity):
    """团队实体 - 业务概念"""
    __relationships__ = [
        # 直接表达"团队有多个成员"的业务关系
        Relationship(
            field='id',
            target_kls=list[UserEntity],
            loader=team_to_users_loader  # loader 内部处理中间表
        ),
    ]
    id: int
    name: str

class UserEntity(BaseModel, BaseEntity):
    """用户实体 - 业务概念"""
    __relationships__ = [
        # 直接表达"用户属于多个团队"的业务关系
        Relationship(
            field='id',
            target_kls=list[TeamEntity],
            loader=user_to_teams_loader
        ),
    ]
    id: int
    name: str

# Loader 实现细节:中间表只在这里出现
async def team_to_users_loader(team_ids: list[int]):
    """加载团队成员 - 内部处理中间表"""
    async with get_session() as session:
        # 只有这里需要知道中间表的存在
        result = await session.execute(
            select(User)
            .join(TeamMember, TeamMember.user_id == User.id)
            .where(TeamMember.team_id.in_(team_ids))
        )
        users = result.scalars().all()

        # 构建映射
        users_by_team = {}
        for user in users:
            for tm in user.team_memberships:
                if tm.team_id not in users_by_team:
                    users_by_team[tm.team_id] = []
                users_by_team[tm.team_id].append(user)

        return [users_by_team.get(tid, []) for tid in team_ids]

关键差异

维度 SQLAlchemy ORM Pydantic-Resolve ERD
中间表位置 暴露在业务层 隐藏在 loader 实现中
业务语义 技术关系 (secondary) 业务关系 (团队包含成员)
查询代码 需要 join 中间表 loader.load(team_id)
代码位置 分散在多处 集中在 loader
测试 依赖数据库表结构 可 mock loader

架构优势

传统方式:
Team → TeamMember (中间表) → User
业务层需要知道中间表的存在

Pydantic-Resolve 方式:
Team → User (业务关系)
中间表是数据层的实现细节,业务层不关心

这意味着:

  1. 业务模型纯净:Team 和 User 的关系直接表达业务语义

  2. 技术细节封装:中间表的存在被封装在 loader 中

  3. 灵活的存储策略


    • 数据库可以用中间表实现
    • 也可以用 JSON 字段存储
    • 甚至可以是外部服务(如 LDAP )
    • 业务层代码无需修改
  4. 易于理解:新人看到 ERD 就能理解业务关系,不需要先学习数据库设计


2. Clean Architecture 思想

2.1 核心原则

Clean Architecture 由 Robert C. Martin (Uncle Bob) 提出,核心思想是:

"Software architecture is the art of drawing lines that I call boundaries."
软件架构的艺术在于画界线。

原则 1:依赖规则

外层依赖内层,内层不依赖外层。

                ↓ 依赖方向
    ┌─────────────────────┐
    │   Frameworks &      │  外层
    │   Drivers           │  (实现细节)
    ├─────────────────────┤
    │   Interface         │
    │   Adapters          │
    ├─────────────────────┤
    │   Use Cases         │
    │   (Application)     │
    ├─────────────────────┤
    │   Entities          │  内层
    │   (Business Rules)  │  (核心)
    └─────────────────────┘

遵循依赖规则有几个关键点需要注意。首先,内层不知道外层的存在,这意味着核心业务逻辑不依赖于任何框架、数据库或 UI 的细节。其次,内层不包含外层的信息,比如业务规则不应该知道数据是用 PostgreSQL 还是 MongoDB 存储的。最后,外层的实现可以随时替换而不影响内层,这意味着我们可以从 SQLAlchemy 切换到 MongoDB ,或者从 FastAPI 切换到 Django ,而业务逻辑代码无需修改。

原则 2:业务规则独立

# ❌ 错误:业务规则依赖数据库
class Task:
    def calculate_priority(self, session):
        # 业务逻辑被数据库实现细节污染
        if self.assignee_id in session.query(TeamMember).filter_by(role='lead'):
            return 'high'

# ✅ 正确:业务规则独立
class Task:
    def calculate_priority(self, assignee_roles):
        # 业务逻辑只依赖业务概念
        if 'lead' in assignee_roles:
            return 'high'

原则 3:跨边界的数据传递

# 内层定义数据结构
class TaskEntity(BaseModel):
    id: int
    name: str
    assignee_id: int

# 外层负责转换
def task_entity_to_orm(entity: TaskEntity) -> Task:
    return Task(
        id=entity.id,
        name=entity.name,
        assignee_id=entity.assignee_id
    )

2.2 依赖规则

在 Web 开发中,依赖规则可以这样理解:

┌────────────────────────────────────────────────────┐
│         Presentation Layer (外层)                   │
│  - FastAPI Routes                                   │
│  - Request/Response Models                          │
│  - 依赖: Application Layer                          │
└────────────────────────────────────────────────────┘
                    ↓
┌────────────────────────────────────────────────────┐
│      Application Layer (Use Cases)                 │
│  - 业务用例(获取用户、创建订单)                    │
│  - 依赖: Domain Layer                               │
└────────────────────────────────────────────────────┘
                    ↓
┌────────────────────────────────────────────────────┐
│           Domain Layer (内层)                      │
│  - Entities (业务实体)                              │
│  - Business Rules (业务规则)                        │
│  - Value Objects (值对象)                           │
│  - 不依赖任何外层                                    │
└────────────────────────────────────────────────────┘
                    ↓
┌────────────────────────────────────────────────────┐
│    Infrastructure Layer (最外层)                   │
│  - Database (SQLAlchemy)                           │
│  - External Services                               │
│  - File System                                     │
└────────────────────────────────────────────────────┘

关键洞察

  • Entities 不应该知道 SQLAlchemy 的存在
  • Business Rules 不应该知道数据库表结构
  • Use Cases 不应该知道 HTTP 协议的细节

2.3 在 Web 开发中的应用

传统架构的问题

# 传统方式:所有层次耦合

# Domain Layer (应该独立,但实际上依赖了 ORM)
class User(Base):  # ← SQLAlchemy Base
    __tablename__ = 'users'
    id = Column(Integer, primary_key=True)

# Application Layer (应该只依赖 Domain ,但直接使用了 ORM)
async def create_user(data: dict, session: AsyncSession):
    user = User(**data)  # ← 直接使用 ORM Model
    session.add(user)
    await session.commit()

# Presentation Layer
@router.post("/users")
async def api_create_user(data: dict, session=Depends(get_session)):
    return await create_user(data, session)  # ← 暴露了数据库细节

这段代码暴露了传统架构的核心问题。SQLAlchemy 虽然建立了对象关系映射( ORM ),让数据库表可以通过 Python 对象来操作,但这种映射关系过于紧密。ORM Model 既承担了数据持久化的职责,又要表达业务概念,导致对象无法自由地代表业务模型。业务实体被数据库的实现细节所绑架,每个字段、每个关系都必须与数据库表结构一一对应,完全失去了作为独立业务概念存在的自由。

更深层次的问题包括:

  1. Domain Layer 被 SQLAlchemy 绑定:业务实体继承了 SQLAlchemy 的 Base ,无法独立于数据库存在
  2. 业务逻辑无法脱离数据库测试:编写单元测试时必须启动完整的数据库环境,大大降低了测试效率
  3. 切换数据库需要修改所有层:当从 PostgreSQL 迁移到 MongoDB 时,所有使用 ORM Model 的代码都需要重写


。。。

之前喜欢刷手机,后来感觉可以利用这段时间,索性 Vibe 了一个学英语的 ide 插件,支持 Cursor 、Antigravity 。

主要是内嵌了一个播放器,利用 yt-dl ,贴上油管地址,练习听力挺好用的,没啥特别的。

当然你想用来摸鱼看油管也不是不行。

如果你有喜欢的英文频道,可以拿来学习。

大家有什么推荐的英语学习频道可以分享下。

https://github.com/kylesean/lingo-tube

折腾了一圈衬线字体看书用,口味上偏楷书,目前最喜欢这两个。



霞鹜文楷规整清晰,偏旁部首倾泻而出;方正楷书则更顿挫,字字浑然一体。

V 友有没有推荐?

去年底(距今也没有多久),发现我为上上家公司写的 Git 构建脚本还在用,于是我花业余时间写了一个新的脚本,用来构建仅依赖 libc 或者静态编译 Git 的项目,现在分享出来:https://github.com/baulk/git-minimal,旨在提供最新版无依赖的 git 二进制。

Release 可下载 deb/rpm/apk(alpine) 安装包,还有 tar.xz 压缩包(压缩包里有启动器,修正了路径和 SSL 证书,证书下载自 cURL 站点),压缩包(安装包)中还有开启了 HTTP/3 的 cURL 最新版本。

风味

包名 libc 可运行的系统
git-minimal glibc Linux ,x86_64 ,glibc >= 2.39
git-minimal-static glibc (静态链接) Linux ,x86_64
git-minimal-musl musl (静态链接) Linux ,x86_64/aarch64

由于 musl 的内存分配器比较差,git-minimal 在链接阶段链接了 mimalloc 。

0. 不说废话,只分享干货。

1. 前情提要 https://www.v2ex.com/t/1149991

2. 第一家店是 2025.8.3 开业。
第二家店是 2025.12.28 开业。均定位中高端自助洗车。

3. 第一家店目前月流水在 2w 多,第二家店半个月目前 1w 多,单店月利润在 1w 多,单店投资 20 左右,回本时间预 计在 1 年左右。

4. 目前还在全职上班中,当然工作不忙,不加班,每个店雇兼职保洁月成本 1k 。

5. 目前店里还需要自己做的就是:接电话、定期补充药剂、维护设备。

6. 未来计划:再复制几家店,雇全职管理所有店。

7. 行业优势:风险小,新能源车火爆导致洗车服务供不应求,回本周期还算比较短,投资相对不高,人力成本低可以做副业,门槛低。

8. 行业劣势:严重依赖场地,面向的顾客群体五花八门,琐碎事情多,有人真的会半夜打电话,收入不算暴利,需要跟各色人打交道,门槛低但想做好不容易。

9. 加盟还是自己搞品牌:加盟最快但是要擦亮眼睛,割韭菜的太多太多,我目前加盟的品牌算是比较良心,没有加盟费只有小程序订阅费,不抽点,用户付款直接到自己账户,不干预后期经营,当然缺点就是没啥服务(服务的人力成本太高了);自己搞品牌,可以省点钱,但是设备稳定性和小程序需要自己慢慢踩坑,小程序做个简单的不难,好用也不容易。

10. 行业核心在于好的场地,场地决定了生死,拿场地很多时候需要关系或者票子疏通。怎么简单判断一个场地的地段能不能干,去找附近的同行,蹲门口计数或者通过小程序统计一天的车流量。

11. 如何估算成本和收益:我这里提供一些经验值供大家参考。1 个工位白天洗车拉满的情况下撑死也就是洗 20 来辆车,过节可能还会多一些,但是也多不哪里去,1 个车平均在 30-60 分钟,客单价在 20 左右。我 1 店周内在 30 左右,周末在 50 辆左右,1 个月目前 1k 多辆。成本 1 辆车按照 0.1 吨水,1 度电来估算,药剂耗材几乎可以忽略不计。

12. 花那么多钱自己洗车为什么不去京东途虎养车 9.9 洗车呢:首先要明确一个事,外面的三四十普洗都是不够成本的。为什么还会有低价洗车?无非两种,一是低价引流然后推销高端项目,二是办卡才能享受。这就导致外面那些要么排队要么跑路。还有两个原因,低价洗车或者 4s 店免费洗车都比较糙,不仅洗不干净还容易把车漆洗化,另外一个原因就是自己洗车比较解压能提供情绪价值。

13. 感悟:真正从打工贩卖时间来赚钱到利用生产资料来换钱,完全是两码事,上班认识的人大部分都是上班的,等你开始做生意了,认识的老板会越来越多,等你生意做的好了就自然会有老板愿意来投资你,你拥有了输入钱就可以输出更多钱的能力,这个时候你的人脉会越来越广,这个能力确实很多时候比写一段牛逼的代码对老板更有用。从上班的角度来看,程序员依然是众多行业的顶流,不用操太多心,工资高,环境好,周围人的素质相对高很多。做生意以后才能体会到,老板的时间就是金钱这句话。

14. 我可以为大家提供的价值:我也是跌跌撞撞干了半年才算对这个行业比较熟悉了,踩了很多坑,现在大部分场地我看一眼就知道能不能干,大家可以发场地照片我帮忙判断能否做,给大家一点经验(选场地+运营)。无偿的,但是希望大家真的想干了再来问我,最近忙着找场地扩店,我的精力也是有限的,建议先自己网上多看看再来跟我交流,不要问一些太小白的问题,时间就是金钱啊。啥?你连我的微信都找不到?那还是先干好本职工作吧。

为什么做这个?

备考的日子里,我总是很难准确知道自己每天到底学了多少时间。

手动计时太麻烦,番茄钟又总是忘记开。坐在电脑前一整天,感觉学了很久,但实际有效学习时间可能只有几个小时。

于是我想:能不能让电脑自动帮我记录学习时间?

就像运动手环自动记录步数一样 —— 打开网课页面就自动开始计时,关掉就停止。不需要任何操作,专注学习就好。

快学点儿吧 就这样诞生了

功能亮点

功能说明
桌面程序基于 Tauri 的轻量应用,安静地待在系统托盘
浏览器扩展Chrome 扩展自动检测学习页面,无需手动操作
手机 APPFlutter 开发的 Android 应用,随时随地查看学习数据
云同步多设备数据无缝同步,电脑手机数据互通
数据统计直观的图表展示学习轨迹,日 / 周 / 月维度分析
目标管理设定每日目标,倒计时考试日期
智能通知学习里程碑提醒(可关闭,不打扰你)
开机启动随系统自动运行,打开电脑就开始守护

工作原理

┌─────────────────┐     ┌─────────────────┐     ┌─────────────────┐
│   Chrome 浏览器  │────▶│     桌面程序     │────▶│    手机 APP     │
│    (扩展程序)    │     │   (时间记录器)   │     │   (查看统计)    │
└─────────────────┘     └─────────────────┘     └─────────────────┘
  1. Chrome 扩展 监控你的浏览器标签页
  2. 当你访问的 URL 匹配某个课程时,通知桌面程序
  3. 桌面程序 开始计时,数据存储在本地 SQLite 数据库
  4. 可选同步 到云端,在手机上查看统计数据

演示图:

桌面程序

移动 APP:


📌 转载信息
原作者:
Ar3s
转载时间:
2026/1/12 10:39:05

Spotx
Windows 端的,安装特别简单
直接复制进 powershell 回车按提示完成安装即可

iex “& { $(iwr -useb ‘https://raw.githubusercontent.com/SpotX-Official/SpotX/refs/heads/main/run.ps1’) } -new_theme”

iex “& { $(iwr -useb ‘https://raw.githubusercontent.com/SpotX-Official/SpotX/refs/heads/main/run.ps1’) } -new_theme”

╔════════════════════════════════╗
║ 欢迎使用 SpotX 的 Windows 版本 ║
╚════════════════════════════════╝

您的 Spotify 1.2.79.427 版本已过时,建议更新到 1.2.80.349
是否需要更新? [Y/N]: Y

是否要卸载当前版本 1.2.79.427 或者覆盖安装?Y [卸载] / N [覆盖安装]: N

下载并安装 Spotify 1.2.80.349
请稍等…

#################################################################################################################### 100.0%

您想关闭主页上的播客、剧集与有声读物吗? [Y/N]: Y

您想要阻止 Spotify 更新吗? [Y/N]: Y

修补 Spotify…

安装完成

然后打开 Spotify 开始享受吧


📌 转载信息
原作者:
S_M9
转载时间:
2026/1/12 10:38:14

今日为保稳定,遂开通,但感觉额度略少。以及倍率略高,遂以个人方法测试。
PS:仅使用个人语料库测试,算法各有不同,可保证复现

日期范围:2026-01-11

数据来源:/root/.codex/sessions/2026/01/11/rollout-*.jsonl

计算脚本:codex 倍率计算.py:1

重要说明

1. 本报告使用的是 Codex 本机 rollout 会话文件中 token_count 事件的累计 token 统计;不依赖任何主观估计。

2.“缓存折扣系数 α=0.1” 无法从日志中自动推断(日志只记录 cached_input_tokens 数量,不记录计费规则 / 账单),因此本报告把它作为 “外部配置输入” 参与计算。

3. 同一天如果继续使用 Codex,会新增 / 更新更多 rollout,导致 “当日汇总值” 变化;本报告反映的是运行脚本时刻在该目录内可解析到的结果。

  1. 计费配置(输入参数)
  • 输入单价 Pin = $0.8750 / 1M tokens

  • 输出单价 Pout = $7.0000 / 1M tokens

  • 输出 / 输入价格比 r = Pout / Pin = 8

  • 缓存折扣系数 α = 0.1(即缓存输入 token 按输入价的 10% 计费)

  • 有效工作量口径:W = U + O(新增输入 + 输出)

———

  1. 日志字段与符号定义(从 rollout 直接读取)

从每个 rollout-*.jsonl 的 event_msg.type=token_count 的 info.total_token_usage 取:

  • I = input_tokens(总输入 token)

  • C = cached_input_tokens(命中缓存的输入 token)

  • U = I - C(未命中 / 新增输入 token)

  • O = output_tokens(输出 token)

———

  1. 指标定义(“基准词 + 真实倍率”)

为把 “输出更贵、缓存更便宜” 的成本结构统一到一个尺度,采用 “等价输入 token” 折算:

  • 等价基准词(Equivalent Baseline Tokens)

    E = U + α*C + r*O

  • 有效工作词(Work Tokens)

    W = U + O

  • 真实倍率(Real Multiplier)

    M = E / W

并给出对应成本与 “有效单价”:

  • 输入成本 Cin = (U + α*C) / 1e6 * Pin

  • 输出成本 Cout = O / 1e6 * Pout

  • 总成本 Ctotal = Cin + Cout

  • 有效单价(每 1M 有效工作词)P_eff = Pin * M

———

  1. 取数范围与纳入情况(可复现)
  • 当天目录内存在多个 rollout-*.jsonl;脚本实际读取到 5 个包含可用 token_count 的 rollout 并纳入汇总。

  • 复现命令(本报告实际使用):

    python3 codex 倍率计算.py --date 2026-01-11 --pin 0.875 --pout 7 --alpha 0.1 --sessions-root /root/.codex/sessions --denom U+O --breakdown --classify

———

  1. 当日汇总结果(5 个 rollout 合计)

Token 汇总

  • I = 16,882,855

  • C = 16,058,496

  • U = 824,359

  • O = 145,980

  • 缓存命中率 C/I = 95.117182%

倍率汇总(α=0.1,W=U+O)

  • E = 3,598,048.6

  • W = 970,339

  • 真实倍率 M = 3.708033×

  • 有效单价 P_eff = $3.244528 / 1M 有效工作词

成本拆分(美元,按 α=0.1)

  • Cin = $2.1264325

  • Cout = $1.0218600

  • Ctotal = $3.1482925

  • 基准成本(把 W 全部按输入价计费):baseline_cost = $0.8490466

  • 成本倍率(与 M 一致):Ctotal /baseline_cost = 3.708033×

———

  1. 分会话(rollout)结果与 “模拟用户行为” 分类(基于日志回放)

说明:这里的 “模拟用户行为” 并非人工控制实验,而是对已有会话做回放式归类(依据:提示相似度 + 工具调用密度)。为对外展示,本报告不展示原始提示词全文,仅展示分类、token 与倍率。

  • rollout-2026-01-11T09-49-54-019baabe-e078-7fe2-9d1b-3a11c91e51ac.jsonl

    • 分类:cold_start

    • I/C/U/O = 34,663 / 33,664 / 999 / 88

    • 命中率:97.117964%

    • 真实倍率 M:4.663661×

  • rollout-2026-01-11T09-53-11-019baac1-e04c-72c3-a7df-d5c5d0eb98b2.jsonl

    • 分类:cold_start

    • I/C/U/O = 11,521 / 10,752 / 769 / 97

    • 命中率:93.325232%

    • 真实倍率 M:3.025635×

  • rollout-2026-01-11T09-55-03-019baac3-963c-7353-9849-2614a76f03b6.jsonl

    • 分类:tools_dense(工具调用密集)

    • 工具调用统计(来自 rollout):exec_command=156, update_plan=24, apply_patch=20, write_stdin=8

    • I/C/U/O = 11,633,072 / 11,147,008 / 486,064 / 73,377

    • 命中率:95.821706%

    • 真实倍率 M:3.910655×

  • rollout-2026-01-11T10-34-55-019baae8-149c-7e82-ac18-2de8db88bc1b.jsonl

    • 分类:tools_dense

    • 命中率:93.960516%

    • 真实倍率 M:3.433297×

  • rollout-2026-01-11T11-21-02-019bab12-4eef-7d83-96b4-6de8dc37feb6.jsonl

    • 分类:tools_dense

    • 工具调用统计:exec_command=44, write_stdin=8

    • I/C/U/O = 911,345 / 834,048 / 77,297 / 22,605

    • 命中率:91.518360%

    • 真实倍率 M:3.418768×

———


📌 转载信息
转载时间:
2026/1/12 10:38:09

opencode 是什么就不需要我多说了,是一个非常好用的聚合的 TUI coding agent,原生支持 LSP 和 ASP,很适合佬友们有一堆渠道站的用法。

但是在搭配 codex 的时候,经常会出现下面这些问题

  1. Items not found
all 10 attempts failed: HTTP 404: 
{
    "error": {
        "code": null,
        "message": "{\n \"error\": {\n \"message\": \"Item with id 'rs_jgs9diuh934hu9shag09phq9raf0' not found. Items are not persisted when `store` is set to false. Try again with `store` set to true, or remove this item from your input.\",\n \"type\": \"invalid_request_error\",\n \"param\": \"input\",\n \"code\": null\n  }\n}(traceid: 824gj32q80-94gj-08)",
        "param": null,
        "type": "invalid_request_error"
    }
}

核心问题就是这个 items 字段。codex 全部使用的是有状态的 response api,所以 opencode 默认不会携带上下文给 api,而是只提供一个 item_id ,提供了一种更优雅的方案。
但是 L 站的转发,显然是没办法支持这个的,所以我们需要添加一个关键参数:

"store": false 

这样就会在每次都传递完整的上下文给中转站了。

  1. 不命中缓存
    为了节约宝贵的 token,现在各大中转站也都支持 prompt cache 了,但是也需要在配置文件中启用一下配置:
 "setCacheKey": true 

综上,给各位佬友们一个综合一些的 opencode.jsonc 的完整配置,mcp 就各位佬友自己随便定制啦

{
  "$schema": "https://opencode.ai/config.json",
  "model": "foxcode/google/gemma-3n-e4b",
  "provider": {
    "example": {
      "npm": "@ai-sdk/openai",
      "name": "example",
      "options": {
        "baseURL": "https://new.example.com/codex/v1",
        "setCacheKey": true
      },
      "models": {
        "gpt-5-2-high": {
          "id": "gpt-5.2",
          "name": "GPT 5.2 High",
          "options": {
            "reasoningEffort": "high",
            "textVerbosity": "low",
            "reasoningSummary": "auto",
            "store": false
          }
        },
        "gpt-5-2-medium": {
          "id": "gpt-5.2",
          "name": "GPT 5.2 Medium",
          "options": {
            "reasoningEffort": "medium",
            "textVerbosity": "low",
            "reasoningSummary": "auto",
            "store": false
          }
        },
        "gpt-5-2-xhigh": {
          "id": "gpt-5.2",
          "name": "GPT 5.2 XHigh",
          "options": {
            "reasoningEffort": "xhigh",
            "textVerbosity": "low",
            "reasoningSummary": "auto",
            "store": false
          }
        }
      }
    }
  },
  "mcp": {
    "auggie-mcp": {
      "type": "local",
      "command": [
        "auggie",
        "--mcp"
      ],
      "enabled": true
    },
    "chrome-devtools-mcp": {
      "type": "local",
      "command": [
        "npx",
        "-y",
        "chrome-devtools-mcp@latest"
      ],
      "enabled": false
    },
    "deepwiki": {
      "type": "remote",
      "url": "https://mcp.deepwiki.com/mcp",
      "enabled": true
    },
    "sequential-thinking": {
      "type": "local",
      "command": [
        "npx",
        "-y",
        "@modelcontextprotocol/server-sequential-thinking"
      ],
      "enabled": true
    }
  }
}

📌 转载信息
转载时间:
2026/1/12 10:37:54

给商店版来点好评吧,真的有用诶,审核确实变快了

同站点 Cookie 多账号支持:同站点多个 Cookie 账号也能和平共处

  • 支持同一站点下 多个 Cookie 认证账号共存,互不串号、功能也能正常用
  • Anyrouter 的 cookie 多账号已通过测试

模型情况更透明:各种可用性一测就知道

  • 模型列表新增 接口可用性检测(Beta)
    • 一次性测试常见能力:文本生成 / 工具调用 / 结构化输出(JSON)/ 联网搜索等
    • 每个检测项都有清晰结论:通过 / 失败 / 不支持,并能看到耗时,方便定位是接口问题还是模型问题
  • 模型列表新增 CLI 工具兼容性检测(Beta)
    • 直接模拟 Claude Code / Codex CLI / Gemini CLI 的调用
    • 提前判断 “在这些 CLI 里大概率能不能跑通”,少走很多弯路

兑换更省操作:批量兑换,失败重试

  • 兑换助手支持 批量兑换 功能,一次性解析并兑换多个兑换码,极大提升效率
  • 支持 单码重试:可以单个重试,失败的码不用整批重来

原生签到和外部签到站各走各路:再也不互斥

  • 拆分 “站点签到” 和 “自定义 / 外部签到” 的逻辑,互不干扰
  • 可以在原生签到的基础上,同时使用外部签到站 / 福利站,再也不用书签拉满(虽然其实原来就可以,但之前会互斥嘛

其他更顺手的优化

  • 侧边栏模式下会避免出现 “重复打开侧边栏” 的入口,减少误操作和干扰
  • CLIProxyAPI 导出时可以一起设置 代理 URL、以及 模型 name → alias 的映射列表,导出后更接近 “能直接用” 的状态

此为 3.0 - 3.2 的更新日志,更多内容请见: 更新日志 | All API Hub - 中转站管理器

完整插件介绍


📌 转载信息
原作者:
qi_xing_jk
转载时间:
2026/1/12 10:36:20

这两天死了么很火,作为小白的我也想试试,但是收费了,花钱不存在的。
纯小白,代码 ai 写的,我不会。简简单单的实现了功能,里面还可以加很多功能,注册用户,多用户通知,我就不为难 ai 了,交给你们这群程序员了~嘿嘿~

原理就是签到证明自己活着。

实现:每天都要充电,iPhone 用户插电运行快捷指令,访问固定域名,记录下来,然后到期没有再运行这个快捷指令就证明死了。发 bark 给接收人。

需要用到 Cloudflare 的 worker 和 kv,新建 kv 名称写 CLOCKIN_KV,里面的值是账号密码,照着抄就行。


worker 绑定要写对变量,如图:


worker 中设置运行时间,我设置的是一天两次 0 9,21 * * * 用的白嫖的域名。


iPhone 快捷指令就是一个简单的请求,我的用户名是 mengnimen 密码是 123456,到时候根据你自己在 kv 里设置的值自己改。

https://你的域名/clockin?user=mengnimen&pwd=123456

快捷新建一个 获取 URL 内容 即可。


在自动化中添加一个充电运行的,记得把立即运行打开

以后就是每次充电运行,记录你还活着,一天不记录,就会发通知给 bark 接收人

纯小白,代码 ai 写的,我不会。代码中需要添加 bark 地址,多长时间认为活着也可以改,自己看注释就行了。简简单单的实现了功能,里面还可以加很多功能,注册用户,多用户通知,我就不为难 ai 了,交给你们这群程序员了~嘿嘿

export default {
  async fetch(request, env, ctx) {
    const url = new URL(request.url);
    const path = url.pathname;

    try {
      if (path === "/" || path === "/health") return json({ ok: true });

      if (path === "/clockin") return await handleClockin(url, env);
      if (path === "/check") return await handleCheck(url, env);

      return json({ ok: false, error: "Not Found" }, 404);
    } catch (e) {
      return json({ ok: false, error: e?.message || String(e) }, 500);
    }
  },

  async scheduled(event, env, ctx) {
    ctx.waitUntil(runTimeoutCheck(env));
  },
};

const CONFIG = {
  ALERT_AFTER_DAYS: 1,
  MIN_ALERT_INTERVAL_HOURS: 6,
  DEFAULT_NOTIFY: { type: "bark", url: "" }, // 这里填默认 bark 或钉钉
  TITLE: "死了",
  NOTIFY_ON_CLOCKIN: false,
};

async function handleClockin(url, env) {
  const user = (url.searchParams.get("user") || "").trim();
  const pwd = (url.searchParams.get("pwd") || "").trim();
  if (!user || !pwd) return json({ ok: false, error: "Missing user or pwd" }, 400);

  const ok = await verifyUserPlain(user, pwd, env);
  if (!ok) return json({ ok: false, error: "Auth failed" }, 401);

  const now = Date.now();
  await env.CLOCKIN_KV.put(kLastTime(user), String(now));

  if (CONFIG.NOTIFY_ON_CLOCKIN) {
    await sendNotify(env, user, { title: "还活着", body: `已记录:${formatTime(now)}` });
  }

  return json({ ok: true, user, last_time: now, last_time_text: formatTime(now) });
}

async function handleCheck(url, env) {
  const user = (url.searchParams.get("user") || "").trim();
  const pwd = (url.searchParams.get("pwd") || "").trim();
  if (!user || !pwd) return json({ ok: false, error: "Missing user or pwd" }, 400);

  const ok = await verifyUserPlain(user, pwd, env);
  if (!ok) return json({ ok: false, error: "Auth failed" }, 401);

  const now = Date.now();
  const lastStr = await env.CLOCKIN_KV.get(kLastTime(user));
  const lastMs = lastStr ? Number(lastStr) : null;

  const thresholdMs = CONFIG.ALERT_AFTER_DAYS * 24 * 60 * 60 * 1000;
  return json({
    ok: true,
    user,
    now,
    now_text: formatTime(now),
    last_time: lastMs,
    last_time_text: lastMs ? formatTime(lastMs) : null,
    since_hours: lastMs ? round2((now - lastMs) / 3600000) : null,
    threshold_days: CONFIG.ALERT_AFTER_DAYS,
    is_timeout: lastMs ? (now - lastMs > thresholdMs) : true,
  });
}

async function runTimeoutCheck(env) {
  const now = Date.now();
  const thresholdMs = CONFIG.ALERT_AFTER_DAYS * 24 * 60 * 60 * 1000;
  const minIntervalMs = CONFIG.MIN_ALERT_INTERVAL_HOURS * 60 * 60 * 1000;

  let cursor = undefined;
  let checked = 0;
  let alerted = 0;

  while (true) {
    const listRes = await env.CLOCKIN_KV.list({ prefix: "user_pwd:", cursor });
    cursor = listRes.cursor;

    for (const k of listRes.keys) {
      const user = k.name.slice("user_pwd:".length);
      checked++;

      const lastStr = await env.CLOCKIN_KV.get(kLastTime(user));
      const lastMs = lastStr ? Number(lastStr) : 0;

      const timeout = !lastMs || (now - lastMs > thresholdMs);
      if (!timeout) continue;

      const lastAlertStr = await env.CLOCKIN_KV.get(kLastAlert(user));
      const lastAlertMs = lastAlertStr ? Number(lastAlertStr) : 0;
      if (lastAlertMs && (now - lastAlertMs < minIntervalMs)) continue;

      const hours = lastMs ? round2((now - lastMs) / 3600000) : null;
      const body = lastMs
        ? `你已超过 ${hours} 小时未进行“活着打卡”。\n上次记录:${formatTime(lastMs)}`
        : `未找到打卡记录,请连接充电器触发一次打卡。\n当前时间:${formatTime(now)}`;

      const ok = await sendNotify(env, user, { title: CONFIG.TITLE, body });
      if (ok) {
        alerted++;
        await env.CLOCKIN_KV.put(kLastAlert(user), String(now));
      }
    }

    if (listRes.list_complete) break;
  }

  await env.CLOCKIN_KV.put("meta:last_run", String(now));
  await env.CLOCKIN_KV.put("meta:last_run_summary", JSON.stringify({ now, checked, alerted }));
  return { checked, alerted, now };
}

/** 明文校验:KV 中 user_pwd:<user> 直接存明文 */
async function verifyUserPlain(user, pwd, env) {
  const stored = await env.CLOCKIN_KV.get(kUserPwd(user));
  if (!stored) return false;
  return stored === pwd;
}

async function sendNotify(env, user, msg) {
  let notify = null;
  const perUserStr = await env.CLOCKIN_KV.get(kNotify(user));
  if (perUserStr) {
    try { notify = JSON.parse(perUserStr); } catch {}
  }
  const type = notify?.type || CONFIG.DEFAULT_NOTIFY.type;
  const url = notify?.url || CONFIG.DEFAULT_NOTIFY.url;
  if (!url) return false;

  if (type === "dingtalk") return await sendDingTalk(url, msg);
  return await sendBark(url, msg);
}

async function sendBark(baseUrl, msg) {
  const title = encodeURIComponent(msg.title || "提醒");
  const body = encodeURIComponent(msg.body || "");
  const u = `${baseUrl.replace(/\/$/, "")}/${title}/${body}`;
  const r = await fetch(u, { method: "GET" });
  return r.ok;
}

async function sendDingTalk(webhookUrl, msg) {
  const payload = { msgtype: "text", text: { content: `${msg.title || "提醒"}\n\n${msg.body || ""}` } };
  const r = await fetch(webhookUrl, {
    method: "POST",
    headers: { "content-type": "application/json;charset=utf-8" },
    body: JSON.stringify(payload),
  });
  return r.ok;
}

const kUserPwd = (user) => `user_pwd:${user}`;
const kLastTime = (user) => `last_time:${user}`;
const kLastAlert = (user) => `last_alert:${user}`;
const kNotify = (user) => `notify:${user}`;

function json(obj, status = 200) {
  return new Response(JSON.stringify(obj, null, 2), {
    status,
    headers: { "content-type": "application/json; charset=utf-8" },
  });
}
function formatTime(ms) { return new Date(ms).toISOString(); }
function round2(n) { return Math.round(n * 100) / 100; }

📌 转载信息
转载时间:
2026/1/12 10:36:11

最近大家应该听说过一款叫 “死了么” 的 App。听说此 App 最近估值 1000 万了,相关新闻 “死了么” APP 下载量暴涨 100 倍!创始人:开发成本 1000 多元,计划以 100 万出让 10% 的股份

这么高估值的产品,需要 8 元才能使用,为了让人人都能用得起,我在此开源我花了 0.1 元(电费)与 72 秒开发的产品 ——Alive(活着呢)

如果您没有 1 分钟时间部署,也可以使用我部署好版本:活着呢

希望大家都能好好活着


📌 转载信息
原作者:
Amery2010
转载时间:
2026/1/12 10:35:49

18 号上午在深圳打印了银行卡流水、个税记录、支付宝理财证明、信用卡账单各种纸质材料。中午过口岸,在香港坐地铁去酒店的路上顺手开了众安卡,到酒店放置好行李立马去附近的中国银行。到现场得知已经没有号,只能明天来,经理提示说可以线上预约。当天晚上在酒店用手机流量申请中国银行账号,但是没有立马通过。由于没有找到线上预约的地方,于是早上八点出门去银行,到八点半到银行已经排很长的队了。九点准时开门,进去我以为跟大陆一样需要取号,到处找取号机。然后前面的一位小姐姐直接找经理要了号,我也学着过去要一个号,经理问我是要干嘛,我说开一张银行卡,于是给我一个号。后面就是等叫号,是用粤语叫号,我还怕我听不懂哈哈,实际会有工作人员用普通话提醒。在排队的时候会给你一个二维码,扫描二维码注册账号。办理的时候我把一堆文件拿出来给他,他只拿了信用卡账单、过关小票、港澳通行证。然后开始问我开卡的目的,我就说是投资港股,他问我有没有投资经验,我说在支付宝买了几万块的基金,他让我把支付宝打开给他看,他翻了交易记录和个人资料。后面又让我现场打开手机银行给他看工资流水,个税 app 看交税记录,都在 app 里重点看了个人资料。最后问我有没有更详细的地址证明材料,因为我的信用卡账单地址写的不清楚,我没有,当场以为办不下来了,后面他又说让我把账单 PDF 发给他邮箱,只能按账单地址填我的信息。后面就是输入密码开通理财的功能,最后就办下来了给我一个信封,我去 ATM 机激活就可以了。总体还是挺顺利的!最后感叹一下香港工作真的好轻松啊,工作人员办理完一个客户就会消失一段时间可能是休息去了,30 分钟后才回来,好惬意。


📌 转载信息
转载时间:
2026/1/12 10:35:30

排名不分先后,都是我用过的, 本文不做任何推荐

CC Switch 好像有个 bug, 余额查询的配置好像是不隔离的。

NewAPI 系列

以下几家中转站都是基于 NewAPI 搭建,所以查询余额较为简单

  • IKunCode
  • privnode
  • Duckcoding

配置步骤:

以 ikuncode 站为例,privnode/Duckcoding 步骤都一样

  1. 登录对应的网站,打开控制台 / 个人设置

  2. 点击安全设置,生成系统访问令牌

  3. 回到 CC-Switch, 配置用量查询,预设模板选择 NewAPI, 填入访问令牌和用户 ID

RightCode (订阅余额)

配置步骤:

  1. 预设模板选择 通用模板,填入请求地址 https://right.codes/subscriptions/list

  2. 登录网站 F12 控制台获取 bearer token(任意一个请求), 填入提取器代码(整个替换)

({
request: {
url: "https://right.codes/subscriptions/list",
method: "GET",
headers: {
Authorization: `f12控制台获取 bearer token`,
},
},
extractor: function (response) {
const now = new Date(); // 获取当前时间,用于比较 const results = response.subscriptions.reduce(
(acc, subscription, index) => {
// 解析过期时间 const expiredAt = new Date(subscription.expired_at);

// 判断是否过期:当前时间 > 过期时间,则跳过 if (now > expiredAt) {
return acc; // 跳过该项,直接返回已累积的数组
}

// 根据 reset_today 判断重置状态 const resetStatus = subscription.reset_today ? "已重置" : "未重置";
const extraInfo = `今天${resetStatus}`;

// 将符合条件的项添加到累积数组
acc.push({
id: subscription.id || `subscription_${index + 1}`,
remaining: subscription.remaining_quota,
planName: subscription.name,
unit: "USD",
// 新增的 extra 字段 extra: extraInfo,
});

return acc; // 返回更新后的累积数组
},
[],
); // 初始值为空数组 return results;
},
});

群里有个人开发了 vscode 插件可以更好的显示

cubence (余额)

配置步骤:

  1. 预设模板选择 通用模板,填入请求地址 https://cubence.com/api/v1/auth/me,并从网页端 F12 获取 cookie, 提取器代码填入以下代码:
({
  request: {
    url: "https://cubence.com/api/v1/auth/me",
    method: "GET",
    headers: {
      "Cookie": "token=<yourtoken>",
      "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:146.0) Gecko/20100101 Firefox/146.0"
    }
  },
  extractor: function(response) {
    return {
      remaining: response.user.normal_balance / 1000000,
      unit: "USD"
    };
  }
})

Yescode

步骤:

  1. 预设模板选择 通用模板,填入请求地址 https://co.yes.vg/api/v1/user/balance,并从网页端 F12 获取 cookie, 提取器代码填入以下代码:
({
  request: {
    url: "https://co.yes.vg/api/v1/user/balance",
    method: "GET",
    headers: {
      Cookie:
        "your_cookie",
      "User-Agent":
        "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:146.0) Gecko/20100101 Firefox/146.0",
    },
  },
  extractor: function (response) {
    return {
      remaining: response.balance,
      unit: "USD",
    };
  },
});

📌 转载信息
原作者:
unsafe
转载时间:
2026/1/12 10:35:17

前因

本人即将开启作为全栈工程师的个人职业生涯,但是鉴于之前 AI 开发的经历,开头一时爽快后,后面的代码缺乏各种文档和行之有效的项目迭代管理,导致 AI 开发的项目后面直接变成了屎山。于是本人就和 Claude 一顿头脑风暴,讨论 AI 时代的开发者如何进行迭代,能不能参考以前的敏捷开发的经验等等,忽略过程,最后我们输出这份 solo-agile-template

后果

这份模板采用前后端分离的方式,辅以 3m 原则和敏捷开发的思想,再搭配上各类低耦合的文档,让个人开发者拿到这个模板后只需要进行简单的本地化修改后就可以开始真正愉快的 coding 了。

我在这里抛砖引玉,欢迎佬友们一起来构建这个 template。


📌 转载信息
转载时间:
2026/1/12 10:35:05

测试一下港仔的 KDDI/au 5G Mobile VPS 产品,少数的日本蜂窩網絡 Mobile 家宽,ip 质量优秀,常规流媒体和本土流媒体基本全都解锁,机器性能强劲,i912900H 的 CPU 性能不错,IO 也不错。IPV4 三网不可直连,推荐中转,IPV6 部分地区可直连,带宽应该是 200Mbps,不过都买了这么贵的家宽了,应该不差这点中转费用了

这个机器为双 ip 策略

入口:idc V4入口或者KDDI家宽V6入 //可以自带IPV4入口,直接对接你的线路机器
出口:KDDI家宽V4出或者家宽V6出

测试配置为

2C2G 8GB 
CPE 5G蜂窩網絡Mobile 5G
IPv4 *1 & IPv6 /64 SLAAC
1T流量「工单免费重置」
98/

网络质量

IPV6 入

bestvm V4 入

测了一下日本本土互联,下载速度非常一般,这台前置貌似是限速了

BageVMBoil.5G PCE

23 packets transmitted, 23 received, 0% packet loss, time 22531ms
rtt min/avg/max/mdev = 0.321/0.405/0.507/0.046 ms

[ ID] Interval           Transfer     Bitrate
[  5]   0.00-1.00   sec  3.02 MBytes  25.3 Mbits/sec                  
[  5]   1.00-2.00   sec  4.07 MBytes  34.1 Mbits/sec                  
[  5]   2.00-3.00   sec  4.07 MBytes  34.2 Mbits/sec                  
[  5]   3.00-4.00   sec  2.11 MBytes  17.7 Mbits/sec                  
[  5]   4.00-5.00   sec  2.64 MBytes  22.2 Mbits/sec                  
[  5]   5.00-6.00   sec  4.36 MBytes  36.6 Mbits/sec                  
[  5]   6.00-7.00   sec  5.04 MBytes  42.2 Mbits/sec                  
[  5]   7.00-8.00   sec  11.9 MBytes   100 Mbits/sec                  
[  5]   8.00-9.00   sec  12.3 MBytes   103 Mbits/sec                  
[  5]   9.00-10.00  sec  1.54 MBytes  12.9 Mbits/sec                  
- - - - - - - - - - - - - - - - - - - - - - - - -
[ ID] Interval           Transfer     Bitrate         Retr
[  5]   0.00-10.03  sec  51.3 MBytes  42.9 Mbits/sec  6051             sender
[  5]   0.00-10.00  sec  51.1 MBytes  42.8 Mbits/sec                  receiver

[ ID] Interval           Transfer     Bitrate
[  5]   0.00-1.00   sec  7.88 MBytes  66.1 Mbits/sec                  
[  5]   1.00-2.00   sec  9.15 MBytes  76.8 Mbits/sec                  
[  5]   2.00-3.00   sec  15.2 MBytes   127 Mbits/sec                  
[  5]   3.00-4.00   sec  11.3 MBytes  95.0 Mbits/sec                  
[  5]   4.00-5.00   sec  3.80 MBytes  31.9 Mbits/sec                  
[  5]   5.00-6.00   sec  2.58 MBytes  21.7 Mbits/sec                  
[  5]   6.00-7.00   sec  2.29 MBytes  19.2 Mbits/sec                  
[  5]   7.00-8.00   sec  15.2 MBytes   127 Mbits/sec                  
[  5]   8.00-9.00   sec  22.0 MBytes   185 Mbits/sec                  
[  5]   9.00-10.00  sec  8.12 MBytes  68.2 Mbits/sec                  
[  5]  10.00-11.00  sec  2.39 MBytes  20.1 Mbits/sec                  
[  5]  11.00-12.00  sec  2.94 MBytes  24.6 Mbits/sec                  
[  5]  12.00-13.00  sec  2.32 MBytes  19.4 Mbits/sec                  
[  5]  13.00-14.00  sec   786 KBytes  6.44 Mbits/sec                  
[  5]  14.00-15.00  sec   708 KBytes  5.80 Mbits/sec                  
[  5]  15.00-16.00  sec   499 KBytes  4.09 Mbits/sec                  
[  5]  16.00-17.00  sec   551 KBytes  4.52 Mbits/sec                  
[  5]  17.00-18.00  sec   955 KBytes  7.82 Mbits/sec                  
[  5]  18.00-19.00  sec  1.65 MBytes  13.8 Mbits/sec                  
[  5]  19.00-20.00  sec   878 KBytes  7.19 Mbits/sec                  
[  5]  20.00-21.00  sec   672 KBytes  5.51 Mbits/sec                  
[  5]  21.00-22.00  sec   414 KBytes  3.39 Mbits/sec                  
[  5]  22.00-23.00  sec   487 KBytes  3.99 Mbits/sec                  
[  5]  23.00-24.00  sec  1.46 MBytes  12.3 Mbits/sec                  
[  5]  24.00-25.00  sec  5.53 MBytes  46.4 Mbits/sec                  
[  5]  25.00-26.00  sec  1.12 MBytes  9.42 Mbits/sec                  
[  5]  26.00-27.00  sec  1.08 MBytes  9.07 Mbits/sec                  
[  5]  27.00-28.00  sec   554 KBytes  4.54 Mbits/sec                  
[  5]  28.00-29.00  sec   373 KBytes  3.06 Mbits/sec                  
[  5]  29.00-30.00  sec   313 KBytes  2.57 Mbits/sec                  
[  5]  30.00-31.00  sec  5.22 MBytes  43.8 Mbits/sec                  
[  5]  31.00-32.00  sec  1.83 MBytes  15.4 Mbits/sec                  
[  5]  32.00-33.00  sec  15.4 MBytes   130 Mbits/sec                  
[  5]  33.00-34.00  sec  7.77 MBytes  65.2 Mbits/sec                  
[  5]  34.00-35.00  sec  7.04 MBytes  59.0 Mbits/sec                  
[  5]  35.00-36.00  sec  4.08 MBytes  34.2 Mbits/sec                  
[  5]  36.00-37.00  sec  2.04 MBytes  17.1 Mbits/sec                  
[  5]  37.00-38.00  sec  1.27 MBytes  10.7 Mbits/sec                  
[  5]  38.00-39.00  sec   554 KBytes  4.54 Mbits/sec                  
[  5]  39.00-40.00  sec  1.16 MBytes  9.73 Mbits/sec                  
[  5]  40.00-41.00  sec  6.31 MBytes  52.9 Mbits/sec                  
[  5]  41.00-42.00  sec  5.74 MBytes  48.2 Mbits/sec                  
[  5]  42.00-43.00  sec  4.96 MBytes  41.7 Mbits/sec                  
[  5]  43.00-44.00  sec  3.92 MBytes  32.8 Mbits/sec                  
[  5]  44.00-45.00  sec  3.29 MBytes  27.6 Mbits/sec                  
[  5]  45.00-46.00  sec  2.29 MBytes  19.2 Mbits/sec                  
[  5]  46.00-47.00  sec  3.12 MBytes  26.2 Mbits/sec                  
[  5]  47.00-48.00  sec  8.99 MBytes  75.4 Mbits/sec                  
[  5]  48.00-49.00  sec  13.0 MBytes   109 Mbits/sec                  
[  5]  49.00-50.00  sec  5.77 MBytes  48.4 Mbits/sec                  
[  5]  50.00-51.00  sec  1.10 MBytes  9.25 Mbits/sec                  
[  5]  51.00-52.00  sec  2.92 MBytes  24.5 Mbits/sec                  
[  5]  52.00-53.00  sec  2.81 MBytes  23.6 Mbits/sec                  
[  5]  53.00-54.00  sec  1.82 MBytes  15.3 Mbits/sec                  
[  5]  54.00-55.00  sec   458 KBytes  3.75 Mbits/sec                  
[  5]  55.00-56.00  sec   509 KBytes  4.17 Mbits/sec                  
[  5]  56.00-57.00  sec   501 KBytes  4.10 Mbits/sec                  
[  5]  57.00-58.00  sec   559 KBytes  4.58 Mbits/sec                  
[  5]  58.00-59.00  sec   819 KBytes  6.71 Mbits/sec                  
[  5]  59.00-60.00  sec   665 KBytes  5.45 Mbits/sec                  
- - - - - - - - - - - - - - - - - - - - - - - - -
[ ID] Interval           Transfer     Bitrate         Retr
[  5]   0.00-60.03  sec   239 MBytes  33.4 Mbits/sec  28034             sender
[  5]   0.00-60.00  sec   239 MBytes  33.4 Mbits/sec                  receiver

ip 质量

TK 是解锁的啊,这个脚本有点问题

IPV4 质量

IPV6 质量

常见流媒体解锁

---------------流媒体解锁--感谢oneclickvirt/UnlockTests测试----------------
Can not detect IPv6 Address
测试时间:  2026-01-11 20:15:17
IPV4:
============[ 跨国平台 ]============
Apple                     YES (Region: JPN)
BingSearch                YES (Region: JP)
Claude                    YES
Dazn                      YES (Region: JP)
Disney+                   YES (Region: JP)
Gemini                    YES (Region: JP)
GoogleSearch              YES
Google Play Store         YES (Region: JP)
IQiYi                     YES (Region: JP)
Instagram Licensed Audio  YES
KOCOWA                    NO
MetaAI                    YES (Region: US)
Netflix                   YES (Region: JP)
Netflix CDN               JP
OneTrust                  YES (Region: JP TOKYO)
ChatGPT                   YES (Region: JP)
Paramount+                YES
Amazon Prime Video        YES (Region: JP)
Reddit                    YES
SonyLiv                   Banned
Sora                      YES (Region: JP)
Spotify Registration      NO
Steam Store               YES (Community Available) (Region: JP)
TVBAnywhere+              YES (Region: JP)
TikTok                    YES (Region: JP)
Viu.com                   YES
Wikipedia Editability     YES
YouTube Region            YES (Region: JP)
YouTube CDN               kddi - HND
---------------------TikTok解锁--感谢lmc999的源脚本---------------------
 Tiktok Region:         【JP】

细分流媒体解锁

 ** 正在测试 IPv4 解锁情况
--------------------------------
 ** 您的网络为: au one net (59.132.*.*)
============[ Multination ]============
 Dazn:                                  Yes (Region: JP)
 Disney+:                               Yes (Region: JP)
 Netflix:                               Yes (Region: JP)
 YouTube Premium:                       Yes (Region: JP)
 Amazon Prime Video:                    Yes (Region: JP)
 TVBAnywhere+:                          Yes
 Spotify Registration:                  No
 OneTrust Region:                       JP [Tokyo]
 iQyi Oversea Region:                   JP
 Bing Region:                           JP (Risky)
 Apple Region:                          JP
 YouTube CDN:                           [KDDI] in [Tokyo]
 Netflix Preferred CDN:                 Tokyo
 ChatGPT:                               Yes
 Google Gemini:                         Yes (Region: JPN)
 Claude:                                Yes
 Wikipedia Editability:                 Yes
 Google Play Store:                     Japan 
 Google Search CAPTCHA Free:            Yes
 Steam Currency:                        JPY
 ---Forum---
 Reddit:                                Yes
 ---Game---
 SD Gundam G Generation Eternal:        Yes
=======================================
===============[ Japan ]===============
 DMM:                                   Yes
 DMM TV:                                Yes
 Abema.TV:                              Yes (Region: JP)
 Niconico:                              Failed (Error: PAGE ERROR)
 Telasa:                                Yes
 U-NEXT:                                Yes
 Hulu Japan:                            Yes
 TVer:                                  Failed (Error: PAGE ERROR)
 Lemino:                                Yes
 AnimeFesta:                            Yes
 WOWOW:                                 Failed (Error: PAGE ERROR 1)
 VideoMarket:                           Yes
 D Anime Store:                         Yes
 FOD(Fuji TV):                          Yes
 Radiko:                                Yes (City: KAGOSHIMA)
 Karaoke@DAM:                           Yes
 J:com On Demand:                       Yes
 WATCHA:                                Yes
 Rakuten TV JP:                         Failed (Error: PAGE ERROR 1)
 ---Game---
 Kancolle Japan:                        Failed (Network Connection)
 Pretty Derby Japan:                    Yes
 Konosuba Fantastic Days:               Failed (Network Connection)
 Princess Connect Re:Dive Japan:        Yes
 Project Sekai: Colorful Stage:         Yes
 ---Music---
 Mora:                                  Yes
 music.jp:                              Yes
 ---Forum---
 EroGameSpace:                          Yes
=======================================

常见 IP 库结果

-------------IP质量检测--基于oneclickvirt/securityCheck使用--------------
数据仅作参考,不代表100%准确,如果和实际情况不一致请手动查询多个数据库比对
以下为各数据库编号,输出结果后将自带数据库来源对应的编号
ipinfo数据库  [0] | scamalytics数据库 [1] | virustotal数据库   [2] | abuseipdb数据库   [3] | ip2location数据库    [4]
ip-api数据库  [5] | ipwhois数据库     [6] | ipregistry数据库   [7] | ipdata数据库      [8] | db-ip数据库          [9]
ipapiis数据库 [A] | ipapicom数据库    [B] | bigdatacloud数据库 [C] | dkly数据库        [D] | ipqualityscore数据库 [E]
ipintel数据库 [F] | ipfighter数据库   [G] | fraudlogix数据库   [H] | cloudflare数据库  [I] |
IPV4:
安全得分:
信任得分(越高越好): 100 [8] 
VPN得分(越低越好): 0 [8] 
代理得分(越低越好): 0 [8] 
社区投票-无害: 0 [2] 
社区投票-恶意: 0 [2] 
威胁得分(越低越好): 0 [8] 
欺诈得分(越低越好): 28 [E] 
滥用得分(越低越好): 0 [3] 
威胁级别: low [9] 
流量占比: 真人(越高越好)96% [I] 机器人(越低越好)3% [I]
黑名单记录统计:(有多少黑名单网站有记录):
无害记录数: 0 [2]  恶意记录数: 0 [2] 可疑记录数: 0 [2]  无记录数: 93 [2] 
安全信息:
使用类型: unknown [C] business [9] cellular [3] isp [0 7 8]
公司类型: isp [0 7] 
浏览器类型: 主流37% 其他62% [I] 
设备类型: 桌面27% 移动72% 其他0% [I] 
操作系统类型: 主流98% 其他1% [I] 
是否云提供商: No [7 D] 
是否数据中心: No [0 5 8 C G] 
是否移动设备: No [5 G] Yes [C E]
是否代理: Yes [G] No [0 4 5 7 8 9 C D E]
是否VPN: No [0 7 C D E G] 
是否Tor: No [0 3 7 8 C D E] 
是否Tor出口: No [7 D] 
是否网络爬虫: No [9 E]
是否匿名: No [7 8 D] 
是否攻击者: No [7 8 D] 
是否滥用者: No [7 8 C D E] 
是否威胁: No [7 8 C D] 
是否中继: No [0 7 8 C D] 
是否Bogon: No [7 8 C D] 
是否机器人: No [E] 
Google搜索可行性:NO
------------邮件端口检测--基于oneclickvirt/portchecker开源------------
Platform  SMTP  SMTPS POP3  POP3S IMAP  IMAPS
LocalPort ✔     ✔     ✔     ✔     ✔     ✔    
QQ        ✔     ✔     ✔     ✘     ✔     ✘    
163       ✔     ✔     ✔     ✘     ✔     ✘    
Sohu      ✔     ✔     ✔     ✘     ✔     ✘    
Yandex    ✔     ✔     ✔     ✘     ✔     ✘    
Gmail     ✔     ✔     ✘     ✘     ✘     ✘    
Outlook   ✔     ✘     ✔     ✘     ✔     ✘    
Office365 ✔     ✘     ✔     ✘     ✔     ✘    
Yahoo     ✔     ✔     ✘     ✘     ✘     ✘    
MailCOM   ✔     ✔     ✔     ✘     ✔     ✘    
MailRU    ✔     ✔     ✘     ✘     ✔     ✘    
AOL       ✔     ✔     ✘     ✘     ✘     ✘    
GMX       ✔     ✔     ✔     ✘     ✔     ✘    
Sina      ✔     ✔     ✔     ✘     ✔     ✘    
Apple     ✘     ✘     ✘     ✘     ✘     ✘    
FastMail  ✘     ✔     ✘     ✘     ✘     ✘    
ProtonMail✘     ✘     ✘     ✘     ✘     ✘    
MXRoute   ✔     ✘     ✔     ✘     ✔     ✘    
Namecrane ✔     ✔     ✔     ✘     ✔     ✘    
XYAMail   ✘     ✘     ✘     ✘     ✘     ✘    
ZohoMail  ✘     ✔     ✘     ✘     ✘     ✘    
Inbox_eu  ✔     ✔     ✔     ✘     ✘     ✘    
Free_fr   ✘     ✔     ✔     ✘     ✔     ✘  

机器性能


📌 转载信息
原作者:
STALK
转载时间:
2026/1/12 10:34:35