mirror of
https://github.com/google/blockly.git
synced 2026-01-07 00:50:27 +01:00
Registry (#3914)
Create a global registry that fields, renderers and future objects can use
This commit is contained in:
@@ -55,7 +55,7 @@ goog.addDependency('../../core/field_label.js', ['Blockly.FieldLabel'], ['Blockl
|
||||
goog.addDependency('../../core/field_label_serializable.js', ['Blockly.FieldLabelSerializable'], ['Blockly.FieldLabel', 'Blockly.fieldRegistry', 'Blockly.utils', 'Blockly.utils.object'], {});
|
||||
goog.addDependency('../../core/field_multilineinput.js', ['Blockly.FieldMultilineInput'], ['Blockly.Css', 'Blockly.DropDownDiv', 'Blockly.FieldTextInput', 'Blockly.utils', 'Blockly.utils.Coordinate', 'Blockly.utils.KeyCodes', 'Blockly.utils.aria', 'Blockly.utils.dom', 'Blockly.utils.object', 'Blockly.utils.userAgent'], {'lang': 'es5'});
|
||||
goog.addDependency('../../core/field_number.js', ['Blockly.FieldNumber'], ['Blockly.FieldTextInput', 'Blockly.fieldRegistry', 'Blockly.utils.aria', 'Blockly.utils.object'], {});
|
||||
goog.addDependency('../../core/field_registry.js', ['Blockly.fieldRegistry'], [], {});
|
||||
goog.addDependency('../../core/field_registry.js', ['Blockly.fieldRegistry'], ['Blockly.registry'], {});
|
||||
goog.addDependency('../../core/field_textinput.js', ['Blockly.FieldTextInput'], ['Blockly.Events', 'Blockly.Events.BlockChange', 'Blockly.Field', 'Blockly.Msg', 'Blockly.fieldRegistry', 'Blockly.utils', 'Blockly.utils.Coordinate', 'Blockly.utils.KeyCodes', 'Blockly.utils.Size', 'Blockly.utils.aria', 'Blockly.utils.dom', 'Blockly.utils.object', 'Blockly.utils.userAgent'], {});
|
||||
goog.addDependency('../../core/field_variable.js', ['Blockly.FieldVariable'], ['Blockly.Events', 'Blockly.Events.BlockChange', 'Blockly.FieldDropdown', 'Blockly.Msg', 'Blockly.VariableModel', 'Blockly.Variables', 'Blockly.Xml', 'Blockly.fieldRegistry', 'Blockly.utils', 'Blockly.utils.Size', 'Blockly.utils.object'], {});
|
||||
goog.addDependency('../../core/flyout_base.js', ['Blockly.Flyout'], ['Blockly.Block', 'Blockly.Events', 'Blockly.Events.BlockCreate', 'Blockly.Events.VarCreate', 'Blockly.FlyoutCursor', 'Blockly.Gesture', 'Blockly.Marker', 'Blockly.Scrollbar', 'Blockly.Tooltip', 'Blockly.Touch', 'Blockly.WorkspaceSvg', 'Blockly.Xml', 'Blockly.blockRendering', 'Blockly.utils', 'Blockly.utils.Coordinate', 'Blockly.utils.dom'], {});
|
||||
@@ -70,10 +70,14 @@ goog.addDependency('../../core/icon.js', ['Blockly.Icon'], ['Blockly.utils', 'Bl
|
||||
goog.addDependency('../../core/inject.js', ['Blockly.inject'], ['Blockly.BlockDragSurfaceSvg', 'Blockly.Component', 'Blockly.Css', 'Blockly.DropDownDiv', 'Blockly.Events', 'Blockly.Grid', 'Blockly.Msg', 'Blockly.Options', 'Blockly.ScrollbarPair', 'Blockly.Tooltip', 'Blockly.WorkspaceDragSurfaceSvg', 'Blockly.WorkspaceSvg', 'Blockly.user.keyMap', 'Blockly.utils', 'Blockly.utils.dom', 'Blockly.utils.userAgent'], {});
|
||||
goog.addDependency('../../core/input.js', ['Blockly.Input'], ['Blockly.Connection', 'Blockly.FieldLabel'], {});
|
||||
goog.addDependency('../../core/insertion_marker_manager.js', ['Blockly.InsertionMarkerManager'], ['Blockly.Events', 'Blockly.blockAnimations'], {'lang': 'es5'});
|
||||
goog.addDependency('../../core/interfaces/i_accessibility.js', ['Blockly.IASTNodeLocation', 'Blockly.IASTNodeLocationSvg', 'Blockly.IASTNodeLocationWithBlock', 'Blockly.IBlocklyActionable'], [], {});
|
||||
goog.addDependency('../../core/interfaces/i_bounded_element.js', ['Blockly.IBoundedElement'], [], {});
|
||||
goog.addDependency('../../core/interfaces/i_copyable.js', ['Blockly.ICopyable'], ['Blockly.ISelectable'], {});
|
||||
goog.addDependency('../../core/interfaces/i_deletable.js', ['Blockly.IDeletable'], [], {});
|
||||
goog.addDependency('../../core/interfaces/i_deletearea.js', ['Blockly.IDeleteArea'], [], {});
|
||||
goog.addDependency('../../core/interfaces/i_disposable.js', ['Blockly.IDisposable'], ['Blockly.Inheritance'], {});
|
||||
goog.addDependency('../../core/interfaces/i_movable.js', ['Blockly.IMovable'], [], {});
|
||||
goog.addDependency('../../core/interfaces/i_registrable.js', ['Blockly.IRegistrable'], [], {});
|
||||
goog.addDependency('../../core/interfaces/i_selectable.js', ['Blockly.ISelectable'], ['Blockly.IDeletable', 'Blockly.IMovable'], {});
|
||||
goog.addDependency('../../core/keyboard_nav/action.js', ['Blockly.Action'], [], {});
|
||||
goog.addDependency('../../core/keyboard_nav/ast_node.js', ['Blockly.ASTNode'], ['Blockly.utils.Coordinate'], {'lang': 'es5'});
|
||||
@@ -92,8 +96,9 @@ goog.addDependency('../../core/mutator.js', ['Blockly.Mutator'], ['Blockly.Bubbl
|
||||
goog.addDependency('../../core/names.js', ['Blockly.Names'], ['Blockly.Msg'], {});
|
||||
goog.addDependency('../../core/options.js', ['Blockly.Options'], ['Blockly.Theme', 'Blockly.Themes.Classic', 'Blockly.Xml', 'Blockly.user.keyMap', 'Blockly.utils.Metrics', 'Blockly.utils.toolbox', 'Blockly.utils.userAgent'], {});
|
||||
goog.addDependency('../../core/procedures.js', ['Blockly.Procedures'], ['Blockly.Blocks', 'Blockly.Events', 'Blockly.Events.BlockChange', 'Blockly.Field', 'Blockly.Msg', 'Blockly.Names', 'Blockly.Workspace', 'Blockly.Xml', 'Blockly.constants', 'Blockly.utils.xml'], {});
|
||||
goog.addDependency('../../core/registry.js', ['Blockly.registry'], [], {});
|
||||
goog.addDependency('../../core/rendered_connection.js', ['Blockly.RenderedConnection'], ['Blockly.Connection', 'Blockly.Events', 'Blockly.utils', 'Blockly.utils.Coordinate', 'Blockly.utils.dom', 'Blockly.utils.object'], {});
|
||||
goog.addDependency('../../core/renderers/common/block_rendering.js', ['Blockly.blockRendering'], ['Blockly.utils.object'], {});
|
||||
goog.addDependency('../../core/renderers/common/block_rendering.js', ['Blockly.blockRendering'], ['Blockly.registry', 'Blockly.utils.object'], {});
|
||||
goog.addDependency('../../core/renderers/common/constants.js', ['Blockly.blockRendering.ConstantProvider'], ['Blockly.utils', 'Blockly.utils.colour', 'Blockly.utils.dom', 'Blockly.utils.svgPaths', 'Blockly.utils.userAgent'], {'lang': 'es5'});
|
||||
goog.addDependency('../../core/renderers/common/debugger.js', ['Blockly.blockRendering.Debug'], ['Blockly.blockRendering.BottomRow', 'Blockly.blockRendering.InputRow', 'Blockly.blockRendering.Measurable', 'Blockly.blockRendering.RenderInfo', 'Blockly.blockRendering.Row', 'Blockly.blockRendering.SpacerRow', 'Blockly.blockRendering.TopRow', 'Blockly.blockRendering.Types'], {'lang': 'es5'});
|
||||
goog.addDependency('../../core/renderers/common/drawer.js', ['Blockly.blockRendering.Drawer'], ['Blockly.blockRendering.BottomRow', 'Blockly.blockRendering.InputRow', 'Blockly.blockRendering.Measurable', 'Blockly.blockRendering.RenderInfo', 'Blockly.blockRendering.Row', 'Blockly.blockRendering.SpacerRow', 'Blockly.blockRendering.TopRow', 'Blockly.blockRendering.Types', 'Blockly.utils.svgPaths'], {});
|
||||
|
||||
@@ -14,39 +14,23 @@
|
||||
|
||||
goog.provide('Blockly.fieldRegistry');
|
||||
|
||||
goog.require('Blockly.registry');
|
||||
|
||||
/**
|
||||
* The set of all registered fields, keyed by field type as used in the JSON
|
||||
* definition of a block.
|
||||
* @type {!Object<string, !{fromJson: Function}>}
|
||||
* @private
|
||||
*/
|
||||
Blockly.fieldRegistry.typeMap_ = {};
|
||||
|
||||
/**
|
||||
* Registers a field type.
|
||||
* Blockly.fieldRegistry.fromJson uses this registry to
|
||||
* find the appropriate field type.
|
||||
* @param {string} type The field type name as used in the JSON definition.
|
||||
* @param {!{fromJson: Function}} fieldClass The field class containing a
|
||||
* fromJson function that can construct an instance of the field.
|
||||
* @param {?function(new:Blockly.Field, ...?)} fieldClass The field class
|
||||
* containing a fromJson function that can construct an instance of the
|
||||
* field.
|
||||
* @throws {Error} if the type name is empty, the field is already
|
||||
* registered, or the fieldClass is not an object containing a fromJson
|
||||
* function.
|
||||
*/
|
||||
Blockly.fieldRegistry.register = function(type, fieldClass) {
|
||||
if ((typeof type != 'string') || (type.trim() == '')) {
|
||||
throw Error('Invalid field type "' + type + '". The type must be a' +
|
||||
' non-empty string.');
|
||||
}
|
||||
if (Blockly.fieldRegistry.typeMap_[type]) {
|
||||
throw Error('Error: Field "' + type + '" is already registered.');
|
||||
}
|
||||
if (!fieldClass || (typeof fieldClass.fromJson != 'function')) {
|
||||
throw Error('Field "' + fieldClass + '" must have a fromJson function');
|
||||
}
|
||||
type = type.toLowerCase();
|
||||
Blockly.fieldRegistry.typeMap_[type] = fieldClass;
|
||||
Blockly.registry.register(Blockly.registry.Type.FIELD, type, fieldClass);
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -54,12 +38,7 @@ Blockly.fieldRegistry.register = function(type, fieldClass) {
|
||||
* @param {string} type The field type name as used in the JSON definition.
|
||||
*/
|
||||
Blockly.fieldRegistry.unregister = function(type) {
|
||||
if (Blockly.fieldRegistry.typeMap_[type]) {
|
||||
delete Blockly.fieldRegistry.typeMap_[type];
|
||||
} else {
|
||||
console.warn('No field mapping for type "' + type +
|
||||
'" found to unregister');
|
||||
}
|
||||
Blockly.registry.unregister(Blockly.registry.Type.FIELD, type);
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -73,8 +52,8 @@ Blockly.fieldRegistry.unregister = function(type) {
|
||||
* @package
|
||||
*/
|
||||
Blockly.fieldRegistry.fromJson = function(options) {
|
||||
var type = options['type'].toLowerCase();
|
||||
var fieldClass = Blockly.fieldRegistry.typeMap_[type];
|
||||
var fieldClass = /** @type {{fromJson:function(!Object):!Blockly.Field}} */ (
|
||||
Blockly.registry.getClass(Blockly.registry.Type.FIELD, options['type']));
|
||||
if (!fieldClass) {
|
||||
console.warn('Blockly could not create a field of type ' + options['type'] +
|
||||
'. The field is probably not being registered. This could be because' +
|
||||
|
||||
154
core/registry.js
Normal file
154
core/registry.js
Normal file
@@ -0,0 +1,154 @@
|
||||
/**
|
||||
* @license
|
||||
* Copyright 2020 Google LLC
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
/**
|
||||
* @fileoverview This file is a universal registry that provides generic methods
|
||||
* for registering and unregistering different types of classes.
|
||||
* @author aschmiedt@google.com (Abby Schmiedt)
|
||||
*/
|
||||
'use strict';
|
||||
|
||||
goog.provide('Blockly.registry');
|
||||
|
||||
|
||||
/**
|
||||
* A map of maps. With the keys being the type and name of the class we are
|
||||
* registering and the value being the constructor function.
|
||||
* Ex: {'field': {'field_angle': Blockly.FieldAngle}}
|
||||
*
|
||||
* @type {Object<string, Object<string, function(new:?)>>}
|
||||
*/
|
||||
Blockly.registry.typeMap_ = {};
|
||||
|
||||
/**
|
||||
* A name with the type of the element stored in the generic.
|
||||
* @param {string} name The name of the registry type.
|
||||
* @constructor
|
||||
* @template T
|
||||
*/
|
||||
Blockly.registry.Type = function(name) {
|
||||
/** @private {string} */
|
||||
this.name_ = name;
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns the name of the type.
|
||||
* @return {string} The name.
|
||||
* @override
|
||||
*/
|
||||
Blockly.registry.Type.prototype.toString = function() {
|
||||
return this.name_;
|
||||
};
|
||||
|
||||
/** @type {!Blockly.registry.Type<Blockly.blockRendering.Renderer>} */
|
||||
Blockly.registry.Type.RENDERER = new Blockly.registry.Type('renderer');
|
||||
|
||||
/** @type {!Blockly.registry.Type<Blockly.Field>} */
|
||||
Blockly.registry.Type.FIELD = new Blockly.registry.Type('field');
|
||||
|
||||
/**
|
||||
* Registers a class based on a type and name.
|
||||
* @param {string|Blockly.registry.Type<T>} type The type of the plugin.
|
||||
* (Ex: Field, Renderer)
|
||||
* @param {string} name The plugin's name. (Ex. field_angle, geras)
|
||||
* @param {?function(new:T, ...?)} registryClass The class to register.
|
||||
* @throws {Error} if the type or name is empty, a name with the given type has
|
||||
* already been registered, or if the given class is not valid for it's type.
|
||||
* @template T
|
||||
*/
|
||||
Blockly.registry.register = function(type, name, registryClass) {
|
||||
if ((!(type instanceof Blockly.registry.Type) && typeof type != 'string') || String(type).trim() == '') {
|
||||
throw Error('Invalid type "' + type + '". The type must be a' +
|
||||
' non-empty string or a Blockly.registry.Type.');
|
||||
}
|
||||
type = String(type).toLowerCase();
|
||||
|
||||
if ((typeof name != 'string') || (name.trim() == '')) {
|
||||
throw Error('Invalid name "' + name + '". The name must be a' +
|
||||
' non-empty string.');
|
||||
}
|
||||
name = name.toLowerCase();
|
||||
if (!registryClass) {
|
||||
throw Error('Can not register a null value');
|
||||
}
|
||||
var typeRegistry = Blockly.registry.typeMap_[type];
|
||||
// If the type registry has not been created, create it.
|
||||
if (!typeRegistry) {
|
||||
typeRegistry = Blockly.registry.typeMap_[type] = {};
|
||||
}
|
||||
|
||||
// Validate that the given class has all the required properties.
|
||||
Blockly.registry.validate_(type, registryClass);
|
||||
|
||||
// If the name already exists throw an error.
|
||||
if (typeRegistry[name]) {
|
||||
throw Error('Name "' + name + '" with type "' + type + '" already registered.');
|
||||
}
|
||||
typeRegistry[name] = registryClass;
|
||||
};
|
||||
|
||||
/**
|
||||
* Checks the given class for properties that are required based on the type.
|
||||
* @param {string} type The type of the plugin. (Ex: Field, Renderer)
|
||||
* @param {Function} registryClass A class that we are checking for the required
|
||||
* properties.
|
||||
* @private
|
||||
*/
|
||||
Blockly.registry.validate_ = function(type, registryClass) {
|
||||
switch (type) {
|
||||
case String(Blockly.registry.Type.FIELD):
|
||||
if (typeof registryClass['fromJson'] != 'function') {
|
||||
throw Error('Type "' + type + '" must have a fromJson function');
|
||||
}
|
||||
break;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Unregisters the class with the given type and name.
|
||||
* @param {string|Blockly.registry.Type<T>} type The type of the plugin.
|
||||
* (eg: Field, Renderer)
|
||||
* @param {string} name The plugin's name. (Ex. field_angle, geras)
|
||||
* @template T
|
||||
*/
|
||||
Blockly.registry.unregister = function(type, name) {
|
||||
type = String(type).toLowerCase();
|
||||
name = name.toLowerCase();
|
||||
var typeRegistry = Blockly.registry.typeMap_[type];
|
||||
if (!typeRegistry) {
|
||||
console.warn('No type "' + type + '" found');
|
||||
return;
|
||||
}
|
||||
if (!typeRegistry[name]) {
|
||||
console.warn('No name "' + name + '" with type "' + type + '" found');
|
||||
return;
|
||||
}
|
||||
delete Blockly.registry.typeMap_[type][name];
|
||||
};
|
||||
|
||||
/**
|
||||
* Get the class for the given name and type.
|
||||
* @param {string|Blockly.registry.Type<T>} type The type of the plugin.
|
||||
* (eg: Field, Renderer)
|
||||
* @param {string} name The plugin's name. (Ex. field_angle, geras)
|
||||
* @return {?function(new:T, ...?)} The class with the given name and type or
|
||||
* null if none exists.
|
||||
* @template T
|
||||
*/
|
||||
Blockly.registry.getClass = function(type, name) {
|
||||
type = String(type).toLowerCase();
|
||||
name = name.toLowerCase();
|
||||
var typeRegistry = Blockly.registry.typeMap_[type];
|
||||
if (!typeRegistry) {
|
||||
console.warn('No type "' + type + '" found');
|
||||
return null;
|
||||
}
|
||||
if (!typeRegistry[name]) {
|
||||
console.warn('No name "' + name + '" with type "' + type + '" found');
|
||||
return null;
|
||||
}
|
||||
return typeRegistry[name];
|
||||
};
|
||||
@@ -16,6 +16,7 @@
|
||||
*/
|
||||
goog.provide('Blockly.blockRendering');
|
||||
|
||||
goog.require('Blockly.registry');
|
||||
goog.require('Blockly.utils.object');
|
||||
|
||||
|
||||
@@ -41,10 +42,8 @@ Blockly.blockRendering.useDebugger = false;
|
||||
* @throws {Error} if a renderer with the same name has already been registered.
|
||||
*/
|
||||
Blockly.blockRendering.register = function(name, rendererClass) {
|
||||
if (Blockly.blockRendering.rendererMap_[name]) {
|
||||
throw Error('Renderer has already been registered.');
|
||||
}
|
||||
Blockly.blockRendering.rendererMap_[name] = rendererClass;
|
||||
Blockly.registry.register(Blockly.registry.Type.RENDERER, name,
|
||||
rendererClass);
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -52,14 +51,8 @@ Blockly.blockRendering.register = function(name, rendererClass) {
|
||||
* @param {string} name The name of the renderer.
|
||||
*/
|
||||
Blockly.blockRendering.unregister = function(name) {
|
||||
if (Blockly.blockRendering.rendererMap_[name]) {
|
||||
delete Blockly.blockRendering.rendererMap_[name];
|
||||
} else {
|
||||
console.warn('No renderer mapping for name "' + name +
|
||||
'" found to unregister');
|
||||
}
|
||||
Blockly.registry.unregister(Blockly.registry.Type.RENDERER, name);
|
||||
};
|
||||
|
||||
/**
|
||||
* Turn on the blocks debugger.
|
||||
* @package
|
||||
@@ -85,12 +78,11 @@ Blockly.blockRendering.stopDebugger = function() {
|
||||
* Already initialized.
|
||||
* @package
|
||||
*/
|
||||
|
||||
Blockly.blockRendering.init = function(name, theme, opt_rendererOverrides) {
|
||||
if (!Blockly.blockRendering.rendererMap_[name]) {
|
||||
throw Error('Renderer not registered: ', name);
|
||||
}
|
||||
var renderer = (/** @type {!Blockly.blockRendering.Renderer} */ (
|
||||
new Blockly.blockRendering.rendererMap_[name](name)));
|
||||
var rendererClass = Blockly.registry.getClass(
|
||||
Blockly.registry.Type.RENDERER, name);
|
||||
var renderer = new rendererClass(name);
|
||||
renderer.init(theme, opt_rendererOverrides);
|
||||
return renderer;
|
||||
};
|
||||
|
||||
@@ -20,46 +20,25 @@ suite('Field Registry', function() {
|
||||
};
|
||||
|
||||
teardown(function() {
|
||||
if (Blockly.fieldRegistry.typeMap_['field_custom_test']) {
|
||||
delete Blockly.fieldRegistry.typeMap_['field_custom_test'];
|
||||
if (Blockly.registry.typeMap_['field']['field_custom_test']) {
|
||||
delete Blockly.registry.typeMap_['field']['field_custom_test'];
|
||||
}
|
||||
});
|
||||
suite('Registration', function() {
|
||||
test('Simple', function() {
|
||||
Blockly.fieldRegistry.register('field_custom_test', CustomFieldType);
|
||||
});
|
||||
test('Empty String Key', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register('', CustomFieldType);
|
||||
}, 'Invalid field type');
|
||||
});
|
||||
test('Class as Key', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register(CustomFieldType, '');
|
||||
}, 'Invalid field type');
|
||||
});
|
||||
test('fromJson as Key', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register(CustomFieldType.fromJson, '');
|
||||
}, 'Invalid field type');
|
||||
});
|
||||
test('Overwrite a Key', function() {
|
||||
Blockly.fieldRegistry.register('field_custom_test', CustomFieldType);
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register('field_custom_test', CustomFieldType);
|
||||
}, 'already registered');
|
||||
});
|
||||
test('Null Value', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register('field_custom_test', null);
|
||||
}, 'fromJson function');
|
||||
}, 'Invalid name');
|
||||
});
|
||||
test('No fromJson', function() {
|
||||
var fromJson = CustomFieldType.fromJson;
|
||||
delete CustomFieldType.fromJson;
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register('field_custom_test', CustomFieldType);
|
||||
}, 'fromJson function');
|
||||
}, 'must have a fromJson function');
|
||||
CustomFieldType.fromJson = fromJson;
|
||||
});
|
||||
test('fromJson not a function', function() {
|
||||
@@ -67,7 +46,7 @@ suite('Field Registry', function() {
|
||||
CustomFieldType.fromJson = true;
|
||||
chai.assert.throws(function() {
|
||||
Blockly.fieldRegistry.register('field_custom_test', CustomFieldType);
|
||||
}, 'fromJson function');
|
||||
}, 'must have a fromJson function');
|
||||
CustomFieldType.fromJson = fromJson;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -70,6 +70,7 @@
|
||||
<script src="navigation_modify_test.js"></script>
|
||||
<script src="navigation_test.js"></script>
|
||||
<script src="procedures_test.js"></script>
|
||||
<script src="registry_test.js"></script>
|
||||
<script src="theme_test.js"></script>
|
||||
<script src="toolbox_test.js"></script>
|
||||
<script src="trashcan_test.js"></script>
|
||||
|
||||
51
tests/mocha/registry_test.js
Normal file
51
tests/mocha/registry_test.js
Normal file
@@ -0,0 +1,51 @@
|
||||
/**
|
||||
* @license
|
||||
* Copyright 2020 Google LLC
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
/**
|
||||
* @fileoverview Tests for Blockly.registry
|
||||
* @author aschmiedt@google.com (Abby Schmiedt)
|
||||
*/
|
||||
'use strict';
|
||||
|
||||
suite('Registry', function() {
|
||||
var TestClass = function() {};
|
||||
TestClass.prototype.testMethod = function() {
|
||||
return 'something';
|
||||
};
|
||||
|
||||
teardown(function() {
|
||||
if (Blockly.registry.typeMap_['test'] &&
|
||||
Blockly.registry.typeMap_['test']['test_name']) {
|
||||
delete Blockly.registry.typeMap_['test']['test_name'];
|
||||
}
|
||||
});
|
||||
suite('Registration', function() {
|
||||
test('Simple', function() {
|
||||
Blockly.registry.register('test', 'test_name', TestClass);
|
||||
});
|
||||
test('Empty String Key', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.registry.register('test', '', TestClass);
|
||||
}, 'Invalid name');
|
||||
});
|
||||
test('Class as Key', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.registry.register('test', TestClass, '');
|
||||
}, 'Invalid name');
|
||||
});
|
||||
test('Overwrite a Key', function() {
|
||||
Blockly.registry.register('test', 'test_name', TestClass);
|
||||
chai.assert.throws(function() {
|
||||
Blockly.registry.register('test', 'test_name', TestClass);
|
||||
}, 'already registered');
|
||||
});
|
||||
test('Null Value', function() {
|
||||
chai.assert.throws(function() {
|
||||
Blockly.registry.register('test', 'field_custom_test', null);
|
||||
}, 'Can not register a null value');
|
||||
});
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user