有没有简单高效可靠的方法防止 web 服务半夜定时执行的耗时任务被恶意执行? - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
shendaowu
V2EX    信息安全

有没有简单高效可靠的方法防止 web 服务半夜定时执行的耗时任务被恶意执行?

  •  
  •   shendaowu 28 天前 3325 次点击

    我要求是不是太多了?如果属于不可能三角的话可以去掉高效。反正本来就是很耗时的任务,除非会大幅影响其他页面的延迟之类的。

    耗时任务是一些数据库查询,还有数据库备份,可能还会有别的。每天每种只执行一次。

    我目前计划用 cron 定时访问 web 服务的一个地址。后端语言是 Go 。Go 有个很多人用的第三方的 cron 库,但是五年没更了,看 issue 好像也不是没问题,不敢用。

    我问 deepseek 它说验证源 IP 是不是 127.0.0.1 、::1 、localhost 就行了。另外需要注意一些特殊情况。比如代理、负载均衡器和容器。这个有漏洞吗?还要不要在耗时任务执行之前加个时段判断和今天是否已经执行过了?还有当前是否正在执行耗时任务。cron 好像在特殊情况下会重复执行?比如修改系统时间。

    主要需求就是防止这个东西成为被攻击的点。

    34 条回复    2025-09-12 15:57:43 +08:00
    totoro625
        1
    totoro625  
       28 天前   1
    定时访问 web 服务的一个地址
    nginx 里面把 URL 改成随机字符串

    验证源 IP
    主要看你自己的设置

    cron 重复执行
    用 systemd timer 替代
    oh
        2
    oh  
       28 天前   1
    nginx 里把那个 location 屏蔽掉
    本地 cron 直接访问本地端口
    Zakl21
        3
    Zakl21  
       28 天前   1
    加个对称加密就行了把
    shendaowu
        4
    shendaowu  
    OP
       28 天前
    实在不行简单也去掉吧,最重要的是可靠。
    sduoduo233
        5
    sduoduo233  
       28 天前 via Android   1
    把定时任务拆分成一个单独的二进制文件
    用 cron 定时执行这个二进制
        6
    mengdodo  
       28 天前   1
    历史的经验告诉我们:对应旧项目的老代码,如果自己是接手方,最好就是别动,出问题拿 commit 节点去找人背锅即可。如果别人已离职更好,把锅架他们头上还不会反驳你。
    faceRollingKB
        7
    faceRollingKB  
       28 天前   1
    定义恶意,代码识别恶意,处理恶意
    opengps
        8
    opengps  
       28 天前   1
    我没看明白怎么来的恶意,如果说你使用对外特定接口来做,那么 ds 说的没错,过滤掉白名单之外,自己就可控了。
    94
        9
    94  
       28 天前   1
    对应的 web 服务不对外开放出去不就好了吗?而且数据库备份这种阿里云这种服务商不都是有提供自动备份的功能么,直接用就好了哇。
    如果怕重复执行了,在业务里面增加一个是否执行的标识就好了。

    至于修改系统时间之类的不用放在应该考虑的范围内,如果不是自己修改时间或者时间同步服务器出现问题就不会出现回到历史时间的情况。如果是服务器失守了,在某一个业务里面干啥防御都没有用。
    dode
        10
    dode  
       28 天前   1
    内存设置一个状态,每次执行前检查状态+当前时间,然后在系统内配置一个定时任务脚本,每天自动启动就行,还可以为这个接口加配一个随机密钥参数,简单验证权限
    wogogoing
        11
    wogogoing  
    PRO
       28 天前 via iPhone   1
    robfig/cron 这个库没什么问题,用了好几年了。

    op 可以瞅瞅我实现的计划任务:

    https://go-sail.dev/zh-CN/docs/examples/schedule
    xuanbg
        12
    xuanbg  
       28 天前   1
    不能远程执行的就都很安全,除非服务器被入侵
    FrankAdler
        13
    FrankAdler  
       28 天前 via Android   1
    什么叫被恶意执行
    shendaowu
        14
    shendaowu  
    OP
       28 天前
    @sduoduo233 #5 感谢大佬。我感觉你这个方法的可靠性是碾压性的,就是有点麻烦,如果没有更好的方法我就用这个了。之前我总想就靠一个单独的二进制文件,现在想象好像好处也不是碾压性的。
    shendaowu
        15
    shendaowu  
    OP
       28 天前
    @FrankAdler #13 像 DDoS 那样疯狂调用,然后降低或者破坏系统的可用性。
    FrankAdler
        16
    FrankAdler  
       28 天前 via Android   1
    不对外开放不就行了吗,开放了加个鉴权也行,你在纠结什么
    shendaowu
        17
    shendaowu  
    OP
       28 天前
    @FrankAdler #16 我在纠结我垃圾的智商无法考虑到所有危险的情况。另外我被某小日子写的安全书籍洗脑了,里面提到不是安全专家就别期待自己拍脑袋想出来的方案有多安全。
    oh
        18
    oh  
       28 天前   1
    @shendaowu #14 那也没解决你正文中说的 “修改系统时间 引起 cron 重复执行” 的问题……
    ericguo
        19
    ericguo  
       28 天前   1
    https://github.com/go-dev-frame/sponge/tree/main/pkg/gocron

    你为啥需要通过 web 访问来触发,直接写成 gocron.Run 不就好了。。。
    cheng6563
        20
    cheng6563  
       28 天前   1
    算了吧,这问题也想那么多,不如给我服务器账号,我来帮你搞定。
    ggzhyipeng
        21
    ggzhyipeng  
       28 天前   1
    robfig/cron 我们生产用挺久了,没啥问题吧。
    实在要用外部 cron 的话,接口限制只能从内网/127 调用,或者改成命令行调用
    edward1987
        22
    edward1987  
       28 天前   1
    执行前加个锁呗,就算被多次调用也不怕
    zjyl1994
        23
    zjyl1994  
       28 天前   1
    robfig/cron 没什么问题,程序里直接调用肯定是最安全的。
    如果非要通过 http 进行触发,可以加个 token 验证。

    至于被人进到服务器里面改时间反复触发 cron ,很难解决的。还是要做好防护把安全问题拦在外面。
    juzisang
        24
    juzisang  
       28 天前   1
    加个 token 校验或者随机字符的 url 不就行了,就是个普普通通的 webhook 需求...
    sthwrong
        25
    sthwrong  
       28 天前   1
    触发多次的问题可以上锁,同一个任务只有一个实例在执行。接口鉴权和高频请求都好处理。至于系统时间修改,都能改时间了估计也能删你库了,那没啥了。
    way2create
        26
    way2create  
       28 天前   1
    不知道在讲什么,你定义的恶意执行是什么呢?不如举几个实际场景吧,不要虚空索敌。
    sagnitude
        27
    sagnitude  
       28 天前   1
    1. 管理接口也对互联网开放并且不加任何认证措施?
    2. 为什么不另起一个服务或者 docker 去做耗时的任务?放在生产服务器上跑这种任务是严重影响使用的,万一跑到早上呢,万一出错把线程池占满了,早上起来所有客户都 boom 了呢
    3. 就好比用 spring 的定时执行就可以做到的事情,不应当暴露一个接口出来,其他语言也肯定有类似的功能
    4. 内网找另一台机器用 crontab 启动/停止一个单独的程序,执行完就关掉是最好的
    momocraft
        28
    momocraft  
       28 天前   1
    单独二进制(或者进程入口)挺好的
    不要用 http 触发
    itechify
        29
    itechify  
    PRO
       28 天前   1
    加参数校验
    realpg
        30
    realpg  
    PRO
       28 天前   1
    你连个鉴权都不会写吗?
    ruanimal
        31
    ruanimal  
       28 天前   1
    @sduoduo233 复用二进制文件,加个参数就行了啊
    yinmin
        32
    yinmin  
       28 天前 via iPhone   1
    类似 openai 的 api 认证 key ,每次 web api 调用时都验证 http request header

    Authorization: Bearer YOUR_API_KEY

    然后客户端请求的时候加上 YOUR_API_KEY 访问你的 web api
    litchinn
        33
    litchinn  
       28 天前   1
    首先考虑这个定时任务是不是非得以 http 接口的形式调用 否:用应用内部调度器实现
    这个 http 接口是否必须暴露到外网 是:添加白名单或者认证机制 否:禁止外网的直接访问
    重复执行的问题,如果已经有能修改你的系统时间的权限了,那应该没法避免,重复执行些任务已经是轻的了
    你应该要重点考虑的是这个“耗时任务”会不会影响系统正常功能,能不能限制它使用的资源
    momocraft
        34
    momocraft  
       28 天前
    如果需要理论依据:这类负载类似于 12 factor app 里的这个: https://www.12factor.net/admin-processes
    建议做法是从同一套代码构建,但是和 web server 分开执行
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     1221 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 23ms UTC 17:24 PVG 01:24 LAX 10:24 JFK 13:24
    Do have faith in what you're doing.
    ubao snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86