• R语言
  • 求 Windows 用户测试 xfun::mime_type()

前两天写了一个函数 xfun::mime_type() 用来获取文件的 MIME 类型,这事在 *nix 系统下很容易通过 file 命令完成,但在 Windows 下不一定有这个命令(除非系统安装了 Cygwin 或者 R 兔子)。如果没有的话,那么就绕道用 PowerShell,但那需要系统中安装了 .NET,于是我无法确定这玩意儿在 Windows 上到底靠不靠谱。我自己在 Windows 上测了一下貌似还行,如果其他人也能帮忙测试一下就更好了。

install.packages('xfun', repos = 'https://yihui.r-universe.dev')

重启 R,然后传一些文件路径给 xfun::mime_type,如:

xfun::mime_type(list.files(), FALSE, NA)

返回结果应该是诸如 text/plain application/pdf image/png 之类的字符串。

    yihui 这是我的测试结果:

    > xfun::mime_type(list.files('D:/temp'), FALSE, NA)
     [1] "image/png"                                                              
     [2] "image/png"                                                              
     [3] "application/pdf"                                                        
     [4] "application/pdf"                                                        
     [5] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
     [6] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
     [7] "application/zip"                                                        
     [8] "inode/directory"                                                        
     [9] "application/zip"                                                        
    [10] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
    [11] "inode/directory"                                                        
    [12] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
    [13] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
    [14] "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"      
    [15] "inode/directory"                                                        
    [16] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
    [17] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
    [18] "text/plain"                                                             
    [19] "inode/directory"                                                        
    [20] "application/pdf"                                                        
    [21] "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"      
    [22] "application/vnd.openxmlformats-officedocument.wordprocessingml.document"
    [23] "text/plain"                                                             
    [24] "application/pdf"                                                        
    [25] "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"      
    [26] "image/svg+xml"                                                          
    [27] "text/html"                                                              
    [28] "inode/directory"                                                        
    [29] "inode/directory" 
    > sessionInfo()
    R version 4.4.1 (2024-06-14 ucrt)
    Platform: x86_64-w64-mingw32/x64
    Running under: Windows 10 x64 (build 19045)
    
    Matrix products: default
    
    
    locale:
    [1] LC_COLLATE=Chinese (Simplified)_China.utf8  LC_CTYPE=Chinese (Simplified)_China.utf8    LC_MONETARY=Chinese (Simplified)_China.utf8
    [4] LC_NUMERIC=C                                LC_TIME=Chinese (Simplified)_China.utf8    
    
    time zone: Asia/Shanghai
    tzcode source: internal
    
    attached base packages:
    [1] stats     graphics  grDevices utils     datasets  methods   base     
    
    loaded via a namespace (and not attached):
    [1] compiler_4.4.1    tools_4.4.1       rstudioapi_0.16.0 cellranger_1.1.0  writexl_1.5.0     readxl_1.4.3      xfun_0.47.4   

      用虚拟机测试了微软目前两个存在支持的主线系统版本(对应的各自最早的一般可用版本):

      • Windows 10 2015 LTSB 10240.16384 (2015-07-08)
      • Windows 11 21H2 22000.194 (2021-09-10)

      可以看到裸系统都自带了 Windows Powershell,只安装一个 R for Windows 运行以上可以得到结果(虽然大部分会返回 application/octet-stream)。

      假设在接下来的版本中系统自带的 PowerShell 环境没有对这个接口做出改变,这个解决方案应该是妥妥的。

        nan.xiao 太好了,谢谢!返回 application/octet-stream 没关系,聊胜于无。我刚又加固了一道防御工事,先用 tools:::mime_type() 抵挡一下,这样真正需要用到命令行的可能性就很小了(前面有三重罗生门:如果安装了 mime 包就先用包、再查我自己的 xfun:::mimemap、再查 tools:::mime_type();如果还查不到,最后再到命令行)。

        yihui 是的,但是从没用过 file.exe。

        > Sys.which('file')
                                      file 
        "C:\\rtools44\\usr\\bin\\file.exe"