Perfex Security 是一套面向 Perfex CRM 模块开发的安全编码模式集合,目标读者是 Perfex CRM 安全工程师,用于编写能够抵御并发请求、攻击者可控输入和枚举尝试的模块代码。资料称这些模式提炼自生产环境的 Perfex 部署,每一条都对应一次真实事故。
一、用途 该技能用于在 Perfex CRM 模块开发中落实具体的安全模式,包括原子化令牌消费、限流的布尔状态接口、来源校验的重定向以及 PII 安全日志等。
二、主要能力(按资料列出的模式)
- 开放重定向防护:任何基于用户输入进行重定向的接口都必须校验目标。只允许以单个 / 开头的相对路径;若必须允许绝对 URL,则需对照 site_url() 做白名单校验。协议相对 URL(//evil.com)属于绝对 URL,会被上述检查拒绝。
- 一次性令牌消费的竞态安全模式:令牌(密码重置、magic link 登录、确认链接)在并发下必须单次使用。应使用带 WHERE used=0 的原子 UPDATE,再检查 affected_rows() === 1 来证明是当前请求消费了它。禁止先 SELECT 再 UPDATE,否则存在 TOCTOU 竞态,两个同时打开的标签页都会通过 SELECT 并执行操作。
- 令牌签发:签发新令牌不应使之前未使用的令牌失效;单次使用加 TTL 已足够。轮换会让用户邮件客户端中已点击的 magic link 失效,导致支持工单。过期令牌应通过 cron(app_init 加每日一次标志)清理,而不是每次签发时清理。
- 布尔状态接口限流:任何针对攻击者可控输入返回是/否的 AJAX 接口都是枚举预言机,常见于注册时的“邮箱是否存在”、用户名是否被占用、优惠券是否有效等。资料建议每 IP 每 60 秒 10 次尝试。
- 跨模块依赖:其他模块可能被卸载,需用 file_exists 做防御性守卫,否则会致命错误。
- 日志中的 PII:只记录用户 ID,绝不记录邮箱、电话、地址、出生日期;绝不记录密码、令牌、卡号或其哈希。生产日志应可被运维读取但不公开,需确认 application/logs/ 位于 deny-from-all 的 .htaccess 之后。
- target="_blank" 链接:每个 target="_blank" 都必须带 rel="noopener noreferrer",适用于管理端和客户区视图。
- CSRF:Perfex 内置 CSRF(application/config/app-config.php 中的 APP_CSRF_PROTECTION,由 config.php 读取;任何包含 gateways/ 的 URI 会被强制禁用)。CI 会自动向 form_open() 表单注入令牌。原始 AJAX 请求必须发送令牌,核心在管理端/客户区页面暴露 JS 全局 csrfData = {token_name, hash, formatted},核心自身的 $.ajaxSetup 已将其附加到 jQuery POST。对于 fetch()/XHR 需自行添加,且必须作为 POST 字段,因为 CI 读取 $_POST,不读 JSON body 或 header。JSON body 无论内容如何都会失败。Perfex 在设置 X-Requested-With: XMLHttpRequest(jQuery)时返回 419 Page Expired,否则(裸 fetch())返回 403。服务端等价物是 $this->security->get_csrf_token_name() / $this->security->get_csrf_hash(),不存在独立的 csrf_hash() 辅助函数。被外部服务调用的 webhook 接口需要排除 CSRF,列表应随模块一起提供,由核心的 InitModules 钩子合并。
- 输入校验:使用 CI 的表单校验库设置规则,不要信任客户端。
- HTML 输出:对用户提供的 HTML 原始输出使用 html_purify();模板文本字段使用 e($value)(Perfex 在 application/config/hooks.php 中定义了 Laravel 风格的 e(),即 htmlspecialchars 配合 ENT_QUOTES | ENT_SUBSTITUTE、UTF-8)。不存在 esc()。
- 反序列化漏洞(Perfex 3.4.1 补丁):Perfex 3.4.1 修复了捆绑第三方库中不安全反序列化导致的严重未认证远程代码执行,影响大多数更早版本。绝不 unserialize() 用户可控输入,改用 json_decode();若必须反序列化,使用 allowed_classes 选项(PHP 7.0+)。还需审计模块捆绑的第三方库是否存在同样模式。
- CSRF 排除的模块配置文件:对于模块自有的 webhook 接口,规范机制是模块内的配置文件,application/hooks/InitModules.php 会为每个有效模块读取并合并到 csrf_exclude_uris 过滤器。条目以 preg_match('#^<entry>$#i', $uri) 匹配 URI 字符串(无前导斜杠、无 index.php),因此 (:any) 路由通配符无效,需使用正则。也可在运行时通过 hooks()->add_filter('csrf_exclude_uris', ...) 计算列表。两者都自包含于模块内并随模块移除。绝不要编辑 application/config/config.php,它会在更新时被替换。无论使用哪种方式,被排除的接口都没有请求认证,必须在处理载荷前验证 PSP 签名(hash_equals(hash_hmac(...)))并保证幂等。
三、使用方式 资料以代码示例形式给出错误与正确写法,开发者可对照修改模块代码。相关技能包括 perfex-core-apis、perfex-database、perfex-email、perfex-theme、perfex-payment-gateway。上游参考包括 Perfex 模块安全文档、OWASP 令牌设计、CI3 安全文档。资料称已对照 Perfex CRM 3.4.0 核心源码于 2026-09-15 验证。
四、适用场景 适用于为 Perfex CRM 编写或审计模块代码,尤其是涉及令牌、重定向、AJAX 布尔接口、webhook、日志和跨模块依赖的场景。
五、限制 资料未提供该技能的安装方式、收费模式、平台支持范围或效果数据,这些信息暂未提供。