diff --git a/spec/fixtures/packages/package-with-view-providers/deserializer.js b/spec/fixtures/packages/package-with-view-providers/deserializer.js new file mode 100644 index 000000000..334e7b2ab --- /dev/null +++ b/spec/fixtures/packages/package-with-view-providers/deserializer.js @@ -0,0 +1,3 @@ +module.exports = function (state) { + return {state: state} +} diff --git a/spec/fixtures/packages/package-with-view-providers/package.json b/spec/fixtures/packages/package-with-view-providers/package.json index 989473f95..f67477280 100644 --- a/spec/fixtures/packages/package-with-view-providers/package.json +++ b/spec/fixtures/packages/package-with-view-providers/package.json @@ -2,6 +2,9 @@ "name": "package-with-view-providers", "main": "./index", "version": "1.0.0", + "deserializers": { + "DeserializerFromPackageWithViewProviders": "./deserializer" + }, "viewProviders": [ "./view-provider-1", "./view-provider-2" diff --git a/spec/package-manager-spec.coffee b/spec/package-manager-spec.coffee index 94a6c43c5..d82f37acb 100644 --- a/spec/package-manager-spec.coffee +++ b/spec/package-manager-spec.coffee @@ -96,20 +96,57 @@ describe "PackageManager", -> expect(pack.mainModule).toBeNull() - it "registers any view providers specified in the package's package.json", -> - pack = atom.packages.loadPackage("package-with-view-providers") - + describe "when there are view providers specified in the package's package.json", -> model1 = {worksWithViewProvider1: true} - element1 = atom.views.getView(model1) - expect(element1 instanceof HTMLDivElement).toBe true - expect(element1.dataset.createdBy).toBe 'view-provider-1' - model2 = {worksWithViewProvider2: true} - element2 = atom.views.getView(model2) - expect(element2 instanceof HTMLDivElement).toBe true - expect(element2.dataset.createdBy).toBe 'view-provider-2' - expect(pack.mainModule).toBeNull() + afterEach -> + atom.packages.deactivatePackage('package-with-view-providers') + atom.packages.unloadPackage('package-with-view-providers') + + it "does not load the view providers immediately", -> + pack = atom.packages.loadPackage("package-with-view-providers") + expect(pack.mainModule).toBeNull() + + expect(-> atom.views.getView(model1)).toThrow() + expect(-> atom.views.getView(model2)).toThrow() + + it "registers the view providers when the package is activated", -> + pack = atom.packages.loadPackage("package-with-view-providers") + + waitsForPromise -> + atom.packages.activatePackage("package-with-view-providers").then -> + element1 = atom.views.getView(model1) + expect(element1 instanceof HTMLDivElement).toBe true + expect(element1.dataset.createdBy).toBe 'view-provider-1' + + element2 = atom.views.getView(model2) + expect(element2 instanceof HTMLDivElement).toBe true + expect(element2.dataset.createdBy).toBe 'view-provider-2' + + it "registers the view providers when any of the package's deserializers are used", -> + pack = atom.packages.loadPackage("package-with-view-providers") + + spyOn(atom.views, 'addViewProvider').andCallThrough() + atom.deserializers.deserialize({ + deserializer: 'DeserializerFromPackageWithViewProviders', + a: 'b' + }) + expect(atom.views.addViewProvider.callCount).toBe 2 + + atom.deserializers.deserialize({ + deserializer: 'DeserializerFromPackageWithViewProviders', + a: 'b' + }) + expect(atom.views.addViewProvider.callCount).toBe 2 + + element1 = atom.views.getView(model1) + expect(element1 instanceof HTMLDivElement).toBe true + expect(element1.dataset.createdBy).toBe 'view-provider-1' + + element2 = atom.views.getView(model2) + expect(element2 instanceof HTMLDivElement).toBe true + expect(element2.dataset.createdBy).toBe 'view-provider-2' it "registers the config schema in the package's metadata, if present", -> pack = atom.packages.loadPackage("package-with-json-config-schema") diff --git a/src/package.coffee b/src/package.coffee index b97424d04..f437d327a 100644 --- a/src/package.coffee +++ b/src/package.coffee @@ -85,7 +85,6 @@ class Package @loadMenus() @loadStylesheets() @loadDeserializers() - @loadViewProviders() @registerConfigSchemaFromMetadata() @settingsPromise = @loadSettings() if @shouldRequireMainModuleOnLoad() and not @mainModule? @@ -131,6 +130,7 @@ class Package try @requireMainModule() unless @mainModule? @registerConfigSchemaFromMainModule() + @registerViewProviders() @activateStylesheets() if @mainModule? and not @mainActivated @mainModule.activateConfig?() @@ -279,16 +279,17 @@ class Package deserializeFunction = null atom.deserializers.add name: name, - deserialize: -> + deserialize: => + @registerViewProviders() deserializeFunction ?= require(deserializePath) deserializeFunction.apply(this, arguments) return - loadViewProviders: -> - if @metadata.viewProviders? + registerViewProviders: -> + if @metadata.viewProviders? and not @registeredViewProviders for implementationPath in @metadata.viewProviders @viewRegistry.addViewProvider(require(path.join(@path, implementationPath))) - return + @registeredViewProviders = true getStylesheetsPath: -> path.join(@path, 'styles')