求助:大文件写入数据库报错 OutOfMemoryError: Java heap space - V2EX
ASpiral
V2EX    Java

求助:大文件写入数据库报错 OutOfMemoryError: Java heap space

  •  
  •   ASpiral May 9, 2019 3559 views
    This topic created in 2560 days ago, the information mentioned may be changed or developed.

    想把前端通过网页上传的文件写入 mysql,后台用的公司的框架(基于 spring+mybatis),数据库表字段类型用 longblob,实体类字段类型用 byte[];
    文件较小的时候读写都没问题,但文件稍微大点写入就报错,试了下大概大于 128M 就不行了

    java.lang.OutOfMemoryError: Java heap space at java.util.Arrays.copyOf(Arrays.java:3332) at java.lang.AbstractStringBuilder.ensureCapacityInternal(AbstractStringBuilder.java:124) at java.lang.AbstractStringBuilder.append(AbstractStringBuilder.java:448) at java.lang.StringBuilder.append(StringBuilder.java:136) ...(从这里开始的报错来自框架) 

    通过本地调试,发现后台在接收完文件准备写入数据库阶段报错,在这阶段任务管理器的"java.exe"进程从 1000MB+飙到 2000MB+,试着添加 JVM 参数-Xmx2048m 还是不行…
    我才写入一个 100M+的文件怎么内存就占这么多了… mysql 的 longblob 可以存 4G,这么大的文件一般是怎么读写的啊?有没有办法像流那样从开始接收文件时就写入数据库,边读边写,并且可以事务控制?
    求大佬给点思路或者有没有现成的轮子可以用…

    16 replies    2019-05-10 16:41:08 +08:00
    kaneg
        1
    kaneg  
       May 9, 2019 via iPhone
    你估计把整个文件读到内存了,内存在对象传递过程中可能还要复制来复制去,所以最终比文件大。你要做的就是用分段或者流式写入数据库。
    wc951
        2
    wc951  
       May 9, 2019 via Android
    byte[]改成 blob 用流
    wc951
        3
    wc951  
       May 9, 2019 via Android
    更好的办法是数据库存文件路径,文件单独存储,不管是磁盘存储还是 dfs 都可以
    gz911122
        4
    gz911122  
       May 9, 2019   1
    文件请存 oss,
    数据库保留路径就可以了
    momocraft
        5
    momocraft  
       May 9, 2019
    jdbc 可以绑 InputStream 为 SQL 参数
    fhsan
        6
    fhsan  
       May 9, 2019
    文件肯定存到本地、HDFS、云硬盘之类的,怎么会有写入数据库这种操作?我以前的公司有人就喜欢存 JSON 到数据库,每次查询都卡爆。
    opengps
        7
    opengps  
       May 9, 2019
    文件为啥要写入数据库?
    ASpiral
        8
    ASpiral  
    OP
       May 9, 2019
    @kaneg @wc951 @momocraft
    用流不知道怎么操作…实体类字段用 Blob 类型在写入数据库时值变成 nul 了,难道得手动获取 PreparedStatement 手写 sql 语句再 setBlob 吗?这样就用不了框架自带的事务控制了…
    @gz911122 @fhsan @opengps
    需求就是这样…数据库都有 blob 类型字段为什么不给写入数据库啊?
    gz911122
        9
    gz911122  
       May 9, 2019
    @ASpiral
    1 blob 不是用来存文件的
    2 减轻数据库压力
    3 减轻带宽压力
    4 提高速度
    opengps
        10
    opengps  
       May 9, 2019
    @ASpiral 文件写入数据库虽然不排斥,但是也不提倡。
    大文件读写很占用的连接比较久,而且文件类往往可能有静态加速等方式,行锁需要担心的问题,在大文件写入时候会暴露的更加明显等
    des
        11
    des  
       May 9, 2019
    数据库写文件还是不要了吧,更何况还是这么大的文件
    micean
        12
    micean  
       May 9, 2019
    #5 +1
    youxiachai
        13
    youxiachai  
       May 9, 2019
    想起我刚入行的时候......
    就有人跟我说,数据库的二进制不是用来纯文件的....
    fhsan
        14
    fhsan  
       May 9, 2019
    数据库变的巨大,数据库字段的 IO 远远的低于文件系统的 IO,越来越耗时间
    文件的备份、还原、查找、内容检索等等,也成了一大问题
    如果文件频繁读写增删改查数据,你的数据库立马就崩掉,即使不崩也无法处理大的负载
    数据库锁的问题,如果一个人修改字段会阻塞其他读的,直接 500 超时
    ASpiral
        15
    ASpiral  
    OP
       May 9, 2019
    @all 感谢各位的建议!
    跟领导反馈了,领导的意见是先实现了再说,毕竟这是客户需求
    以后应该是另建一个数据库放文件存储的表,单独一台服务器,后台跟数据库服务器都在内网
    领导建议我文件分块写入数据库,存做多条记录,我该研究怎么分块写入跟取出了…
    sonyxperia
        16
    sonyxperia  
       May 10, 2019
    百兆的文件写入数据库= =
    客户的要求也不能都答应啊
    About     Help     Advertise     Blog     API     FAQ     Solana     3090 Online   Highest 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 69ms UTC 15:08 PVG 23:08 LAX 08:08 JFK 11:08
    Do have faith in what you're doing.
    ubao msn 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