Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 6735726

Browse filesBrowse files
authored
Merge pull request #66185 from code-dot-org/ryan/workshops/feat/allow-edit-course-offering-facilitators_courses
feat(workshops): allow editing course offering facilitators courses
2 parents 104a27f + 08a2385 commit 6735726
Copy full SHA for 6735726

File tree

Expand file treeCollapse file tree

8 files changed

+96
-12
lines changed
Filter options
Expand file treeCollapse file tree

8 files changed

+96
-12
lines changed

‎apps/src/levelbuilder/CourseOfferingEditor.jsx

Copy file name to clipboardExpand all lines: apps/src/levelbuilder/CourseOfferingEditor.jsx
+45-8Lines changed: 45 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ export default function CourseOfferingEditor(props) {
6666
method: 'PUT',
6767
dataType: 'json',
6868
contentType: 'application/json;charset=UTF-8',
69-
data: JSON.stringify(courseOffering),
69+
data: JSON.stringify({course_offering: courseOffering}),
7070
})
7171
.done(data => {
7272
if (shouldCloseAfterSave) {
@@ -82,18 +82,22 @@ export default function CourseOfferingEditor(props) {
8282
});
8383
};
8484

85+
const getSelectedOptions = e =>
86+
Array.from(e.target.options)
87+
.filter(option => option.selected && option.value !== '')
88+
.map(option => option.value);
89+
8590
// Converts selected options within the given fieldName into a string for the table
8691
const handleMultipleSelected = (e, fieldName) => {
87-
var options = e.target.options;
88-
var selectedOptions = [];
89-
for (var i = 0, l = options.length; i < l; i++) {
90-
if (options[i].selected && options[i].value !== '') {
91-
selectedOptions.push(options[i].value);
92-
}
93-
}
92+
const selectedOptions = getSelectedOptions(e);
9493
updateCourseOffering(fieldName, selectedOptions.join(','));
9594
};
9695

96+
const handleFacilitatorsCourses = e => {
97+
const selectedOptions = getSelectedOptions(e);
98+
updateCourseOffering('facilitator_course_permissions', selectedOptions);
99+
};
100+
97101
// Converts selected device compatibility options into a string for the table
98102
const updateDeviceCompatibilities = (device, compatibilityLevel) => {
99103
let updatedDeviceCompatibilities = {};
@@ -478,6 +482,37 @@ export default function CourseOfferingEditor(props) {
478482
))}
479483
</select>
480484
</label>
485+
<label>
486+
Facilitator Course Permissions
487+
<HelpTip>
488+
<p>
489+
For self paced professional learning courses only!
490+
<br />
491+
<br />
492+
Pick which types of facilitators can facilitate workshops associated
493+
with this professional learning topic.
494+
</p>
495+
</HelpTip>
496+
<select
497+
multiple
498+
value={
499+
courseOffering.facilitator_course_permissions.length
500+
? courseOffering.facilitator_course_permissions
501+
: ['']
502+
}
503+
style={styles.dropdown}
504+
onChange={e => {
505+
handleFacilitatorsCourses(e, 'facilitator_course_permissions');
506+
}}
507+
>
508+
<option value="">(Anyone)</option>
509+
{Object.values(props.facilitatorsCourses).map(course => (
510+
<option key={course} value={course}>
511+
{course}
512+
</option>
513+
))}
514+
</select>
515+
</label>
481516
<label>
482517
<div style={styles.flexContainer}>
483518
<h3>Published Date </h3>
@@ -517,6 +552,7 @@ CourseOfferingEditor.propTypes = {
517552
self_paced_pl_course_offering_id: PropTypes.number,
518553
video: PropTypes.string,
519554
published_date: PropTypes.string,
555+
facilitator_course_permissions: PropTypes.arrayOf(PropTypes.string),
520556
}),
521557
selfPacedPLCourseOfferings: PropTypes.arrayOf(
522558
PropTypes.shape({
@@ -534,6 +570,7 @@ CourseOfferingEditor.propTypes = {
534570
locale: PropTypes.string,
535571
})
536572
),
573+
facilitatorsCourses: PropTypes.arrayOf(PropTypes.string),
537574
};
538575

539576
const styles = {

‎apps/src/sites/studio/pages/course_offerings/edit.js

Copy file name to clipboardExpand all lines: apps/src/sites/studio/pages/course_offerings/edit.js
+3Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,12 +19,15 @@ function showCourseOfferingEditor() {
1919

2020
const videos = getScriptData('videos');
2121

22+
const facilitatorsCourses = getScriptData('facilitatorsCourses');
23+
2224
ReactDOM.render(
2325
<CourseOfferingEditor
2426
initialCourseOffering={courseOfferingEditorData}
2527
selfPacedPLCourseOfferings={selfPacedPLCourseOfferings}
2628
professionalLearningProgramPaths={professionalLearningProgramPaths}
2729
videos={videos}
30+
facilitatorsCourses={facilitatorsCourses}
2831
/>,
2932
document.getElementById('course_offering_editor')
3033
);

‎apps/test/unit/levelbuilder/CourseOfferingEditorTest.jsx

Copy file name to clipboardExpand all lines: apps/test/unit/levelbuilder/CourseOfferingEditorTest.jsx
+8Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ describe('CourseOfferingEditor', () => {
3838
self_paced_pl_course_offering_id: 1,
3939
video: 'https://www.youtube-nocookie.com/test_video',
4040
published_date: '2019-07-16 14:00:00',
41+
facilitator_course_permissions: [],
4142
},
4243
selfPacedPLCourseOfferings: [
4344
{
@@ -68,6 +69,11 @@ describe('CourseOfferingEditor', () => {
6869
locale: 'en-US',
6970
},
7071
],
72+
facilitatorsCourses: [
73+
'CS Fundamentals',
74+
'CS Principles',
75+
'CS Discoveries',
76+
],
7177
};
7278
});
7379

@@ -108,6 +114,7 @@ describe('CourseOfferingEditor', () => {
108114
professional_learning: 'code.org/apply',
109115
video: 'https://www.youtube-nocookie.com/test_video',
110116
published_date: '2019-07-16 14:00:00',
117+
facilitator_course_permissions: [],
111118
};
112119
server.respondWith('PUT', '/course_offerings/test-course-offering', [
113120
200,
@@ -184,6 +191,7 @@ describe('CourseOfferingEditor', () => {
184191
professional_learning: 'code.org/apply',
185192
video: 'https://www.youtube-nocookie.com/test_video',
186193
published_date: '2019-07-16 14:00:00',
194+
facilitator_course_permissions: [],
187195
};
188196

189197
server.respondWith('PUT', '/course_offerings/test-course-offering', [

‎dashboard/app/controllers/course_offerings_controller.rb

Copy file name to clipboardExpand all lines: dashboard/app/controllers/course_offerings_controller.rb
+10-1Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,15 @@ def self_paced_pl_course_offerings
4444
end
4545

4646
private def course_offering_params
47-
params.permit(:display_name, :is_featured, :assignable, :grade_levels, :curriculum_type, :header, :marketing_initiative, :image, :cs_topic, :school_subject, :device_compatibility, :description, :professional_learning_program, :self_paced_pl_course_offering_id, :video, :published_date, :ai_teaching_assistant_available).to_h
47+
permitted = [
48+
:display_name, :is_featured, :assignable, :grade_levels, :curriculum_type, :header, :marketing_initiative, :image, :cs_topic, :school_subject, :device_compatibility, :description, :professional_learning_program, :self_paced_pl_course_offering_id, :video, :published_date, :ai_teaching_assistant_available, {facilitator_course_permissions: []}
49+
]
50+
if params[:course_offering]
51+
# rails convention is to use nested strong parameter
52+
params.require(:course_offering).permit(*permitted).to_h
53+
else
54+
# retain backwards compatibility
55+
params.permit(*permitted).to_h
56+
end
4857
end
4958
end

‎dashboard/app/models/course_offering.rb

Copy file name to clipboardExpand all lines: dashboard/app/models/course_offering.rb
+2Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -322,6 +322,7 @@ def summarize_for_edit
322322
published_date: published_date,
323323
self_paced_pl_course_offering_id: self_paced_pl_course_offering_id,
324324
ai_teaching_assistant_available: ai_teaching_assistant_available,
325+
facilitator_course_permissions: facilitator_course_permissions || [],
325326
}
326327
end
327328

@@ -373,6 +374,7 @@ def serialize
373374
published_date: published_date,
374375
self_paced_pl_course_offering_key: self_paced_pl_course_offering&.key,
375376
ai_teaching_assistant_available: ai_teaching_assistant_available,
377+
facilitator_course_permissions: facilitator_course_permissions
376378
}
377379
end
378380

+1-1Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
1-
%script{src: webpack_asset_path('js/course_offerings/edit.js'), data: {courseOfferingEditor: @course_offering.summarize_for_edit.to_json, selfPacedPlCourseOfferings: @self_paced_pl_course_offerings.to_json, professionalLearningProgramPaths: @professional_learning_program_paths.to_json, videos: @videos.to_json}}
1+
%script{src: webpack_asset_path('js/course_offerings/edit.js'), data: {courseOfferingEditor: @course_offering.summarize_for_edit.to_json, facilitatorsCourses: Pd::Workshop::ACTIVE_COURSES - [Pd::Workshop::COURSE_BUILD_YOUR_OWN], selfPacedPlCourseOfferings: @self_paced_pl_course_offerings.to_json, professionalLearningProgramPaths: @professional_learning_program_paths.to_json, videos: @videos.to_json}}
22

33
#course_offering_editor

‎dashboard/app/views/pd/workshop_user_management/facilitator_courses_form.html.haml

Copy file name to clipboardExpand all lines: dashboard/app/views/pd/workshop_user_management/facilitator_courses_form.html.haml
+1-1Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -45,5 +45,5 @@
4545
%td
4646
%input{:hidden => true, :name => "user_id", :value => @user.id}
4747
.field
48-
= select_tag :course, options_for_select(Pd::Workshop::COURSES)
48+
= select_tag :course, options_for_select(Pd::Workshop::ACTIVE_COURSES)
4949
%td

‎dashboard/test/controllers/course_offerings_controller_test.rb

Copy file name to clipboardExpand all lines: dashboard/test/controllers/course_offerings_controller_test.rb
+26-1Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,13 +42,38 @@ class CourseOfferingsControllerTest < ActionController::TestCase
4242
key: course_offering.key,
4343
display_name: 'New Display Name',
4444
marketing_initiative: 'CSD',
45-
is_featured: false
45+
is_featured: false,
46+
facilitator_course_permissions: ["CS Fundamentals", "CS Principles", "CS Discoveries"]
47+
}
48+
49+
course_offering.reload
50+
51+
assert_equal 'New Display Name', course_offering.display_name
52+
assert_equal 'CSD', course_offering.marketing_initiative
53+
assert_equal false, course_offering.is_featured
54+
assert_equal ["CS Fundamentals", "CS Principles", "CS Discoveries"], course_offering.facilitator_course_permissions
55+
end
56+
57+
test 'update course offering updates fields with nested strong parameters' do
58+
sign_in @levelbuilder
59+
60+
course_offering = create :course_offering, display_name: 'Course Offering Name', marketing_initiative: 'HOC', is_featured: true
61+
62+
put :update, params: {
63+
key: course_offering.key,
64+
course_offering: {
65+
display_name: 'New Display Name',
66+
marketing_initiative: 'CSD',
67+
is_featured: false,
68+
facilitator_course_permissions: ["CS Fundamentals", "CS Principles", "CS Discoveries"]
69+
}
4670
}
4771

4872
course_offering.reload
4973

5074
assert_equal 'New Display Name', course_offering.display_name
5175
assert_equal 'CSD', course_offering.marketing_initiative
5276
assert_equal false, course_offering.is_featured
77+
assert_equal ["CS Fundamentals", "CS Principles", "CS Discoveries"], course_offering.facilitator_course_permissions
5378
end
5479
end

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.