More CMI tests
This commit is contained in:
@@ -3,10 +3,11 @@ 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 {
|
||||||
import {check12ValidFormat} from './scorm12_cmi';
|
check12ValidFormat,
|
||||||
import {throwReadOnlyError} from './scorm12_cmi';
|
throwReadOnlyError,
|
||||||
import {throwWriteOnlyError} from './scorm12_cmi';
|
throwWriteOnlyError,
|
||||||
|
} from './scorm12_cmi';
|
||||||
|
|
||||||
const constants = aicc_constants;
|
const constants = aicc_constants;
|
||||||
const regex = aicc_regex;
|
const regex = aicc_regex;
|
||||||
@@ -36,6 +37,41 @@ export class CMI extends Scorm12CMI.CMI {
|
|||||||
this.student_data?.initialize();
|
this.student_data?.initialize();
|
||||||
this.evaluation?.initialize();
|
this.evaluation?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* toJSON for cmi
|
||||||
|
*
|
||||||
|
* @return {
|
||||||
|
* {
|
||||||
|
* suspend_data: string,
|
||||||
|
* launch_data: string,
|
||||||
|
* comments: string,
|
||||||
|
* comments_from_lms: string,
|
||||||
|
* core: CMICore,
|
||||||
|
* objectives: CMIObjectives,
|
||||||
|
* student_data: CMIStudentData,
|
||||||
|
* student_preference: CMIStudentPreference,
|
||||||
|
* interactions: CMIInteractions
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
toJSON() {
|
||||||
|
this.jsonString = true;
|
||||||
|
const result = {
|
||||||
|
'suspend_data': this.suspend_data,
|
||||||
|
'launch_data': this.launch_data,
|
||||||
|
'comments': this.comments,
|
||||||
|
'comments_from_lms': this.comments_from_lms,
|
||||||
|
'core': this.core,
|
||||||
|
'objectives': this.objectives,
|
||||||
|
'student_data': this.student_data,
|
||||||
|
'student_preference': this.student_preference,
|
||||||
|
'interactions': this.interactions,
|
||||||
|
'evaluation': this.evaluation,
|
||||||
|
};
|
||||||
|
delete this.jsonString;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -58,6 +94,19 @@ class CMIEvaluation extends BaseCMI {
|
|||||||
super.initialize();
|
super.initialize();
|
||||||
this.comments?.initialize();
|
this.comments?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* toJSON for cmi.evaluation object
|
||||||
|
* @return {{comments: CMIEvaluationComments}}
|
||||||
|
*/
|
||||||
|
toJSON() {
|
||||||
|
this.jsonString = true;
|
||||||
|
const result = {
|
||||||
|
'comments': this.comments,
|
||||||
|
};
|
||||||
|
delete this.jsonString;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -114,6 +163,29 @@ class AICCCMIStudentData extends Scorm12CMI.CMIStudentData {
|
|||||||
this.#tries_during_lesson = tries_during_lesson :
|
this.#tries_during_lesson = tries_during_lesson :
|
||||||
throwReadOnlyError();
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* toJSON for cmi.student_data object
|
||||||
|
* @return {
|
||||||
|
* {
|
||||||
|
* mastery_score: string,
|
||||||
|
* max_time_allowed: string,
|
||||||
|
* time_limit_action: string,
|
||||||
|
* tries: CMITries
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
toJSON() {
|
||||||
|
this.jsonString = true;
|
||||||
|
const result = {
|
||||||
|
'mastery_score': this.mastery_score,
|
||||||
|
'max_time_allowed': this.max_time_allowed,
|
||||||
|
'time_limit_action': this.time_limit_action,
|
||||||
|
'tries': this.tries,
|
||||||
|
};
|
||||||
|
delete this.jsonString;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -138,7 +210,14 @@ export class CMITriesObject extends BaseCMI {
|
|||||||
constructor() {
|
constructor() {
|
||||||
super();
|
super();
|
||||||
|
|
||||||
this.score = new CMIScore();
|
this.score = new CMIScore(
|
||||||
|
{
|
||||||
|
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,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -187,6 +266,27 @@ export class CMITriesObject extends BaseCMI {
|
|||||||
this.#time = time;
|
this.#time = time;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* toJSON for cmi.student_data.tries.n object
|
||||||
|
* @return {
|
||||||
|
* {
|
||||||
|
* status: string,
|
||||||
|
* time: string,
|
||||||
|
* score: CMIScore
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
toJSON() {
|
||||||
|
this.jsonString = true;
|
||||||
|
const result = {
|
||||||
|
'status': this.status,
|
||||||
|
'time': this.time,
|
||||||
|
'score': this.score,
|
||||||
|
};
|
||||||
|
delete this.jsonString;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -257,6 +357,27 @@ export class CMIEvaluationCommentsObject extends BaseCMI {
|
|||||||
this.#time = time;
|
this.#time = time;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* toJSON for cmi.evaulation.comments.n object
|
||||||
|
* @return {
|
||||||
|
* {
|
||||||
|
* content: string,
|
||||||
|
* location: string,
|
||||||
|
* time: string
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
toJSON() {
|
||||||
|
this.jsonString = true;
|
||||||
|
const result = {
|
||||||
|
'content': this.content,
|
||||||
|
'location': this.location,
|
||||||
|
'time': this.time,
|
||||||
|
};
|
||||||
|
delete this.jsonString;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -289,4 +410,21 @@ export class NAV extends BaseCMI {
|
|||||||
this.#event = event;
|
this.#event = event;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* toJSON for nav object
|
||||||
|
* @returns {
|
||||||
|
* {
|
||||||
|
* event: string
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
toJSON() {
|
||||||
|
this.jsonString = true;
|
||||||
|
const result = {
|
||||||
|
'event': this.event,
|
||||||
|
};
|
||||||
|
delete this.jsonString;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -96,7 +96,7 @@ export class CMIScore extends BaseCMI {
|
|||||||
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 ? false : scorm12_regex.score_range;
|
||||||
this.#max = max ? max : '100';
|
this.#max = max ? max : '100';
|
||||||
this.#_invalid_error_code = invalidErrorCode ?
|
this.#_invalid_error_code = invalidErrorCode ?
|
||||||
invalidErrorCode :
|
invalidErrorCode :
|
||||||
|
|||||||
@@ -236,7 +236,9 @@ export class CMI extends BaseCMI {
|
|||||||
* @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.initialized ? this.#comments_from_lms = comments_from_lms : throwReadOnlyError();
|
!this.initialized ?
|
||||||
|
this.#comments_from_lms = comments_from_lms :
|
||||||
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -250,7 +252,7 @@ class CMICore extends BaseCMI {
|
|||||||
constructor() {
|
constructor() {
|
||||||
super();
|
super();
|
||||||
|
|
||||||
this.score = new Scorm12CMIScore(
|
this.score = new CMIScore(
|
||||||
{
|
{
|
||||||
score_children: constants.score_children,
|
score_children: constants.score_children,
|
||||||
score_range: regex.score_range,
|
score_range: regex.score_range,
|
||||||
@@ -327,7 +329,9 @@ class CMICore extends BaseCMI {
|
|||||||
* @param {string} student_name
|
* @param {string} student_name
|
||||||
*/
|
*/
|
||||||
set student_name(student_name) {
|
set student_name(student_name) {
|
||||||
!this.initialized ? this.#student_name = student_name : throwReadOnlyError();
|
!this.initialized ?
|
||||||
|
this.#student_name = student_name :
|
||||||
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -474,7 +478,7 @@ class CMICore extends BaseCMI {
|
|||||||
* student_name: string,
|
* student_name: string,
|
||||||
* entry: string,
|
* entry: string,
|
||||||
* exit: string,
|
* exit: string,
|
||||||
* score: Scorm12CMIScore,
|
* score: CMIScore,
|
||||||
* student_id: string,
|
* student_id: string,
|
||||||
* lesson_mode: string,
|
* lesson_mode: string,
|
||||||
* lesson_location: string,
|
* lesson_location: string,
|
||||||
@@ -572,7 +576,9 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
* @param {string} mastery_score
|
* @param {string} mastery_score
|
||||||
*/
|
*/
|
||||||
set mastery_score(mastery_score) {
|
set mastery_score(mastery_score) {
|
||||||
!this.initialized ? this.#mastery_score = mastery_score : throwReadOnlyError();
|
!this.initialized ?
|
||||||
|
this.#mastery_score = mastery_score :
|
||||||
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -588,7 +594,9 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
* @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.initialized ? this.#max_time_allowed = max_time_allowed : throwReadOnlyError();
|
!this.initialized ?
|
||||||
|
this.#max_time_allowed = max_time_allowed :
|
||||||
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -604,7 +612,9 @@ export class CMIStudentData extends BaseCMI {
|
|||||||
* @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.initialized ? this.#time_limit_action = time_limit_action : throwReadOnlyError();
|
!this.initialized ?
|
||||||
|
this.#time_limit_action = time_limit_action :
|
||||||
|
throwReadOnlyError();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -809,13 +819,13 @@ export class CMIInteractionsObject extends BaseCMI {
|
|||||||
this.correct_responses?.initialize();
|
this.correct_responses?.initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
#id: '';
|
#id = '';
|
||||||
#time: '';
|
#time = '';
|
||||||
#type: '';
|
#type = '';
|
||||||
#weighting: '';
|
#weighting = '';
|
||||||
#student_response: '';
|
#student_response = '';
|
||||||
#result: '';
|
#result = '';
|
||||||
#latency: '';
|
#latency = '';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Getter for #id. Should only be called during JSON export.
|
* Getter for #id. Should only be called during JSON export.
|
||||||
@@ -991,11 +1001,18 @@ export class CMIObjectivesObject extends BaseCMI {
|
|||||||
constructor() {
|
constructor() {
|
||||||
super();
|
super();
|
||||||
|
|
||||||
this.score = new Scorm12CMIScore();
|
this.score = new CMIScore(
|
||||||
|
{
|
||||||
|
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,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
#id: '';
|
#id = '';
|
||||||
#status: '';
|
#status = '';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Getter for #id
|
* Getter for #id
|
||||||
@@ -1039,7 +1056,7 @@ export class CMIObjectivesObject extends BaseCMI {
|
|||||||
* {
|
* {
|
||||||
* id: string,
|
* id: string,
|
||||||
* status: string,
|
* status: string,
|
||||||
* score: Scorm12CMIScore
|
* score: CMIScore
|
||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
*/
|
*/
|
||||||
@@ -1066,7 +1083,7 @@ export class CMIInteractionsObjectivesObject extends BaseCMI {
|
|||||||
super();
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#id: '';
|
#id = '';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Getter for #id
|
* Getter for #id
|
||||||
@@ -1115,14 +1132,14 @@ export class CMIInteractionsCorrectResponsesObject extends BaseCMI {
|
|||||||
super();
|
super();
|
||||||
}
|
}
|
||||||
|
|
||||||
#pattern: '';
|
#pattern = '';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Getter for #pattern
|
* Getter for #pattern
|
||||||
* @return {""}
|
* @return {string}
|
||||||
*/
|
*/
|
||||||
get pattern() {
|
get pattern() {
|
||||||
return this.#pattern;
|
return (!this.jsonString) ? throwWriteOnlyError() : this.#pattern;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1152,10 +1169,3 @@ export class CMIInteractionsCorrectResponsesObject extends BaseCMI {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Basic extension of CMIScore
|
|
||||||
*/
|
|
||||||
class Scorm12CMIScore extends CMIScore {
|
|
||||||
toJSON = super.toJSON;
|
|
||||||
}
|
|
||||||
|
|||||||
30
src/regex.js
30
src/regex.js
@@ -3,7 +3,7 @@
|
|||||||
export const scorm12_regex = {
|
export const scorm12_regex = {
|
||||||
CMIString256: '^.{0,255}$',
|
CMIString256: '^.{0,255}$',
|
||||||
CMIString4096: '^.{0,4096}$',
|
CMIString4096: '^.{0,4096}$',
|
||||||
CMITime: '^([0-2]{1}[0-9]{1}):([0-5]{1}[0-9]{1}):([0-5]{1}[0-9]{1})(\.[0-9]{1,6})?$', // eslint-disable-line
|
CMITime: '^(?:[01]\\d|2[0123]):(?:[012345]\\d):(?:[012345]\\d)$', // eslint-disable-line
|
||||||
CMITimespan: '^([0-9]{2,}):([0-9]{2}):([0-9]{2})(\.[0-9]{1,2})?$', // eslint-disable-line
|
CMITimespan: '^([0-9]{2,}):([0-9]{2}):([0-9]{2})(\.[0-9]{1,2})?$', // eslint-disable-line
|
||||||
CMIInteger: '^\\d+$',
|
CMIInteger: '^\\d+$',
|
||||||
CMISInteger: '^-?([0-9]+)$',
|
CMISInteger: '^-?([0-9]+)$',
|
||||||
@@ -13,12 +13,12 @@ export const scorm12_regex = {
|
|||||||
CMIIndex: '[._](\\d+).',
|
CMIIndex: '[._](\\d+).',
|
||||||
|
|
||||||
// Vocabulary Data Type Definition
|
// Vocabulary Data Type Definition
|
||||||
CMIStatus: '^passed$|^completed$|^failed$|^incomplete$|^browsed$',
|
CMIStatus: '^(passed|completed|failed|incomplete|browsed)$',
|
||||||
CMIStatus2: '^passed$|^completed$|^failed$|^incomplete$|^browsed$|^not attempted$',
|
CMIStatus2: '^(passed|completed|failed|incomplete|browsed|not attempted)$',
|
||||||
CMIExit: '^time-out$|^suspend$|^logout$|^$',
|
CMIExit: '^(time-out|suspend|logout|)$',
|
||||||
CMIType: '^true-false$|^choice$|^fill-in$|^matching$|^performance$|^sequencing$|^likert$|^numeric$',
|
CMIType: '^(true-false|choice|fill-in|matching|performance|sequencing|likert|numeric)$',
|
||||||
CMIResult: '^correct$|^wrong$|^unanticipated$|^neutral$|^([0-9]{0,3})?(\.[0-9]*)?$', // eslint-disable-line
|
CMIResult: '^(correct|wrong|unanticipated|neutral|([0-9]{0,3})?(\\.[0-9]*)?)$', // eslint-disable-line
|
||||||
NAVEvent: '^previous$|^continue$',
|
NAVEvent: '^(previous|continue)$',
|
||||||
|
|
||||||
// Data ranges
|
// Data ranges
|
||||||
score_range: '0#100',
|
score_range: '0#100',
|
||||||
@@ -58,14 +58,14 @@ export const scorm2004_regex = {
|
|||||||
CMIIndexStore: '.N(\\d+).',
|
CMIIndexStore: '.N(\\d+).',
|
||||||
|
|
||||||
// Vocabulary Data Type Definition
|
// Vocabulary Data Type Definition
|
||||||
CMICStatus: '^completed$|^incomplete$|^not attempted$|^unknown$',
|
CMICStatus: '^(completed|incomplete|not attempted|unknown)$',
|
||||||
CMISStatus: '^passed$|^failed$|^unknown$',
|
CMISStatus: '^(passed|failed|unknown)$',
|
||||||
CMIExit: '^time-out$|^suspend$|^logout$|^normal$|^$',
|
CMIExit: '^(time-out|suspend|logout|normal|)$',
|
||||||
CMIType: '^true-false$|^choice$|^(long-)?fill-in$|^matching$|^performance$|^sequencing$|^likert$|^numeric$|^other$',
|
CMIType: '^(true-false|choice|(long-)?fill-in|matching|performance|sequencing|likert|numeric|other)$',
|
||||||
CMIResult: '^correct$|^incorrect$|^unanticipated$|^neutral$|^-?([0-9]{1,4})(\\.[0-9]{1,18})?$',
|
CMIResult: '^(correct|incorrect|unanticipated|neutral|-?([0-9]{1,4})(\\.[0-9]{1,18})?)$',
|
||||||
NAVEvent: '^previous$|^continue$|^exit$|^exitAll$|^abandon$|^abandonAll$|^suspendAll$|^\{target=\\S{0,200}[a-zA-Z0-9]\}choice|jump$', // eslint-disable-line
|
NAVEvent: '^(previous|continue|exit|exitAll|abandon|abandonAll|suspendAll|\{target=\\S{0,200}[a-zA-Z0-9]\}choice|jump)$', // eslint-disable-line
|
||||||
NAVBoolean: '^unknown$|^true$|^false$',
|
NAVBoolean: '^(unknown|true|false$)',
|
||||||
NAVTarget: '^previous$|^continue$|^choice.{target=\\S{0,200}[a-zA-Z0-9]}$',
|
NAVTarget: '^(previous|continue|choice.{target=\\S{0,200}[a-zA-Z0-9]})$',
|
||||||
|
|
||||||
// Data ranges
|
// Data ranges
|
||||||
scaled_range: '-1#1',
|
scaled_range: '-1#1',
|
||||||
|
|||||||
@@ -1,8 +1,18 @@
|
|||||||
import {describe} from 'mocha';
|
import {describe, it} from 'mocha';
|
||||||
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';
|
import {
|
||||||
|
CMI,
|
||||||
|
CMIEvaluationCommentsObject,
|
||||||
|
CMITriesObject, NAV,
|
||||||
|
} from '../../src/cmi/aicc_cmi';
|
||||||
import * as h from '../helpers';
|
import * as h from '../helpers';
|
||||||
|
import {
|
||||||
|
CMIInteractionsCorrectResponsesObject,
|
||||||
|
CMIInteractionsObject,
|
||||||
|
CMIObjectivesObject,
|
||||||
|
} from '../../src/cmi/scorm12_cmi';
|
||||||
|
import {expect} from 'chai';
|
||||||
|
|
||||||
const invalid_set = scorm12_error_codes.INVALID_SET_VALUE;
|
const invalid_set = scorm12_error_codes.INVALID_SET_VALUE;
|
||||||
const type_mismatch = scorm12_error_codes.TYPE_MISMATCH;
|
const type_mismatch = scorm12_error_codes.TYPE_MISMATCH;
|
||||||
@@ -707,6 +717,229 @@ describe('AICC CMI Tests', () => {
|
|||||||
fieldName: 'cmi.interactions._count', expectedValue: 0,
|
fieldName: 'cmi.interactions._count', expectedValue: 0,
|
||||||
expectedError: invalid_set,
|
expectedError: invalid_set,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmiObj = cmi();
|
||||||
|
cmiObj.objectives.childArray.push(new CMIObjectivesObject());
|
||||||
|
cmiObj.interactions.childArray.push(new CMIInteractionsObject());
|
||||||
|
cmiObj.evaluation.comments.childArray.push(
|
||||||
|
new CMIEvaluationCommentsObject());
|
||||||
|
cmiObj.student_data.tries.childArray.push(new CMITriesObject());
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmiObj),
|
||||||
|
).
|
||||||
|
to.
|
||||||
|
equal(
|
||||||
|
'{"suspend_data":"","launch_data":"","comments":"","comments_from_lms":"","core":{"student_id":"","student_name":"","lesson_location":"","credit":"","lesson_status":"","entry":"","total_time":"","lesson_mode":"normal","exit":"","session_time":"00:00:00","score":{"raw":"","min":"","max":"100"}},"objectives":{"0":{"id":"","status":"","score":{"raw":"","min":"","max":"100"}}},"student_data":{"mastery_score":"","max_time_allowed":"","time_limit_action":"","tries":{"0":{"status":"","time":"","score":{"raw":"","min":"","max":"100"}}}},"student_preference":{"audio":"","language":"","speed":"","text":""},"interactions":{"0":{"id":"","time":"","type":"","weighting":"","student_response":"","result":"","latency":"","objectives":{},"correct_responses":{}}},"evaluation":{"comments":{"0":{"content":"","location":"","time":""}}}}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CMITriesObject Tests', () => {
|
||||||
|
const triesObject = () => {
|
||||||
|
return new CMITriesObject();
|
||||||
|
};
|
||||||
|
const triesInitialized = () => {
|
||||||
|
const cmi = new CMITriesObject();
|
||||||
|
cmi.initialize();
|
||||||
|
return cmi;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.interactions.n.objectives.n object
|
||||||
|
*/
|
||||||
|
h.checkRead({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.status',
|
||||||
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: triesInitialized(),
|
||||||
|
fieldName: 'cmi.status',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.status',
|
||||||
|
validValues: [
|
||||||
|
'passed',
|
||||||
|
'completed',
|
||||||
|
'failed',
|
||||||
|
'incomplete',
|
||||||
|
'browsed',
|
||||||
|
'not attempted',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'P',
|
||||||
|
'f',
|
||||||
|
'complete',
|
||||||
|
'started',
|
||||||
|
'in progress',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkReadAndWrite({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.time',
|
||||||
|
expectedError: write_only,
|
||||||
|
valueToTest: '23:59:59',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.time',
|
||||||
|
validValues: [
|
||||||
|
'15:00:30',
|
||||||
|
'00:50:30',
|
||||||
|
'23:00:30',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-00:00:30',
|
||||||
|
'0:50:30',
|
||||||
|
'23:00:30.',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.student_data.tries.n.score Properties
|
||||||
|
*/
|
||||||
|
h.checkInvalidSet({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.score._children',
|
||||||
|
expectedValue: aicc_constants.score_children,
|
||||||
|
expectedError: invalid_set,
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.score.raw',
|
||||||
|
validValues: [
|
||||||
|
'0',
|
||||||
|
'25.1',
|
||||||
|
'50.5',
|
||||||
|
'75',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'101',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.score.min',
|
||||||
|
validValues: [
|
||||||
|
'0',
|
||||||
|
'25.1',
|
||||||
|
'50.5',
|
||||||
|
'75',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'101',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: triesObject(),
|
||||||
|
fieldName: 'cmi.score.max',
|
||||||
|
validValues: [
|
||||||
|
'0',
|
||||||
|
'25.1',
|
||||||
|
'50.5',
|
||||||
|
'75',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'101',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = triesObject();
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).
|
||||||
|
to.
|
||||||
|
equal(
|
||||||
|
'{"status":"","time":"","score":{"raw":"","min":"","max":"100"}}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CMIEvaluationCommentsObject Tests', () => {
|
||||||
|
const evaluationComment = () => {
|
||||||
|
return new CMIEvaluationCommentsObject();
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.evaluation.comments.n object
|
||||||
|
*/
|
||||||
|
h.checkFieldConstraintSize({
|
||||||
|
cmi: evaluationComment(),
|
||||||
|
fieldName: 'cmi.content',
|
||||||
|
expectedError: type_mismatch,
|
||||||
|
limit: 255,
|
||||||
|
});
|
||||||
|
h.checkFieldConstraintSize({
|
||||||
|
cmi: evaluationComment(),
|
||||||
|
fieldName: 'cmi.location',
|
||||||
|
expectedError: type_mismatch,
|
||||||
|
limit: 255,
|
||||||
|
});
|
||||||
|
h.checkReadAndWrite({
|
||||||
|
cmi: evaluationComment(),
|
||||||
|
fieldName: 'cmi.time',
|
||||||
|
expectedError: write_only,
|
||||||
|
valueToTest: '23:59:59',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: evaluationComment(),
|
||||||
|
fieldName: 'cmi.time',
|
||||||
|
validValues: [
|
||||||
|
'15:00:30',
|
||||||
|
'00:50:30',
|
||||||
|
'23:00:30',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-00:00:30',
|
||||||
|
'0:50:30',
|
||||||
|
'23:00:30.',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = evaluationComment();
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).to.equal('{"content":"","location":"","time":""}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('NAV Tests', () => {
|
||||||
|
const nav = () => {
|
||||||
|
return new NAV();
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.interactions.n.correct_responses.n object
|
||||||
|
*/
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: nav(),
|
||||||
|
fieldName: 'cmi.event',
|
||||||
|
validValues: [
|
||||||
|
'previous',
|
||||||
|
'continue',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'P',
|
||||||
|
'f',
|
||||||
|
'complete',
|
||||||
|
'started',
|
||||||
|
'in progress',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = nav();
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).to.equal('{"event":""}');
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,7 +1,14 @@
|
|||||||
import {describe, beforeEach, afterEach} from 'mocha';
|
import {expect} from 'chai';
|
||||||
|
import {describe, it} from 'mocha';
|
||||||
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';
|
import {
|
||||||
|
CMI,
|
||||||
|
CMIInteractionsCorrectResponsesObject,
|
||||||
|
CMIInteractionsObject,
|
||||||
|
CMIInteractionsObjectivesObject,
|
||||||
|
CMIObjectivesObject,
|
||||||
|
} from '../../src/cmi/scorm12_cmi';
|
||||||
import * as h from '../helpers';
|
import * as h from '../helpers';
|
||||||
|
|
||||||
const invalid_set = scorm12_error_codes.INVALID_SET_VALUE;
|
const invalid_set = scorm12_error_codes.INVALID_SET_VALUE;
|
||||||
@@ -164,6 +171,10 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
expectedValue: scorm12_constants.score_children,
|
expectedValue: scorm12_constants.score_children,
|
||||||
expectedError: invalid_set,
|
expectedError: invalid_set,
|
||||||
});
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: cmi(),
|
||||||
|
fieldName: 'cmi.core.score.raw',
|
||||||
|
});
|
||||||
h.checkValidValues({
|
h.checkValidValues({
|
||||||
cmi: cmi(),
|
cmi: cmi(),
|
||||||
fieldName: 'cmi.core.score.raw',
|
fieldName: 'cmi.core.score.raw',
|
||||||
@@ -179,6 +190,10 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
'101',
|
'101',
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: cmi(),
|
||||||
|
fieldName: 'cmi.core.score.min',
|
||||||
|
});
|
||||||
h.checkValidValues({
|
h.checkValidValues({
|
||||||
cmi: cmi(),
|
cmi: cmi(),
|
||||||
fieldName: 'cmi.core.score.min',
|
fieldName: 'cmi.core.score.min',
|
||||||
@@ -194,6 +209,11 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
'101',
|
'101',
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: cmi(),
|
||||||
|
fieldName: 'cmi.core.score.max',
|
||||||
|
expectedValue: '100',
|
||||||
|
});
|
||||||
h.checkValidValues({
|
h.checkValidValues({
|
||||||
cmi: cmi(),
|
cmi: cmi(),
|
||||||
fieldName: 'cmi.core.score.max',
|
fieldName: 'cmi.core.score.max',
|
||||||
@@ -257,6 +277,10 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
expectedValue: scorm12_constants.student_preference_children,
|
expectedValue: scorm12_constants.student_preference_children,
|
||||||
expectedError: invalid_set,
|
expectedError: invalid_set,
|
||||||
});
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: cmi(),
|
||||||
|
fieldName: 'cmi.student_preference.audio',
|
||||||
|
});
|
||||||
h.checkValidValues({
|
h.checkValidValues({
|
||||||
cmi: cmi(),
|
cmi: cmi(),
|
||||||
fieldName: 'cmi.student_preference.audio',
|
fieldName: 'cmi.student_preference.audio',
|
||||||
@@ -269,13 +293,6 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
invalidValues: [
|
invalidValues: [
|
||||||
'invalid',
|
'invalid',
|
||||||
'a100',
|
'a100',
|
||||||
],
|
|
||||||
});
|
|
||||||
h.checkValidValues({
|
|
||||||
cmi: cmi(),
|
|
||||||
fieldName: 'cmi.student_preference.audio',
|
|
||||||
validValues: [],
|
|
||||||
invalidValues: [
|
|
||||||
'101',
|
'101',
|
||||||
'5000000',
|
'5000000',
|
||||||
'-500',
|
'-500',
|
||||||
@@ -287,6 +304,10 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
limit: 255,
|
limit: 255,
|
||||||
expectedError: type_mismatch,
|
expectedError: type_mismatch,
|
||||||
});
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: cmi(),
|
||||||
|
fieldName: 'cmi.student_preference.speed',
|
||||||
|
});
|
||||||
h.checkValidValues({
|
h.checkValidValues({
|
||||||
cmi: cmi(),
|
cmi: cmi(),
|
||||||
fieldName: 'cmi.student_preference.speed',
|
fieldName: 'cmi.student_preference.speed',
|
||||||
@@ -299,19 +320,16 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
invalidValues: [
|
invalidValues: [
|
||||||
'invalid',
|
'invalid',
|
||||||
'a100',
|
'a100',
|
||||||
],
|
|
||||||
});
|
|
||||||
h.checkValidValues({
|
|
||||||
cmi: cmi(),
|
|
||||||
fieldName: 'cmi.student_preference.speed',
|
|
||||||
validValues: [],
|
|
||||||
invalidValues: [
|
|
||||||
'101',
|
'101',
|
||||||
'-101',
|
'-101',
|
||||||
'5000000',
|
'5000000',
|
||||||
'-500',
|
'-500',
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: cmi(),
|
||||||
|
fieldName: 'cmi.student_preference.text',
|
||||||
|
});
|
||||||
h.checkValidValues({
|
h.checkValidValues({
|
||||||
cmi: cmi(),
|
cmi: cmi(),
|
||||||
fieldName: 'cmi.student_preference.text',
|
fieldName: 'cmi.student_preference.text',
|
||||||
@@ -702,6 +720,332 @@ describe('SCORM 1.2 CMI Tests', () => {
|
|||||||
expectedValue: 0,
|
expectedValue: 0,
|
||||||
expectedError: invalid_set,
|
expectedError: invalid_set,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmiObj = cmi();
|
||||||
|
cmiObj.objectives.childArray.push(new CMIObjectivesObject());
|
||||||
|
cmiObj.interactions.childArray.push(new CMIInteractionsObject());
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmiObj),
|
||||||
|
).to.equal('{"suspend_data":"","launch_data":"","comments":"","comments_from_lms":"","core":{"student_id":"","student_name":"","lesson_location":"","credit":"","lesson_status":"","entry":"","total_time":"","lesson_mode":"normal","exit":"","session_time":"00:00:00","score":{"raw":"","min":"","max":"100"}},"objectives":{"0":{"id":"","status":"","score":{"raw":"","min":"","max":"100"}}},"student_data":{"mastery_score":"","max_time_allowed":"","time_limit_action":""},"student_preference":{"audio":"","language":"","speed":"","text":""},"interactions":{"0":{"id":"","time":"","type":"","weighting":"","student_response":"","result":"","latency":"","objectives":{},"correct_responses":{}}}}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CMIInteractionsObject Tests', () => {
|
||||||
|
const interaction = () => {
|
||||||
|
return new CMIInteractionsObject();
|
||||||
|
};
|
||||||
|
const interactionInitialized = () => {
|
||||||
|
const cmi = new CMIInteractionsObject();
|
||||||
|
cmi.initialize();
|
||||||
|
return cmi;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.interactions.n object
|
||||||
|
*/
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.id',
|
||||||
|
expectedError: write_only,
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interactionInitialized(),
|
||||||
|
fieldName: 'cmi.id',
|
||||||
|
expectedError: write_only,
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.time',
|
||||||
|
expectedError: write_only,
|
||||||
|
valueToTest: '23:59:59',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.time',
|
||||||
|
validValues: [
|
||||||
|
'15:00:30',
|
||||||
|
'00:50:30',
|
||||||
|
'23:00:30',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-00:00:30',
|
||||||
|
'0:50:30',
|
||||||
|
'23:00:30.',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.type',
|
||||||
|
expectedError: write_only,
|
||||||
|
valueToTest: 'true-false',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.type',
|
||||||
|
validValues: [
|
||||||
|
'true-false',
|
||||||
|
'choice',
|
||||||
|
'fill-in',
|
||||||
|
'matching',
|
||||||
|
'performance',
|
||||||
|
'sequencing',
|
||||||
|
'likert',
|
||||||
|
'numeric',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'correct',
|
||||||
|
'wrong',
|
||||||
|
'logout',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkReadOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.objectives._count',
|
||||||
|
expectedValue: 0,
|
||||||
|
expectedError: invalid_set,
|
||||||
|
});
|
||||||
|
h.checkReadOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.correct_responses._count',
|
||||||
|
expectedValue: 0,
|
||||||
|
expectedError: invalid_set,
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.weighting',
|
||||||
|
expectedError: write_only,
|
||||||
|
valueToTest: '0',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.weighting',
|
||||||
|
validValues: [
|
||||||
|
'-100',
|
||||||
|
'-1',
|
||||||
|
'1',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-101',
|
||||||
|
'101',
|
||||||
|
'invalid',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.student_response',
|
||||||
|
expectedError: write_only,
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.result',
|
||||||
|
expectedError: write_only,
|
||||||
|
valueToTest: 'correct',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.result',
|
||||||
|
validValues: [
|
||||||
|
'correct',
|
||||||
|
'wrong',
|
||||||
|
'unanticipated',
|
||||||
|
'neutral',
|
||||||
|
'1',
|
||||||
|
'999',
|
||||||
|
'999.99999',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'10000',
|
||||||
|
'invalid',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.latency',
|
||||||
|
valueToTest: '00:00:00',
|
||||||
|
expectedError: write_only,
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: interaction(),
|
||||||
|
fieldName: 'cmi.latency',
|
||||||
|
validValues: [
|
||||||
|
'10:06:57',
|
||||||
|
'00:00:01.56',
|
||||||
|
'23:59:59',
|
||||||
|
'47:59:59',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'06:5:13',
|
||||||
|
'23:59:59.123',
|
||||||
|
'P1DT23H59M59S',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = interaction();
|
||||||
|
cmi.objectives.childArray.push(new CMIInteractionsObjectivesObject());
|
||||||
|
cmi.correct_responses.childArray.push(new CMIInteractionsCorrectResponsesObject());
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).to.equal('{"id":"","time":"","type":"","weighting":"","student_response":"","result":"","latency":"","objectives":{"0":{"id":""}},"correct_responses":{"0":{"pattern":""}}}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CMIInteractionsObjectivesObject Tests', () => {
|
||||||
|
const interactionObjective = () => {
|
||||||
|
return new CMIInteractionsObjectivesObject();
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.interactions.n.objectives.n object
|
||||||
|
*/
|
||||||
|
h.checkReadAndWrite({
|
||||||
|
cmi: interactionObjective(),
|
||||||
|
fieldName: 'cmi.id',
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = interactionObjective();
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).to.equal('{"id":""}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CMIInteractionsCorrectResponsesObject Tests', () => {
|
||||||
|
const correctResponse = () => {
|
||||||
|
return new CMIInteractionsCorrectResponsesObject();
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.interactions.n.correct_responses.n object
|
||||||
|
*/
|
||||||
|
h.checkWriteOnly({
|
||||||
|
cmi: correctResponse(),
|
||||||
|
fieldName: 'cmi.pattern',
|
||||||
|
expectedError: write_only,
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = correctResponse();
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).to.equal('{"pattern":""}');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('CMIObjectivesObject Tests', () => {
|
||||||
|
const objective = () => {
|
||||||
|
return new CMIObjectivesObject();
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.objectives.n object
|
||||||
|
*/
|
||||||
|
h.checkReadAndWrite({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.id',
|
||||||
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.status',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.status',
|
||||||
|
validValues: [
|
||||||
|
'passed',
|
||||||
|
'completed',
|
||||||
|
'failed',
|
||||||
|
'incomplete',
|
||||||
|
'browsed',
|
||||||
|
'not attempted',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'P',
|
||||||
|
'f',
|
||||||
|
'complete',
|
||||||
|
'started',
|
||||||
|
'in progress',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* cmi.objectives.n.score Properties
|
||||||
|
*/
|
||||||
|
h.checkInvalidSet({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score._children',
|
||||||
|
expectedValue: scorm12_constants.score_children,
|
||||||
|
expectedError: invalid_set,
|
||||||
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score.raw',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score.raw',
|
||||||
|
validValues: [
|
||||||
|
'0',
|
||||||
|
'25.1',
|
||||||
|
'50.5',
|
||||||
|
'75',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'101',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score.min',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score.min',
|
||||||
|
validValues: [
|
||||||
|
'0',
|
||||||
|
'25.1',
|
||||||
|
'50.5',
|
||||||
|
'75',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'101',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
h.checkRead({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score.max',
|
||||||
|
expectedValue: '100',
|
||||||
|
});
|
||||||
|
h.checkValidValues({
|
||||||
|
cmi: objective(),
|
||||||
|
fieldName: 'cmi.score.max',
|
||||||
|
validValues: [
|
||||||
|
'0',
|
||||||
|
'25.1',
|
||||||
|
'50.5',
|
||||||
|
'75',
|
||||||
|
'100',
|
||||||
|
],
|
||||||
|
invalidValues: [
|
||||||
|
'-1',
|
||||||
|
'101',
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should export JSON', () => {
|
||||||
|
const cmi = objective();
|
||||||
|
expect(
|
||||||
|
JSON.stringify(cmi),
|
||||||
|
).to.equal('{"id":"","status":"","score":{"raw":"","min":"","max":"100"}}');
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user