Check installed packages for working native modules

Test require each native module in each installed package to make sure
it can be required successfully in Atom.
This commit is contained in:
Kevin Sawicki 2014-07-25 15:19:16 -07:00
parent caa6f9b06e
commit 1ea909d4db
8 changed files with 72 additions and 0 deletions

View File

@ -0,0 +1 @@
throw new Error("this simulates a native module's failure to load")

View File

@ -0,0 +1,4 @@
{
"name": "native-module",
"main": "./main.js"
}

View File

@ -0,0 +1,4 @@
{
"name": "package-with-incompatible-native-module",
"main": "./main.js"
}

View File

@ -1,8 +1,17 @@
{$} = require 'atom'
path = require 'path'
Package = require '../src/package'
ThemePackage = require '../src/theme-package'
describe "Package", ->
describe "when the package contains incompatible native modules", ->
it "does not activate it", ->
packagePath = atom.project.resolve('packages/package-with-incompatible-native-module')
pack = new Package(packagePath)
expect(pack.isCompatible()).toBe false
expect(pack.incompatibleModules[0].name).toBe 'native-module'
expect(pack.incompatibleModules[0].path).toBe path.join(packagePath, 'node_modules', 'native-module')
describe "theme", ->
theme = null

View File

@ -36,6 +36,7 @@ class PackageManager
@loadedPackages = {}
@activePackages = {}
@incompatiblePackages = {}
@packageStates = {}
@packageActivators = []
@ -159,6 +160,7 @@ class PackageManager
pack = new Package(packagePath, metadata)
pack.load()
@loadedPackages[pack.name] = pack
@incompatiblePackages[pack.name] = pack unless pack.isCompatible()
pack
catch error
console.warn "Failed to load package.json '#{path.basename(packagePath)}'", error.stack ? error

View File

@ -269,6 +269,7 @@ class Package
requireMainModule: ->
return @mainModule if @mainModule?
return unless @isCompatible()
mainModulePath = @getMainModulePath()
@mainModule = require(mainModulePath) if fs.isFileSync(mainModulePath)
@ -340,3 +341,54 @@ class Package
for eventHandler in eventHandlers
eventHandler.handler = eventHandler.disabledHandler
delete eventHandler.disabledHandler
containsNativeModule: (modulePath) ->
try
fs.listSync(path.join(modulePath, 'build', 'Release'), ['.node']).length > 0
catch error
false
getNativeModuleDependencyPaths: ->
nativeModulePaths = []
traversePath = (nodeModulesPath) =>
try
for modulePath in fs.listSync(nodeModulesPath)
if @containsNativeModule(modulePath)
nativeModulePaths.push(modulePath)
traversePath(path.join(modulePath, 'node_modules'))
traversePath(path.join(@path, 'node_modules'))
nativeModulePaths
getIncompatibleNativeModules: ->
incompatibleNativeModules = []
for nativeModulePath in @getNativeModuleDependencyPaths()
try
require(nativeModulePath)
catch error
incompatibleNativeModules.push
path: nativeModulePath
name: path.basename(nativeModulePath)
error: error
incompatibleNativeModules
# Public: Is this package compatible with this version of Atom?
# Incompatible packages cannot be activated.
#
# Returns a {Boolean}, true if compatible, false if incompatible.
isCompatible: ->
return @compatible if @compatible?
# Bundled packages are always considered compatible
if @path.indexOf(path.join(atom.packages.resourcePath, 'node_modules') + path.sep) is 0
@compatible = true
return
if packageMain = @getMainModulePath()
@incompatibleModules = @getIncompatibleNativeModules()
@compatible = @incompatibleModules.length is 0
else
@compatible = true