Commit 182921f1 by Brian Jacobel

Merge pull request #12433 from edx/bjacobel/upgrade-jquery

Upgrade jQuery to 2.2
parents 136f3d34 f4bede6c
...@@ -27,7 +27,8 @@ ...@@ -27,7 +27,8 @@
"mustache": "js/vendor/mustache", "mustache": "js/vendor/mustache",
"codemirror": "js/vendor/codemirror-compressed", "codemirror": "js/vendor/codemirror-compressed",
"codemirror/stex": "js/vendor/CodeMirror/stex", "codemirror/stex": "js/vendor/CodeMirror/stex",
"jquery": "js/vendor/jquery.min", "jquery": "common/js/vendor/jquery",
"jquery-migrate": "common/js/vendor/jquery-migrate",
"jquery.ui": "js/vendor/jquery-ui.min", "jquery.ui": "js/vendor/jquery-ui.min",
"jquery.form": "js/vendor/jquery.form", "jquery.form": "js/vendor/jquery.form",
"jquery.markitup": "js/vendor/markitup/jquery.markitup", "jquery.markitup": "js/vendor/markitup/jquery.markitup",
...@@ -37,7 +38,7 @@ ...@@ -37,7 +38,7 @@
"jquery.timepicker": "js/vendor/timepicker/jquery.timepicker", "jquery.timepicker": "js/vendor/timepicker/jquery.timepicker",
"jquery.cookie": "js/vendor/jquery.cookie", "jquery.cookie": "js/vendor/jquery.cookie",
"jquery.qtip": "js/vendor/jquery.qtip.min", "jquery.qtip": "js/vendor/jquery.qtip.min",
"jquery.scrollTo": "js/vendor/jquery.scrollTo-1.4.2-min", "jquery.scrollTo": "common/js/vendor/jquery.scrollTo",
"jquery.flot": "js/vendor/flot/jquery.flot.min", "jquery.flot": "js/vendor/flot/jquery.flot.min",
"jquery.fileupload": "js/vendor/jQuery-File-Upload/js/jquery.fileupload", "jquery.fileupload": "js/vendor/jQuery-File-Upload/js/jquery.fileupload",
"jquery.fileupload-process": "js/vendor/jQuery-File-Upload/js/jquery.fileupload-process", "jquery.fileupload-process": "js/vendor/jQuery-File-Upload/js/jquery.fileupload-process",
...@@ -112,6 +113,7 @@ ...@@ -112,6 +113,7 @@
"date": { "date": {
exports: "Date" exports: "Date"
}, },
"jquery-migrate": ['jquery'],
"jquery.ui": { "jquery.ui": {
deps: ["jquery"], deps: ["jquery"],
exports: "jQuery.ui" exports: "jQuery.ui"
...@@ -146,7 +148,7 @@ ...@@ -146,7 +148,7 @@
}, },
"jquery.scrollTo": { "jquery.scrollTo": {
deps: ["jquery"], deps: ["jquery"],
exports: "jQuery.fn.scrollTo", exports: "jQuery.fn.scrollTo"
}, },
"jquery.flot": { "jquery.flot": {
deps: ["jquery"], deps: ["jquery"],
......
...@@ -4,14 +4,15 @@ requirejs.config({ ...@@ -4,14 +4,15 @@ requirejs.config({
"gettext": "xmodule_js/common_static/js/test/i18n", "gettext": "xmodule_js/common_static/js/test/i18n",
"mustache": "xmodule_js/common_static/js/vendor/mustache", "mustache": "xmodule_js/common_static/js/vendor/mustache",
"codemirror": "xmodule_js/common_static/js/vendor/CodeMirror/codemirror", "codemirror": "xmodule_js/common_static/js/vendor/CodeMirror/codemirror",
"jquery": "xmodule_js/common_static/js/vendor/jquery.min", "jquery": "xmodule_js/common_static/common/js/vendor/jquery",
"jquery-migrate": "xmodule_js/common_static/common/js/vendor/jquery-migrate",
"jquery.ui": "xmodule_js/common_static/js/vendor/jquery-ui.min", "jquery.ui": "xmodule_js/common_static/js/vendor/jquery-ui.min",
"jquery.form": "xmodule_js/common_static/js/vendor/jquery.form", "jquery.form": "xmodule_js/common_static/js/vendor/jquery.form",
"jquery.markitup": "xmodule_js/common_static/js/vendor/markitup/jquery.markitup", "jquery.markitup": "xmodule_js/common_static/js/vendor/markitup/jquery.markitup",
"jquery.leanModal": "xmodule_js/common_static/js/vendor/jquery.leanModal", "jquery.leanModal": "xmodule_js/common_static/js/vendor/jquery.leanModal",
"jquery.ajaxQueue": "xmodule_js/common_static/js/vendor/jquery.ajaxQueue", "jquery.ajaxQueue": "xmodule_js/common_static/js/vendor/jquery.ajaxQueue",
"jquery.smoothScroll": "xmodule_js/common_static/js/vendor/jquery.smooth-scroll.min", "jquery.smoothScroll": "xmodule_js/common_static/js/vendor/jquery.smooth-scroll.min",
"jquery.scrollTo": "xmodule_js/common_static/js/vendor/jquery.scrollTo-1.4.2-min", "jquery.scrollTo": "common/js/vendor/jquery.scrollTo",
"jquery.timepicker": "xmodule_js/common_static/js/vendor/timepicker/jquery.timepicker", "jquery.timepicker": "xmodule_js/common_static/js/vendor/timepicker/jquery.timepicker",
"jquery.cookie": "xmodule_js/common_static/js/vendor/jquery.cookie", "jquery.cookie": "xmodule_js/common_static/js/vendor/jquery.cookie",
"jquery.qtip": "xmodule_js/common_static/js/vendor/jquery.qtip.min", "jquery.qtip": "xmodule_js/common_static/js/vendor/jquery.qtip.min",
...@@ -65,6 +66,7 @@ requirejs.config({ ...@@ -65,6 +66,7 @@ requirejs.config({
"date": { "date": {
exports: "Date" exports: "Date"
}, },
"jquery-migrate": ['jquery'],
"jquery.ui": { "jquery.ui": {
deps: ["jquery"], deps: ["jquery"],
exports: "jQuery.ui" exports: "jQuery.ui"
......
...@@ -33,7 +33,7 @@ require ["jquery", "backbone", "coffee/src/main", "common/js/spec_helpers/ajax_h ...@@ -33,7 +33,7 @@ require ["jquery", "backbone", "coffee/src/main", "common/js/spec_helpers/ajax_h
server && server.restore() server && server.restore()
it "successful AJAX request does not pop an error notification", -> it "successful AJAX request does not pop an error notification", ->
server = AjaxHelpers.server([200, {}, '']) server = AjaxHelpers.server([200, {"Content-Type": "application/json"}, "{}"])
expect($("#page-notification")).toBeEmpty() expect($("#page-notification")).toBeEmpty()
$.ajax("/test") $.ajax("/test")
...@@ -42,7 +42,7 @@ require ["jquery", "backbone", "coffee/src/main", "common/js/spec_helpers/ajax_h ...@@ -42,7 +42,7 @@ require ["jquery", "backbone", "coffee/src/main", "common/js/spec_helpers/ajax_h
expect($("#page-notification")).toBeEmpty() expect($("#page-notification")).toBeEmpty()
it "AJAX request with error should pop an error notification", -> it "AJAX request with error should pop an error notification", ->
server = AjaxHelpers.server([500, {}, '']) server = AjaxHelpers.server([500, {"Content-Type": "application/json"}, "{}"])
$.ajax("/test") $.ajax("/test")
server.respond() server.respond()
...@@ -50,7 +50,7 @@ require ["jquery", "backbone", "coffee/src/main", "common/js/spec_helpers/ajax_h ...@@ -50,7 +50,7 @@ require ["jquery", "backbone", "coffee/src/main", "common/js/spec_helpers/ajax_h
expect($("#page-notification")).toContainElement('div.wrapper-notification-error') expect($("#page-notification")).toContainElement('div.wrapper-notification-error')
it "can override AJAX request with error so it does not pop an error notification", -> it "can override AJAX request with error so it does not pop an error notification", ->
server = AjaxHelpers.server([500, {}, '']) server = AjaxHelpers.server([500, {"Content-Type": "application/json"}, "{}"])
$.ajax $.ajax
url: "/test" url: "/test"
......
...@@ -5,13 +5,14 @@ requirejs.config({ ...@@ -5,13 +5,14 @@ requirejs.config({
"gettext": "xmodule_js/common_static/js/test/i18n", "gettext": "xmodule_js/common_static/js/test/i18n",
"mustache": "xmodule_js/common_static/js/vendor/mustache", "mustache": "xmodule_js/common_static/js/vendor/mustache",
"codemirror": "xmodule_js/common_static/js/vendor/CodeMirror/codemirror", "codemirror": "xmodule_js/common_static/js/vendor/CodeMirror/codemirror",
"jquery": "xmodule_js/common_static/js/vendor/jquery.min", "jquery": "common/js/vendor/jquery",
"jquery-migrate": "common/js/vendor/jquery-migrate",
"jquery.ui": "xmodule_js/common_static/js/vendor/jquery-ui.min", "jquery.ui": "xmodule_js/common_static/js/vendor/jquery-ui.min",
"jquery.form": "xmodule_js/common_static/js/vendor/jquery.form", "jquery.form": "xmodule_js/common_static/js/vendor/jquery.form",
"jquery.markitup": "xmodule_js/common_static/js/vendor/markitup/jquery.markitup", "jquery.markitup": "xmodule_js/common_static/js/vendor/markitup/jquery.markitup",
"jquery.leanModal": "xmodule_js/common_static/js/vendor/jquery.leanModal", "jquery.leanModal": "xmodule_js/common_static/js/vendor/jquery.leanModal",
"jquery.smoothScroll": "xmodule_js/common_static/js/vendor/jquery.smooth-scroll.min", "jquery.smoothScroll": "xmodule_js/common_static/js/vendor/jquery.smooth-scroll.min",
"jquery.scrollTo": "xmodule_js/common_static/js/vendor/jquery.scrollTo-1.4.2-min", "jquery.scrollTo": "common/js/vendor/jquery.scrollTo",
"jquery.timepicker": "xmodule_js/common_static/js/vendor/timepicker/jquery.timepicker", "jquery.timepicker": "xmodule_js/common_static/js/vendor/timepicker/jquery.timepicker",
"jquery.cookie": "xmodule_js/common_static/js/vendor/jquery.cookie", "jquery.cookie": "xmodule_js/common_static/js/vendor/jquery.cookie",
"jquery.qtip": "xmodule_js/common_static/js/vendor/jquery.qtip.min", "jquery.qtip": "xmodule_js/common_static/js/vendor/jquery.qtip.min",
......
...@@ -34,7 +34,7 @@ define ["js/models/section", "common/js/spec_helpers/ajax_helpers", "js/utils/mo ...@@ -34,7 +34,7 @@ define ["js/models/section", "common/js/spec_helpers/ajax_helpers", "js/utils/mo
}) })
it "show/hide a notification when it saves to the server", -> it "show/hide a notification when it saves to the server", ->
server = AjaxHelpers.server([200, {}, '']) server = AjaxHelpers.server([200, {"Content-Type": "application/json"}, "{}"])
@model.save() @model.save()
expect(Section.prototype.showNotification).toHaveBeenCalled() expect(Section.prototype.showNotification).toHaveBeenCalled()
...@@ -43,7 +43,7 @@ define ["js/models/section", "common/js/spec_helpers/ajax_helpers", "js/utils/mo ...@@ -43,7 +43,7 @@ define ["js/models/section", "common/js/spec_helpers/ajax_helpers", "js/utils/mo
it "don't hide notification when saving fails", -> it "don't hide notification when saving fails", ->
# this is handled by the global AJAX error handler # this is handled by the global AJAX error handler
server = AjaxHelpers.server([500, {}, '']) server = AjaxHelpers.server([500, {"Content-Type": "application/json"}, "{}"])
@model.save() @model.save()
server.respond() server.respond()
......
...@@ -84,7 +84,7 @@ define ["jquery", "common/js/spec_helpers/ajax_helpers", "squire"], ...@@ -84,7 +84,7 @@ define ["jquery", "common/js/spec_helpers/ajax_helpers", "squire"],
expect(@confirmationSpies.constructor).not.toHaveBeenCalled() expect(@confirmationSpies.constructor).not.toHaveBeenCalled()
expect(@collection.contains(@model)).toBeTruthy() expect(@collection.contains(@model)).toBeTruthy()
# return a success response # return a success response
requests[0].respond(200) requests[0].respond(204)
expect(@confirmationSpies.constructor).toHaveBeenCalled() expect(@confirmationSpies.constructor).toHaveBeenCalled()
expect(@confirmationSpies.show).toHaveBeenCalled() expect(@confirmationSpies.show).toHaveBeenCalled()
savingOptions = @confirmationSpies.constructor.calls.mostRecent().args[0] savingOptions = @confirmationSpies.constructor.calls.mostRecent().args[0]
...@@ -118,7 +118,7 @@ define ["jquery", "common/js/spec_helpers/ajax_helpers", "squire"], ...@@ -118,7 +118,7 @@ define ["jquery", "common/js/spec_helpers/ajax_helpers", "squire"],
expect(savingOptions.title).toMatch("Saving") expect(savingOptions.title).toMatch("Saving")
expect(@model.get("locked")).toBeFalsy() expect(@model.get("locked")).toBeFalsy()
# return a success response # return a success response
requests[0].respond(200) requests[0].respond(204)
expect(@savingSpies.hide).toHaveBeenCalled() expect(@savingSpies.hide).toHaveBeenCalled()
expect(@model.get("locked")).toBeTruthy() expect(@model.get("locked")).toBeTruthy()
......
...@@ -87,7 +87,7 @@ define ["js/models/textbook", "js/models/chapter", "js/collections/chapter", "js ...@@ -87,7 +87,7 @@ define ["js/models/textbook", "js/models/chapter", "js/collections/chapter", "js
savingOptions = @savingSpies.constructor.calls.mostRecent().args[0] savingOptions = @savingSpies.constructor.calls.mostRecent().args[0]
expect(savingOptions.title).toMatch(/Deleting/) expect(savingOptions.title).toMatch(/Deleting/)
# return a success response # return a success response
requests[0].respond(200) requests[0].respond(204)
expect(@savingSpies.hide).toHaveBeenCalled() expect(@savingSpies.hide).toHaveBeenCalled()
expect(@collection.contains(@model)).toBeFalsy() expect(@collection.contains(@model)).toBeFalsy()
......
...@@ -58,6 +58,20 @@ function(_, Course, CertificatesCollection, CertificateModel, CertificateDetails ...@@ -58,6 +58,20 @@ function(_, Course, CertificatesCollection, CertificateModel, CertificateDetails
}; };
beforeEach(function() { beforeEach(function() {
window.course = new Course({
id: '5',
name: 'Course Name',
url_name: 'course_name',
org: 'course_org',
num: 'course_num',
revision: 'course_rev'
});
window.certWebPreview = new CertificatePreview({
course_modes: ['honor', 'test'],
certificate_web_view_url: '/users/1/courses/orgX/009/2016'
});
window.CMS.User = {isGlobalStaff: true};
TemplateHelpers.installTemplates(['certificate-details', 'signatory-details', 'signatory-editor', 'signatory-actions'], true); TemplateHelpers.installTemplates(['certificate-details', 'signatory-details', 'signatory-editor', 'signatory-actions'], true);
window.course = new Course({ window.course = new Course({
...@@ -99,6 +113,12 @@ function(_, Course, CertificatesCollection, CertificateModel, CertificateDetails ...@@ -99,6 +113,12 @@ function(_, Course, CertificatesCollection, CertificateModel, CertificateDetails
delete window.CMS.User; delete window.CMS.User;
}); });
afterEach(function() {
delete window.course;
delete window.CMS.User;
});
describe('The Certificate Details view', function() { describe('The Certificate Details view', function() {
it('should parse a JSON string collection into a Backbone model collection', function () { it('should parse a JSON string collection into a Backbone model collection', function () {
...@@ -234,7 +254,7 @@ function(_, Course, CertificatesCollection, CertificateModel, CertificateDetails ...@@ -234,7 +254,7 @@ function(_, Course, CertificatesCollection, CertificateModel, CertificateDetails
this.view.$(SELECTORS.signatory_panel_save).click(); this.view.$(SELECTORS.signatory_panel_save).click();
ViewHelpers.verifyNotificationShowing(notificationSpy, /Saving/); ViewHelpers.verifyNotificationShowing(notificationSpy, /Saving/);
requests[0].respond(200); requests[0].respond(204);
ViewHelpers.verifyNotificationHidden(notificationSpy); ViewHelpers.verifyNotificationHidden(notificationSpy);
expect(this.view.$(SELECTORS.signatory_name_value)).toContainText('New Signatory Test Name'); expect(this.view.$(SELECTORS.signatory_name_value)).toContainText('New Signatory Test Name');
......
...@@ -28,8 +28,6 @@ function(_, $, Course, CertificatePreview, TemplateHelpers, ViewHelpers, AjaxHel ...@@ -28,8 +28,6 @@ function(_, $, Course, CertificatePreview, TemplateHelpers, ViewHelpers, AjaxHel
}; };
beforeEach(function() { beforeEach(function() {
appendSetFixtures('<div class="preview-certificate nav-actions"></div>');
window.course = new Course({ window.course = new Course({
id: '5', id: '5',
name: 'Course Name', name: 'Course Name',
...@@ -40,6 +38,8 @@ function(_, $, Course, CertificatePreview, TemplateHelpers, ViewHelpers, AjaxHel ...@@ -40,6 +38,8 @@ function(_, $, Course, CertificatePreview, TemplateHelpers, ViewHelpers, AjaxHel
}); });
window.CMS.User = {isGlobalStaff: true}; window.CMS.User = {isGlobalStaff: true};
TemplateHelpers.installTemplate('certificate-web-preview', true);
appendSetFixtures('<div class="preview-certificate nav-actions"></div>');
this.view = new CertificatePreview({ this.view = new CertificatePreview({
el: $('.preview-certificate'), el: $('.preview-certificate'),
course_modes: ['test1', 'test2', 'test3'], course_modes: ['test1', 'test2', 'test3'],
......
...@@ -331,7 +331,7 @@ define(["js/utils/drag_and_drop", "common/js/components/views/feedback_notificat ...@@ -331,7 +331,7 @@ define(["js/utils/drag_and_drop", "common/js/components/views/feedback_notificat
expect(savingOptions.title).toMatch(/Saving/); expect(savingOptions.title).toMatch(/Saving/);
expect($('#unit-1')).toHaveClass('was-dropped'); expect($('#unit-1')).toHaveClass('was-dropped');
expect(request.requestBody).toEqual('{"children":["fourth-unit-id","first-unit-id"]}'); expect(request.requestBody).toEqual('{"children":["fourth-unit-id","first-unit-id"]}');
request.respond(200); request.respond(204);
expect(this.savingSpies.hide).toHaveBeenCalled(); expect(this.savingSpies.hide).toHaveBeenCalled();
this.clock.tick(1001); this.clock.tick(1001);
expect($('#unit-1')).not.toHaveClass('was-dropped'); expect($('#unit-1')).not.toHaveClass('was-dropped');
...@@ -360,7 +360,7 @@ define(["js/utils/drag_and_drop", "common/js/components/views/feedback_notificat ...@@ -360,7 +360,7 @@ define(["js/utils/drag_and_drop", "common/js/components/views/feedback_notificat
expect(request.requestBody).toEqual( expect(request.requestBody).toEqual(
'{"children":["second-unit-id","first-unit-id","third-unit-id"]}' '{"children":["second-unit-id","first-unit-id","third-unit-id"]}'
); );
request.respond(200); request.respond(204);
this.clock.tick(1001); this.clock.tick(1001);
expect($('#unit-1')).not.toHaveClass('was-dropped'); expect($('#unit-1')).not.toHaveClass('was-dropped');
// parent // parent
......
...@@ -491,21 +491,6 @@ define([ ...@@ -491,21 +491,6 @@ define([
AjaxHelpers.expectNoRequests(requests); AjaxHelpers.expectNoRequests(requests);
}); });
it('should have appropriate class names on focus/blur', function (done) {
var groupInput = this.view.$(SELECTORS.inputGroupName).first(),
groupFields = this.view.$(SELECTORS.groupFields);
groupInput.focus();
jasmine.waitUntil(function() {
return groupFields.hasClass('is-focused');
}).then(function () {
groupInput.blur();
jasmine.waitUntil(function() {
return !groupFields.hasClass('is-focused');
}).then(done);
});
});
describe('removes all newly created groups on cancel', function () { describe('removes all newly created groups on cancel', function () {
it('if the model has a non-empty groups', function() { it('if the model has a non-empty groups', function() {
var groups = this.model.get('groups'); var groups = this.model.get('groups');
......
...@@ -253,6 +253,16 @@ define(["jquery", "common/js/spec_helpers/ajax_helpers", "common/js/components/u ...@@ -253,6 +253,16 @@ define(["jquery", "common/js/spec_helpers/ajax_helpers", "common/js/components/u
]) ])
]); ]);
// Create a mock Course object as the JS now expects it.
window.course = new Course({
id: '333',
name: 'Course Name',
url_name: 'course_name',
org: 'course_org',
num: 'course_num',
revision: 'course_rev'
});
}); });
afterEach(function () { afterEach(function () {
......
...@@ -101,7 +101,7 @@ define(["jquery", "common/js/spec_helpers/ajax_helpers", "common/js/spec_helpers ...@@ -101,7 +101,7 @@ define(["jquery", "common/js/spec_helpers/ajax_helpers", "common/js/spec_helpers
var values_with_blank = values.slice(); var values_with_blank = values.slice();
values_with_blank[i] = ''; values_with_blank[i] = '';
fillInLibraryFields.apply(this, values_with_blank); fillInLibraryFields.apply(this, values_with_blank);
expect($('.create-library li.field.text input[value=]').parent()).toHaveClass('error'); expect($('.create-library li.field.text input').parent()).toHaveClass('error');
expect($('.new-library-save')).toHaveClass('is-disabled'); expect($('.new-library-save')).toHaveClass('is-disabled');
expect($('.new-library-save')).toHaveAttr('aria-disabled', 'true'); expect($('.new-library-save')).toHaveAttr('aria-disabled', 'true');
$('.new-library-save').click(); $('.new-library-save').click();
......
...@@ -5,11 +5,11 @@ define([ ...@@ -5,11 +5,11 @@ define([
function ($, AjaxHelpers, ViewHelpers, ManageUsersFactory, ViewUtils) { function ($, AjaxHelpers, ViewHelpers, ManageUsersFactory, ViewUtils) {
"use strict"; "use strict";
describe("Library Instructor Access Page", function () { describe("Library Instructor Access Page", function () {
const changeRoleUrl = "dummy_change_role_url/@@EMAIL@@"; var changeRoleUrl = "dummy_change_role_url/@@EMAIL@@";
var team_member_fixture = readFixtures("team-member.underscore"); var team_member_fixture = readFixtures("team-member.underscore");
function setRole(email, role){ function setRole(email, role){
var user_li = $("li.user-item[data-email="+ email + "]"); var user_li = $('li.user-item[data-email="'+ email + '"]');
var role_action = $("li.action-role a.make-"+role, user_li); var role_action = $("li.action-role a.make-"+role, user_li);
expect(role_action).toBeVisible(); expect(role_action).toBeVisible();
role_action.click(); role_action.click();
...@@ -48,7 +48,7 @@ function ($, AjaxHelpers, ViewHelpers, ManageUsersFactory, ViewUtils) { ...@@ -48,7 +48,7 @@ function ($, AjaxHelpers, ViewHelpers, ManageUsersFactory, ViewUtils) {
}); });
it("can give a user permission to use the library", function () { it("can give a user permission to use the library", function () {
const email = 'other@example.com'; var email = 'other@example.com';
var requests = AjaxHelpers.requests(this); var requests = AjaxHelpers.requests(this);
var reloadSpy = spyOn(ViewUtils, 'reload'); var reloadSpy = spyOn(ViewUtils, 'reload');
$('.create-user-button').click(); $('.create-user-button').click();
...@@ -61,7 +61,7 @@ function ($, AjaxHelpers, ViewHelpers, ManageUsersFactory, ViewUtils) { ...@@ -61,7 +61,7 @@ function ($, AjaxHelpers, ViewHelpers, ManageUsersFactory, ViewUtils) {
}); });
it("can promote user", function() { it("can promote user", function() {
const email = "staff@example.com"; var email = "staff@example.com";
var requests = AjaxHelpers.requests(this); var requests = AjaxHelpers.requests(this);
var reloadSpy = spyOn(ViewUtils, 'reload'); var reloadSpy = spyOn(ViewUtils, 'reload');
setRole("staff@example.com", 'staff'); setRole("staff@example.com", 'staff');
......
...@@ -144,7 +144,7 @@ define([ ...@@ -144,7 +144,7 @@ define([
// select the entrance-exam-enabled checkbox. grade requirement section should be visible. // select the entrance-exam-enabled checkbox. grade requirement section should be visible.
entrance_exam_enabled_field entrance_exam_enabled_field
.attr('checked', 'true') .prop('checked', true)
.trigger('change'); .trigger('change');
this.view.render(); this.view.render();
...@@ -152,7 +152,7 @@ define([ ...@@ -152,7 +152,7 @@ define([
// deselect the entrance-exam-enabled checkbox. grade requirement section should be hidden. // deselect the entrance-exam-enabled checkbox. grade requirement section should be hidden.
entrance_exam_enabled_field entrance_exam_enabled_field
.removeAttr('checked') .prop('checked', false)
.trigger('change'); .trigger('change');
expect(this.view.$(SELECTORS.grade_requirement_div)).toBeHidden(); expect(this.view.$(SELECTORS.grade_requirement_div)).toBeHidden();
...@@ -173,7 +173,7 @@ define([ ...@@ -173,7 +173,7 @@ define([
// select the entrance-exam-enabled checkbox. // select the entrance-exam-enabled checkbox.
entrance_exam_enabled_field entrance_exam_enabled_field
.attr('checked', 'true') .prop('checked', true)
.trigger('change'); .trigger('change');
// input a valid value for entrance exam minimum score. // input a valid value for entrance exam minimum score.
......
...@@ -99,7 +99,7 @@ define(["jquery", "URI", "common/js/spec_helpers/ajax_helpers", "common/js/compo ...@@ -99,7 +99,7 @@ define(["jquery", "URI", "common/js/spec_helpers/ajax_helpers", "common/js/compo
mimetype: "application/javascript", kind: "url", data: missingJavaScriptUrl mimetype: "application/javascript", kind: "url", data: missingJavaScriptUrl
}] }]
]); ]);
expect(promise.isRejected()).toBe(true); expect(promise.state()).toBe("rejected");
}); });
it('Triggers an event to the runtime when a notification-action-button is clicked', function () { it('Triggers an event to the runtime when a notification-action-button is clicked', function () {
......
...@@ -10,8 +10,8 @@ define(["js/views/validation", "codemirror", "js/models/course_update", ...@@ -10,8 +10,8 @@ define(["js/views/validation", "codemirror", "js/models/course_update",
// collection is CourseUpdateCollection // collection is CourseUpdateCollection
events: { events: {
"click .new-update-button" : "onNew", "click .new-update-button" : "onNew",
"click #course-update-view .save-button" : "onSave", "click .save-button" : "onSave",
"click #course-update-view .cancel-button" : "onCancel", "click .cancel-button" : "onCancel",
"click .post-actions > .edit-button" : "onEdit", "click .post-actions > .edit-button" : "onEdit",
"click .post-actions > .delete-button" : "onDelete" "click .post-actions > .delete-button" : "onDelete"
}, },
......
...@@ -12,8 +12,8 @@ function(BaseView, _, str, gettext, groupEditTemplate) { ...@@ -12,8 +12,8 @@ function(BaseView, _, str, gettext, groupEditTemplate) {
events: { events: {
'click .action-close': 'removeGroup', 'click .action-close': 'removeGroup',
'change .group-name': 'changeName', 'change .group-name': 'changeName',
'focus .groups-fields input': 'onFocus', 'focus .group-name': 'onFocus',
'blur .groups-fields input': 'onBlur' 'blur .group-name': 'onBlur'
}, },
className: function() { className: function() {
......
...@@ -215,7 +215,6 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview', ...@@ -215,7 +215,6 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview',
} }
}); });
AbstractEditor = BaseView.extend({ AbstractEditor = BaseView.extend({
tagName: 'section', tagName: 'section',
templateName: null, templateName: null,
...@@ -328,6 +327,7 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview', ...@@ -328,6 +327,7 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview',
}; };
} }
}); });
TimedExaminationPreferenceEditor = AbstractEditor.extend({ TimedExaminationPreferenceEditor = AbstractEditor.extend({
templateName: 'timed-examination-preference-editor', templateName: 'timed-examination-preference-editor',
className: 'edit-settings-timed-examination', className: 'edit-settings-timed-examination',
...@@ -496,6 +496,7 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview', ...@@ -496,6 +496,7 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview',
}; };
} }
}); });
AccessEditor = AbstractEditor.extend({ AccessEditor = AbstractEditor.extend({
templateName: 'access-editor', templateName: 'access-editor',
className: 'edit-settings-access', className: 'edit-settings-access',
...@@ -548,13 +549,14 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview', ...@@ -548,13 +549,14 @@ define(['jquery', 'backbone', 'underscore', 'gettext', 'js/views/baseview',
}; };
} }
}); });
GradingEditor = AbstractEditor.extend({ GradingEditor = AbstractEditor.extend({
templateName: 'grading-editor', templateName: 'grading-editor',
className: 'edit-settings-grading', className: 'edit-settings-grading',
afterRender: function () { afterRender: function () {
AbstractEditor.prototype.afterRender.call(this); AbstractEditor.prototype.afterRender.call(this);
this.setValue(this.model.get('format')); this.setValue(this.model.get('format') || 'notgraded');
}, },
setValue: function (value) { setValue: function (value) {
......
...@@ -89,7 +89,7 @@ function($, _, AbstractEditor, FileUpload, UploadDialog) { ...@@ -89,7 +89,7 @@ function($, _, AbstractEditor, FileUpload, UploadDialog) {
items = this.$el.find('ol').find('.list-settings-item'); items = this.$el.find('ol').find('.list-settings-item');
_.each(items, function(element, index) { _.each(items, function(element, index) {
var key = $(element).find('select').val(), var key = $(element).find('select option:selected').val(),
value = $(element).find('.input').val(); value = $(element).find('.input').val();
// Keys should be unique, so if our keys are duplicated and // Keys should be unique, so if our keys are duplicated and
......
...@@ -13,6 +13,11 @@ var options = { ...@@ -13,6 +13,11 @@ var options = {
libraryFiles: [], libraryFiles: [],
libraryFilesToInclude: [
{pattern: 'common/js/vendor/jquery.js', included: true},
{pattern: 'common/js/vendor/jquery-migrate.js', included: true}
],
// Make sure the patterns in sourceFiles and specFiles do not match the same file. // Make sure the patterns in sourceFiles and specFiles do not match the same file.
// Otherwise Istanbul which is used for coverage tracking will cause tests to not run. // Otherwise Istanbul which is used for coverage tracking will cause tests to not run.
sourceFiles: [ sourceFiles: [
......
...@@ -13,6 +13,11 @@ var options = { ...@@ -13,6 +13,11 @@ var options = {
libraryFiles: [], libraryFiles: [],
libraryFilesToInclude: [
{pattern: 'common/js/vendor/jquery.js', included: true},
{pattern: 'common/js/vendor/jquery-migrate.js', included: true}
],
// Make sure the patterns in sourceFiles and specFiles do not match the same file. // Make sure the patterns in sourceFiles and specFiles do not match the same file.
// Otherwise Istanbul which is used for coverage tracking will cause tests to not run. // Otherwise Istanbul which is used for coverage tracking will cause tests to not run.
sourceFiles: [ sourceFiles: [
......
...@@ -93,12 +93,12 @@ def render_require_js_path_overrides(path_overrides): # pylint: disable=invalid ...@@ -93,12 +93,12 @@ def render_require_js_path_overrides(path_overrides): # pylint: disable=invalid
For example: For example:
"js/vendor/jquery.min.js" --> "js/vendor/jquery.min.abcd1234" "js/vendor/jquery.js" --> "js/vendor/jquery.abcd1234"
To achive this we will add overrided paths in requirejs config at runtime. To achive this we will add overrided paths in requirejs config at runtime.
So that any reference to 'jquery' in a JavaScript module So that any reference to 'jquery' in a JavaScript module
will cause RequireJS to load '/static/js/vendor/jquery.min.abcd1234.js' will cause RequireJS to load '/static/js/vendor/jquery.abcd1234.js'
If running in DEBUG mode (as in devstack), the resolved JavaScript URLs If running in DEBUG mode (as in devstack), the resolved JavaScript URLs
won't contain hashes, so the new paths will match the original paths. won't contain hashes, so the new paths will match the original paths.
......
...@@ -14,7 +14,7 @@ class RequireJSPathOverridesTest(TestCase): ...@@ -14,7 +14,7 @@ class RequireJSPathOverridesTest(TestCase):
"""Test RequireJS path overrides. """ """Test RequireJS path overrides. """
OVERRIDES = { OVERRIDES = {
'jquery': 'js/vendor/jquery.min.js', 'jquery': 'common/js/vendor/jquery.js',
'backbone': 'common/js/vendor/backbone.js', 'backbone': 'common/js/vendor/backbone.js',
'text': 'js/vendor/text.js' 'text': 'js/vendor/text.js'
} }
...@@ -24,7 +24,7 @@ class RequireJSPathOverridesTest(TestCase): ...@@ -24,7 +24,7 @@ class RequireJSPathOverridesTest(TestCase):
"(function (require) {", "(function (require) {",
"require.config({", "require.config({",
"paths: {", "paths: {",
"'jquery': 'js/vendor/jquery.min',", "'jquery': 'common/js/vendor/jquery',",
"'text': 'js/vendor/text',", "'text': 'js/vendor/text',",
"'backbone': 'common/js/vendor/backbone'", "'backbone': 'common/js/vendor/backbone'",
"}", "}",
......
...@@ -28,7 +28,8 @@ var options = { ...@@ -28,7 +28,8 @@ var options = {
{pattern: 'common_static/edx-ui-toolkit/js/utils/global-loader.js', included: true}, {pattern: 'common_static/edx-ui-toolkit/js/utils/global-loader.js', included: true},
{pattern: 'common_static/js/vendor/CodeMirror/codemirror.js', included: true}, {pattern: 'common_static/js/vendor/CodeMirror/codemirror.js', included: true},
{pattern: 'common_static/js/vendor/draggabilly.js'}, {pattern: 'common_static/js/vendor/draggabilly.js'},
{pattern: 'common_static/js/vendor/jquery.min.js', included: true}, {pattern: 'common_static/common/js/vendor/jquery.js', included: true},
{pattern: 'common_static/common/js/vendor/jquery-migrate.js', included: true},
{pattern: 'common_static/js/vendor/jquery.cookie.js', included: true}, {pattern: 'common_static/js/vendor/jquery.cookie.js', included: true},
{pattern: 'common_static/js/vendor/jquery.leanModal.js', included: true}, {pattern: 'common_static/js/vendor/jquery.leanModal.js', included: true},
{pattern: 'common_static/js/vendor/jquery.timeago.js', included: true}, {pattern: 'common_static/js/vendor/jquery.timeago.js', included: true},
......
...@@ -289,9 +289,9 @@ describe 'Problem', -> ...@@ -289,9 +289,9 @@ describe 'Problem', ->
$('#input_example_1').replaceWith(html) $('#input_example_1').replaceWith(html)
@problem.checkAnswersAndCheckButton true @problem.checkAnswersAndCheckButton true
@checkDisabled true @checkDisabled true
$('#input_1_1_1').attr('checked', true).trigger('click') $('#input_1_1_1').click()
@checkDisabled false @checkDisabled false
$('#input_1_1_1').attr('checked', false).trigger('click') $('#input_1_1_1').click()
@checkDisabled true @checkDisabled true
it 'should become enabled after a radiobutton is checked', -> it 'should become enabled after a radiobutton is checked', ->
......
...@@ -343,7 +343,7 @@ ...@@ -343,7 +343,7 @@
expect(parseIntAttribute(item, 'data-index')).toEqual(index); expect(parseIntAttribute(item, 'data-index')).toEqual(index);
expect(parseIntAttribute(item, 'data-start')).toEqual(captionsData.start[index]); expect(parseIntAttribute(item, 'data-start')).toEqual(captionsData.start[index]);
expect(item.attr('tabindex')).toEqual(0); expect(item.attr('tabindex')).toEqual('0');
expect(item.text().trim()).toEqual(captionsData.text[index]); expect(item.text().trim()).toEqual(captionsData.text[index]);
}); });
}); });
...@@ -432,7 +432,7 @@ ...@@ -432,7 +432,7 @@
expect(parseIntAttribute(item, 'data-index')).toEqual(index); expect(parseIntAttribute(item, 'data-index')).toEqual(index);
expect(parseIntAttribute(item, 'data-start')).toEqual(captionsData.start[index]); expect(parseIntAttribute(item, 'data-start')).toEqual(captionsData.start[index]);
expect(item.attr('tabindex')).toEqual(0); expect(item.attr('tabindex')).toEqual('0');
expect(item.text().trim()).toEqual(text); expect(item.text().trim()).toEqual(text);
}); });
}).always(done); }).always(done);
...@@ -842,7 +842,7 @@ ...@@ -842,7 +842,7 @@
function (index, item) { function (index, item) {
expect(parseIntAttribute($(item), 'data-index')).toEqual(index); expect(parseIntAttribute($(item), 'data-index')).toEqual(index);
expect(parseIntAttribute($(item), 'data-start')).toEqual(captionsData.start[index]); expect(parseIntAttribute($(item), 'data-start')).toEqual(captionsData.start[index]);
expect($(item).attr('tabindex')).toEqual(0); expect($(item).attr('tabindex')).toEqual('0');
expect($(item).text().trim()).toEqual(captionsData.text[index]); expect($(item).text().trim()).toEqual(captionsData.text[index]);
}); });
}); });
......
...@@ -49,8 +49,8 @@ ...@@ -49,8 +49,8 @@
}); });
it('from the start, focus grabbers are disabled', function () { it('from the start, focus grabbers are disabled', function () {
expect(state.focusGrabber.elFirst.attr('tabindex')).toBe(-1); expect(state.focusGrabber.elFirst.attr('tabindex')).toBe('-1');
expect(state.focusGrabber.elLast.attr('tabindex')).toBe(-1); expect(state.focusGrabber.elLast.attr('tabindex')).toBe('-1');
}); });
it( it(
......
...@@ -55,7 +55,7 @@ ...@@ -55,7 +55,7 @@
expect(btnPlay).not.toHaveClass('is-hidden'); expect(btnPlay).not.toHaveClass('is-hidden');
expect(btnPlay).toHaveAttrs({ expect(btnPlay).toHaveAttrs({
'aria-hidden': 'false', 'aria-hidden': 'false',
'tabindex': 0 'tabindex': '0'
}); });
state.videoPlayPlaceholder.hide(); state.videoPlayPlaceholder.hide();
...@@ -63,7 +63,7 @@ ...@@ -63,7 +63,7 @@
expect(btnPlay).toHaveClass('is-hidden'); expect(btnPlay).toHaveClass('is-hidden');
expect(btnPlay).toHaveAttrs({ expect(btnPlay).toHaveAttrs({
'aria-hidden': 'true', 'aria-hidden': 'true',
'tabindex': -1 'tabindex': '-1'
}); });
}); });
......
...@@ -39,15 +39,15 @@ class @Annotatable ...@@ -39,15 +39,15 @@ class @Annotatable
# the associated problem. The reply buttons are part of the tooltip # the associated problem. The reply buttons are part of the tooltip
# content. It's important that the tooltips be configured to render # content. It's important that the tooltips be configured to render
# as descendants of the annotation module and *not* the document.body. # as descendants of the annotation module and *not* the document.body.
@$el.delegate @replySelector, 'click', @onClickReply @$el.on 'click', @replySelector, @onClickReply
# Initialize handler for 'return to annotation' events triggered from problems. # Initialize handler for 'return to annotation' events triggered from problems.
# 1) There are annotationinput capa problems rendered on the page # 1) There are annotationinput capa problems rendered on the page
# 2) Each one has an embedded return link (see annotation capa problem template). # 2) Each one has an embedded return link (see annotation capa problem template).
# Since the capa problem injects HTML content via AJAX, the best we can do is # Since the capa problem injects HTML content via AJAX, the best we can do is
# is let the click events bubble up to the body and handle them there. # is let the click events bubble up to the body and handle them there.
$('body').delegate @problemReturnSelector, 'click', @onClickReturn $(document).on 'click', @problemReturnSelector, @onClickReturn
initTips: () -> initTips: () ->
# tooltips are used to display annotations for highlighted text spans # tooltips are used to display annotations for highlighted text spans
@$(@spanSelector).each (index, el) => @$(@spanSelector).each (index, el) =>
...@@ -91,8 +91,9 @@ class @Annotatable ...@@ -91,8 +91,9 @@ class @Annotatable
onMoveTip: (event, api, position) => onMoveTip: (event, api, position) =>
### ###
This method handles an edge case in which a tooltip is displayed above This method handles a vertical positioning bug in Firefox as
a non-overlapping span like this: well as an edge case in which a tooltip is displayed above a
non-overlapping span like this:
(( TOOLTIP )) (( TOOLTIP ))
\/ \/
...@@ -115,28 +116,33 @@ class @Annotatable ...@@ -115,28 +116,33 @@ class @Annotatable
# we want to choose the largest of the two non-overlapping spans and display # we want to choose the largest of the two non-overlapping spans and display
# the tooltip above the center of it (see api.options.position settings) # the tooltip above the center of it (see api.options.position settings)
focus_rect = (if rects[0].width > rects[1].width then rects[0] else rects[1]) focus_rect = (if rects[0].width > rects[1].width then rects[0] else rects[1])
rect_center = focus_rect.left + (focus_rect.width / 2) else
rect_top = focus_rect.top # always compute the new position because Firefox doesn't
tip_width = $(tip).width() # properly vertically position the tooltip
tip_height = $(tip).height() focus_rect = rects[0]
# tooltip is positioned relative to its container, so we need to factor in offsets rect_center = focus_rect.left + (focus_rect.width / 2)
container_offset = $(container).offset() rect_top = focus_rect.top
offset_left = -container_offset.left tip_width = $(tip).width()
offset_top = $(document).scrollTop() - container_offset.top tip_height = $(tip).height()
tip_left = offset_left + rect_center - (tip_width / 2) # tooltip is positioned relative to its container, so we need to factor in offsets
tip_top = offset_top + rect_top - tip_height + adjust_y container_offset = $(container).offset()
offset_left = -container_offset.left
offset_top = $(document).scrollTop() - container_offset.top
# make sure the new tip position doesn't clip the edges of the screen tip_left = offset_left + rect_center - (tip_width / 2)
win_width = $(window).width() tip_top = offset_top + rect_top - tip_height + adjust_y
if tip_left < offset_left
tip_left = offset_left
else if tip_left + tip_width > win_width + offset_left
tip_left = win_width + offset_left - tip_width
# final step: update the position object (used by qtip2 to show the tip after the move event) # make sure the new tip position doesn't clip the edges of the screen
$.extend position, 'left': tip_left, 'top': tip_top win_width = $(window).width()
if tip_left < offset_left
tip_left = offset_left
else if tip_left + tip_width > win_width + offset_left
tip_left = win_width + offset_left - tip_width
# final step: update the position object (used by qtip2 to show the tip after the move event)
$.extend position, 'left': tip_left, 'top': tip_top
getSpanForProblemReturn: (el) -> getSpanForProblemReturn: (el) ->
problem_id = $(@problemReturnSelector).index(el) problem_id = $(@problemReturnSelector).index(el)
...@@ -144,7 +150,7 @@ class @Annotatable ...@@ -144,7 +150,7 @@ class @Annotatable
getProblem: (el) -> getProblem: (el) ->
problem_id = @getProblemId(el) problem_id = @getProblemId(el)
$(@problemSelector).has(@problemInputSelector).eq(problem_id) $(@problemInputSelector).eq(problem_id)
getProblemId: (el) -> getProblemId: (el) ->
$(el).data('problem-id') $(el).data('problem-id')
...@@ -208,7 +214,7 @@ class @Annotatable ...@@ -208,7 +214,7 @@ class @Annotatable
onAfter: @_once => after?.call this, el onAfter: @_once => after?.call this, el
offset: offset offset: offset
}) if $(el).length > 0 }) if $(el).length > 0
afterScrollToProblem: (problem_el) -> afterScrollToProblem: (problem_el) ->
problem_el.effect 'highlight', {}, 500 problem_el.effect 'highlight', {}, 500
......
...@@ -129,7 +129,8 @@ if Backbone? ...@@ -129,7 +129,8 @@ if Backbone?
isPrivilegedUser: DiscussionUtil.isPrivilegedUser() isPrivilegedUser: DiscussionUtil.isPrivilegedUser()
}) })
) )
@$(".forum-nav-sort-control").val(@collection.sort_preference) @$(".forum-nav-sort-control option").removeProp("selected")
@$(".forum-nav-sort-control option[value=#{@collection.sort_preference}]").prop("selected", true)
$(window).bind "load scroll resize", @updateSidebar $(window).bind "load scroll resize", @updateSidebar
...@@ -524,5 +525,3 @@ if Backbone? ...@@ -524,5 +525,3 @@ if Backbone?
type: "POST" type: "POST"
error: () => error: () =>
$('input.email-setting').attr('checked','checked') $('input.email-setting').attr('checked','checked')
...@@ -3,6 +3,7 @@ define([ ...@@ -3,6 +3,7 @@ define([
'edx-ui-toolkit/js/utils/html-utils', 'edx-ui-toolkit/js/utils/html-utils',
'domReady!', 'domReady!',
'jquery', 'jquery',
'jquery-migrate',
'backbone', 'backbone',
'underscore', 'underscore',
'gettext' 'gettext'
......
(function(requirejs, define) { (function(requirejs, define) {
'use strict';
requirejs.config({ requirejs.config({
baseUrl: '/base/', baseUrl: '/base/',
paths: { paths: {
'gettext': 'js/test/i18n', 'gettext': 'js/test/i18n',
'jquery': 'js/vendor/jquery.min', 'jquery': 'common/js/vendor/jquery',
'jquery-migrate': 'common/js/vendor/jquery-migrate',
'jquery.ui': 'js/vendor/jquery-ui.min', 'jquery.ui': 'js/vendor/jquery-ui.min',
'jquery.flot': 'js/vendor/flot/jquery.flot.min', 'jquery.flot': 'js/vendor/flot/jquery.flot.min',
'jquery.form': 'js/vendor/jquery.form', 'jquery.form': 'js/vendor/jquery.form',
...@@ -11,7 +14,7 @@ ...@@ -11,7 +14,7 @@
'jquery.leanModal': 'js/vendor/jquery.leanModal', 'jquery.leanModal': 'js/vendor/jquery.leanModal',
'jquery.ajaxQueue': 'js/vendor/jquery.ajaxQueue', 'jquery.ajaxQueue': 'js/vendor/jquery.ajaxQueue',
'jquery.smoothScroll': 'js/vendor/jquery.smooth-scroll.min', 'jquery.smoothScroll': 'js/vendor/jquery.smooth-scroll.min',
'jquery.scrollTo': 'js/vendor/jquery.scrollTo-1.4.2-min', 'jquery.scrollTo': 'common/js/vendor/jquery.scrollTo',
'jquery.timepicker': 'js/vendor/timepicker/jquery.timepicker', 'jquery.timepicker': 'js/vendor/timepicker/jquery.timepicker',
'jquery.cookie': 'js/vendor/jquery.cookie', 'jquery.cookie': 'js/vendor/jquery.cookie',
'jquery.qtip': 'js/vendor/jquery.qtip.min', 'jquery.qtip': 'js/vendor/jquery.qtip.min',
......
/**
* jQuery.ScrollTo - Easy element scrolling using jQuery.
* Copyright (c) 2007-2009 Ariel Flesler - aflesler(at)gmail(dot)com | http://flesler.blogspot.com
* Dual licensed under MIT and GPL.
* Date: 5/25/2009
* @author Ariel Flesler
* @version 1.4.2
*
* http://flesler.blogspot.com/2007/10/jqueryscrollto.html
*/
;(function(d){var k=d.scrollTo=function(a,i,e){d(window).scrollTo(a,i,e)};k.defaults={axis:'xy',duration:parseFloat(d.fn.jquery)>=1.3?0:1};k.window=function(a){return d(window)._scrollable()};d.fn._scrollable=function(){return this.map(function(){var a=this,i=!a.nodeName||d.inArray(a.nodeName.toLowerCase(),['iframe','#document','html','body'])!=-1;if(!i)return a;var e=(a.contentWindow||a).document||a.ownerDocument||a;return d.browser.safari||e.compatMode=='BackCompat'?e.body:e.documentElement})};d.fn.scrollTo=function(n,j,b){if(typeof j=='object'){b=j;j=0}if(typeof b=='function')b={onAfter:b};if(n=='max')n=9e9;b=d.extend({},k.defaults,b);j=j||b.speed||b.duration;b.queue=b.queue&&b.axis.length>1;if(b.queue)j/=2;b.offset=p(b.offset);b.over=p(b.over);return this._scrollable().each(function(){var q=this,r=d(q),f=n,s,g={},u=r.is('html,body');switch(typeof f){case'number':case'string':if(/^([+-]=)?\d+(\.\d+)?(px|%)?$/.test(f)){f=p(f);break}f=d(f,this);case'object':if(f.is||f.style)s=(f=d(f)).offset()}d.each(b.axis.split(''),function(a,i){var e=i=='x'?'Left':'Top',h=e.toLowerCase(),c='scroll'+e,l=q[c],m=k.max(q,i);if(s){g[c]=s[h]+(u?0:l-r.offset()[h]);if(b.margin){g[c]-=parseInt(f.css('margin'+e))||0;g[c]-=parseInt(f.css('border'+e+'Width'))||0}g[c]+=b.offset[h]||0;if(b.over[h])g[c]+=f[i=='x'?'width':'height']()*b.over[h]}else{var o=f[h];g[c]=o.slice&&o.slice(-1)=='%'?parseFloat(o)/100*m:o}if(/^\d+$/.test(g[c]))g[c]=g[c]<=0?0:Math.min(g[c],m);if(!a&&b.queue){if(l!=g[c])t(b.onAfterFirst);delete g[c]}});t(b.onAfter);function t(a){r.animate(g,j,b.easing,a&&function(){a.call(this,n,b)})}}).end()};k.max=function(a,i){var e=i=='x'?'Width':'Height',h='scroll'+e;if(!d(a).is('html,body'))return a[h]-d(a)[e.toLowerCase()]();var c='client'+e,l=a.ownerDocument.documentElement,m=a.ownerDocument.body;return Math.max(l[h],m[h])-Math.min(l[c],m[c])};function p(a){return typeof a=='object'?a:{top:a,left:a}}})(jQuery);
\ No newline at end of file
...@@ -19,7 +19,8 @@ var options = { ...@@ -19,7 +19,8 @@ var options = {
libraryFilesToInclude: [ libraryFilesToInclude: [
{pattern: 'coffee/src/ajax_prefix.js', included: true}, {pattern: 'coffee/src/ajax_prefix.js', included: true},
{pattern: 'js/vendor/draggabilly.js', included: true}, {pattern: 'js/vendor/draggabilly.js', included: true},
{pattern: 'js/vendor/jquery.min.js', included: true}, {pattern: 'common/js/vendor/jquery.js', included: true},
{pattern: 'common/js/vendor/jquery-migrate.js', included: true},
{pattern: 'coffee/src/jquery.immediateDescendents.js', included: true}, {pattern: 'coffee/src/jquery.immediateDescendents.js', included: true},
{pattern: 'js/vendor/jquery.leanModal.js', included: true}, {pattern: 'js/vendor/jquery.leanModal.js', included: true},
{pattern: 'js/vendor/jquery.timeago.js', included: true}, {pattern: 'js/vendor/jquery.timeago.js', included: true},
......
...@@ -229,10 +229,9 @@ Feature: LMS.Answer problems ...@@ -229,10 +229,9 @@ Feature: LMS.Answer problems
Given I am viewing a "<ProblemType>" problem Given I am viewing a "<ProblemType>" problem
When I answer a "<ProblemType>" problem "<InitialCorrectness>ly" When I answer a "<ProblemType>" problem "<InitialCorrectness>ly"
Then my "<ProblemType>" answer is marked "<InitialCorrectness>" Then my "<ProblemType>" answer is marked "<InitialCorrectness>"
And I input an answer on a "<ProblemType>" problem "<OtherCorrectness>ly" And I reset the problem
Then my "<ProblemType>" answer is NOT marked "<InitialCorrectness>" Then my "<ProblemType>" answer is NOT marked "<InitialCorrectness>"
And my "<ProblemType>" answer is NOT marked "<OtherCorrectness>" And my "<ProblemType>" answer is NOT marked "<OtherCorrectness>"
And I reset the problem
Examples: Examples:
| ProblemType | InitialCorrectness | OtherCorrectness | | ProblemType | InitialCorrectness | OtherCorrectness |
......
...@@ -1240,7 +1240,8 @@ proctoring_js = ( ...@@ -1240,7 +1240,8 @@ proctoring_js = (
# In the future, we will likely refactor this to use # In the future, we will likely refactor this to use
# RequireJS and an optimizer. # RequireJS and an optimizer.
base_vendor_js = [ base_vendor_js = [
'js/vendor/jquery.min.js', 'common/js/vendor/jquery.js',
'common/js/vendor/jquery-migrate.js',
'js/vendor/jquery.cookie.js', 'js/vendor/jquery.cookie.js',
'js/vendor/url.min.js', 'js/vendor/url.min.js',
'common/js/vendor/underscore.js', 'common/js/vendor/underscore.js',
...@@ -1352,14 +1353,16 @@ incourse_reverify_js = [ ...@@ -1352,14 +1353,16 @@ incourse_reverify_js = [
ccx_js = sorted(rooted_glob(PROJECT_ROOT / 'static', 'js/ccx/**/*.js')) ccx_js = sorted(rooted_glob(PROJECT_ROOT / 'static', 'js/ccx/**/*.js'))
certificates_web_view_js = [ certificates_web_view_js = [
'js/vendor/jquery.min.js', 'common/js/vendor/jquery.js',
'common/js/vendor/jquery-migrate.js',
'js/vendor/jquery.cookie.js', 'js/vendor/jquery.cookie.js',
'js/src/logger.js', 'js/src/logger.js',
'js/utils/facebook.js', 'js/utils/facebook.js',
] ]
credit_web_view_js = [ credit_web_view_js = [
'js/vendor/jquery.min.js', 'common/js/vendor/jquery.js',
'common/js/vendor/jquery-migrate.js',
'js/vendor/jquery.cookie.js', 'js/vendor/jquery.cookie.js',
'js/src/logger.js', 'js/src/logger.js',
] ]
......
...@@ -8,9 +8,6 @@ describe 'FeedbackForm', -> ...@@ -8,9 +8,6 @@ describe 'FeedbackForm', ->
spyOn($, 'postWithPrefix').and.callFake (url, data, callback, format) -> spyOn($, 'postWithPrefix').and.callFake (url, data, callback, format) ->
callback() callback()
it 'binds to the #feedback_button', ->
expect($('#feedback_button')).toHandle 'click'
it 'post data to /send_feedback on click', -> it 'post data to /send_feedback on click', ->
$('#feedback_subject').val 'Awesome!' $('#feedback_subject').val 'Awesome!'
$('#feedback_message').val 'This site is really good.' $('#feedback_message').val 'This site is really good.'
......
...@@ -3,12 +3,6 @@ describe 'AutoEnrollment', -> ...@@ -3,12 +3,6 @@ describe 'AutoEnrollment', ->
loadFixtures 'coffee/fixtures/autoenrollment.html' loadFixtures 'coffee/fixtures/autoenrollment.html'
@autoenrollment = new AutoEnrollmentViaCsv $('.auto_enroll_csv') @autoenrollment = new AutoEnrollmentViaCsv $('.auto_enroll_csv')
it 'binds to the enrollment_signup_button on click event', ->
expect(@autoenrollment.$enrollment_signup_button).toHandle 'click'
it 'binds to the browse button on change event', ->
expect(@autoenrollment.$browse_button).toHandle 'change'
it 'binds the ajax call and the result will be success', -> it 'binds the ajax call and the result will be success', ->
spyOn($, "ajax").and.callFake((params) => spyOn($, "ajax").and.callFake((params) =>
params.success({row_errors: [], general_errors: [], warnings: []}) params.success({row_errors: [], general_errors: [], warnings: []})
......
...@@ -15,8 +15,8 @@ ReportDownloads = -> window.InstructorDashboard.util.ReportDownloads ...@@ -15,8 +15,8 @@ ReportDownloads = -> window.InstructorDashboard.util.ReportDownloads
class @DataDownload_Certificate class @DataDownload_Certificate
constructor: (@$container) -> constructor: (@$container) ->
# gather elements # gather elements
@$list_issued_certificate_table_btn = @$container.find("input[name='issued-certificates-list']'") @$list_issued_certificate_table_btn = @$container.find("input[name='issued-certificates-list']")
@$list_issued_certificate_csv_btn = @$container.find("input[name='issued-certificates-csv']'") @$list_issued_certificate_csv_btn = @$container.find("input[name='issued-certificates-csv']")
@$certificate_display_table = @$container.find '.certificate-data-display-table' @$certificate_display_table = @$container.find '.certificate-data-display-table'
@$certificates_request_response_error = @$container.find '.issued-certificates-error.request-response-error' @$certificates_request_response_error = @$container.find '.issued-certificates-error.request-response-error'
...@@ -72,18 +72,18 @@ class DataDownload ...@@ -72,18 +72,18 @@ class DataDownload
new DataDownload_Certificate @$section.find '.issued_certificates' new DataDownload_Certificate @$section.find '.issued_certificates'
# gather elements # gather elements
@$list_studs_btn = @$section.find("input[name='list-profiles']'") @$list_studs_btn = @$section.find("input[name='list-profiles']")
@$list_studs_csv_btn = @$section.find("input[name='list-profiles-csv']'") @$list_studs_csv_btn = @$section.find("input[name='list-profiles-csv']")
@$list_proctored_exam_results_csv_btn = @$section.find("input[name='proctored-exam-results-report']'") @$list_proctored_exam_results_csv_btn = @$section.find("input[name='proctored-exam-results-report']")
@$survey_results_csv_btn = @$section.find("input[name='survey-results-report']'") @$survey_results_csv_btn = @$section.find("input[name='survey-results-report']")
@$list_may_enroll_csv_btn = @$section.find("input[name='list-may-enroll-csv']") @$list_may_enroll_csv_btn = @$section.find("input[name='list-may-enroll-csv']")
@$list_problem_responses_csv_input = @$section.find("input[name='problem-location']") @$list_problem_responses_csv_input = @$section.find("input[name='problem-location']")
@$list_problem_responses_csv_btn = @$section.find("input[name='list-problem-responses-csv']") @$list_problem_responses_csv_btn = @$section.find("input[name='list-problem-responses-csv']")
@$list_anon_btn = @$section.find("input[name='list-anon-ids']'") @$list_anon_btn = @$section.find("input[name='list-anon-ids']")
@$grade_config_btn = @$section.find("input[name='dump-gradeconf']'") @$grade_config_btn = @$section.find("input[name='dump-gradeconf']")
@$calculate_grades_csv_btn = @$section.find("input[name='calculate-grades-csv']'") @$calculate_grades_csv_btn = @$section.find("input[name='calculate-grades-csv']")
@$problem_grade_report_csv_btn = @$section.find("input[name='problem-grade-report']'") @$problem_grade_report_csv_btn = @$section.find("input[name='problem-grade-report']")
@$async_report_btn = @$section.find("input[class='async-report-btn']'") @$async_report_btn = @$section.find("input[class='async-report-btn']")
# response areas # response areas
@$download = @$section.find '.data-download-container' @$download = @$section.find '.data-download-container'
......
...@@ -13,10 +13,10 @@ class ECommerce ...@@ -13,10 +13,10 @@ class ECommerce
# this object to call event handlers like 'onClickTitle' # this object to call event handlers like 'onClickTitle'
@$section.data 'wrapper', @ @$section.data 'wrapper', @
# gather elements # gather elements
@$list_sale_csv_btn = @$section.find("input[name='list-sale-csv']'") @$list_sale_csv_btn = @$section.find("input[name='list-sale-csv']")
@$list_order_sale_csv_btn = @$section.find("input[name='list-order-sale-csv']'") @$list_order_sale_csv_btn = @$section.find("input[name='list-order-sale-csv']")
@$download_company_name = @$section.find("input[name='download_company_name']'") @$download_company_name = @$section.find("input[name='download_company_name']")
@$active_company_name = @$section.find("input[name='active_company_name']'") @$active_company_name = @$section.find("input[name='active_company_name']")
@$spent_company_name = @$section.find('input[name="spent_company_name"]') @$spent_company_name = @$section.find('input[name="spent_company_name"]')
@$download_coupon_codes = @$section.find('input[name="download-coupon-codes-csv"]') @$download_coupon_codes = @$section.find('input[name="download-coupon-codes-csv"]')
...@@ -89,4 +89,4 @@ class ECommerce ...@@ -89,4 +89,4 @@ class ECommerce
_.defaults window, InstructorDashboard: {} _.defaults window, InstructorDashboard: {}
_.defaults window.InstructorDashboard, sections: {} _.defaults window.InstructorDashboard, sections: {}
_.defaults window.InstructorDashboard.sections, _.defaults window.InstructorDashboard.sections,
ECommerce: ECommerce ECommerce: ECommerce
\ No newline at end of file
...@@ -19,15 +19,15 @@ class SendEmail ...@@ -19,15 +19,15 @@ class SendEmail
constructor: (@$container) -> constructor: (@$container) ->
# gather elements # gather elements
@$emailEditor = XBlock.initializeBlock($('.xblock-studio_view')); @$emailEditor = XBlock.initializeBlock($('.xblock-studio_view'));
@$send_to = @$container.find("select[name='send_to']'") @$send_to = @$container.find("select[name='send_to']")
@$subject = @$container.find("input[name='subject']'") @$subject = @$container.find("input[name='subject']")
@$btn_send = @$container.find("input[name='send']'") @$btn_send = @$container.find("input[name='send']")
@$task_response = @$container.find(".request-response") @$task_response = @$container.find(".request-response")
@$request_response_error = @$container.find(".request-response-error") @$request_response_error = @$container.find(".request-response-error")
@$content_request_response_error = @$container.find(".content-request-response-error") @$content_request_response_error = @$container.find(".content-request-response-error")
@$history_request_response_error = @$container.find(".history-request-response-error") @$history_request_response_error = @$container.find(".history-request-response-error")
@$btn_task_history_email = @$container.find("input[name='task-history-email']'") @$btn_task_history_email = @$container.find("input[name='task-history-email']")
@$btn_task_history_email_content = @$container.find("input[name='task-history-email-content']'") @$btn_task_history_email_content = @$container.find("input[name='task-history-email-content']")
@$table_task_history_email = @$container.find(".task-history-email-table") @$table_task_history_email = @$container.find(".task-history-email-table")
@$table_email_content_history = @$container.find(".content-history-email-table") @$table_email_content_history = @$container.find(".content-history-email-table")
@$email_content_table_inner = @$container.find(".content-history-table-inner") @$email_content_table_inner = @$container.find(".content-history-table-inner")
......
...@@ -32,7 +32,7 @@ $ -> ...@@ -32,7 +32,7 @@ $ ->
# fix for ie # fix for ie
if !Array::indexOf if !Array::indexOf
Array::indexOf = (obj, start = 0) -> Array::indexOf = (obj, start = 0) ->
for ele, i in this[start..] for ele, i in this[start..]
if ele is obj if ele is obj
return i + start return i + start
return -1 return -1
...@@ -6,23 +6,6 @@ define([ ...@@ -6,23 +6,6 @@ define([
var _t = Annotator._t; var _t = Annotator._t;
/** /**
* We currently run JQuery 1.7.2 in Jasmine tests and LMS.
* AnnotatorJS 1.2.9. uses two calls to addBack (in the two functions
* 'isAnnotator' and 'onHighlightMouseover') which was only defined in
* JQuery 1.8.0. In LMS, it works without throwing an error because
* JQuery.UI 1.10.0 adds support to jQuery<1.8 by augmenting '$.fn' with
* that missing function. It is not the case for all Jasmine unit tests,
* so we add it here if necessary.
**/
if (!$.fn.addBack) {
$.fn.addBack = function (selector) {
return this.add(
selector === null ? this.prevObject : this.prevObject.filter(selector)
);
};
}
/**
* The original _setupDynamicStyle uses a very expensive call to * The original _setupDynamicStyle uses a very expensive call to
* Util.maxZIndex(...) that sets the z-index of .annotator-adder, * Util.maxZIndex(...) that sets the z-index of .annotator-adder,
* .annotator-outer, .annotator-notice, .annotator-filter. We set these * .annotator-outer, .annotator-notice, .annotator-filter. We set these
......
...@@ -56,7 +56,7 @@ ...@@ -56,7 +56,7 @@
if (!groupsEnabled) { if (!groupsEnabled) {
// If the user has chosen 'no', then clear the selection by setting // If the user has chosen 'no', then clear the selection by setting
// it to the first option which represents no selection. // it to the first option which represents no selection.
this.$('.input-cohort-group-association').val('None'); this.$('.input-cohort-group-association').val(null);
} }
// Enable the select if the user has chosen groups, else disable it // Enable the select if the user has chosen groups, else disable it
this.$('.input-cohort-group-association').prop('disabled', !groupsEnabled); this.$('.input-cohort-group-association').prop('disabled', !groupsEnabled);
...@@ -69,7 +69,7 @@ ...@@ -69,7 +69,7 @@
getSelectedContentGroup: function() { getSelectedContentGroup: function() {
var selectValue = this.$('.input-cohort-group-association').val(), var selectValue = this.$('.input-cohort-group-association').val(),
ids, groupId, userPartitionId, i, contentGroup; ids, groupId, userPartitionId, i, contentGroup;
if (!this.hasAssociatedContentGroup() || selectValue === 'None') { if (!this.hasAssociatedContentGroup() || _.isNull(selectValue)) {
return null; return null;
} }
ids = selectValue.split(':'); ids = selectValue.split(':');
...@@ -107,7 +107,7 @@ ...@@ -107,7 +107,7 @@
errorMessages.push(gettext('You must specify a name for the cohort')); errorMessages.push(gettext('You must specify a name for the cohort'));
} }
if (this.hasAssociatedContentGroup() && fieldData.group_id === null) { if (this.hasAssociatedContentGroup() && fieldData.group_id === null) {
if (this.$('.input-cohort-group-association').val() === 'None') { if (_.isNull(this.$('.input-cohort-group-association').val())) {
errorMessages.push(gettext('You did not select a content group')); errorMessages.push(gettext('You did not select a content group'));
} else { } else {
// If a value was selected, then it must be for a non-existent/deleted content group // If a value was selected, then it must be for a non-existent/deleted content group
......
...@@ -17,12 +17,18 @@ var edx = edx || {}; ...@@ -17,12 +17,18 @@ var edx = edx || {};
}, },
clicked: function (event) { clicked: function (event) {
if (event.currentTarget.checked) { if (event.currentTarget.checked) {
this.$el.find('#coupon_expiration_date').show(); this.show(this.$('#coupon_expiration_date'));
this.$el.find('#coupon_expiration_date').focus(); this.$el.find('#coupon_expiration_date').focus();
} }
else { else {
this.$el.find('#coupon_expiration_date').hide(); this.hide(this.$('#coupon_expiration_date'));
} }
},
show: function ($el) {
$el.css('display', 'inline');
},
hide: function ($el) {
$el.css('display', 'none');
} }
}); });
......
define(['jquery', 'logger', 'js/courseware/toggle_element_visibility'], define(['jquery', 'logger', 'js/courseware/toggle_element_visibility', 'moment'],
function ($, Logger, ToggleElementVisibility) { function ($, Logger, ToggleElementVisibility, moment) {
'use strict'; 'use strict';
describe('show/hide with mouse click', function () { describe('show/hide with mouse click', function () {
...@@ -43,7 +43,7 @@ define(['jquery', 'logger', 'js/courseware/toggle_element_visibility'], ...@@ -43,7 +43,7 @@ define(['jquery', 'logger', 'js/courseware/toggle_element_visibility'],
$update.siblings('.toggle-visibility-button').trigger('click'); $update.siblings('.toggle-visibility-button').trigger('click');
expect(Logger.log).toHaveBeenCalledWith('edx.course.home.course_update.toggled', { expect(Logger.log).toHaveBeenCalledWith('edx.course.home.course_update.toggled', {
action: 'hide', action: 'hide',
publish_date: '2015-12-01T00:00:00+00:00' publish_date: moment('December 1, 2015', 'MMM DD, YYYY').format()
}); });
}); });
}); });
......
...@@ -107,6 +107,12 @@ define([ ...@@ -107,6 +107,12 @@ define([
'templates/discovery/filter_bar' 'templates/discovery/filter_bar'
]); ]);
DiscoveryFactory(MEANINGS); DiscoveryFactory(MEANINGS);
jasmine.clock().install();
});
afterEach(function () {
jasmine.clock().uninstall();
}); });
it('does search', function () { it('does search', function () {
...@@ -121,22 +127,20 @@ define([ ...@@ -121,22 +127,20 @@ define([
it('loads more', function () { it('loads more', function () {
var requests = AjaxHelpers.requests(this); var requests = AjaxHelpers.requests(this);
jasmine.clock().install();
$('.discovery-input').val('test'); $('.discovery-input').val('test');
$('.discovery-submit').trigger('click'); $('.discovery-submit').trigger('click');
AjaxHelpers.respondWithJson(requests, JSON_RESPONSE); AjaxHelpers.respondWithJson(requests, JSON_RESPONSE);
expect($('.courses-listing article').length).toEqual(1); expect($('.courses-listing article').length).toEqual(1);
expect($('.courses-listing .course-title')).toContainHtml('edX Demonstration Course'); expect($('.courses-listing .course-title')).toContainHtml('edX Demonstration Course');
jasmine.clock().tick(500);
window.scroll(0, $(document).height()); window.scroll(0, $(document).height());
$(window).trigger('scroll'); $(window).trigger('scroll');
jasmine.clock().tick(500);
// TODO: determine why the search API is invoked twice // TODO: determine why the search API is invoked twice
AjaxHelpers.respondWithJson(requests, JSON_RESPONSE); AjaxHelpers.respondWithJson(requests, JSON_RESPONSE);
AjaxHelpers.respondWithJson(requests, JSON_RESPONSE); AjaxHelpers.respondWithJson(requests, JSON_RESPONSE);
expect($('.courses-listing article').length).toEqual(2); expect($('.courses-listing article').length).toEqual(2);
jasmine.clock().uninstall();
}); });
it('displays not found message', function () { it('displays not found message', function () {
......
...@@ -223,7 +223,7 @@ define(['backbone', 'jquery', 'common/js/spec_helpers/ajax_helpers', 'common/js/ ...@@ -223,7 +223,7 @@ define(['backbone', 'jquery', 'common/js/spec_helpers/ajax_helpers', 'common/js/
clearContentGroup = function() { clearContentGroup = function() {
cohortsView.$('.radio-no').prop('checked', true).change(); cohortsView.$('.radio-no').prop('checked', true).change();
expect(cohortsView.$('.input-cohort-group-association').prop('disabled')).toBeTruthy(); expect(cohortsView.$('.input-cohort-group-association').prop('disabled')).toBeTruthy();
expect(cohortsView.$('.input-cohort-group-association').val()).toBe('None'); expect(cohortsView.$('.input-cohort-group-association').val()).toBe(null);
}; };
verifyMessage = function(expectedTitle, expectedMessageType, expectedAction, hasDetails) { verifyMessage = function(expectedTitle, expectedMessageType, expectedAction, hasDetails) {
......
...@@ -22,7 +22,6 @@ define(['backbone', 'jquery', 'js/instructor_dashboard/ecommerce'], ...@@ -22,7 +22,6 @@ define(['backbone', 'jquery', 'js/instructor_dashboard/ecommerce'],
it("shows the input field when the checkbox is checked", function () { it("shows the input field when the checkbox is checked", function () {
var target = expiryCouponView.$el.find('input[type="checkbox"]'); var target = expiryCouponView.$el.find('input[type="checkbox"]');
target.attr("checked","checked");
target.click(); target.click();
expect(expiryCouponView.$el.find('#coupon_expiration_date').is(':visible')).toBe(true); expect(expiryCouponView.$el.find('#coupon_expiration_date').is(':visible')).toBe(true);
}); });
...@@ -30,7 +29,6 @@ define(['backbone', 'jquery', 'js/instructor_dashboard/ecommerce'], ...@@ -30,7 +29,6 @@ define(['backbone', 'jquery', 'js/instructor_dashboard/ecommerce'],
it("hides the input field when the checkbox is unchecked", function () { it("hides the input field when the checkbox is unchecked", function () {
var target = expiryCouponView.$el.find('input[type="checkbox"]'); var target = expiryCouponView.$el.find('input[type="checkbox"]');
expect(expiryCouponView.$el.find('#coupon_expiration_date')).toHaveAttr('style','display: none;'); expect(expiryCouponView.$el.find('#coupon_expiration_date')).toHaveAttr('style','display: none;');
}); });
}); });
}); });
...@@ -8,7 +8,8 @@ ...@@ -8,7 +8,8 @@
paths: { paths: {
'gettext': 'xmodule_js/common_static/js/test/i18n', 'gettext': 'xmodule_js/common_static/js/test/i18n',
'codemirror': 'xmodule_js/common_static/js/vendor/CodeMirror/codemirror', 'codemirror': 'xmodule_js/common_static/js/vendor/CodeMirror/codemirror',
'jquery': 'xmodule_js/common_static/js/vendor/jquery.min', 'jquery': 'xmodule_js/common_static/common/js/vendor/jquery',
'jquery-migrate': 'xmodule_js/common_static/common/js/vendor/jquery-migrate',
'jquery.ui': 'xmodule_js/common_static/js/vendor/jquery-ui.min', 'jquery.ui': 'xmodule_js/common_static/js/vendor/jquery-ui.min',
'jquery.eventDrag': 'xmodule_js/common_static/js/vendor/jquery.event.drag-2.2', 'jquery.eventDrag': 'xmodule_js/common_static/js/vendor/jquery.event.drag-2.2',
'jquery.flot': 'xmodule_js/common_static/js/vendor/flot/jquery.flot.min', 'jquery.flot': 'xmodule_js/common_static/js/vendor/flot/jquery.flot.min',
...@@ -18,7 +19,7 @@ ...@@ -18,7 +19,7 @@
'jquery.ajaxQueue': 'xmodule_js/common_static/js/vendor/jquery.ajaxQueue', 'jquery.ajaxQueue': 'xmodule_js/common_static/js/vendor/jquery.ajaxQueue',
'jquery.ajax-retry': 'js/vendor/jquery.ajax-retry', 'jquery.ajax-retry': 'js/vendor/jquery.ajax-retry',
'jquery.smoothScroll': 'xmodule_js/common_static/js/vendor/jquery.smooth-scroll.min', 'jquery.smoothScroll': 'xmodule_js/common_static/js/vendor/jquery.smooth-scroll.min',
'jquery.scrollTo': 'xmodule_js/common_static/js/vendor/jquery.scrollTo-1.4.2-min', 'jquery.scrollTo': 'common/js/vendor/jquery.scrollTo',
'jquery.timepicker': 'xmodule_js/common_static/js/vendor/timepicker/jquery.timepicker', 'jquery.timepicker': 'xmodule_js/common_static/js/vendor/timepicker/jquery.timepicker',
'jquery.cookie': 'xmodule_js/common_static/js/vendor/jquery.cookie', 'jquery.cookie': 'xmodule_js/common_static/js/vendor/jquery.cookie',
'jquery.qtip': 'xmodule_js/common_static/js/vendor/jquery.qtip.min', 'jquery.qtip': 'xmodule_js/common_static/js/vendor/jquery.qtip.min',
...@@ -92,7 +93,7 @@ ...@@ -92,7 +93,7 @@
// Discussion classes loaded explicitly until they are converted to use RequireJS // Discussion classes loaded explicitly until they are converted to use RequireJS
'DiscussionModuleView': 'xmodule_js/common_static/coffee/src/discussion/discussion_module_view', 'DiscussionModuleView': 'xmodule_js/common_static/coffee/src/discussion/discussion_module_view',
'js/bookmarks/collections/bookmarks': 'js/bookmarks/collections/bookmarks', 'js/bookmarks/collections/bookmarks': 'js/bookmarks/collections/bookmarks',
'js/bookmarks/models/bookmark': 'js/bookmarks/models/bookmark', 'js/bookmarks/models/bookmark': 'js/bookmarks/models/bookmark',
'js/bookmarks/views/bookmarks_list_button': 'js/bookmarks/views/bookmarks_list_button', 'js/bookmarks/views/bookmarks_list_button': 'js/bookmarks/views/bookmarks_list_button',
...@@ -119,6 +120,7 @@ ...@@ -119,6 +120,7 @@
'date': { 'date': {
exports: 'Date' exports: 'Date'
}, },
"jquery-migrate": ['jquery'],
'jquery.ui': { 'jquery.ui': {
deps: ['jquery'], deps: ['jquery'],
exports: 'jQuery.ui' exports: 'jQuery.ui'
...@@ -289,6 +291,10 @@ ...@@ -289,6 +291,10 @@
exports: 'coffee/src/instructor_dashboard/student_admin', exports: 'coffee/src/instructor_dashboard/student_admin',
deps: ['jquery', 'underscore', 'coffee/src/instructor_dashboard/util', 'string_utils'] deps: ['jquery', 'underscore', 'coffee/src/instructor_dashboard/util', 'string_utils']
}, },
'coffee/src/instructor_dashboard/util': {
exports: 'coffee/src/instructor_dashboard/util',
deps: ['jquery', 'underscore', 'slick.core', 'slick.grid']
},
'js/instructor_dashboard/certificates': { 'js/instructor_dashboard/certificates': {
exports: 'js/instructor_dashboard/certificates', exports: 'js/instructor_dashboard/certificates',
deps: ['jquery', 'gettext', 'underscore'] deps: ['jquery', 'gettext', 'underscore']
...@@ -492,6 +498,14 @@ ...@@ -492,6 +498,14 @@
exports: 'Annotator', exports: 'Annotator',
deps: ['jquery'] deps: ['jquery']
}, },
'slick.core': {
deps: ['jquery'],
exports: 'Slick'
},
'slick.grid': {
deps: ['jquery', 'jquery.eventDrag', 'slick.core'],
exports: 'Slick'
},
// Discussions // Discussions
'xmodule_js/common_static/coffee/src/discussion/utils': { 'xmodule_js/common_static/coffee/src/discussion/utils': {
deps: [ deps: [
......
...@@ -132,6 +132,7 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers ...@@ -132,6 +132,7 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers
}); });
it("expects all fields to behave correctly", function () { it("expects all fields to behave correctly", function () {
var i, view;
requests = AjaxHelpers.requests(this); requests = AjaxHelpers.requests(this);
...@@ -146,9 +147,8 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers ...@@ -146,9 +147,8 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers
expect(sectionsData[0].fields.length).toBe(6); expect(sectionsData[0].fields.length).toBe(6);
var textFields = [sectionsData[0].fields[1], sectionsData[0].fields[2]]; var textFields = [sectionsData[0].fields[1], sectionsData[0].fields[2]];
for (var i = 0; i < textFields.length ; i++) { for (i = 0; i < textFields.length ; i++) {
view = textFields[i].view;
var view = textFields[i].view;
FieldViewsSpecHelpers.verifyTextField(view, { FieldViewsSpecHelpers.verifyTextField(view, {
title: view.options.title, title: view.options.title,
valueAttribute: view.options.valueAttribute, valueAttribute: view.options.valueAttribute,
......
...@@ -3,13 +3,14 @@ ...@@ -3,13 +3,14 @@
define([ define([
'jquery', 'jquery',
'underscore', 'underscore',
'sinon',
'common/js/spec_helpers/template_helpers', 'common/js/spec_helpers/template_helpers',
'common/js/spec_helpers/ajax_helpers', 'common/js/spec_helpers/ajax_helpers',
'js/student_account/models/LoginModel', 'js/student_account/models/LoginModel',
'js/student_account/views/LoginView', 'js/student_account/views/LoginView',
'js/student_account/models/PasswordResetModel' 'js/student_account/models/PasswordResetModel'
], ],
function($, _, TemplateHelpers, AjaxHelpers, LoginModel, LoginView, PasswordResetModel) { function($, _, sinon, TemplateHelpers, AjaxHelpers, LoginModel, LoginView, PasswordResetModel) {
describe('edx.student.account.LoginView', function() { describe('edx.student.account.LoginView', function() {
var model = null, var model = null,
...@@ -267,13 +268,25 @@ ...@@ -267,13 +268,25 @@
}); });
it('displays an error if there is no internet connection', function () { it('displays an error if there is no internet connection', function () {
var clock,
oldTimeout,
timeout;
// We're defining "no internet connection" in this case as the
// request timing out. We use a combination of the sinon fake
// timer and jQuery.ajaxSetup() to force a request timeout.
clock = sinon.useFakeTimers();
oldTimeout = $.ajaxSetup().timeout;
timeout = 1;
$.ajaxSetup({timeout: timeout});
createLoginView(this); createLoginView(this);
// Submit the form, with successful validation // Submit the form, with successful validation
submitForm(true); submitForm(true);
// Simulate an error from the LMS servers // Simulate a request timeout
AjaxHelpers.respondWithError(requests, 0); clock.tick(timeout + 1);
// Expect that an error is displayed and that auth complete is not triggered // Expect that an error is displayed and that auth complete is not triggered
expect(view.$errors).not.toHaveClass('hidden'); expect(view.$errors).not.toHaveClass('hidden');
...@@ -281,7 +294,12 @@ ...@@ -281,7 +294,12 @@
expect(view.$errors.text()).toContain( expect(view.$errors.text()).toContain(
'An error has occurred. Check your Internet connection and try again.' 'An error has occurred. Check your Internet connection and try again.'
); );
// Finally, restore the old timeout and turn off the fake timer.
$.ajaxSetup({timeout: oldTimeout});
clock.restore();
}); });
it('displays an error if there is a server error', function () { it('displays an error if there is a server error', function () {
createLoginView(this); createLoginView(this);
......
...@@ -54,6 +54,11 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers ...@@ -54,6 +54,11 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers
TemplateHelpers.installTemplate("templates/fields/message_banner"); TemplateHelpers.installTemplate("templates/fields/message_banner");
}); });
afterEach(function () {
// image_field.js's window.onBeforeUnload breaks Karma in Chrome, clean it up after each test
$(window).off('beforeunload');
});
var createFakeImageFile = function (size) { var createFakeImageFile = function (size) {
var fileFakeData = 'i63ljc6giwoskyb9x5sw0169bdcmcxr3cdz8boqv0lik971972cmd6yknvcxr5sw0nvc169bdcmcxsdf'; var fileFakeData = 'i63ljc6giwoskyb9x5sw0169bdcmcxr3cdz8boqv0lik971972cmd6yknvcxr5sw0nvc169bdcmcxsdf';
return new Blob( return new Blob(
...@@ -260,6 +265,7 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers ...@@ -260,6 +265,7 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers
// Verify image upload progress message // Verify image upload progress message
verifyImageUploadButtonMessage(imageView, true); verifyImageUploadButtonMessage(imageView, true);
window.onbeforeunload = null;
$(window).trigger('beforeunload'); $(window).trigger('beforeunload');
expect(imageView.onBeforeUnload).toHaveBeenCalled(); expect(imageView.onBeforeUnload).toHaveBeenCalled();
}); });
......
...@@ -42,7 +42,7 @@ define([ ...@@ -42,7 +42,7 @@ define([
// Simulate the server response // Simulate the server response
if ( succeeds ) { if ( succeeds ) {
AjaxHelpers.respondWithJson( requests, {} ); AjaxHelpers.respondWithJson( requests, {url: '/arbitrary-url/'} );
} else { } else {
AjaxHelpers.respondWithTextError( requests, 400, SERVER_ERROR_MSG ); AjaxHelpers.respondWithTextError( requests, 400, SERVER_ERROR_MSG );
} }
......
...@@ -240,8 +240,8 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers ...@@ -240,8 +240,8 @@ define(['backbone', 'jquery', 'underscore', 'common/js/spec_helpers/ajax_helpers
verifyEditableField(view, _.extend({ verifyEditableField(view, _.extend({
valueSelector: '.u-field-value', valueSelector: '.u-field-value',
valueInputSelector: '.u-field-value > input' valueInputSelector: '.u-field-value > input'
}, data }, data),
), requests); requests);
}; };
var verifyDropDownField = function (view, data, requests) { var verifyDropDownField = function (view, data, requests) {
......
...@@ -28,7 +28,7 @@ ...@@ -28,7 +28,7 @@
}, },
parse : function(response) { parse : function(response) {
if (_.isNull(response)) { if (_.isNull(response) || _.isUndefined(response)) {
return {}; return {};
} }
......
...@@ -78,7 +78,8 @@ ...@@ -78,7 +78,8 @@
$(this.el).show(); // Show in case the form was hidden for auto-submission $(this.el).show(); // Show in case the form was hidden for auto-submission
this.errors = _.flatten( this.errors = _.flatten(
_.map( _.map(
JSON.parse(error.responseText), // Something is passing this 'undefined'. Protect against this.
JSON.parse(error.responseText || "[]"),
function(error_list) { function(error_list) {
return _.map( return _.map(
error_list, error_list,
......
...@@ -218,13 +218,13 @@ ...@@ -218,13 +218,13 @@
this.backend = this.backends[obj.backendName] || obj.backend; this.backend = this.backends[obj.backendName] || obj.backend;
this.captureSoundPath = obj.captureSoundPath || ""; this.captureSoundPath = obj.captureSoundPath || "";
_.extend( this.backend, Backbone.Events );
this.backend.initialize({ this.backend.initialize({
wrapper: "#camera", wrapper: "#camera",
video: '#photo_id_video', video: '#photo_id_video',
canvas: '#photo_id_canvas' canvas: '#photo_id_canvas'
}); });
_.extend( this.backend, Backbone.Events );
this.listenTo( this.backend, 'error', this.handleError ); this.listenTo( this.backend, 'error', this.handleError );
this.listenTo( this.backend, 'webcam-loaded', this.handleWebcamLoaded ); this.listenTo( this.backend, 'webcam-loaded', this.handleWebcamLoaded );
}, },
......
...@@ -13,6 +13,8 @@ var options = { ...@@ -13,6 +13,8 @@ var options = {
// Avoid adding files to this list. Use RequireJS. // Avoid adding files to this list. Use RequireJS.
libraryFilesToInclude: [ libraryFilesToInclude: [
{pattern: 'common/js/vendor/jquery.js', included: true},
{pattern: 'common/js/vendor/jquery-migrate.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/jquery.event.drag-2.2.js', included: true}, {pattern: 'xmodule_js/common_static/js/vendor/jquery.event.drag-2.2.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/slick.core.js', included: true}, {pattern: 'xmodule_js/common_static/js/vendor/slick.core.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/slick.grid.js', included: true} {pattern: 'xmodule_js/common_static/js/vendor/slick.grid.js', included: true}
......
...@@ -25,7 +25,8 @@ var options = { ...@@ -25,7 +25,8 @@ var options = {
{pattern: 'xmodule_js/common_static/js/src/logger.js', included: true}, {pattern: 'xmodule_js/common_static/js/src/logger.js', included: true},
{pattern: 'xmodule_js/common_static/js/test/i18n.js', included: true}, {pattern: 'xmodule_js/common_static/js/test/i18n.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/CodeMirror/codemirror.js', included: true}, {pattern: 'xmodule_js/common_static/js/vendor/CodeMirror/codemirror.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/jquery.min.js', included: true}, {pattern: 'common/js/vendor/jquery.js', included: true},
{pattern: 'common/js/vendor/jquery-migrate.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/jquery.cookie.js', included: true}, {pattern: 'xmodule_js/common_static/js/vendor/jquery.cookie.js', included: true},
{pattern: 'xmodule_js/common_static/js/vendor/flot/jquery.flot.js', included: true}, {pattern: 'xmodule_js/common_static/js/vendor/flot/jquery.flot.js', included: true},
{pattern: 'xmodule_js/common_static/coffee/src/jquery.immediateDescendents.js', included: true}, {pattern: 'xmodule_js/common_static/coffee/src/jquery.immediateDescendents.js', included: true},
......
...@@ -66,6 +66,7 @@ ...@@ -66,6 +66,7 @@
'gettext': 'empty:', 'gettext': 'empty:',
'coffee/src/ajax_prefix': 'empty:', 'coffee/src/ajax_prefix': 'empty:',
'jquery': 'empty:', 'jquery': 'empty:',
'jquery-migrate': 'empty:',
'jquery.cookie': 'empty:', 'jquery.cookie': 'empty:',
'jquery.url': 'empty:', 'jquery.url': 'empty:',
'backbone': 'empty:', 'backbone': 'empty:',
......
...@@ -28,6 +28,7 @@ ...@@ -28,6 +28,7 @@
} }
}; };
defineDependency("jQuery", "jquery"); defineDependency("jQuery", "jquery");
defineDependency("jQuery", "jquery-migrate");
defineDependency("_", "underscore"); defineDependency("_", "underscore");
defineDependency("s", "underscore.string"); defineDependency("s", "underscore.string");
// Underscore.string no longer installs itself directly on "_". For compatibility with existing // Underscore.string no longer installs itself directly on "_". For compatibility with existing
...@@ -64,7 +65,13 @@ ...@@ -64,7 +65,13 @@
"backbone.paginator": "js/vendor/backbone.paginator.min", "backbone.paginator": "js/vendor/backbone.paginator.min",
"underscore": "common/js/vendor/underscore", "underscore": "common/js/vendor/underscore",
"underscore.string": "common/js/vendor/underscore.string", "underscore.string": "common/js/vendor/underscore.string",
"jquery": "js/vendor/jquery.min", // The jquery-migrate library was added in upgrading from
// jQuery 1.7.x to 2.2.x. This config allows developers
// to depend on "jquery" which opaquely requires both
// libraries.
"jquery": "common/js/vendor/jquery",
"jquery-migrate": "common/js/vendor/jquery-migrate",
"jquery.scrollTo": "common/js/vendor/jquery.scrollTo",
"jquery.cookie": "js/vendor/jquery.cookie", "jquery.cookie": "js/vendor/jquery.cookie",
'jquery.timeago': 'js/vendor/jquery.timeago', 'jquery.timeago': 'js/vendor/jquery.timeago',
"jquery.url": "js/vendor/url.min", "jquery.url": "js/vendor/url.min",
...@@ -111,6 +118,10 @@ ...@@ -111,6 +118,10 @@
"date": { "date": {
exports: "Date" exports: "Date"
}, },
"jquery": {
exports: "jQuery"
},
"jquery-migrate": ['jquery'],
"jquery.cookie": { "jquery.cookie": {
deps: ["jquery"], deps: ["jquery"],
exports: "jQuery.fn.cookie" exports: "jQuery.fn.cookie"
......
...@@ -45,7 +45,7 @@ ${static.get_page_title_breadcrumbs(course_name())} ...@@ -45,7 +45,7 @@ ${static.get_page_title_breadcrumbs(course_name())}
</%block> </%block>
<%block name="js_extra"> <%block name="js_extra">
<script type="text/javascript" src="${static.url('js/vendor/jquery.scrollTo-1.4.2-min.js')}"></script> <script type="text/javascript" src="${static.url('common/js/vendor/jquery.scrollTo.js')}"></script>
<script type="text/javascript" src="${static.url('js/vendor/flot/jquery.flot.js')}"></script> <script type="text/javascript" src="${static.url('js/vendor/flot/jquery.flot.js')}"></script>
## codemirror ## codemirror
......
...@@ -65,7 +65,7 @@ ${static.get_page_title_breadcrumbs(course_name())} ...@@ -65,7 +65,7 @@ ${static.get_page_title_breadcrumbs(course_name())}
</%block> </%block>
<%block name="js_extra"> <%block name="js_extra">
<script type="text/javascript" src="${static.url('js/vendor/jquery.scrollTo-1.4.2-min.js')}"></script> <script type="text/javascript" src="${static.url('common/js/vendor/jquery.scrollTo.js')}"></script>
<script type="text/javascript" src="${static.url('js/vendor/flot/jquery.flot.js')}"></script> <script type="text/javascript" src="${static.url('js/vendor/flot/jquery.flot.js')}"></script>
## codemirror ## codemirror
......
...@@ -21,7 +21,7 @@ ...@@ -21,7 +21,7 @@
</body> </body>
</html> </html>
<script type="text/javascript" src="${static.url('js/vendor/jquery.min.js')}"></script> <script type="text/javascript" src="${static.url('common/js/vendor/jquery.js')}"></script>
<script type="text/javascript"> <script type="text/javascript">
$(document).ready(function() { $(document).ready(function() {
......
...@@ -2,15 +2,18 @@ ...@@ -2,15 +2,18 @@
"name": "edx", "name": "edx",
"version": "0.1.0", "version": "0.1.0",
"dependencies": { "dependencies": {
"backbone": "~1.3.2",
"coffee-script": "1.6.1", "coffee-script": "1.6.1",
"edx-pattern-library": "~0.12.4", "edx-pattern-library": "~0.12.4",
"edx-ui-toolkit": "~0.9.1", "edx-ui-toolkit": "~0.9.1",
"jquery": "~2.2.0",
"jquery-migrate": "^1.4.1",
"jquery.scrollto": "~2.1.2",
"picturefill": "~3.0.2",
"requirejs": "~2.1.22", "requirejs": "~2.1.22",
"uglify-js": "2.4.24", "uglify-js": "2.4.24",
"underscore": "~1.8.3", "underscore": "~1.8.3",
"underscore.string": "~3.3.4", "underscore.string": "~3.3.4"
"picturefill": "~3.0.2",
"backbone": "~1.3.2"
}, },
"devDependencies": { "devDependencies": {
"edx-custom-a11y-rules": "edx/edx-custom-a11y-rules", "edx-custom-a11y-rules": "edx/edx-custom-a11y-rules",
......
...@@ -45,6 +45,9 @@ SASS_LOAD_PATHS = [ ...@@ -45,6 +45,9 @@ SASS_LOAD_PATHS = [
# A list of NPM installed libraries that should be copied into the common # A list of NPM installed libraries that should be copied into the common
# static directory. # static directory.
NPM_INSTALLED_LIBRARIES = [ NPM_INSTALLED_LIBRARIES = [
'jquery/dist/jquery.js',
'jquery-migrate/dist/jquery-migrate.js',
'jquery.scrollto/jquery.scrollTo.js',
'underscore/underscore.js', 'underscore/underscore.js',
'underscore.string/dist/underscore.string.js', 'underscore.string/dist/underscore.string.js',
'picturefill/dist/picturefill.js', 'picturefill/dist/picturefill.js',
......
...@@ -10,7 +10,6 @@ ...@@ -10,7 +10,6 @@
"date": "1.0", "date": "1.0",
"domready": "2.0.1", "domready": "2.0.1",
"draggabilly": "1.2.4", "draggabilly": "1.2.4",
"jquery": "1.7.2",
"jquery-form": "3.18.0", "jquery-form": "3.18.0",
"jquery-watch": "2.0", "jquery-watch": "2.0",
"moment": "2.10.6", "moment": "2.10.6",
......
...@@ -22,7 +22,6 @@ ...@@ -22,7 +22,6 @@
"domReady": "2.0.1", "domReady": "2.0.1",
"draggabilly": "1.2.4", "draggabilly": "1.2.4",
// "history": "1.8b2", // "history": "1.8b2",
"jquery": "1.7.2",
// "jquery.ajaxQueue": "unknown", // "jquery.ajaxQueue": "unknown",
// "jquery.ajax-retry": "unknown", // "jquery.ajax-retry": "unknown",
"jquery.colorhelpers": "1.1", "jquery.colorhelpers": "1.1",
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment