Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: ignore dates set in studio edit modal when non-manual date config is set #2229

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 16 additions & 3 deletions karma.conf.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,8 @@ module.exports = function(config) {
'karma-sinon',
'karma-jasmine-html-reporter',
'karma-spec-reporter',
'karma-webpack'
'karma-webpack',
require("karma-firefox-launcher")
],

// frameworks to use
Expand Down Expand Up @@ -107,7 +108,13 @@ module.exports = function(config) {

// start these browsers
// available browser launchers: https://npmjs.org/browse/keyword/karma-launcher
browsers: ['HeadlessChrome'],

browsers: [
'HeadlessChrome'
// 'HeadlessFirefox'
],
// If chrome headless is not working, try swapping out which line is commented above
// to use firefox for local dev
customLaunchers: {
HeadlessChrome: {
base: 'ChromeHeadless',
Expand All @@ -118,7 +125,13 @@ module.exports = function(config) {
'--disable-translate',
'--disable-extensions'
]
}
},
HeadlessFirefox: {
base: 'Firefox',
flags: [
'--headless',
]
},
},

// Continuous Integration mode
Expand Down
4 changes: 2 additions & 2 deletions openassessment/xblock/static/dist/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@
"openassessment-rtl.js": "/openassessment-rtl.9de7c9bc7c1048c07707.js",
"openassessment-rtl.css.map": "/openassessment-rtl.9de7c9bc7c1048c07707.css.map",
"openassessment-rtl.js.map": "/openassessment-rtl.9de7c9bc7c1048c07707.js.map",
"openassessment-studio.js": "/openassessment-studio.227e19b5d099e14574a2.js",
"openassessment-studio.js.map": "/openassessment-studio.227e19b5d099e14574a2.js.map",
"openassessment-studio.js": "/openassessment-studio.416a8cebe8d26d1457c0.js",
"openassessment-studio.js.map": "/openassessment-studio.416a8cebe8d26d1457c0.js.map",
"fallback-default.png": "/1b90ce76fe01a1aa6e5ec289a5fb3799.png",
"default-avatar.svg": "/95ec738c0b7faac5b5c9126794446bbd.svg"
}

Large diffs are not rendered by default.

99 changes: 98 additions & 1 deletion openassessment/xblock/static/js/fixtures/templates.json
Original file line number Diff line number Diff line change
Expand Up @@ -510,10 +510,107 @@
"peer_assessment",
"self_assessment",
"staff_assessment"
]
],
"subsection_end_date": "2024-09-09",
"course_end_date": "2040-10-11"
},
"output": "oa_edit.html"
},
{
"template": "legacy/edit/oa_edit.html",
"context": {
"prompts": [{ "description": "How much do you like waffles?" }, { "description": "How much do you like waffles 2?" }],
"title": "The most important of all questions.",
"submission_start": "2014-01-02T12:15",
"submission_due": "2014-10-01T04:53",
"date_config_type": "manual",
"text_response": "required",
"file_upload_response": "",
"leaderboard_show": 12,
"allow_learner_resubmissions": false,
"resubmissions_grace_period": "",
"necessity_options": {
"required": "Required",
"optional": "Optional",
"": "None"
},
"teams_feature_enabled": true,
"teams_enabled": false,
"criteria": [
{
"name": "criterion_1",
"label": "Criterion with two options",
"prompt": "Prompt for criterion with two options",
"order_num": 0,
"feedback": "disabled",
"options": [
{
"order_num": 0,
"points": 1,
"name": "option_1",
"label": "Fair",
"explanation": "Fair explanation"
},
{
"order_num": 1,
"points": 2,
"name": "option_2",
"label": "Good",
"explanation": "Good explanation"
}
],
"points_possible": 2
},
{
"name": "criterion_2",
"label": "Criterion with no options",
"prompt": "Prompt for criterion with no options",
"order_num": 0,
"options": [],
"feedback": "required",
"points_possible": 0
},
{
"name": "criterion_3",
"label": "Criterion with optional feedback",
"prompt": "Prompt for criterion with optional feedback",
"order_num": 2,
"feedback": "optional",
"options": [
{
"order_num": 0,
"points": 2,
"name": "option_1",
"label": "Good",
"explanation": "Good explanation"
}
],
"points_possible": 2
}
],
"feedbackprompt": "Feedback default prompt",
"feedback_default_text": "Feedback default text",
"assessments": {
"peer_assessment": {
"start": "2014-01-02T00:00",
"due": "2014-01-03T00:00",
"must_grade": 5,
"must_be_graded_by": 3
},
"self_assessment": {
"start": "2014-01-04T00:00",
"due": "2014-01-05T00:00"
}
},
"editor_assessments_order": [
"student_training",
"peer_assessment",
"self_assessment",
"staff_assessment"
]
},
"output": "oa_edit_no_subsection_course_deadlines.html"
},
{
"template": "legacy/edit/oa_edit.html",
"context": {
Expand Down
40 changes: 40 additions & 0 deletions openassessment/xblock/static/js/spec/studio/oa_edit_fields.js
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,46 @@ describe("OpenAssessment.DatetimeControl", function() {
datetimeControl.clearValidationErrors();
expect(datetimeControl.validationErrors()).toEqual([]);
});

describe("stash and pop", function() {
const dates = ["2024-09-09", "2030-03-02", "2031-03-05"]
const times = ["05:28", null, "02:13"]

beforeEach(function() {
datetimeControl.datetime(dates[0], times[0]);
expect(datetimeControl.datetime()).toEqual(`${dates[0]}T${times[0]}`);
})

it('update values correctly', function() {
datetimeControl.stash(dates[1]);
expect(datetimeControl.datetime()).toEqual(`${dates[1]}T00:00`);

datetimeControl.pop()
expect(datetimeControl.datetime()).toEqual(`${dates[0]}T${times[0]}`);
});

it('stashing multiple times does nothing until popping', function() {
datetimeControl.stash(dates[1], times[1]);
expect(datetimeControl.datetime()).toEqual(`${dates[1]}T00:00`);
datetimeControl.stash(dates[2], times[2]);
expect(datetimeControl.datetime()).toEqual(`${dates[1]}T00:00`);

datetimeControl.pop()
expect(datetimeControl.datetime()).toEqual(`${dates[0]}T${times[0]}`);
});

it('popping multiple times does nothing', function() {
datetimeControl.stash(dates[1], times[1]);
expect(datetimeControl.datetime()).toEqual(`${dates[1]}T00:00`);

datetimeControl.pop()
expect(datetimeControl.datetime()).toEqual(`${dates[0]}T${times[0]}`);

datetimeControl.pop()
expect(datetimeControl.datetime()).toEqual(`${dates[0]}T${times[0]}`);
});
})

});

describe("OpenAssessment.ToggleControl", function() {
Expand Down
72 changes: 70 additions & 2 deletions openassessment/xblock/static/js/spec/studio/oa_edit_schedule.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,9 @@ describe('OpenAssessment.EditScheduleView', function() {
}
};

beforeEach(function() {
var setupTest = function (fixture) {
// Load the DOM fixture
loadFixtures('oa_edit.html');
loadFixtures(fixture);

// Create the view
var element = $('#oa_schedule_editor_wrapper', this.element).get(0);
Expand All @@ -54,6 +54,13 @@ describe('OpenAssessment.EditScheduleView', function() {

view.submissionStart('2014-01-01', '00:00');
view.submissionDue('2014-03-04', '00:00');
}
beforeAll(function() {
this.setupTest = setupTest.bind(this)
})

beforeEach(function() {
this.setupTest('oa_edit.html')
});

it('sets and loads the submission start/due dates', function() {
Expand All @@ -65,6 +72,7 @@ describe('OpenAssessment.EditScheduleView', function() {
});

it('has working date config type', function() {
this.setupTest('oa_edit_no_subsection_course_deadlines.html')
const expectedValue = $('input[name="date_config_type"][type="radio"]:checked', this.element).val();
expect(view.dateConfigType()).toEqual(expectedValue);

Expand All @@ -77,6 +85,66 @@ describe('OpenAssessment.EditScheduleView', function() {
expect(courseEndEl.prop('disabled')).toBe(true);
});

it('stashes and restores manual dates on date config change', function() {
const dateConfigRadios = {
manual: $('input#manual_date_config_type', this.element),
subsection: $('input#subsection_date_config_type', this.element),
course_end: $('input#course_end_date_config_type', this.element),
}
function expectSelectedRadio(expectedValue) {
// Helper to cleanly assert the currently selected radio button
expect($('input[name="date_config_type"][type="radio"]:checked').val()).toEqual(expectedValue);
}
function getCurrentValues() {
// Helper to get the current state of the controls as an object
return {
submission: {
start: view.submissionStart(),
due: view.submissionDue(),
},
self: {
start: assessmentViews.oa_self_assessment_editor.startDatetimeControl.datetime(),
due: assessmentViews.oa_self_assessment_editor.dueDatetimeControl.datetime(),
},
peer: {
start: assessmentViews.oa_peer_assessment_editor.startDatetimeControl.datetime(),
due: assessmentViews.oa_peer_assessment_editor.dueDatetimeControl.datetime(),
}
}
}
// If we select a non-manual setting, the current manual values should be stashed, and the
// values of the controls should be set to a default, to avoid any backend validation issues.
const startingValues = getCurrentValues();
expectSelectedRadio('manual')
dateConfigRadios.subsection.trigger('click');
expectSelectedRadio('subsection');

const expectedPostStashValues = {
submission: {
start: "2001-01-01T00:00",
due: "2099-12-31T00:00",
},
self: {
start: "2001-01-01T00:00",
due: "2099-12-31T00:00",
},
peer: {
start: "2001-01-01T00:00",
due: "2099-12-31T00:00",
},
}

expect(getCurrentValues()).toEqual(expectedPostStashValues);
// clicking course end now should have no effect
dateConfigRadios.course_end.trigger('click');
expectSelectedRadio('course_end');
expect(getCurrentValues()).toEqual(expectedPostStashValues);
// clicking manual will pop the stashed values back into the controls
dateConfigRadios.manual.trigger('click');
expectSelectedRadio('manual');
expect(getCurrentValues()).toEqual(startingValues);
});

it('validates submission start datetime fields', function() {
testValidateDate(
view.startDatetimeControl,
Expand Down
26 changes: 26 additions & 0 deletions openassessment/xblock/static/js/src/studio/oa_edit_fields.js
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,8 @@ export class DatetimeControl {
this.element = element;
this.datePicker = datePicker;
this.timePicker = timePicker;
this.stashedDate = null;
this.stashedTime = null;
}

/**
Expand Down Expand Up @@ -234,6 +236,30 @@ export class DatetimeControl {
return `${datePickerSel.val()}T${timePickerSel.val()}`;
}

hasStash() {
return this.stashedDate !== null && this.stashedTime !== null;
}

stash(dateString) {
if (this.hasStash()) { return; }
const datePickerSel = $(this.datePicker, this.element);
const timePickerSel = $(this.timePicker, this.element);
this.stashedDate = datePickerSel.val();
this.stashedTime = timePickerSel.val();
datePickerSel.val(dateString);
timePickerSel.val('00:00');
}

pop() {
if (!this.hasStash()) { return; }
const datePickerSel = $(this.datePicker, this.element);
const timePickerSel = $(this.timePicker, this.element);
datePickerSel.val(this.stashedDate);
timePickerSel.val(this.stashedTime);
this.stashedDate = null;
this.stashedTime = null;
}

/**
Mark validation errors.

Expand Down
Loading
Loading