Removed circular dependencies between APIs and CMI objects
No longer directly setting error codes on the API when a read/write or data validation fails, throwing exceptions instead that can then be caught by the APi.
This commit is contained in:
247
src/BaseAPI.js
247
src/BaseAPI.js
@@ -14,8 +14,6 @@ const api_constants = {
|
|||||||
LOG_LEVEL_NONE: 5,
|
LOG_LEVEL_NONE: 5,
|
||||||
};
|
};
|
||||||
|
|
||||||
let _self;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Base API class for AICC, SCORM 1.2, and SCORM 2004. Should be considered
|
* Base API class for AICC, SCORM 1.2, and SCORM 2004. Should be considered
|
||||||
* abstract, and never initialized on it's own.
|
* abstract, and never initialized on it's own.
|
||||||
@@ -31,14 +29,13 @@ export default class BaseAPI {
|
|||||||
* @param {object} error_codes
|
* @param {object} error_codes
|
||||||
*/
|
*/
|
||||||
constructor(error_codes) {
|
constructor(error_codes) {
|
||||||
_self = this;
|
this.currentState = api_constants.STATE_NOT_INITIALIZED;
|
||||||
_self.currentState = api_constants.STATE_NOT_INITIALIZED;
|
this.apiLogLevel = api_constants.LOG_LEVEL_ERROR;
|
||||||
_self.apiLogLevel = api_constants.LOG_LEVEL_ERROR;
|
this.lastErrorCode = 0;
|
||||||
_self.lastErrorCode = 0;
|
this.listenerArray = [];
|
||||||
_self.listenerArray = [];
|
|
||||||
|
|
||||||
_self.#timeout = null;
|
this.#timeout = null;
|
||||||
_self.#error_codes = error_codes;
|
this.#error_codes = error_codes;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -54,20 +51,20 @@ export default class BaseAPI {
|
|||||||
terminationMessage?: String) {
|
terminationMessage?: String) {
|
||||||
let returnValue = api_constants.SCORM_FALSE;
|
let returnValue = api_constants.SCORM_FALSE;
|
||||||
|
|
||||||
if (_self.isInitialized()) {
|
if (this.isInitialized()) {
|
||||||
_self.throwSCORMError(_self.#error_codes.INITIALIZED, initializeMessage);
|
this.throwSCORMError(this.#error_codes.INITIALIZED, initializeMessage);
|
||||||
} else if (_self.isTerminated()) {
|
} else if (this.isTerminated()) {
|
||||||
_self.throwSCORMError(_self.#error_codes.TERMINATED, terminationMessage);
|
this.throwSCORMError(this.#error_codes.TERMINATED, terminationMessage);
|
||||||
} else {
|
} else {
|
||||||
_self.currentState = api_constants.STATE_INITIALIZED;
|
this.currentState = api_constants.STATE_INITIALIZED;
|
||||||
_self.lastErrorCode = 0;
|
this.lastErrorCode = 0;
|
||||||
returnValue = api_constants.SCORM_TRUE;
|
returnValue = api_constants.SCORM_TRUE;
|
||||||
_self.processListeners(callbackName);
|
this.processListeners(callbackName);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, null, 'returned: ' + returnValue,
|
this.apiLog(callbackName, null, 'returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
_self.clearSCORMError(returnValue);
|
this.clearSCORMError(returnValue);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
}
|
}
|
||||||
@@ -83,18 +80,18 @@ export default class BaseAPI {
|
|||||||
checkTerminated: boolean) {
|
checkTerminated: boolean) {
|
||||||
let returnValue = api_constants.SCORM_FALSE;
|
let returnValue = api_constants.SCORM_FALSE;
|
||||||
|
|
||||||
if (_self.checkState(checkTerminated,
|
if (this.checkState(checkTerminated,
|
||||||
_self.#error_codes.TERMINATION_BEFORE_INIT,
|
this.#error_codes.TERMINATION_BEFORE_INIT,
|
||||||
_self.#error_codes.MULTIPLE_TERMINATION)) {
|
this.#error_codes.MULTIPLE_TERMINATION)) {
|
||||||
if (checkTerminated) _self.lastErrorCode = 0;
|
if (checkTerminated) this.lastErrorCode = 0;
|
||||||
_self.currentState = api_constants.STATE_TERMINATED;
|
this.currentState = api_constants.STATE_TERMINATED;
|
||||||
returnValue = api_constants.SCORM_TRUE;
|
returnValue = api_constants.SCORM_TRUE;
|
||||||
_self.processListeners(callbackName);
|
this.processListeners(callbackName);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, null, 'returned: ' + returnValue,
|
this.apiLog(callbackName, null, 'returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
_self.clearSCORMError(returnValue);
|
this.clearSCORMError(returnValue);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
}
|
}
|
||||||
@@ -113,17 +110,17 @@ export default class BaseAPI {
|
|||||||
CMIElement: String) {
|
CMIElement: String) {
|
||||||
let returnValue = '';
|
let returnValue = '';
|
||||||
|
|
||||||
if (_self.checkState(checkTerminated,
|
if (this.checkState(checkTerminated,
|
||||||
_self.#error_codes.RETRIEVE_BEFORE_INIT,
|
this.#error_codes.RETRIEVE_BEFORE_INIT,
|
||||||
_self.#error_codes.RETRIEVE_AFTER_TERM)) {
|
this.#error_codes.RETRIEVE_AFTER_TERM)) {
|
||||||
if (checkTerminated) _self.lastErrorCode = 0;
|
if (checkTerminated) this.lastErrorCode = 0;
|
||||||
returnValue = _self.getCMIValue(CMIElement);
|
returnValue = this.getCMIValue(CMIElement);
|
||||||
_self.processListeners(callbackName, CMIElement);
|
this.processListeners(callbackName, CMIElement);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, CMIElement, ': returned: ' + returnValue,
|
this.apiLog(callbackName, CMIElement, ': returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
_self.clearSCORMError(returnValue);
|
this.clearSCORMError(returnValue);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
}
|
}
|
||||||
@@ -144,17 +141,17 @@ export default class BaseAPI {
|
|||||||
value) {
|
value) {
|
||||||
let returnValue = '';
|
let returnValue = '';
|
||||||
|
|
||||||
if (_self.checkState(checkTerminated, _self.#error_codes.STORE_BEFORE_INIT,
|
if (this.checkState(checkTerminated, this.#error_codes.STORE_BEFORE_INIT,
|
||||||
_self.#error_codes.STORE_AFTER_TERM)) {
|
this.#error_codes.STORE_AFTER_TERM)) {
|
||||||
if (checkTerminated) _self.lastErrorCode = 0;
|
if (checkTerminated) this.lastErrorCode = 0;
|
||||||
returnValue = _self.setCMIValue(CMIElement, value);
|
returnValue = this.setCMIValue(CMIElement, value);
|
||||||
_self.processListeners(callbackName, CMIElement, value);
|
this.processListeners(callbackName, CMIElement, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, CMIElement,
|
this.apiLog(callbackName, CMIElement,
|
||||||
': ' + value + ': result: ' + returnValue,
|
': ' + value + ': result: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
_self.clearSCORMError(returnValue);
|
this.clearSCORMError(returnValue);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
}
|
}
|
||||||
@@ -170,16 +167,16 @@ export default class BaseAPI {
|
|||||||
checkTerminated: boolean) {
|
checkTerminated: boolean) {
|
||||||
let returnValue = api_constants.SCORM_FALSE;
|
let returnValue = api_constants.SCORM_FALSE;
|
||||||
|
|
||||||
if (_self.checkState(checkTerminated, _self.#error_codes.COMMIT_BEFORE_INIT,
|
if (this.checkState(checkTerminated, this.#error_codes.COMMIT_BEFORE_INIT,
|
||||||
_self.#error_codes.COMMIT_AFTER_TERM)) {
|
this.#error_codes.COMMIT_AFTER_TERM)) {
|
||||||
if (checkTerminated) _self.lastErrorCode = 0;
|
if (checkTerminated) this.lastErrorCode = 0;
|
||||||
returnValue = api_constants.SCORM_TRUE;
|
returnValue = api_constants.SCORM_TRUE;
|
||||||
_self.processListeners(callbackName);
|
this.processListeners(callbackName);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, null, 'returned: ' + returnValue,
|
this.apiLog(callbackName, null, 'returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
_self.clearSCORMError(returnValue);
|
this.clearSCORMError(returnValue);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
}
|
}
|
||||||
@@ -190,11 +187,11 @@ export default class BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
getLastError(callbackName: String) {
|
getLastError(callbackName: String) {
|
||||||
const returnValue = String(_self.lastErrorCode);
|
const returnValue = String(this.lastErrorCode);
|
||||||
|
|
||||||
_self.processListeners(callbackName);
|
this.processListeners(callbackName);
|
||||||
|
|
||||||
_self.apiLog(callbackName, null, 'returned: ' + returnValue,
|
this.apiLog(callbackName, null, 'returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
@@ -211,11 +208,11 @@ export default class BaseAPI {
|
|||||||
let returnValue = '';
|
let returnValue = '';
|
||||||
|
|
||||||
if (CMIErrorCode !== null && CMIErrorCode !== '') {
|
if (CMIErrorCode !== null && CMIErrorCode !== '') {
|
||||||
returnValue = _self.getLmsErrorMessageDetails(CMIErrorCode);
|
returnValue = this.getLmsErrorMessageDetails(CMIErrorCode);
|
||||||
_self.processListeners(callbackName);
|
this.processListeners(callbackName);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, null, 'returned: ' + returnValue,
|
this.apiLog(callbackName, null, 'returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
@@ -232,11 +229,11 @@ export default class BaseAPI {
|
|||||||
let returnValue = '';
|
let returnValue = '';
|
||||||
|
|
||||||
if (CMIErrorCode !== null && CMIErrorCode !== '') {
|
if (CMIErrorCode !== null && CMIErrorCode !== '') {
|
||||||
returnValue = _self.getLmsErrorMessageDetails(CMIErrorCode, true);
|
returnValue = this.getLmsErrorMessageDetails(CMIErrorCode, true);
|
||||||
_self.processListeners(callbackName);
|
this.processListeners(callbackName);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog(callbackName, null, 'returned: ' + returnValue,
|
this.apiLog(callbackName, null, 'returned: ' + returnValue,
|
||||||
api_constants.LOG_LEVEL_INFO);
|
api_constants.LOG_LEVEL_INFO);
|
||||||
|
|
||||||
return returnValue;
|
return returnValue;
|
||||||
@@ -254,11 +251,11 @@ export default class BaseAPI {
|
|||||||
checkTerminated: boolean,
|
checkTerminated: boolean,
|
||||||
beforeInitError: number,
|
beforeInitError: number,
|
||||||
afterTermError?: number) {
|
afterTermError?: number) {
|
||||||
if (_self.isNotInitialized()) {
|
if (this.isNotInitialized()) {
|
||||||
_self.throwSCORMError(beforeInitError);
|
this.throwSCORMError(beforeInitError);
|
||||||
return false;
|
return false;
|
||||||
} else if (checkTerminated && _self.isTerminated()) {
|
} else if (checkTerminated && this.isTerminated()) {
|
||||||
_self.throwSCORMError(afterTermError);
|
this.throwSCORMError(afterTermError);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -278,9 +275,9 @@ export default class BaseAPI {
|
|||||||
CMIElement: String,
|
CMIElement: String,
|
||||||
logMessage: String,
|
logMessage: String,
|
||||||
messageLevel: number) {
|
messageLevel: number) {
|
||||||
logMessage = _self.formatMessage(functionName, CMIElement, logMessage);
|
logMessage = this.formatMessage(functionName, CMIElement, logMessage);
|
||||||
|
|
||||||
if (messageLevel >= _self.apiLogLevel) {
|
if (messageLevel >= this.apiLogLevel) {
|
||||||
switch (messageLevel) {
|
switch (messageLevel) {
|
||||||
case api_constants.LOG_LEVEL_ERROR:
|
case api_constants.LOG_LEVEL_ERROR:
|
||||||
console.error(logMessage);
|
console.error(logMessage);
|
||||||
@@ -402,8 +399,8 @@ export default class BaseAPI {
|
|||||||
|
|
||||||
const invalidErrorMessage = `The data model element passed to ${methodName} (${CMIElement}) is not a valid SCORM data model element.`;
|
const invalidErrorMessage = `The data model element passed to ${methodName} (${CMIElement}) is not a valid SCORM data model element.`;
|
||||||
const invalidErrorCode = scorm2004 ?
|
const invalidErrorCode = scorm2004 ?
|
||||||
_self.#error_codes.UNDEFINED_DATA_MODEL :
|
this.#error_codes.UNDEFINED_DATA_MODEL :
|
||||||
_self.#error_codes.GENERAL;
|
this.#error_codes.GENERAL;
|
||||||
|
|
||||||
for (let i = 0; i < structure.length; i++) {
|
for (let i = 0; i < structure.length; i++) {
|
||||||
const attribute = structure[i];
|
const attribute = structure[i];
|
||||||
@@ -411,15 +408,15 @@ export default class BaseAPI {
|
|||||||
if (i === structure.length - 1) {
|
if (i === structure.length - 1) {
|
||||||
if (scorm2004 && (attribute.substr(0, 8) === '{target=') &&
|
if (scorm2004 && (attribute.substr(0, 8) === '{target=') &&
|
||||||
(typeof refObject._isTargetValid == 'function')) {
|
(typeof refObject._isTargetValid == 'function')) {
|
||||||
_self.throwSCORMError(_self.#error_codes.READ_ONLY_ELEMENT);
|
this.throwSCORMError(this.#error_codes.READ_ONLY_ELEMENT);
|
||||||
} else if (!{}.hasOwnProperty.call(refObject, attribute)) {
|
} else if (!{}.hasOwnProperty.call(refObject, attribute)) {
|
||||||
_self.throwSCORMError(invalidErrorCode, invalidErrorMessage);
|
this.throwSCORMError(invalidErrorCode, invalidErrorMessage);
|
||||||
} else {
|
} else {
|
||||||
if (_self.stringContains(CMIElement, '.correct_responses')) {
|
if (this.stringContains(CMIElement, '.correct_responses')) {
|
||||||
_self.validateCorrectResponse(CMIElement, value);
|
this.validateCorrectResponse(CMIElement, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!scorm2004 || _self.lastErrorCode === 0) {
|
if (!scorm2004 || this.lastErrorCode === 0) {
|
||||||
refObject[attribute] = value;
|
refObject[attribute] = value;
|
||||||
returnValue = api_constants.SCORM_TRUE;
|
returnValue = api_constants.SCORM_TRUE;
|
||||||
}
|
}
|
||||||
@@ -427,7 +424,7 @@ export default class BaseAPI {
|
|||||||
} else {
|
} else {
|
||||||
refObject = refObject[attribute];
|
refObject = refObject[attribute];
|
||||||
if (!refObject) {
|
if (!refObject) {
|
||||||
_self.throwSCORMError(invalidErrorCode, invalidErrorMessage);
|
this.throwSCORMError(invalidErrorCode, invalidErrorMessage);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -441,10 +438,10 @@ export default class BaseAPI {
|
|||||||
if (item) {
|
if (item) {
|
||||||
refObject = item;
|
refObject = item;
|
||||||
} else {
|
} else {
|
||||||
const newChild = _self.getChildElement(CMIElement, value);
|
const newChild = this.getChildElement(CMIElement, value);
|
||||||
|
|
||||||
if (!newChild) {
|
if (!newChild) {
|
||||||
_self.throwSCORMError(invalidErrorCode, invalidErrorMessage);
|
this.throwSCORMError(invalidErrorCode, invalidErrorMessage);
|
||||||
} else {
|
} else {
|
||||||
refObject.childArray.push(newChild);
|
refObject.childArray.push(newChild);
|
||||||
refObject = newChild;
|
refObject = newChild;
|
||||||
@@ -459,7 +456,7 @@ export default class BaseAPI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (returnValue === api_constants.SCORM_FALSE) {
|
if (returnValue === api_constants.SCORM_FALSE) {
|
||||||
_self.apiLog(methodName, null,
|
this.apiLog(methodName, null,
|
||||||
`There was an error setting the value for: ${CMIElement}, value of: ${value}`,
|
`There was an error setting the value for: ${CMIElement}, value of: ${value}`,
|
||||||
api_constants.LOG_LEVEL_WARNING);
|
api_constants.LOG_LEVEL_WARNING);
|
||||||
}
|
}
|
||||||
@@ -512,7 +509,7 @@ export default class BaseAPI {
|
|||||||
if (!scorm2004) {
|
if (!scorm2004) {
|
||||||
if (i === structure.length - 1) {
|
if (i === structure.length - 1) {
|
||||||
if (!{}.hasOwnProperty.call(refObject, attribute)) {
|
if (!{}.hasOwnProperty.call(refObject, attribute)) {
|
||||||
_self.throwSCORMError(101,
|
this.throwSCORMError(101,
|
||||||
'getCMIValue did not find a value for: ' + CMIElement);
|
'getCMIValue did not find a value for: ' + CMIElement);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -523,7 +520,7 @@ export default class BaseAPI {
|
|||||||
substr(8, String(attribute).length - 9);
|
substr(8, String(attribute).length - 9);
|
||||||
return refObject._isTargetValid(target);
|
return refObject._isTargetValid(target);
|
||||||
} else if (!{}.hasOwnProperty.call(refObject, attribute)) {
|
} else if (!{}.hasOwnProperty.call(refObject, attribute)) {
|
||||||
_self.throwSCORMError(401,
|
this.throwSCORMError(401,
|
||||||
'The data model element passed to GetValue (' + CMIElement +
|
'The data model element passed to GetValue (' + CMIElement +
|
||||||
') is not a valid SCORM data model element.');
|
') is not a valid SCORM data model element.');
|
||||||
return '';
|
return '';
|
||||||
@@ -536,9 +533,9 @@ export default class BaseAPI {
|
|||||||
if (refObject === null || refObject === undefined) {
|
if (refObject === null || refObject === undefined) {
|
||||||
if (!scorm2004) {
|
if (!scorm2004) {
|
||||||
if (attribute === '_children') {
|
if (attribute === '_children') {
|
||||||
_self.throwSCORMError(202);
|
this.throwSCORMError(202);
|
||||||
} else if (attribute === '_count') {
|
} else if (attribute === '_count') {
|
||||||
_self.throwSCORMError(203);
|
this.throwSCORMError(203);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return '';
|
return '';
|
||||||
@@ -553,7 +550,7 @@ export default class BaseAPI {
|
|||||||
* @return {boolean}
|
* @return {boolean}
|
||||||
*/
|
*/
|
||||||
isInitialized() {
|
isInitialized() {
|
||||||
return _self.currentState === api_constants.STATE_INITIALIZED;
|
return this.currentState === api_constants.STATE_INITIALIZED;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -562,7 +559,7 @@ export default class BaseAPI {
|
|||||||
* @return {boolean}
|
* @return {boolean}
|
||||||
*/
|
*/
|
||||||
isNotInitialized() {
|
isNotInitialized() {
|
||||||
return _self.currentState === api_constants.STATE_NOT_INITIALIZED;
|
return this.currentState === api_constants.STATE_NOT_INITIALIZED;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -571,7 +568,7 @@ export default class BaseAPI {
|
|||||||
* @return {boolean}
|
* @return {boolean}
|
||||||
*/
|
*/
|
||||||
isTerminated() {
|
isTerminated() {
|
||||||
return _self.currentState === api_constants.STATE_TERMINATED;
|
return this.currentState === api_constants.STATE_TERMINATED;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -595,7 +592,7 @@ export default class BaseAPI {
|
|||||||
CMIElement = listenerName.replace(functionName + '.', '');
|
CMIElement = listenerName.replace(functionName + '.', '');
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.listenerArray.push({
|
this.listenerArray.push({
|
||||||
functionName: functionName,
|
functionName: functionName,
|
||||||
CMIElement: CMIElement,
|
CMIElement: CMIElement,
|
||||||
callback: callback,
|
callback: callback,
|
||||||
@@ -611,8 +608,8 @@ export default class BaseAPI {
|
|||||||
* @param {*} value
|
* @param {*} value
|
||||||
*/
|
*/
|
||||||
processListeners(functionName: String, CMIElement: String, value: any) {
|
processListeners(functionName: String, CMIElement: String, value: any) {
|
||||||
for (let i = 0; i < _self.listenerArray.length; i++) {
|
for (let i = 0; i < this.listenerArray.length; i++) {
|
||||||
const listener = _self.listenerArray[i];
|
const listener = this.listenerArray[i];
|
||||||
const functionsMatch = listener.functionName === functionName;
|
const functionsMatch = listener.functionName === functionName;
|
||||||
const listenerHasCMIElement = !!listener.CMIElement;
|
const listenerHasCMIElement = !!listener.CMIElement;
|
||||||
const CMIElementsMatch = listener.CMIElement === CMIElement;
|
const CMIElementsMatch = listener.CMIElement === CMIElement;
|
||||||
@@ -631,13 +628,13 @@ export default class BaseAPI {
|
|||||||
*/
|
*/
|
||||||
throwSCORMError(errorNumber: number, message: String) {
|
throwSCORMError(errorNumber: number, message: String) {
|
||||||
if (!message) {
|
if (!message) {
|
||||||
message = _self.getLmsErrorMessageDetails(errorNumber);
|
message = this.getLmsErrorMessageDetails(errorNumber);
|
||||||
}
|
}
|
||||||
|
|
||||||
_self.apiLog('throwSCORMError', null, errorNumber + ': ' + message,
|
this.apiLog('throwSCORMError', null, errorNumber + ': ' + message,
|
||||||
api_constants.LOG_LEVEL_ERROR);
|
api_constants.LOG_LEVEL_ERROR);
|
||||||
|
|
||||||
_self.lastErrorCode = String(errorNumber);
|
this.lastErrorCode = String(errorNumber);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -647,7 +644,7 @@ export default class BaseAPI {
|
|||||||
*/
|
*/
|
||||||
clearSCORMError(success: String) {
|
clearSCORMError(success: String) {
|
||||||
if (success !== api_constants.SCORM_FALSE) {
|
if (success !== api_constants.SCORM_FALSE) {
|
||||||
_self.lastErrorCode = 0;
|
this.lastErrorCode = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -658,7 +655,7 @@ export default class BaseAPI {
|
|||||||
* @param {string} CMIElement
|
* @param {string} CMIElement
|
||||||
*/
|
*/
|
||||||
loadFromJSON(json, CMIElement) {
|
loadFromJSON(json, CMIElement) {
|
||||||
if (!_self.isNotInitialized()) {
|
if (!this.isNotInitialized()) {
|
||||||
console.error(
|
console.error(
|
||||||
'loadFromJSON can only be called before the call to lmsInitialize.');
|
'loadFromJSON can only be called before the call to lmsInitialize.');
|
||||||
return;
|
return;
|
||||||
@@ -673,13 +670,13 @@ export default class BaseAPI {
|
|||||||
|
|
||||||
if (value['childArray']) {
|
if (value['childArray']) {
|
||||||
for (let i = 0; i < value['childArray'].length; i++) {
|
for (let i = 0; i < value['childArray'].length; i++) {
|
||||||
_self.loadFromJSON(value['childArray'][i],
|
this.loadFromJSON(value['childArray'][i],
|
||||||
currentCMIElement + '.' + i);
|
currentCMIElement + '.' + i);
|
||||||
}
|
}
|
||||||
} else if (value.constructor === Object) {
|
} else if (value.constructor === Object) {
|
||||||
_self.loadFromJSON(value, currentCMIElement);
|
this.loadFromJSON(value, currentCMIElement);
|
||||||
} else {
|
} else {
|
||||||
_self.setCMIValue(currentCMIElement, value);
|
this.setCMIValue(currentCMIElement, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -691,68 +688,28 @@ export default class BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
renderCMIToJSON() {
|
renderCMIToJSON() {
|
||||||
const cmi = _self.cmi;
|
const cmi = this.cmi;
|
||||||
// Do we want/need to return fields that have no set value?
|
// Do we want/need to return fields that have no set value?
|
||||||
// return JSON.stringify({ cmi }, (k, v) => v === undefined ? null : v, 2);
|
// return JSON.stringify({ cmi }, (k, v) => v === undefined ? null : v, 2);
|
||||||
return JSON.stringify({cmi});
|
return JSON.stringify({cmi});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Check if the value matches the proper format. If not, throw proper error code.
|
|
||||||
*
|
|
||||||
* @param {string} value
|
|
||||||
* @param {string} regexPattern
|
|
||||||
* @return {boolean}
|
|
||||||
*/
|
|
||||||
checkValidFormat(value: String, regexPattern: String) {
|
|
||||||
const formatRegex = new RegExp(regexPattern);
|
|
||||||
if (!value || !value.match(formatRegex)) {
|
|
||||||
_self.throwSCORMError(_self.#error_codes.TYPE_MISMATCH);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Check if the value matches the proper range. If not, throw proper error code.
|
|
||||||
*
|
|
||||||
* @param {*} value
|
|
||||||
* @param {string} rangePattern
|
|
||||||
* @return {boolean}
|
|
||||||
*/
|
|
||||||
checkValidRange(value: any, rangePattern: String) {
|
|
||||||
const ranges = rangePattern.split('#');
|
|
||||||
value = value * 1.0;
|
|
||||||
if (value >= ranges[0]) {
|
|
||||||
if ((ranges[1] === '*') || (value <= ranges[1])) {
|
|
||||||
_self.clearSCORMError(api_constants.SCORM_TRUE);
|
|
||||||
return true;
|
|
||||||
} else {
|
|
||||||
_self.throwSCORMError(_self.#error_codes.VALUE_OUT_OF_RANGE);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
_self.throwSCORMError(_self.#error_codes.VALUE_OUT_OF_RANGE);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Throws a SCORM error
|
* Throws a SCORM error
|
||||||
*
|
*
|
||||||
* @param {number} when - the number of milliseconds to wait before committing
|
* @param {number} when - the number of milliseconds to wait before committing
|
||||||
*/
|
*/
|
||||||
scheduleCommit(when: number) {
|
scheduleCommit(when: number) {
|
||||||
_self.#timeout = new ScheduledCommit(this, when);
|
this.#timeout = new ScheduledCommit(this, when);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Clears and cancels any currently scheduled commits
|
* Clears and cancels any currently scheduled commits
|
||||||
*/
|
*/
|
||||||
clearScheduledCommit() {
|
clearScheduledCommit() {
|
||||||
if (_self.#timeout) {
|
if (this.#timeout) {
|
||||||
_self.#timeout.cancel();
|
this.#timeout.cancel();
|
||||||
_self.#timeout = null;
|
this.#timeout = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -771,26 +728,26 @@ class ScheduledCommit {
|
|||||||
* @param {number} when
|
* @param {number} when
|
||||||
*/
|
*/
|
||||||
constructor(API: any, when: number) {
|
constructor(API: any, when: number) {
|
||||||
_self.#API = API;
|
this.#API = API;
|
||||||
_self.#timeout = setTimeout(_self.#wrapper, when);
|
this.#timeout = setTimeout(this.#wrapper, when);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Cancel any currently scheduled commit
|
* Cancel any currently scheduled commit
|
||||||
*/
|
*/
|
||||||
cancel() {
|
cancel() {
|
||||||
_self.#cancelled = true;
|
this.#cancelled = true;
|
||||||
if (_self.#timeout) {
|
if (this.#timeout) {
|
||||||
clearTimeout(_self.#timeout);
|
clearTimeout(this.#timeout);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Wrap the API commit call to check if the call has already been cancelled
|
* Wrap the API commit call to check if the call has already been cancelled
|
||||||
*/
|
*/
|
||||||
#wrapper = () => {
|
#wrapper() {
|
||||||
if (!_self.#cancelled) {
|
if (!this.#cancelled) {
|
||||||
_self.#API.commit();
|
this.#API.commit();
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,12 +18,11 @@ import {valid_languages} from './constants/language_constants';
|
|||||||
import {scorm2004_regex} from './regex';
|
import {scorm2004_regex} from './regex';
|
||||||
|
|
||||||
const constants = scorm2004_constants;
|
const constants = scorm2004_constants;
|
||||||
let _self;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* API class for SCORM 2004
|
* API class for SCORM 2004
|
||||||
*/
|
*/
|
||||||
class Scorm2004API extends BaseAPI {
|
export default class Scorm2004API extends BaseAPI {
|
||||||
#version: '1.0';
|
#version: '1.0';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -32,19 +31,18 @@ class Scorm2004API extends BaseAPI {
|
|||||||
constructor() {
|
constructor() {
|
||||||
super(scorm2004_error_codes);
|
super(scorm2004_error_codes);
|
||||||
|
|
||||||
_self = this;
|
this.cmi = new CMI(this);
|
||||||
_self.cmi = new CMI(_self);
|
this.adl = new ADL(this);
|
||||||
_self.adl = new ADL(_self);
|
|
||||||
|
|
||||||
// Rename functions to match 2004 Spec and expose to modules
|
// Rename functions to match 2004 Spec and expose to modules
|
||||||
_self.Initialize = _self.lmsInitialize;
|
this.Initialize = this.lmsInitialize;
|
||||||
_self.Terminate = _self.lmsTerminate;
|
this.Terminate = this.lmsTerminate;
|
||||||
_self.GetValue = _self.lmsGetValue;
|
this.GetValue = this.lmsGetValue;
|
||||||
_self.SetValue = _self.lmsSetValue;
|
this.SetValue = this.lmsSetValue;
|
||||||
_self.Commit = _self.lmsCommit;
|
this.Commit = this.lmsCommit;
|
||||||
_self.GetLastError = _self.lmsGetLastError;
|
this.GetLastError = this.lmsGetLastError;
|
||||||
_self.GetErrorString = _self.lmsGetErrorString;
|
this.GetErrorString = this.lmsGetErrorString;
|
||||||
_self.GetDiagnostic = _self.lmsGetDiagnostic;
|
this.GetDiagnostic = this.lmsGetDiagnostic;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -59,14 +57,14 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string} bool
|
* @return {string} bool
|
||||||
*/
|
*/
|
||||||
lmsInitialize() {
|
lmsInitialize() {
|
||||||
return _self.initialize('Initialize');
|
return this.initialize('Initialize');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return {string} bool
|
* @return {string} bool
|
||||||
*/
|
*/
|
||||||
lmsTerminate() {
|
lmsTerminate() {
|
||||||
return _self.terminate('Terminate', true);
|
return this.terminate('Terminate', true);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -74,7 +72,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
lmsGetValue(CMIElement) {
|
lmsGetValue(CMIElement) {
|
||||||
return _self.getValue('GetValue', true, CMIElement);
|
return this.getValue('GetValue', true, CMIElement);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -83,7 +81,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
lmsSetValue(CMIElement, value) {
|
lmsSetValue(CMIElement, value) {
|
||||||
return _self.setValue('SetValue', true, CMIElement, value);
|
return this.setValue('SetValue', true, CMIElement, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -92,7 +90,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string} bool
|
* @return {string} bool
|
||||||
*/
|
*/
|
||||||
lmsCommit() {
|
lmsCommit() {
|
||||||
return _self.commit('Commit');
|
return this.commit('Commit');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -101,7 +99,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
lmsGetLastError() {
|
lmsGetLastError() {
|
||||||
return _self.getLastError('GetLastError');
|
return this.getLastError('GetLastError');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -111,7 +109,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
lmsGetErrorString(CMIErrorCode) {
|
lmsGetErrorString(CMIErrorCode) {
|
||||||
return _self.getErrorString('GetErrorString', CMIErrorCode);
|
return this.getErrorString('GetErrorString', CMIErrorCode);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -121,7 +119,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
lmsGetDiagnostic(CMIErrorCode) {
|
lmsGetDiagnostic(CMIErrorCode) {
|
||||||
return _self.getDiagnostic('GetDiagnostic', CMIErrorCode);
|
return this.getDiagnostic('GetDiagnostic', CMIErrorCode);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -131,7 +129,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @param {any} value
|
* @param {any} value
|
||||||
*/
|
*/
|
||||||
setCMIValue(CMIElement, value) {
|
setCMIValue(CMIElement, value) {
|
||||||
_self._commonSetCMIValue('SetValue', true, CMIElement, value);
|
this._commonSetCMIValue('SetValue', true, CMIElement, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -144,23 +142,23 @@ class Scorm2004API extends BaseAPI {
|
|||||||
getChildElement(CMIElement, value) {
|
getChildElement(CMIElement, value) {
|
||||||
let newChild;
|
let newChild;
|
||||||
|
|
||||||
if (_self.stringContains(CMIElement, 'cmi.objectives')) {
|
if (this.stringContains(CMIElement, 'cmi.objectives')) {
|
||||||
newChild = new CMIObjectivesObject(this);
|
newChild = new CMIObjectivesObject(this);
|
||||||
} else if (_self.stringContains(CMIElement, '.correct_responses')) {
|
} else if (this.stringContains(CMIElement, '.correct_responses')) {
|
||||||
const parts = CMIElement.split('.');
|
const parts = CMIElement.split('.');
|
||||||
const index = Number(parts[2]);
|
const index = Number(parts[2]);
|
||||||
const interaction = _self.cmi.interactions.childArray[index];
|
const interaction = this.cmi.interactions.childArray[index];
|
||||||
if (typeof interaction.type === 'undefined') {
|
if (typeof interaction.type === 'undefined') {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.DEPENDENCY_NOT_ESTABLISHED);
|
this.throwSCORMError(scorm2004_error_codes.DEPENDENCY_NOT_ESTABLISHED);
|
||||||
} else {
|
} else {
|
||||||
const interaction_type = interaction.type;
|
const interaction_type = interaction.type;
|
||||||
const interaction_count = interaction.correct_responses._count;
|
const interaction_count = interaction.correct_responses._count;
|
||||||
if (interaction_type === 'choice') {
|
if (interaction_type === 'choice') {
|
||||||
for (let i = 0; i < interaction_count && _self.lastErrorCode ===
|
for (let i = 0; i < interaction_count && this.lastErrorCode ===
|
||||||
0; i++) {
|
0; i++) {
|
||||||
const response = interaction.correct_responses.childArray[i];
|
const response = interaction.correct_responses.childArray[i];
|
||||||
if (response.pattern === value) {
|
if (response.pattern === value) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE);
|
this.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -174,22 +172,22 @@ class Scorm2004API extends BaseAPI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (nodes.length > 0 && nodes.length <= response_type.max) {
|
if (nodes.length > 0 && nodes.length <= response_type.max) {
|
||||||
_self.#checkCorrectResponseValue(interaction_type, nodes, value);
|
this.#checkCorrectResponseValue(interaction_type, nodes, value);
|
||||||
} else if (nodes.length > response_type.max) {
|
} else if (nodes.length > response_type.max) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
this.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
||||||
'Data Model Element Pattern Too Long');
|
'Data Model Element Pattern Too Long');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (_self.lastErrorCode === 0) {
|
if (this.lastErrorCode === 0) {
|
||||||
newChild = new CMIInteractionsCorrectResponsesObject(this);
|
newChild = new CMIInteractionsCorrectResponsesObject(this);
|
||||||
}
|
}
|
||||||
} else if (_self.stringContains(CMIElement, '.objectives')) {
|
} else if (this.stringContains(CMIElement, '.objectives')) {
|
||||||
newChild = new CMIInteractionsObjectivesObject(this);
|
newChild = new CMIInteractionsObjectivesObject(this);
|
||||||
} else if (_self.stringContains(CMIElement, 'cmi.interactions')) {
|
} else if (this.stringContains(CMIElement, 'cmi.interactions')) {
|
||||||
newChild = new CMIInteractionsObject(this);
|
newChild = new CMIInteractionsObject(this);
|
||||||
} else if (_self.stringContains(CMIElement, 'cmi.comments_from_learner')) {
|
} else if (this.stringContains(CMIElement, 'cmi.comments_from_learner')) {
|
||||||
newChild = new CMICommentsFromLearnerObject(this);
|
newChild = new CMICommentsFromLearnerObject(this);
|
||||||
} else if (_self.stringContains(CMIElement, 'cmi.comments_from_lms')) {
|
} else if (this.stringContains(CMIElement, 'cmi.comments_from_lms')) {
|
||||||
newChild = new CMICommentsFromLMSObject(this);
|
newChild = new CMICommentsFromLMSObject(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -205,15 +203,15 @@ class Scorm2004API extends BaseAPI {
|
|||||||
const parts = CMIElement.split('.');
|
const parts = CMIElement.split('.');
|
||||||
const index = Number(parts[2]);
|
const index = Number(parts[2]);
|
||||||
const pattern_index = Number(parts[4]);
|
const pattern_index = Number(parts[4]);
|
||||||
const interaction = _self.cmi.interactions.childArray[index];
|
const interaction = this.cmi.interactions.childArray[index];
|
||||||
|
|
||||||
const interaction_type = interaction.type;
|
const interaction_type = interaction.type;
|
||||||
const interaction_count = interaction.correct_responses._count;
|
const interaction_count = interaction.correct_responses._count;
|
||||||
if (interaction_type === 'choice') {
|
if (interaction_type === 'choice') {
|
||||||
for (let i = 0; i < interaction_count && _self.lastErrorCode === 0; i++) {
|
for (let i = 0; i < interaction_count && this.lastErrorCode === 0; i++) {
|
||||||
const response = interaction.correct_responses.childArray[i];
|
const response = interaction.correct_responses.childArray[i];
|
||||||
if (response.pattern === value) {
|
if (response.pattern === value) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE);
|
this.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -229,26 +227,26 @@ class Scorm2004API extends BaseAPI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (nodes.length > 0 && nodes.length <= response_type.max) {
|
if (nodes.length > 0 && nodes.length <= response_type.max) {
|
||||||
_self.#checkCorrectResponseValue(interaction_type, nodes, value);
|
this.#checkCorrectResponseValue(interaction_type, nodes, value);
|
||||||
} else if (nodes.length > response_type.max) {
|
} else if (nodes.length > response_type.max) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
this.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
||||||
'Data Model Element Pattern Too Long');
|
'Data Model Element Pattern Too Long');
|
||||||
}
|
}
|
||||||
|
|
||||||
if (_self.lastErrorCode === 0 &&
|
if (this.lastErrorCode === 0 &&
|
||||||
(!response_type.duplicate ||
|
(!response_type.duplicate ||
|
||||||
!_self.#checkDuplicatedPattern(interaction.correct_responses,
|
!this.#checkDuplicatedPattern(interaction.correct_responses,
|
||||||
pattern_index, value)) ||
|
pattern_index, value)) ||
|
||||||
(_self.lastErrorCode === 0 && value === '')) {
|
(this.lastErrorCode === 0 && value === '')) {
|
||||||
// do nothing, we want the inverse
|
// do nothing, we want the inverse
|
||||||
} else {
|
} else {
|
||||||
if (_self.lastErrorCode === 0) {
|
if (this.lastErrorCode === 0) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
this.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
||||||
'Data Model Element Pattern Already Exists');
|
'Data Model Element Pattern Already Exists');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
this.throwSCORMError(scorm2004_error_codes.GENERAL_SET_FAILURE,
|
||||||
'Data Model Element Collection Limit Reached');
|
'Data Model Element Collection Limit Reached');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -260,7 +258,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
getCMIValue(CMIElement) {
|
getCMIValue(CMIElement) {
|
||||||
return _self._commonGetCMIValue('GetValue', true, CMIElement);
|
return this._commonGetCMIValue('GetValue', true, CMIElement);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -311,10 +309,10 @@ class Scorm2004API extends BaseAPI {
|
|||||||
#checkCorrectResponseValue = (interaction_type, nodes, value) => {
|
#checkCorrectResponseValue = (interaction_type, nodes, value) => {
|
||||||
const response = correct_responses[interaction_type];
|
const response = correct_responses[interaction_type];
|
||||||
const formatRegex = new RegExp(response.format);
|
const formatRegex = new RegExp(response.format);
|
||||||
for (let i = 0; i < nodes.length && _self.lastErrorCode === 0; i++) {
|
for (let i = 0; i < nodes.length && this.lastErrorCode === 0; i++) {
|
||||||
if (interaction_type.match(
|
if (interaction_type.match(
|
||||||
'^(fill-in|long-fill-in|matching|performance|sequencing)$')) {
|
'^(fill-in|long-fill-in|matching|performance|sequencing)$')) {
|
||||||
nodes[i] = _self.#removeCorrectResponsePrefixes(nodes[i]);
|
nodes[i] = this.#removeCorrectResponsePrefixes(nodes[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (response.delimiter2 !== undefined) {
|
if (response.delimiter2 !== undefined) {
|
||||||
@@ -322,30 +320,30 @@ class Scorm2004API extends BaseAPI {
|
|||||||
if (values.length === 2) {
|
if (values.length === 2) {
|
||||||
const matches = values[0].match(formatRegex);
|
const matches = values[0].match(formatRegex);
|
||||||
if (!matches) {
|
if (!matches) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
} else {
|
} else {
|
||||||
if (!values[1].match(new RegExp(response.format2))) {
|
if (!values[1].match(new RegExp(response.format2))) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
const matches = nodes[i].match(formatRegex);
|
const matches = nodes[i].match(formatRegex);
|
||||||
if ((!matches && value !== '') ||
|
if ((!matches && value !== '') ||
|
||||||
(!matches && interaction_type === 'true-false')) {
|
(!matches && interaction_type === 'true-false')) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
} else {
|
} else {
|
||||||
if (interaction_type === 'numeric' && nodes.length > 1) {
|
if (interaction_type === 'numeric' && nodes.length > 1) {
|
||||||
if (Number(nodes[0]) > Number(nodes[1])) {
|
if (Number(nodes[0]) > Number(nodes[1])) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (nodes[i] !== '' && response.unique) {
|
if (nodes[i] !== '' && response.unique) {
|
||||||
for (let j = 0; j < i && _self.lastErrorCode === 0; j++) {
|
for (let j = 0; j < i && this.lastErrorCode === 0; j++) {
|
||||||
if (nodes[i] === nodes[j]) {
|
if (nodes[i] === nodes[j]) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -377,7 +375,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
const lang = langMatches[3];
|
const lang = langMatches[3];
|
||||||
if (lang !== undefined && lang.length > 0) {
|
if (lang !== undefined && lang.length > 0) {
|
||||||
if (valid_languages[lang.toLowerCase()] === undefined) {
|
if (valid_languages[lang.toLowerCase()] === undefined) {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -386,7 +384,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
case 'case_matters':
|
case 'case_matters':
|
||||||
if (!seenLang && !seenOrder && !seenCase) {
|
if (!seenLang && !seenOrder && !seenCase) {
|
||||||
if (matches[3] !== 'true' && matches[3] !== 'false') {
|
if (matches[3] !== 'true' && matches[3] !== 'false') {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -395,7 +393,7 @@ class Scorm2004API extends BaseAPI {
|
|||||||
case 'order_matters':
|
case 'order_matters':
|
||||||
if (!seenCase && !seenLang && !seenOrder) {
|
if (!seenCase && !seenLang && !seenOrder) {
|
||||||
if (matches[3] !== 'true' && matches[3] !== 'false') {
|
if (matches[3] !== 'true' && matches[3] !== 'false') {
|
||||||
_self.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
this.throwSCORMError(scorm2004_error_codes.TYPE_MISMATCH);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -417,8 +415,8 @@ class Scorm2004API extends BaseAPI {
|
|||||||
*/
|
*/
|
||||||
replaceWithAnotherScormAPI(newAPI) {
|
replaceWithAnotherScormAPI(newAPI) {
|
||||||
// Data Model
|
// Data Model
|
||||||
_self.cmi = newAPI.cmi;
|
this.cmi = newAPI.cmi;
|
||||||
_self.adl = newAPI.adl;
|
this.adl = newAPI.adl;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -427,8 +425,8 @@ class Scorm2004API extends BaseAPI {
|
|||||||
* @return {string} ISO8601 Duration
|
* @return {string} ISO8601 Duration
|
||||||
*/
|
*/
|
||||||
getCurrentTotalTime() {
|
getCurrentTotalTime() {
|
||||||
const totalTime = _self.cmi.total_time;
|
const totalTime = this.cmi.total_time;
|
||||||
const sessionTime = _self.cmi.session_time;
|
const sessionTime = this.cmi.session_time;
|
||||||
|
|
||||||
return Util.addTwoDurations(totalTime, sessionTime,
|
return Util.addTwoDurations(totalTime, sessionTime,
|
||||||
scorm2004_regex.CMITimespan);
|
scorm2004_regex.CMITimespan);
|
||||||
|
|||||||
@@ -3,31 +3,38 @@ import {BaseCMI, CMIArray, CMIScore} from './common';
|
|||||||
import {aicc_constants} from '../constants/api_constants';
|
import {aicc_constants} from '../constants/api_constants';
|
||||||
import {aicc_regex} from '../regex';
|
import {aicc_regex} from '../regex';
|
||||||
import {scorm12_error_codes} from '../constants/error_codes';
|
import {scorm12_error_codes} from '../constants/error_codes';
|
||||||
|
import {ValidationError} from '../exceptions';
|
||||||
|
import {check12ValidFormat} from './scorm12_cmi';
|
||||||
|
import {throwReadOnlyError} from './scorm12_cmi';
|
||||||
|
import {throwWriteOnlyError} from './scorm12_cmi';
|
||||||
|
|
||||||
const constants = aicc_constants;
|
const constants = aicc_constants;
|
||||||
const regex = aicc_regex;
|
const regex = aicc_regex;
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets a READ_ONLY error on the API
|
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
|
||||||
function throwReadOnlyError(API) {
|
|
||||||
API.throwSCORMError(scorm12_error_codes.READ_ONLY_ELEMENT);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* CMI Class for AICC
|
* CMI Class for AICC
|
||||||
*/
|
*/
|
||||||
export class CMI extends Scorm12CMI.CMI {
|
export class CMI extends Scorm12CMI.CMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for AICC CMI object
|
* Constructor for AICC CMI object
|
||||||
* @param {AICC} API
|
* @param {boolean} initialized
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor(initialized: boolean) {
|
||||||
super(API, constants.cmi_children);
|
super(constants.cmi_children);
|
||||||
|
|
||||||
this.student_data = new AICCCMIStudentData(API);
|
if (initialized) this.initialize();
|
||||||
this.evaluation = new CMIEvaluation(API);
|
|
||||||
|
this.student_data = new AICCCMIStudentData();
|
||||||
|
this.evaluation = new CMIEvaluation();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.student_data?.initialize();
|
||||||
|
this.evaluation?.initialize();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -37,12 +44,19 @@ export class CMI extends Scorm12CMI.CMI {
|
|||||||
class CMIEvaluation extends BaseCMI {
|
class CMIEvaluation extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for AICC Evaluation object
|
* Constructor for AICC Evaluation object
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
this.comments = new CMIEvaluationComments(API);
|
this.comments = new CMIEvaluationComments();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.comments?.initialize();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -52,10 +66,9 @@ class CMIEvaluation extends BaseCMI {
|
|||||||
class CMIEvaluationComments extends CMIArray {
|
class CMIEvaluationComments extends CMIArray {
|
||||||
/**
|
/**
|
||||||
* Constructor for AICC Evaluation Comments object
|
* Constructor for AICC Evaluation Comments object
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API, constants.comments_children,
|
super(constants.comments_children,
|
||||||
scorm12_error_codes.INVALID_SET_VALUE);
|
scorm12_error_codes.INVALID_SET_VALUE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -66,12 +79,19 @@ class CMIEvaluationComments extends CMIArray {
|
|||||||
class AICCCMIStudentData extends Scorm12CMI.CMIStudentData {
|
class AICCCMIStudentData extends Scorm12CMI.CMIStudentData {
|
||||||
/**
|
/**
|
||||||
* Constructor for AICC StudentData object
|
* Constructor for AICC StudentData object
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API, constants.student_data_children);
|
super(constants.student_data_children);
|
||||||
|
|
||||||
this.tries = new CMITries(API);
|
this.tries = new CMITries();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.tries?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
#tries_during_lesson = '';
|
#tries_during_lesson = '';
|
||||||
@@ -86,13 +106,13 @@ class AICCCMIStudentData extends Scorm12CMI.CMIStudentData {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #tries_during_lesson. Sets an error if trying to set after
|
* Setter for #tries_during_lesson. Sets an error if trying to set after
|
||||||
* API initialization.
|
* initialization.
|
||||||
* @param {string} tries_during_lesson
|
* @param {string} tries_during_lesson
|
||||||
*/
|
*/
|
||||||
set tries_during_lesson(tries_during_lesson) {
|
set tries_during_lesson(tries_during_lesson) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ?
|
||||||
this.#tries_during_lesson = tries_during_lesson :
|
this.#tries_during_lesson = tries_during_lesson :
|
||||||
throwReadOnlyError(this.API);
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -102,10 +122,9 @@ class AICCCMIStudentData extends Scorm12CMI.CMIStudentData {
|
|||||||
export class CMITries extends CMIArray {
|
export class CMITries extends CMIArray {
|
||||||
/**
|
/**
|
||||||
* Constructor for inline Tries Array class
|
* Constructor for inline Tries Array class
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API, aicc_constants.tries_children);
|
super(aicc_constants.tries_children);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -115,12 +134,19 @@ export class CMITries extends CMIArray {
|
|||||||
export class CMITriesObject extends BaseCMI {
|
export class CMITriesObject extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for AICC Tries object
|
* Constructor for AICC Tries object
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
this.score = new CMIScore(API);
|
this.score = new CMIScore();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.score?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
#status = '';
|
#status = '';
|
||||||
@@ -139,7 +165,7 @@ export class CMITriesObject extends BaseCMI {
|
|||||||
* @param {string} status
|
* @param {string} status
|
||||||
*/
|
*/
|
||||||
set status(status) {
|
set status(status) {
|
||||||
if (this.API.checkValidFormat(status, regex.CMIStatus2)) {
|
if (check12ValidFormat(status, regex.CMIStatus2)) {
|
||||||
this.#status = status;
|
this.#status = status;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -157,7 +183,7 @@ export class CMITriesObject extends BaseCMI {
|
|||||||
* @param {string} time
|
* @param {string} time
|
||||||
*/
|
*/
|
||||||
set time(time) {
|
set time(time) {
|
||||||
if (this.API.checkValidFormat(time, regex.CMITime)) {
|
if (check12ValidFormat(time, regex.CMITime)) {
|
||||||
this.#time = time;
|
this.#time = time;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -169,10 +195,9 @@ export class CMITriesObject extends BaseCMI {
|
|||||||
export class CMIEvaluationCommentsObject extends BaseCMI {
|
export class CMIEvaluationCommentsObject extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for Evaluation Comments
|
* Constructor for Evaluation Comments
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#content = '';
|
#content = '';
|
||||||
@@ -192,7 +217,7 @@ export class CMIEvaluationCommentsObject extends BaseCMI {
|
|||||||
* @param {string} content
|
* @param {string} content
|
||||||
*/
|
*/
|
||||||
set content(content) {
|
set content(content) {
|
||||||
if (this.API.checkValidFormat(content, regex.CMIString256)) {
|
if (check12ValidFormat(content, regex.CMIString256)) {
|
||||||
this.#content = content;
|
this.#content = content;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -210,7 +235,7 @@ export class CMIEvaluationCommentsObject extends BaseCMI {
|
|||||||
* @param {string} location
|
* @param {string} location
|
||||||
*/
|
*/
|
||||||
set location(location) {
|
set location(location) {
|
||||||
if (this.API.checkValidFormat(location, regex.CMIString256)) {
|
if (check12ValidFormat(location, regex.CMIString256)) {
|
||||||
this.#location = location;
|
this.#location = location;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -228,7 +253,7 @@ export class CMIEvaluationCommentsObject extends BaseCMI {
|
|||||||
* @param {string} time
|
* @param {string} time
|
||||||
*/
|
*/
|
||||||
set time(time) {
|
set time(time) {
|
||||||
if (this.API.checkValidFormat(time, regex.CMITime)) {
|
if (check12ValidFormat(time, regex.CMITime)) {
|
||||||
this.#time = time;
|
this.#time = time;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -240,10 +265,9 @@ export class CMIEvaluationCommentsObject extends BaseCMI {
|
|||||||
export class NAV extends BaseCMI {
|
export class NAV extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for NAV object
|
* Constructor for NAV object
|
||||||
* @param {AICC} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#event = '';
|
#event = '';
|
||||||
@@ -253,9 +277,7 @@ export class NAV extends BaseCMI {
|
|||||||
* @return {string}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
get event() {
|
get event() {
|
||||||
return (!this.jsonString) ?
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#event;
|
||||||
this.API.throwSCORMError(scorm12_error_codes.WRITE_ONLY_ELEMENT) :
|
|
||||||
this.#event;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -263,7 +285,7 @@ export class NAV extends BaseCMI {
|
|||||||
* @param {string} event
|
* @param {string} event
|
||||||
*/
|
*/
|
||||||
set event(event) {
|
set event(event) {
|
||||||
if (this.API.checkValidFormat(event, regex.NAVEvent)) {
|
if (check12ValidFormat(event, regex.NAVEvent)) {
|
||||||
this.#event = event;
|
this.#event = event;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,20 +1,68 @@
|
|||||||
// @flow
|
// @flow
|
||||||
import {scorm12_constants} from '../constants/api_constants';
|
import {scorm12_constants} from '../constants/api_constants';
|
||||||
import {scorm12_error_codes} from '../constants/error_codes';
|
import {scorm12_error_codes} from '../constants/error_codes';
|
||||||
|
import {ValidationError} from '../exceptions';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the value matches the proper format. If not, throw proper error code.
|
||||||
|
*
|
||||||
|
* @param {string} value
|
||||||
|
* @param {string} regexPattern
|
||||||
|
* @param {number} errorCode
|
||||||
|
* @return {boolean}
|
||||||
|
*/
|
||||||
|
export function checkValidFormat(
|
||||||
|
value: String, regexPattern: String, errorCode: number) {
|
||||||
|
const formatRegex = new RegExp(regexPattern);
|
||||||
|
if (!value || !value.match(formatRegex)) {
|
||||||
|
throw new ValidationError(errorCode);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the value matches the proper range. If not, throw proper error code.
|
||||||
|
*
|
||||||
|
* @param {*} value
|
||||||
|
* @param {string} rangePattern
|
||||||
|
* @param {number} errorCode
|
||||||
|
* @return {boolean}
|
||||||
|
*/
|
||||||
|
export function checkValidRange(
|
||||||
|
value: any, rangePattern: String, errorCode: number) {
|
||||||
|
const ranges = rangePattern.split('#');
|
||||||
|
value = value * 1.0;
|
||||||
|
if (value >= ranges[0]) {
|
||||||
|
if ((ranges[1] === '*') || (value <= ranges[1])) {
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
throw new ValidationError(errorCode);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new ValidationError(errorCode);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Base class for API cmi objects
|
* Base class for API cmi objects
|
||||||
*/
|
*/
|
||||||
export class BaseCMI {
|
export class BaseCMI {
|
||||||
jsonString = false;
|
jsonString = false;
|
||||||
API;
|
#initialized = false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Constructor for base cmi
|
* Getter for #initialized
|
||||||
* @param {BaseAPI} API
|
* @return {boolean}
|
||||||
*/
|
*/
|
||||||
constructor(API: any) {
|
get initialized() {
|
||||||
this.API = API;
|
return this.#initialized;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
this.#initialized = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -24,29 +72,48 @@ export class BaseCMI {
|
|||||||
export class CMIScore extends BaseCMI {
|
export class CMIScore extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for *.score
|
* Constructor for *.score
|
||||||
* @param {BaseAPI} API
|
|
||||||
* @param {string} score_children
|
* @param {string} score_children
|
||||||
* @param {string} score_range
|
* @param {string} score_range
|
||||||
|
* @param {string} max
|
||||||
* @param {number} invalidErrorCode
|
* @param {number} invalidErrorCode
|
||||||
|
* @param {number} invalidTypeCode
|
||||||
|
* @param {number} invalidRangeCode
|
||||||
*/
|
*/
|
||||||
constructor(API, score_children?, score_range?, invalidErrorCode) {
|
constructor(
|
||||||
super(API);
|
{
|
||||||
|
score_children,
|
||||||
|
score_range,
|
||||||
|
max,
|
||||||
|
invalidErrorCode,
|
||||||
|
invalidTypeCode,
|
||||||
|
invalidRangeCode,
|
||||||
|
}) {
|
||||||
|
super();
|
||||||
|
|
||||||
this.#_children = score_children ?
|
this.#_children = score_children ?
|
||||||
score_children :
|
score_children :
|
||||||
scorm12_constants.score_children;
|
scorm12_constants.score_children;
|
||||||
this.#_score_range = score_range ? score_range : false;
|
this.#_score_range = score_range ? score_range : false;
|
||||||
|
this.#max = max ? max : '100';
|
||||||
this.#_invalid_error_code = invalidErrorCode ?
|
this.#_invalid_error_code = invalidErrorCode ?
|
||||||
invalidErrorCode :
|
invalidErrorCode :
|
||||||
scorm12_error_codes.INVALID_SET_VALUE;
|
scorm12_error_codes.INVALID_SET_VALUE;
|
||||||
|
this.#_invalid_type_code = invalidTypeCode ?
|
||||||
|
invalidTypeCode :
|
||||||
|
scorm12_error_codes.TYPE_MISMATCH;
|
||||||
|
this.#_invalid_range_code = invalidRangeCode ?
|
||||||
|
invalidRangeCode :
|
||||||
|
scorm12_error_codes.VALUE_OUT_OF_RANGE;
|
||||||
}
|
}
|
||||||
|
|
||||||
#_children;
|
#_children;
|
||||||
#_score_range;
|
#_score_range;
|
||||||
#_invalid_error_code;
|
#_invalid_error_code;
|
||||||
|
#_invalid_type_code;
|
||||||
|
#_invalid_range_code;
|
||||||
#raw = '';
|
#raw = '';
|
||||||
#min = '';
|
#min = '';
|
||||||
#max = '100';
|
#max;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Getter for _children
|
* Getter for _children
|
||||||
@@ -63,7 +130,7 @@ export class CMIScore extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _children(_children) {
|
set _children(_children) {
|
||||||
this.API.throwSCORMError(this.#_invalid_error_code);
|
throw new ValidationError(this.#_invalid_error_code);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -79,9 +146,11 @@ export class CMIScore extends BaseCMI {
|
|||||||
* @param {string} raw
|
* @param {string} raw
|
||||||
*/
|
*/
|
||||||
set raw(raw) {
|
set raw(raw) {
|
||||||
if (this.API.checkValidFormat(raw, scorm12_constants.CMIDecimal) &&
|
if (checkValidFormat(raw, scorm12_constants.CMIDecimal,
|
||||||
|
this.#_invalid_type_code) &&
|
||||||
(!this.#_score_range ||
|
(!this.#_score_range ||
|
||||||
this.API.checkValidRange(raw, this.#_score_range))) {
|
checkValidRange(raw, this.#_score_range,
|
||||||
|
this.#_invalid_range_code))) {
|
||||||
this.#raw = raw;
|
this.#raw = raw;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -99,9 +168,11 @@ export class CMIScore extends BaseCMI {
|
|||||||
* @param {string} min
|
* @param {string} min
|
||||||
*/
|
*/
|
||||||
set min(min) {
|
set min(min) {
|
||||||
if (this.API.checkValidFormat(min, scorm12_constants.CMIDecimal) &&
|
if (checkValidFormat(min, scorm12_constants.CMIDecimal,
|
||||||
|
this.#_invalid_type_code) &&
|
||||||
(!this.#_score_range ||
|
(!this.#_score_range ||
|
||||||
this.API.checkValidRange(min, this.#_score_range))) {
|
checkValidRange(min, this.#_score_range,
|
||||||
|
this.#_invalid_range_code))) {
|
||||||
this.#min = min;
|
this.#min = min;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -119,9 +190,11 @@ export class CMIScore extends BaseCMI {
|
|||||||
* @param {string} max
|
* @param {string} max
|
||||||
*/
|
*/
|
||||||
set max(max) {
|
set max(max) {
|
||||||
if (this.API.checkValidFormat(max, scorm12_constants.CMIDecimal) &&
|
if (checkValidFormat(max, scorm12_constants.CMIDecimal,
|
||||||
|
this.#_invalid_type_code) &&
|
||||||
(!this.#_score_range ||
|
(!this.#_score_range ||
|
||||||
this.API.checkValidRange(max, this.#_score_range))) {
|
checkValidRange(max, this.#_score_range,
|
||||||
|
this.#_invalid_range_code))) {
|
||||||
this.#max = max;
|
this.#max = max;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -145,12 +218,11 @@ export class CMIScore extends BaseCMI {
|
|||||||
export class CMIArray extends BaseCMI {
|
export class CMIArray extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor cmi *.n arrays
|
* Constructor cmi *.n arrays
|
||||||
* @param {BaseAPI} API
|
|
||||||
* @param {string} children
|
* @param {string} children
|
||||||
* @param {number} errorCode
|
* @param {number} errorCode
|
||||||
*/
|
*/
|
||||||
constructor({API, children, errorCode}) {
|
constructor({children, errorCode}) {
|
||||||
super(API);
|
super();
|
||||||
this.#_children = children;
|
this.#_children = children;
|
||||||
this.#errorCode = errorCode;
|
this.#errorCode = errorCode;
|
||||||
this.childArray = [];
|
this.childArray = [];
|
||||||
@@ -174,7 +246,7 @@ export class CMIArray extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _children(_children) {
|
set _children(_children) {
|
||||||
this.API.throwSCORMError(this.#errorCode);
|
throw new ValidationError(this.#errorCode);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -192,7 +264,7 @@ export class CMIArray extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _count(_count) {
|
set _count(_count) {
|
||||||
this.API.throwSCORMError(this.#errorCode);
|
throw new ValidationError(this.#errorCode);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,34 +1,60 @@
|
|||||||
// @flow
|
// @flow
|
||||||
import {BaseCMI, CMIArray, CMIScore} from './common';
|
import {
|
||||||
|
BaseCMI,
|
||||||
|
checkValidFormat,
|
||||||
|
checkValidRange,
|
||||||
|
CMIArray,
|
||||||
|
CMIScore,
|
||||||
|
} from './common';
|
||||||
import {scorm12_constants} from '../constants/api_constants';
|
import {scorm12_constants} from '../constants/api_constants';
|
||||||
import {scorm12_error_codes} from '../constants/error_codes';
|
import {scorm12_error_codes} from '../constants/error_codes';
|
||||||
import {scorm12_regex} from '../regex';
|
import {scorm12_regex} from '../regex';
|
||||||
|
import {ValidationError} from '../exceptions';
|
||||||
|
|
||||||
const constants = scorm12_constants;
|
const constants = scorm12_constants;
|
||||||
const regex = scorm12_regex;
|
const regex = scorm12_regex;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper method for throwing Read Only error
|
* Helper method for throwing Read Only error
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
function throwReadOnlyError(API) {
|
export function throwReadOnlyError() {
|
||||||
API.throwSCORMError(scorm12_error_codes.READ_ONLY_ELEMENT);
|
throw new ValidationError(scorm12_error_codes.READ_ONLY_ELEMENT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper method for throwing Write Only error
|
* Helper method for throwing Write Only error
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
function throwWriteOnlyError(API) {
|
export function throwWriteOnlyError() {
|
||||||
API.throwSCORMError(scorm12_error_codes.WRITE_ONLY_ELEMENT);
|
throw new ValidationError(scorm12_error_codes.WRITE_ONLY_ELEMENT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper method for throwing Invalid Set error
|
* Helper method for throwing Invalid Set error
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
function throwInvalidValueError(API) {
|
function throwInvalidValueError() {
|
||||||
API.throwSCORMError(scorm12_error_codes.INVALID_SET_VALUE);
|
throw new ValidationError(scorm12_error_codes.INVALID_SET_VALUE);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper method, no reason to have to pass the same error codes every time
|
||||||
|
* @param {*} value
|
||||||
|
* @param {string} regexPattern
|
||||||
|
* @return {boolean}
|
||||||
|
*/
|
||||||
|
export function check12ValidFormat(value: String, regexPattern: String) {
|
||||||
|
return checkValidFormat(value, regexPattern,
|
||||||
|
scorm12_error_codes.TYPE_MISMATCH);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper method, no reason to have to pass the same error codes every time
|
||||||
|
* @param {*} value
|
||||||
|
* @param {string} rangePattern
|
||||||
|
* @return {boolean}
|
||||||
|
*/
|
||||||
|
export function check12ValidRange(value: any, rangePattern: String) {
|
||||||
|
return checkValidRange(value, rangePattern,
|
||||||
|
scorm12_error_codes.VALUE_OUT_OF_RANGE);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -46,21 +72,33 @@ export class CMI extends BaseCMI {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Constructor for the SCORM 1.2 cmi object
|
* Constructor for the SCORM 1.2 cmi object
|
||||||
* @param {Scorm12API} API
|
|
||||||
* @param {string} cmi_children
|
* @param {string} cmi_children
|
||||||
* @param {string} student_data
|
* @param {(CMIStudentData|AICCCMIStudentData)} student_data
|
||||||
|
* @param {boolean} initialized
|
||||||
*/
|
*/
|
||||||
constructor(API, cmi_children, student_data) {
|
constructor(cmi_children, student_data, initialized: boolean) {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
|
if (initialized) this.initialize();
|
||||||
|
|
||||||
this.#_children = cmi_children ? cmi_children : constants.cmi_children;
|
this.#_children = cmi_children ? cmi_children : constants.cmi_children;
|
||||||
this.core = new CMICore(API);
|
this.core = new CMICore();
|
||||||
this.objectives = new CMIObjectives(API);
|
this.objectives = new CMIObjectives();
|
||||||
this.student_data = student_data ?
|
this.student_data = student_data ? student_data : new CMIStudentData();
|
||||||
student_data :
|
this.student_preference = new CMIStudentPreference();
|
||||||
new CMIStudentData(API);
|
this.interactions = new CMIInteractions();
|
||||||
this.student_preference = new CMIStudentPreference(API);
|
}
|
||||||
this.interactions = new CMIInteractions(API);
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.core?.initialize();
|
||||||
|
this.objectives?.initialize();
|
||||||
|
this.student_data?.initialize();
|
||||||
|
this.student_preference?.initialize();
|
||||||
|
this.interactions?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -112,7 +150,7 @@ export class CMI extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _version(_version) {
|
set _version(_version) {
|
||||||
throwInvalidValueError(this.API);
|
throwInvalidValueError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -130,7 +168,7 @@ export class CMI extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _children(_children) {
|
set _children(_children) {
|
||||||
throwInvalidValueError(this.API);
|
throwInvalidValueError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -146,7 +184,7 @@ export class CMI extends BaseCMI {
|
|||||||
* @param {string} suspend_data
|
* @param {string} suspend_data
|
||||||
*/
|
*/
|
||||||
set suspend_data(suspend_data) {
|
set suspend_data(suspend_data) {
|
||||||
if (this.API.checkValidFormat(suspend_data, regex.CMIString4096)) {
|
if (check12ValidFormat(suspend_data, regex.CMIString4096)) {
|
||||||
this.#suspend_data = suspend_data;
|
this.#suspend_data = suspend_data;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -160,13 +198,11 @@ export class CMI extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #launch_data. Can only be called before API initialization.
|
* Setter for #launch_data. Can only be called before initialization.
|
||||||
* @param {string} launch_data
|
* @param {string} launch_data
|
||||||
*/
|
*/
|
||||||
set launch_data(launch_data) {
|
set launch_data(launch_data) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#launch_data = launch_data : throwReadOnlyError();
|
||||||
this.#launch_data = launch_data :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -182,7 +218,7 @@ export class CMI extends BaseCMI {
|
|||||||
* @param {string} comments
|
* @param {string} comments
|
||||||
*/
|
*/
|
||||||
set comments(comments) {
|
set comments(comments) {
|
||||||
if (this.API.checkValidFormat(comments, regex.CMIString4096)) {
|
if (check12ValidFormat(comments, regex.CMIString4096)) {
|
||||||
this.#comments = comments;
|
this.#comments = comments;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -196,13 +232,11 @@ export class CMI extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #comments_from_lms. Can only be called before API initialization.
|
* Setter for #comments_from_lms. Can only be called before initialization.
|
||||||
* @param {string} comments_from_lms
|
* @param {string} comments_from_lms
|
||||||
*/
|
*/
|
||||||
set comments_from_lms(comments_from_lms) {
|
set comments_from_lms(comments_from_lms) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#comments_from_lms = comments_from_lms : throwReadOnlyError();
|
||||||
this.#comments_from_lms = comments_from_lms :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -212,13 +246,26 @@ export class CMI extends BaseCMI {
|
|||||||
class CMICore extends BaseCMI {
|
class CMICore extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.core
|
* Constructor for cmi.core
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
this.score = new Scorm12CMIScore(API, constants.score_children,
|
this.score = new Scorm12CMIScore(
|
||||||
regex.score_range);
|
{
|
||||||
|
score_children: constants.score_children,
|
||||||
|
score_range: regex.score_range,
|
||||||
|
invalidErrorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
||||||
|
invalidTypeCode: scorm12_error_codes.TYPE_MISMATCH,
|
||||||
|
invalidRangeCode: scorm12_error_codes.VALUE_OUT_OF_RANGE,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.score?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
#_children = constants.core_children;
|
#_children = constants.core_children;
|
||||||
@@ -248,7 +295,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _children(_children) {
|
set _children(_children) {
|
||||||
throwInvalidValueError(this.API);
|
throwInvalidValueError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -260,13 +307,11 @@ class CMICore extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #student_id. Can only be called before API initialization.
|
* Setter for #student_id. Can only be called before initialization.
|
||||||
* @param {string} student_id
|
* @param {string} student_id
|
||||||
*/
|
*/
|
||||||
set student_id(student_id) {
|
set student_id(student_id) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#student_id = student_id : throwReadOnlyError();
|
||||||
this.#student_id = student_id :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -278,13 +323,11 @@ class CMICore extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #student_name. Can only be called before API initialization.
|
* Setter for #student_name. Can only be called before initialization.
|
||||||
* @param {string} student_name
|
* @param {string} student_name
|
||||||
*/
|
*/
|
||||||
set student_name(student_name) {
|
set student_name(student_name) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#student_name = student_name : throwReadOnlyError();
|
||||||
this.#student_name = student_name :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -300,7 +343,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @param {string} lesson_location
|
* @param {string} lesson_location
|
||||||
*/
|
*/
|
||||||
set lesson_location(lesson_location) {
|
set lesson_location(lesson_location) {
|
||||||
if (this.API.checkValidFormat(lesson_location, regex.CMIString256)) {
|
if (check12ValidFormat(lesson_location, regex.CMIString256)) {
|
||||||
this.#lesson_location = lesson_location;
|
this.#lesson_location = lesson_location;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -314,13 +357,11 @@ class CMICore extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #credit. Can only be called before API initialization.
|
* Setter for #credit. Can only be called before initialization.
|
||||||
* @param {string} credit
|
* @param {string} credit
|
||||||
*/
|
*/
|
||||||
set credit(credit) {
|
set credit(credit) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#credit = credit : throwReadOnlyError();
|
||||||
this.#credit = credit :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -336,7 +377,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @param {string} lesson_status
|
* @param {string} lesson_status
|
||||||
*/
|
*/
|
||||||
set lesson_status(lesson_status) {
|
set lesson_status(lesson_status) {
|
||||||
if (this.API.checkValidFormat(lesson_status, regex.CMIStatus)) {
|
if (check12ValidFormat(lesson_status, regex.CMIStatus)) {
|
||||||
this.#lesson_status = lesson_status;
|
this.#lesson_status = lesson_status;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -350,13 +391,11 @@ class CMICore extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #entry. Can only be called before API initialization.
|
* Setter for #entry. Can only be called before initialization.
|
||||||
* @param {string} entry
|
* @param {string} entry
|
||||||
*/
|
*/
|
||||||
set entry(entry) {
|
set entry(entry) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#entry = entry : throwReadOnlyError();
|
||||||
this.#entry = entry :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -368,13 +407,11 @@ class CMICore extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #total_time. Can only be called before API initialization.
|
* Setter for #total_time. Can only be called before initialization.
|
||||||
* @param {string} total_time
|
* @param {string} total_time
|
||||||
*/
|
*/
|
||||||
set total_time(total_time) {
|
set total_time(total_time) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#total_time = total_time : throwReadOnlyError();
|
||||||
this.#total_time = total_time :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -386,13 +423,11 @@ class CMICore extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #lesson_mode. Can only be called before API initialization.
|
* Setter for #lesson_mode. Can only be called before initialization.
|
||||||
* @param {string} lesson_mode
|
* @param {string} lesson_mode
|
||||||
*/
|
*/
|
||||||
set lesson_mode(lesson_mode) {
|
set lesson_mode(lesson_mode) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#lesson_mode = lesson_mode : throwReadOnlyError();
|
||||||
this.#lesson_mode = lesson_mode :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -400,7 +435,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get exit() {
|
get exit() {
|
||||||
return (!this.jsonString) ? throwWriteOnlyError(this.API) : this.#exit;
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -408,7 +443,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @param {string} exit
|
* @param {string} exit
|
||||||
*/
|
*/
|
||||||
set exit(exit) {
|
set exit(exit) {
|
||||||
if (this.API.checkValidFormat(exit, regex.CMIExit)) {
|
if (check12ValidFormat(exit, regex.CMIExit)) {
|
||||||
this.#exit = exit;
|
this.#exit = exit;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -418,9 +453,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get session_time() {
|
get session_time() {
|
||||||
return (!this.jsonString) ?
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#session_time;
|
||||||
throwWriteOnlyError(this.API) :
|
|
||||||
this.#session_time;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -428,7 +461,7 @@ class CMICore extends BaseCMI {
|
|||||||
* @param {string} session_time
|
* @param {string} session_time
|
||||||
*/
|
*/
|
||||||
set session_time(session_time) {
|
set session_time(session_time) {
|
||||||
if (this.API.checkValidFormat(session_time, regex.CMITimespan)) {
|
if (check12ValidFormat(session_time, regex.CMITimespan)) {
|
||||||
this.#session_time = session_time;
|
this.#session_time = session_time;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -478,11 +511,9 @@ class CMICore extends BaseCMI {
|
|||||||
class CMIObjectives extends CMIArray {
|
class CMIObjectives extends CMIArray {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.objectives
|
* Constructor for cmi.objectives
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super({
|
super({
|
||||||
API: API,
|
|
||||||
children: constants.objectives_children,
|
children: constants.objectives_children,
|
||||||
errorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
errorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
||||||
});
|
});
|
||||||
@@ -500,11 +531,10 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.student_data
|
* Constructor for cmi.student_data
|
||||||
* @param {Scorm12API} API
|
|
||||||
* @param {string} student_data_children
|
* @param {string} student_data_children
|
||||||
*/
|
*/
|
||||||
constructor(API, student_data_children) {
|
constructor(student_data_children) {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
this.#_children = student_data_children ?
|
this.#_children = student_data_children ?
|
||||||
student_data_children :
|
student_data_children :
|
||||||
@@ -526,7 +556,7 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _children(_children) {
|
set _children(_children) {
|
||||||
throwInvalidValueError(this.API);
|
throwInvalidValueError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -538,13 +568,11 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #master_score. Can only be called before API initialization.
|
* Setter for #master_score. Can only be called before initialization.
|
||||||
* @param {string} mastery_score
|
* @param {string} mastery_score
|
||||||
*/
|
*/
|
||||||
set mastery_score(mastery_score) {
|
set mastery_score(mastery_score) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#mastery_score = mastery_score : throwReadOnlyError();
|
||||||
this.#mastery_score = mastery_score :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -556,13 +584,11 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #max_time_allowed. Can only be called before API initialization.
|
* Setter for #max_time_allowed. Can only be called before initialization.
|
||||||
* @param {string} max_time_allowed
|
* @param {string} max_time_allowed
|
||||||
*/
|
*/
|
||||||
set max_time_allowed(max_time_allowed) {
|
set max_time_allowed(max_time_allowed) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#max_time_allowed = max_time_allowed : throwReadOnlyError();
|
||||||
this.#max_time_allowed = max_time_allowed :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -574,13 +600,11 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setter for #time_limit_action. Can only be called before API initialization.
|
* Setter for #time_limit_action. Can only be called before initialization.
|
||||||
* @param {string} time_limit_action
|
* @param {string} time_limit_action
|
||||||
*/
|
*/
|
||||||
set time_limit_action(time_limit_action) {
|
set time_limit_action(time_limit_action) {
|
||||||
this.API.isNotInitialized() ?
|
!this.initialized ? this.#time_limit_action = time_limit_action : throwReadOnlyError();
|
||||||
this.#time_limit_action = time_limit_action :
|
|
||||||
throwReadOnlyError(this.API);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -612,10 +636,9 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
class CMIStudentPreference extends BaseCMI {
|
class CMIStudentPreference extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.student_preference
|
* Constructor for cmi.student_preference
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#_children = constants.student_preference_children;
|
#_children = constants.student_preference_children;
|
||||||
@@ -639,7 +662,7 @@ class CMIStudentPreference extends BaseCMI {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
set _children(_children) {
|
set _children(_children) {
|
||||||
throwInvalidValueError(this.API);
|
throwInvalidValueError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -655,8 +678,8 @@ class CMIStudentPreference extends BaseCMI {
|
|||||||
* @param {string} audio
|
* @param {string} audio
|
||||||
*/
|
*/
|
||||||
set audio(audio) {
|
set audio(audio) {
|
||||||
if (this.API.checkValidFormat(audio, regex.CMISInteger) &&
|
if (check12ValidFormat(audio, regex.CMISInteger) &&
|
||||||
this.API.checkValidRange(audio, regex.audio_range)) {
|
check12ValidRange(audio, regex.audio_range)) {
|
||||||
this.#audio = audio;
|
this.#audio = audio;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -674,7 +697,7 @@ class CMIStudentPreference extends BaseCMI {
|
|||||||
* @param {string} language
|
* @param {string} language
|
||||||
*/
|
*/
|
||||||
set language(language) {
|
set language(language) {
|
||||||
if (this.API.checkValidFormat(language, regex.CMIString256)) {
|
if (check12ValidFormat(language, regex.CMIString256)) {
|
||||||
this.#language = language;
|
this.#language = language;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -692,8 +715,8 @@ class CMIStudentPreference extends BaseCMI {
|
|||||||
* @param {string} speed
|
* @param {string} speed
|
||||||
*/
|
*/
|
||||||
set speed(speed) {
|
set speed(speed) {
|
||||||
if (this.API.checkValidFormat(speed, regex.CMISInteger) &&
|
if (check12ValidFormat(speed, regex.CMISInteger) &&
|
||||||
this.API.checkValidRange(speed, regex.speed_range)) {
|
check12ValidRange(speed, regex.speed_range)) {
|
||||||
this.#speed = speed;
|
this.#speed = speed;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -711,8 +734,8 @@ class CMIStudentPreference extends BaseCMI {
|
|||||||
* @param {string} text
|
* @param {string} text
|
||||||
*/
|
*/
|
||||||
set text(text) {
|
set text(text) {
|
||||||
if (this.API.checkValidFormat(text, regex.CMISInteger) &&
|
if (check12ValidFormat(text, regex.CMISInteger) &&
|
||||||
this.API.checkValidRange(text, regex.text_range)) {
|
check12ValidRange(text, regex.text_range)) {
|
||||||
this.#text = text;
|
this.#text = text;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -748,11 +771,9 @@ class CMIStudentPreference extends BaseCMI {
|
|||||||
class CMIInteractions extends CMIArray {
|
class CMIInteractions extends CMIArray {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.interactions
|
* Constructor for cmi.interactions
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super({
|
super({
|
||||||
API: API,
|
|
||||||
children: constants.interactions_children,
|
children: constants.interactions_children,
|
||||||
errorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
errorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
||||||
});
|
});
|
||||||
@@ -765,23 +786,29 @@ class CMIInteractions extends CMIArray {
|
|||||||
export class CMIInteractionsObject extends BaseCMI {
|
export class CMIInteractionsObject extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.interactions.n object
|
* Constructor for cmi.interactions.n object
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
this.objectives = new CMIArray({
|
this.objectives = new CMIArray({
|
||||||
API: API,
|
errorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
||||||
errorCode: 402,
|
|
||||||
children: constants.objectives_children,
|
children: constants.objectives_children,
|
||||||
});
|
});
|
||||||
this.correct_responses = new CMIArray({
|
this.correct_responses = new CMIArray({
|
||||||
API: API,
|
errorCode: scorm12_error_codes.INVALID_SET_VALUE,
|
||||||
errorCode: 402,
|
|
||||||
children: constants.correct_responses_children,
|
children: constants.correct_responses_children,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Called when the API has been initialized after the CMI has been created
|
||||||
|
*/
|
||||||
|
initialize() {
|
||||||
|
super.initialize();
|
||||||
|
this.objectives?.initialize();
|
||||||
|
this.correct_responses?.initialize();
|
||||||
|
}
|
||||||
|
|
||||||
#id: '';
|
#id: '';
|
||||||
#time: '';
|
#time: '';
|
||||||
#type: '';
|
#type: '';
|
||||||
@@ -795,7 +822,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get id() {
|
get id() {
|
||||||
return (!this.jsonString) ? throwWriteOnlyError(this.API) : this.#id;
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#id;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -803,7 +830,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} id
|
* @param {string} id
|
||||||
*/
|
*/
|
||||||
set id(id) {
|
set id(id) {
|
||||||
if (this.API.checkValidFormat(id, regex.CMIIdentifier)) {
|
if (check12ValidFormat(id, regex.CMIIdentifier)) {
|
||||||
this.#id = id;
|
this.#id = id;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -813,7 +840,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get time() {
|
get time() {
|
||||||
return (!this.jsonString) ? throwWriteOnlyError(this.API) : this.#time;
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#time;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -821,7 +848,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} time
|
* @param {string} time
|
||||||
*/
|
*/
|
||||||
set time(time) {
|
set time(time) {
|
||||||
if (this.API.checkValidFormat(time, regex.CMITime)) {
|
if (check12ValidFormat(time, regex.CMITime)) {
|
||||||
this.#time = time;
|
this.#time = time;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -831,7 +858,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get type() {
|
get type() {
|
||||||
return (!this.jsonString) ? throwWriteOnlyError(this.API) : this.#type;
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#type;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -839,7 +866,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} type
|
* @param {string} type
|
||||||
*/
|
*/
|
||||||
set type(type) {
|
set type(type) {
|
||||||
if (this.API.checkValidFormat(type, regex.CMIType)) {
|
if (check12ValidFormat(type, regex.CMIType)) {
|
||||||
this.#type = type;
|
this.#type = type;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -850,7 +877,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
*/
|
*/
|
||||||
get weighting() {
|
get weighting() {
|
||||||
return (!this.jsonString) ?
|
return (!this.jsonString) ?
|
||||||
throwWriteOnlyError(this.API) :
|
throwWriteOnlyError() :
|
||||||
this.#weighting;
|
this.#weighting;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -859,8 +886,8 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} weighting
|
* @param {string} weighting
|
||||||
*/
|
*/
|
||||||
set weighting(weighting) {
|
set weighting(weighting) {
|
||||||
if (this.API.checkValidFormat(weighting, regex.CMIDecimal) &&
|
if (check12ValidFormat(weighting, regex.CMIDecimal) &&
|
||||||
this.API.checkValidRange(weighting, regex.weighting_range)) {
|
check12ValidRange(weighting, regex.weighting_range)) {
|
||||||
this.#weighting = weighting;
|
this.#weighting = weighting;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -870,9 +897,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get student_response() {
|
get student_response() {
|
||||||
return (!this.jsonString) ?
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#student_response;
|
||||||
throwWriteOnlyError(this.API) :
|
|
||||||
this.#student_response;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -880,7 +905,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} student_response
|
* @param {string} student_response
|
||||||
*/
|
*/
|
||||||
set student_response(student_response) {
|
set student_response(student_response) {
|
||||||
if (this.API.checkValidFormat(student_response, regex.CMIFeedback)) {
|
if (check12ValidFormat(student_response, regex.CMIFeedback)) {
|
||||||
this.#student_response = student_response;
|
this.#student_response = student_response;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -890,9 +915,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get result() {
|
get result() {
|
||||||
return (!this.jsonString) ?
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#result;
|
||||||
throwWriteOnlyError(this.API) :
|
|
||||||
this.#result;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -900,7 +923,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} result
|
* @param {string} result
|
||||||
*/
|
*/
|
||||||
set result(result) {
|
set result(result) {
|
||||||
if (this.API.checkValidFormat(result, regex.CMIResult)) {
|
if (check12ValidFormat(result, regex.CMIResult)) {
|
||||||
this.#result = result;
|
this.#result = result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -910,9 +933,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @return {*}
|
* @return {*}
|
||||||
*/
|
*/
|
||||||
get latency() {
|
get latency() {
|
||||||
return (!this.jsonString) ?
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#latency;
|
||||||
throwWriteOnlyError(this.API) :
|
|
||||||
this.#latency;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -920,7 +941,7 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
* @param {string} latency
|
* @param {string} latency
|
||||||
*/
|
*/
|
||||||
set latency(latency) {
|
set latency(latency) {
|
||||||
if (this.API.checkValidFormat(latency, regex.CMITimespan)) {
|
if (check12ValidFormat(latency, regex.CMITimespan)) {
|
||||||
this.#latency = latency;
|
this.#latency = latency;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -966,12 +987,11 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
export class CMIObjectivesObject extends BaseCMI {
|
export class CMIObjectivesObject extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.objectives.n
|
* Constructor for cmi.objectives.n
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
|
|
||||||
this.score = new Scorm12CMIScore(API);
|
this.score = new Scorm12CMIScore();
|
||||||
}
|
}
|
||||||
|
|
||||||
#id: '';
|
#id: '';
|
||||||
@@ -990,7 +1010,7 @@ export class CMIObjectivesObject extends BaseCMI {
|
|||||||
* @param {string} id
|
* @param {string} id
|
||||||
*/
|
*/
|
||||||
set id(id) {
|
set id(id) {
|
||||||
if (this.API.checkValidFormat(id, regex.CMIIdentifier)) {
|
if (check12ValidFormat(id, regex.CMIIdentifier)) {
|
||||||
this.#id = id;
|
this.#id = id;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1008,7 +1028,7 @@ export class CMIObjectivesObject extends BaseCMI {
|
|||||||
* @param {string} status
|
* @param {string} status
|
||||||
*/
|
*/
|
||||||
set status(status) {
|
set status(status) {
|
||||||
if (this.API.checkValidFormat(status, regex.CMIStatus2)) {
|
if (check12ValidFormat(status, regex.CMIStatus2)) {
|
||||||
this.#status = status;
|
this.#status = status;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1041,10 +1061,9 @@ export class CMIObjectivesObject extends BaseCMI {
|
|||||||
export class CMIInteractionsObjectivesObject extends BaseCMI {
|
export class CMIInteractionsObjectivesObject extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.interactions.n.objectives.n
|
* Constructor for cmi.interactions.n.objectives.n
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#id: '';
|
#id: '';
|
||||||
@@ -1062,7 +1081,7 @@ export class CMIInteractionsObjectivesObject extends BaseCMI {
|
|||||||
* @param {string} id
|
* @param {string} id
|
||||||
*/
|
*/
|
||||||
set id(id) {
|
set id(id) {
|
||||||
if (this.API.checkValidFormat(id, regex.CMIIdentifier)) {
|
if (check12ValidFormat(id, regex.CMIIdentifier)) {
|
||||||
this.#id = id;
|
this.#id = id;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1091,10 +1110,9 @@ export class CMIInteractionsObjectivesObject extends BaseCMI {
|
|||||||
export class CMIInteractionsCorrectResponsesObject extends BaseCMI {
|
export class CMIInteractionsCorrectResponsesObject extends BaseCMI {
|
||||||
/**
|
/**
|
||||||
* Constructor for cmi.interactions.correct_responses.n
|
* Constructor for cmi.interactions.correct_responses.n
|
||||||
* @param {Scorm12API} API
|
|
||||||
*/
|
*/
|
||||||
constructor(API) {
|
constructor() {
|
||||||
super(API);
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#pattern: '';
|
#pattern: '';
|
||||||
@@ -1112,7 +1130,7 @@ export class CMIInteractionsCorrectResponsesObject extends BaseCMI {
|
|||||||
* @param {string} pattern
|
* @param {string} pattern
|
||||||
*/
|
*/
|
||||||
set pattern(pattern) {
|
set pattern(pattern) {
|
||||||
if (this.API.checkValidFormat(pattern, regex.CMIFeedback)) {
|
if (check12ValidFormat(pattern, regex.CMIFeedback)) {
|
||||||
this.#pattern = pattern;
|
this.#pattern = pattern;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
33
src/exceptions.js
Normal file
33
src/exceptions.js
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
// @flow
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Data Validation Exception
|
||||||
|
*/
|
||||||
|
export class ValidationError extends Error {
|
||||||
|
/**
|
||||||
|
* Constructor to take in an error message and code
|
||||||
|
* @param {number} errorCode
|
||||||
|
*/
|
||||||
|
constructor(errorCode: number) {
|
||||||
|
super(errorCode);
|
||||||
|
this.#errorCode = errorCode;
|
||||||
|
}
|
||||||
|
|
||||||
|
#errorCode;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Getter for #errorCode
|
||||||
|
* @return {number}
|
||||||
|
*/
|
||||||
|
get errorCode() {
|
||||||
|
return this.#errorCode;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Trying to override the default Error message
|
||||||
|
* @return {string}
|
||||||
|
*/
|
||||||
|
get message() {
|
||||||
|
return this.#errorCode + '';
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,29 +1,27 @@
|
|||||||
import {expect, assert} from 'chai';
|
import {expect} from 'chai';
|
||||||
import {describe, it, beforeEach, afterEach} from 'mocha';
|
import {describe, it, beforeEach, afterEach} from 'mocha';
|
||||||
import AICC from '../../src/AICC';
|
|
||||||
import {aicc_constants} from '../../src/constants/api_constants';
|
import {aicc_constants} from '../../src/constants/api_constants';
|
||||||
import {scorm12_error_codes} from '../../src/constants/error_codes';
|
import {scorm12_error_codes} from '../../src/constants/error_codes';
|
||||||
|
import {CMI} from '../../src/cmi/aicc_cmi';
|
||||||
|
|
||||||
let API;
|
let cmi;
|
||||||
|
|
||||||
const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should be able to write upto ${limit} characters to ${fieldName}`,
|
it(`Should be able to write upto ${limit} characters to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = 'x'.repeat(${limit})`);
|
expect(() => eval(`${fieldName} = 'x'.repeat(${limit})`)).
|
||||||
expect(0).to.equal(API.lastErrorCode);
|
to.not.throw();
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should fail to write more than ${limit} characters to ${fieldName}`,
|
it(`Should fail to write more than ${limit} characters to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = 'x'.repeat(${limit + 1})`);
|
expect(() => eval(`${fieldName} = 'x'.repeat(${limit + 1})`)).
|
||||||
expect(scorm12_error_codes.TYPE_MISMATCH + '').
|
to.throw(scorm12_error_codes.TYPE_MISMATCH + '');
|
||||||
to.
|
|
||||||
equal(API.lastErrorCode);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -31,14 +29,12 @@ const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
|||||||
const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should fail to write to ${fieldName}`, () => {
|
it(`Should fail to write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = 'xxx'`);
|
expect(() => eval(`${fieldName} = 'xxx'`)).
|
||||||
expect(API.lastErrorCode).
|
to.throw(scorm12_error_codes.INVALID_SET_VALUE + '');
|
||||||
to.
|
|
||||||
equal(scorm12_error_codes.INVALID_SET_VALUE + '');
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -46,14 +42,12 @@ const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
|||||||
const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should fail to write to ${fieldName}`, () => {
|
it(`Should fail to write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = 'xxx'`);
|
expect(() => eval(`${fieldName} = 'xxx'`)).
|
||||||
expect(API.lastErrorCode).
|
to.throw(scorm12_error_codes.READ_ONLY_ELEMENT + '');
|
||||||
to.
|
|
||||||
equal(scorm12_error_codes.READ_ONLY_ELEMENT + '');
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -61,7 +55,7 @@ const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
|||||||
const checkRead = ({fieldName, expectedValue = ''}) => {
|
const checkRead = ({fieldName, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -69,12 +63,12 @@ const checkRead = ({fieldName, expectedValue = ''}) => {
|
|||||||
const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'}) => {
|
const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should successfully write to ${fieldName}`, () => {
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = '${valueToTest}'`);
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
to.not.throw();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -82,15 +76,12 @@ const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'})
|
|||||||
const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should fail to read from ${fieldName}`, () => {
|
it(`Should fail to read from ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName}`);
|
expect(() => eval(`${fieldName}`)).
|
||||||
expect(API.lastErrorCode).
|
to.throw(scorm12_error_codes.WRITE_ONLY_ELEMENT + '');
|
||||||
to.
|
|
||||||
equal(scorm12_error_codes.WRITE_ONLY_ELEMENT + '');
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should successfully write to ${fieldName}`, () => {
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = '${valueToTest}'`);
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).to.not.throw();
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -98,8 +89,7 @@ const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
|||||||
const checkWrite = ({fieldName, valueToTest = 'xxx'}) => {
|
const checkWrite = ({fieldName, valueToTest = 'xxx'}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should successfully write to ${fieldName}`, () => {
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = '${valueToTest}'`);
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).to.not.throw();
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -110,8 +100,8 @@ const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}
|
|||||||
if ({}.hasOwnProperty.call(validValues, idx)) {
|
if ({}.hasOwnProperty.call(validValues, idx)) {
|
||||||
it(`Should successfully write '${validValues[idx]}' to ${fieldName}`,
|
it(`Should successfully write '${validValues[idx]}' to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = '${validValues[idx]}'`);
|
expect(() => eval(`${fieldName} = '${validValues[idx]}'`)).
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
to.not.throw();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -120,8 +110,8 @@ const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}
|
|||||||
if ({}.hasOwnProperty.call(invalidValues, idx)) {
|
if ({}.hasOwnProperty.call(invalidValues, idx)) {
|
||||||
it(`Should fail to write '${invalidValues[idx]}' to ${fieldName}`,
|
it(`Should fail to write '${invalidValues[idx]}' to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = '${invalidValues[idx]}'`);
|
expect(() => eval(`${fieldName} = '${invalidValues[idx]}'`)).
|
||||||
expect(API.lastErrorCode).to.equal(expectedError + '');
|
to.throw(expectedError + '');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -130,30 +120,12 @@ const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}
|
|||||||
|
|
||||||
describe('AICC CMI Tests', () => {
|
describe('AICC CMI Tests', () => {
|
||||||
describe('CMI Spec Tests', () => {
|
describe('CMI Spec Tests', () => {
|
||||||
beforeEach('Create the API object', () => {
|
|
||||||
API = new AICC();
|
|
||||||
API.lmsInitialize();
|
|
||||||
});
|
|
||||||
afterEach('Destroy API object', () => {
|
|
||||||
API = null;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('lmsInitialize should create CMI object', () => {
|
|
||||||
assert(API.cmi !== undefined, 'CMI object is created');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('Exporting CMI to JSON produces proper Object', () => {
|
|
||||||
expect(
|
|
||||||
JSON.parse(API.renderCMIToJSON()).cmi?.core !== undefined,
|
|
||||||
).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Pre-Initialize Tests', () => {
|
describe('Pre-Initialize Tests', () => {
|
||||||
beforeEach('Create the API object', () => {
|
beforeEach('Create the API object', () => {
|
||||||
API = new AICC();
|
cmi = new CMI();
|
||||||
});
|
});
|
||||||
afterEach('Destroy API object', () => {
|
afterEach('Destroy API object', () => {
|
||||||
API = null;
|
cmi = null;
|
||||||
});
|
});
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -409,11 +381,11 @@ describe('AICC CMI Tests', () => {
|
|||||||
|
|
||||||
describe('Post-Initialize Tests', () => {
|
describe('Post-Initialize Tests', () => {
|
||||||
beforeEach('Create the API object', () => {
|
beforeEach('Create the API object', () => {
|
||||||
API = new AICC();
|
cmi = new CMI();
|
||||||
API.lmsInitialize();
|
cmi.initialize();
|
||||||
});
|
});
|
||||||
afterEach('Destroy API object', () => {
|
afterEach('Destroy API object', () => {
|
||||||
API = null;
|
cmi = null;
|
||||||
});
|
});
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,29 +1,27 @@
|
|||||||
import {expect, assert} from 'chai';
|
import {expect} from 'chai';
|
||||||
import {describe, it, beforeEach, afterEach} from 'mocha';
|
import {describe, it, beforeEach, afterEach} from 'mocha';
|
||||||
import Scorm12API from '../../src/Scorm12API';
|
|
||||||
import {scorm12_constants} from '../../src/constants/api_constants';
|
import {scorm12_constants} from '../../src/constants/api_constants';
|
||||||
import {scorm12_error_codes} from '../../src/constants/error_codes';
|
import {scorm12_error_codes} from '../../src/constants/error_codes';
|
||||||
|
import {CMI} from '../../src/cmi/scorm12_cmi';
|
||||||
|
|
||||||
let API;
|
let cmi;
|
||||||
|
|
||||||
const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should be able to write upto ${limit} characters to ${fieldName}`,
|
it(`Should be able to write upto ${limit} characters to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = 'x'.repeat(${limit})`);
|
expect(() => eval(`${fieldName} = 'x'.repeat(${limit})`)).
|
||||||
expect(0).to.equal(API.lastErrorCode);
|
to.not.throw();
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should fail to write more than ${limit} characters to ${fieldName}`,
|
it(`Should fail to write more than ${limit} characters to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = 'x'.repeat(${limit + 1})`);
|
expect(() => eval(`${fieldName} = 'x'.repeat(${limit + 1})`)).
|
||||||
expect(scorm12_error_codes.TYPE_MISMATCH + '').
|
to.throw(scorm12_error_codes.TYPE_MISMATCH + '');
|
||||||
to.
|
|
||||||
equal(API.lastErrorCode);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -31,14 +29,12 @@ const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
|||||||
const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should fail to write to ${fieldName}`, () => {
|
it(`Should fail to write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = 'xxx'`);
|
expect(() => eval(`${fieldName} = 'xxx'`)).
|
||||||
expect(API.lastErrorCode).
|
to.throw(scorm12_error_codes.INVALID_SET_VALUE + '');
|
||||||
to.
|
|
||||||
equal(scorm12_error_codes.INVALID_SET_VALUE + '');
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -46,14 +42,12 @@ const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
|||||||
const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should fail to write to ${fieldName}`, () => {
|
it(`Should fail to write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = 'xxx'`);
|
expect(() => eval(`${fieldName} = 'xxx'`)).
|
||||||
expect(API.lastErrorCode).
|
to.throw(scorm12_error_codes.READ_ONLY_ELEMENT + '');
|
||||||
to.
|
|
||||||
equal(scorm12_error_codes.READ_ONLY_ELEMENT + '');
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -61,7 +55,7 @@ const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
|||||||
const checkRead = ({fieldName, expectedValue = ''}) => {
|
const checkRead = ({fieldName, expectedValue = ''}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -69,12 +63,12 @@ const checkRead = ({fieldName, expectedValue = ''}) => {
|
|||||||
const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'}) => {
|
const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should be able to read from ${fieldName}`, () => {
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
expect(eval(`API.${fieldName}`)).to.equal(expectedValue);
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should successfully write to ${fieldName}`, () => {
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = '${valueToTest}'`);
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
to.not.throw();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -82,15 +76,12 @@ const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'})
|
|||||||
const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should fail to read from ${fieldName}`, () => {
|
it(`Should fail to read from ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName}`);
|
expect(() => eval(`${fieldName}`)).
|
||||||
expect(API.lastErrorCode).
|
to.throw(scorm12_error_codes.WRITE_ONLY_ELEMENT + '');
|
||||||
to.
|
|
||||||
equal(scorm12_error_codes.WRITE_ONLY_ELEMENT + '');
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it(`Should successfully write to ${fieldName}`, () => {
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = '${valueToTest}'`);
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).to.not.throw();
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -98,8 +89,7 @@ const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
|||||||
const checkWrite = ({fieldName, valueToTest = 'xxx'}) => {
|
const checkWrite = ({fieldName, valueToTest = 'xxx'}) => {
|
||||||
describe(`Field: ${fieldName}`, () => {
|
describe(`Field: ${fieldName}`, () => {
|
||||||
it(`Should successfully write to ${fieldName}`, () => {
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
eval(`API.${fieldName} = '${valueToTest}'`);
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).to.not.throw();
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@@ -110,8 +100,8 @@ const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}
|
|||||||
if ({}.hasOwnProperty.call(validValues, idx)) {
|
if ({}.hasOwnProperty.call(validValues, idx)) {
|
||||||
it(`Should successfully write '${validValues[idx]}' to ${fieldName}`,
|
it(`Should successfully write '${validValues[idx]}' to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = '${validValues[idx]}'`);
|
expect(() => eval(`${fieldName} = '${validValues[idx]}'`)).
|
||||||
expect(API.lastErrorCode).to.equal(0);
|
to.not.throw();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -120,8 +110,8 @@ const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}
|
|||||||
if ({}.hasOwnProperty.call(invalidValues, idx)) {
|
if ({}.hasOwnProperty.call(invalidValues, idx)) {
|
||||||
it(`Should fail to write '${invalidValues[idx]}' to ${fieldName}`,
|
it(`Should fail to write '${invalidValues[idx]}' to ${fieldName}`,
|
||||||
() => {
|
() => {
|
||||||
eval(`API.${fieldName} = '${invalidValues[idx]}'`);
|
expect(() => eval(`${fieldName} = '${invalidValues[idx]}'`)).
|
||||||
expect(API.lastErrorCode).to.equal(expectedError + '');
|
to.throw(expectedError + '');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -130,30 +120,12 @@ const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}
|
|||||||
|
|
||||||
describe('SCORM 1.2 CMI Tests', () => {
|
describe('SCORM 1.2 CMI Tests', () => {
|
||||||
describe('CMI Spec Tests', () => {
|
describe('CMI Spec Tests', () => {
|
||||||
beforeEach('Create the API object', () => {
|
|
||||||
API = new Scorm12API();
|
|
||||||
API.lmsInitialize();
|
|
||||||
});
|
|
||||||
afterEach('Destroy API object', () => {
|
|
||||||
API = null;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('lmsInitialize should create CMI object', () => {
|
|
||||||
assert(API.cmi !== undefined, 'CMI object is created');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('Exporting CMI to JSON produces proper Object', () => {
|
|
||||||
expect(
|
|
||||||
JSON.parse(API.renderCMIToJSON()).cmi?.core !== undefined,
|
|
||||||
).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Pre-Initialize Tests', () => {
|
describe('Pre-Initialize Tests', () => {
|
||||||
beforeEach('Create the API object', () => {
|
beforeEach('Create the API object', () => {
|
||||||
API = new Scorm12API();
|
cmi = new CMI();
|
||||||
});
|
});
|
||||||
afterEach('Destroy API object', () => {
|
afterEach('Destroy API object', () => {
|
||||||
API = null;
|
cmi = null;
|
||||||
});
|
});
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -408,11 +380,11 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
|
|
||||||
describe('Post-Initialize Tests', () => {
|
describe('Post-Initialize Tests', () => {
|
||||||
beforeEach('Create the API object', () => {
|
beforeEach('Create the API object', () => {
|
||||||
API = new Scorm12API();
|
cmi = new CMI();
|
||||||
API.lmsInitialize();
|
cmi.initialize();
|
||||||
});
|
});
|
||||||
afterEach('Destroy API object', () => {
|
afterEach('Destroy API object', () => {
|
||||||
API = null;
|
cmi = null;
|
||||||
});
|
});
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
156
test/cmi/scorm2004_cmi.spec.js
Normal file
156
test/cmi/scorm2004_cmi.spec.js
Normal file
@@ -0,0 +1,156 @@
|
|||||||
|
import {expect} from 'chai';
|
||||||
|
import {describe, it, beforeEach, afterEach} from 'mocha';
|
||||||
|
import {scorm2004_error_codes} from '../../src/constants/error_codes';
|
||||||
|
import {scorm2004_constants} from '../../src/constants/api_constants';
|
||||||
|
import {CMI} from '../../src/cmi/scorm2004_cmi';
|
||||||
|
|
||||||
|
let cmi;
|
||||||
|
|
||||||
|
const checkFieldConstraintSize = ({fieldName, limit, expectedValue = ''}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`Should be able to write upto ${limit} characters to ${fieldName}`,
|
||||||
|
() => {
|
||||||
|
expect(() => eval(`${fieldName} = 'x'.repeat(${limit})`)).
|
||||||
|
to.not.throw();
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`Should fail to write more than ${limit} characters to ${fieldName}`,
|
||||||
|
() => {
|
||||||
|
expect(() => eval(`${fieldName} = 'x'.repeat(${limit + 1})`)).
|
||||||
|
to.throw(scorm2004_error_codes.TYPE_MISMATCH + '');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkInvalidSet = ({fieldName, expectedValue = ''}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`Should fail to write to ${fieldName}`, () => {
|
||||||
|
expect(() => eval(`${fieldName} = 'xxx'`)).
|
||||||
|
to.throw(scorm2004_error_codes.INVALID_SET_VALUE + '');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkReadOnly = ({fieldName, expectedValue = ''}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`Should fail to write to ${fieldName}`, () => {
|
||||||
|
expect(() => eval(`${fieldName} = 'xxx'`)).
|
||||||
|
to.throw(scorm2004_error_codes.READ_ONLY_ELEMENT + '');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkRead = ({fieldName, expectedValue = ''}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkReadAndWrite = ({fieldName, expectedValue = '', valueToTest = 'xxx'}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should be able to read from ${fieldName}`, () => {
|
||||||
|
expect(eval(`${fieldName}`)).to.equal(expectedValue);
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).
|
||||||
|
to.not.throw();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkWriteOnly = ({fieldName, valueToTest = 'xxx'}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should fail to read from ${fieldName}`, () => {
|
||||||
|
expect(() => eval(`${fieldName}`)).
|
||||||
|
to.throw(scorm2004_error_codes.WRITE_ONLY_ELEMENT + '');
|
||||||
|
});
|
||||||
|
|
||||||
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).to.not.throw();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkWrite = ({fieldName, valueToTest = 'xxx'}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
it(`Should successfully write to ${fieldName}`, () => {
|
||||||
|
expect(() => eval(`${fieldName} = '${valueToTest}'`)).to.not.throw();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const checkValidValues = ({fieldName, expectedError, validValues, invalidValues}) => {
|
||||||
|
describe(`Field: ${fieldName}`, () => {
|
||||||
|
for (const idx in validValues) {
|
||||||
|
if ({}.hasOwnProperty.call(validValues, idx)) {
|
||||||
|
it(`Should successfully write '${validValues[idx]}' to ${fieldName}`,
|
||||||
|
() => {
|
||||||
|
expect(() => eval(`${fieldName} = '${validValues[idx]}'`)).
|
||||||
|
to.not.throw();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (const idx in invalidValues) {
|
||||||
|
if ({}.hasOwnProperty.call(invalidValues, idx)) {
|
||||||
|
it(`Should fail to write '${invalidValues[idx]}' to ${fieldName}`,
|
||||||
|
() => {
|
||||||
|
expect(() => eval(`${fieldName} = '${invalidValues[idx]}'`)).
|
||||||
|
to.throw(expectedError + '');
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
describe('SCORM 2004 CMI Tests', () => {
|
||||||
|
describe('CMI Spec Tests', () => {
|
||||||
|
describe('Pre-Initialize Tests', () => {
|
||||||
|
beforeEach('Create the API object', () => {
|
||||||
|
cmi = new CMI();
|
||||||
|
});
|
||||||
|
afterEach('Destroy API object', () => {
|
||||||
|
cmi = null;
|
||||||
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Base CMI Properties
|
||||||
|
*/
|
||||||
|
checkReadOnly({fieldName: 'cmi._version', expectedValue: '1.0'});
|
||||||
|
checkReadOnly({
|
||||||
|
fieldName: 'cmi._children',
|
||||||
|
expectedValue: scorm2004_constants.cmi_children,
|
||||||
|
});
|
||||||
|
checkValidValues({
|
||||||
|
fieldName: 'cmi.completion_status',
|
||||||
|
expectedError: scorm2004_error_codes.TYPE_MISMATCH,
|
||||||
|
validValues: [
|
||||||
|
'completed',
|
||||||
|
'incomplete',
|
||||||
|
'not attempted',
|
||||||
|
'unknown',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'complete',
|
||||||
|
'passed',
|
||||||
|
'failed',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
Reference in New Issue
Block a user