From f71f0c92f708c82e9a84246541de3569abd91612 Mon Sep 17 00:00:00 2001 From: David Bailey Date: Wed, 2 Aug 2017 16:55:23 -0700 Subject: [PATCH 01/11] send feedback image to the server when updating artist solution_blocks --- apps/src/turtle/turtle.js | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/apps/src/turtle/turtle.js b/apps/src/turtle/turtle.js index 0434f57bb5215..e4ea3ae516152 100644 --- a/apps/src/turtle/turtle.js +++ b/apps/src/turtle/turtle.js @@ -1803,9 +1803,16 @@ Artist.prototype.checkAnswer = function () { // Never send up frozen images for now. var isFrozen = (this.skin.id === 'anna' || this.skin.id === 'elsa'); + // Include the feedback image whenever a levelbuilder edits solution blocks. + const isEditingSolution = (level.editBlocks === 'solution_blocks'); + + const didPassLevel = this.testResults >= TestResults.TOO_MANY_BLOCKS_FAIL; + // Get the canvas data for feedback. - if (this.testResults >= TestResults.TOO_MANY_BLOCKS_FAIL && - !isFrozen && (level.freePlay || level.impressive)) { + if ( + isEditingSolution || + (didPassLevel && !isFrozen && (level.freePlay || level.impressive)) + ) { reportData.image = encodeURIComponent(this.getFeedbackImage_().split(',')[1]); } From 47424554acb56e4fe7dafc11af6d669debb7d54b Mon Sep 17 00:00:00 2001 From: David Bailey Date: Wed, 2 Aug 2017 18:51:43 -0700 Subject: [PATCH 02/11] extract Artist.prototype.setReportDataImage_ --- apps/src/turtle/turtle.js | 48 ++++++++++++++++++++++++++------------- 1 file changed, 32 insertions(+), 16 deletions(-) diff --git a/apps/src/turtle/turtle.js b/apps/src/turtle/turtle.js index e4ea3ae516152..1d732d02277d2 100644 --- a/apps/src/turtle/turtle.js +++ b/apps/src/turtle/turtle.js @@ -1799,22 +1799,7 @@ Artist.prototype.checkAnswer = function () { save_to_gallery: level.impressive }; - // https://www.pivotaltracker.com/story/show/84171560 - // Never send up frozen images for now. - var isFrozen = (this.skin.id === 'anna' || this.skin.id === 'elsa'); - - // Include the feedback image whenever a levelbuilder edits solution blocks. - const isEditingSolution = (level.editBlocks === 'solution_blocks'); - - const didPassLevel = this.testResults >= TestResults.TOO_MANY_BLOCKS_FAIL; - - // Get the canvas data for feedback. - if ( - isEditingSolution || - (didPassLevel && !isFrozen && (level.freePlay || level.impressive)) - ) { - reportData.image = encodeURIComponent(this.getFeedbackImage_().split(',')[1]); - } + reportData = this.setReportDataImage_(level, reportData); this.studioApp_.report(reportData); } @@ -1827,6 +1812,37 @@ Artist.prototype.checkAnswer = function () { // The call to displayFeedback() will happen later in onReportComplete() }; +/** + * Adds the feedback image to the report data if indicated by the level config. + * @param {Object} level Level config. + * @param {Object} reportData Original reportData. + * @returns {Object} Updated reportData, or original report data if not updated. + * @private + */ +Artist.prototype.setReportDataImage_ = function (level, reportData) { + // https://www.pivotaltracker.com/story/show/84171560 + // Never send up frozen images for now. + var isFrozen = (this.skin.id === 'anna' || this.skin.id === 'elsa'); + + // Include the feedback image whenever a levelbuilder edits solution blocks. + const isEditingSolution = (level.editBlocks === 'solution_blocks'); + + const didPassLevel = this.testResults >= TestResults.TOO_MANY_BLOCKS_FAIL; + + // Get the canvas data for feedback. + if ( + isEditingSolution || + (didPassLevel && !isFrozen && (level.freePlay || level.impressive)) + ) { + const image = encodeURIComponent(this.getFeedbackImage_().split(',')[1]); + return { + ...reportData, + image, + }; + } + return reportData; +}; + Artist.prototype.getFeedbackImage_ = function (width, height) { var origWidth = this.ctxFeedback.canvas.width; From 13b0e92a353184314dcb0e6832c94c4abed18b2d Mon Sep 17 00:00:00 2001 From: David Bailey Date: Wed, 2 Aug 2017 17:02:35 -0700 Subject: [PATCH 03/11] extract get_level_source_image from ActivitiesController to LevelsHelper --- .../app/controllers/activities_controller.rb | 11 +---------- dashboard/app/helpers/levels_helper.rb | 15 +++++++++++++++ 2 files changed, 16 insertions(+), 10 deletions(-) diff --git a/dashboard/app/controllers/activities_controller.rb b/dashboard/app/controllers/activities_controller.rb index 961d293c6d0d8..6755b216c2edd 100644 --- a/dashboard/app/controllers/activities_controller.rb +++ b/dashboard/app/controllers/activities_controller.rb @@ -87,16 +87,7 @@ def milestone params[:lines] = MAX_LINES_OF_CODE if params[:lines] > MAX_LINES_OF_CODE end - # Store the image only if the image is set, and the image has not been saved - if params[:image] && @level_source.try(:id) - @level_source_image = LevelSourceImage.find_by(level_source_id: @level_source.id) - unless @level_source_image - @level_source_image = LevelSourceImage.new(level_source_id: @level_source.id) - unless @level_source_image.save_to_s3(Base64.decode64(params[:image])) - @level_source_image = nil - end - end - end + @level_source_image = get_level_source_image(params[:image], @level_source.try(:id)) @new_level_completed = false if current_user diff --git a/dashboard/app/helpers/levels_helper.rb b/dashboard/app/helpers/levels_helper.rb index a310d17f8eaa2..b14c14c80a745 100644 --- a/dashboard/app/helpers/levels_helper.rb +++ b/dashboard/app/helpers/levels_helper.rb @@ -770,4 +770,19 @@ def can_view_teacher_markdown? def include_multi_answers?(standalone) standalone || current_user.try(:should_see_inline_answer?, @script_level) end + + def get_level_source_image(level_image, level_source_id) + level_source_image = nil + # Store the image only if the image is set, and the image has not been saved + if level_image && level_source_id + level_source_image = LevelSourceImage.find_by(level_source_id: level_source_id) + unless level_source_image + level_source_image = LevelSourceImage.new(level_source_id: level_source_id) + unless level_source_image.save_to_s3(Base64.decode64(level_image)) + level_source_image = nil + end + end + end + level_source_image + end end From 3391639966b25b7a8944450c1c87f860f6552269 Mon Sep 17 00:00:00 2001 From: David Bailey Date: Wed, 2 Aug 2017 18:04:27 -0700 Subject: [PATCH 04/11] save solution_image_url to level properties when solution_blocks are updated --- dashboard/app/controllers/levels_controller.rb | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/dashboard/app/controllers/levels_controller.rb b/dashboard/app/controllers/levels_controller.rb index 3c2bac5b9bc7c..a130e2d94cfae 100644 --- a/dashboard/app/controllers/levels_controller.rb +++ b/dashboard/app/controllers/levels_controller.rb @@ -95,6 +95,7 @@ def update_blocks authorize! :update, @level blocks_xml = params[:program] type = params[:type] + set_solution_image_url(@level) if type == 'solution_blocks' blocks_xml = Blockly.convert_toolbox_to_category(blocks_xml) if type == 'toolbox_blocks' @level.properties[type] = blocks_xml @level.log_changes(current_user) @@ -289,4 +290,13 @@ def level_params permitted_params.concat(Level.permitted_params) params[:level].permit(permitted_params) end + + def set_solution_image_url(level) + level_source = LevelSource.find_identical_or_create( + level, + params[:program].strip_utf8mb4 + ) + level_source_image = get_level_source_image(params[:image], level_source.try(:id)) + @level.properties['solution_image_url'] = level_source_image.s3_url if level_source_image + end end From b52e255b7e2f60a510baf6a153d2b9056e159410 Mon Sep 17 00:00:00 2001 From: David Bailey Date: Fri, 4 Aug 2017 11:28:05 -0700 Subject: [PATCH 05/11] Add tests for solution_image_url to LevelsControllerTest --- .../controllers/levels_controller_test.rb | 47 +++++++++++++++++++ 1 file changed, 47 insertions(+) diff --git a/dashboard/test/controllers/levels_controller_test.rb b/dashboard/test/controllers/levels_controller_test.rb index ce5b55145579a..27b05a49c96b3 100644 --- a/dashboard/test/controllers/levels_controller_test.rb +++ b/dashboard/test/controllers/levels_controller_test.rb @@ -13,6 +13,13 @@ class LevelsControllerTest < ActionController::TestCase @levelbuilder = create(:levelbuilder) sign_in(@levelbuilder) @program = '' + + # Ensure that we get a real S3 url for the level source image when + # requested, and that we never try to upload an image to S3. + + CDO.stubs(:disable_s3_image_uploads).returns(false) + LevelSourceImage.any_instance.expects(:save_to_s3).never + create(:level_source, :with_image, level: @level, data: @program) end test "should get index" do @@ -298,6 +305,36 @@ class LevelsControllerTest < ActionController::TestCase assert_response :success level = assigns(:level) assert_equal level.properties[:toolbox_blocks.to_s], @program + assert_nil level.properties[:solution_image_url.to_s] + end + + test "should update solution image when updating solution blocks" do + post :update_blocks, params: { + level_id: @level.id, + game_id: @level.game.id, + type: 'solution_blocks', + program: @program, + image: 'stub-image-data', + } + assert_response :success + level = assigns(:level) + puts "level.properties #{level.properties}" + assert_equal level.properties[:solution_blocks.to_s], @program + assert_s3_image_url(level.properties[:solution_image_url.to_s]) + end + + test "should not update solution image when updating toolbox blocks" do + post :update_blocks, params: { + level_id: @level.id, + game_id: @level.game.id, + type: 'toolbox_blocks', + program: @program, + image: 'stub-image-data', + } + assert_response :success + level = assigns(:level) + assert_equal level.properties[:toolbox_blocks.to_s], @program + assert_nil level.properties[:solution_image_url.to_s] end test "should not update blocks if not levelbuilder" do @@ -706,4 +743,14 @@ class LevelsControllerTest < ActionController::TestCase get :embed_blocks, params: {level_id: level, block_type: :solution_blocks} assert_response :success end + + private + + # Assert that the url is a real S3 url, and not a placeholder. + def assert_s3_image_url(url) + assert( + %r{#{LevelSourceImage::S3_URL}.*\.png}.match(url), + "expected #{url.inspect} to be an S3 URL" + ) + end end From c973dee40f0379f70fcde803e967e47c6564b5f3 Mon Sep 17 00:00:00 2001 From: David Bailey Date: Wed, 2 Aug 2017 18:35:16 -0700 Subject: [PATCH 06/11] generate a solution image for one artist level --- dashboard/config/scripts/levels/courseC_artist_prog7.level | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/dashboard/config/scripts/levels/courseC_artist_prog7.level b/dashboard/config/scripts/levels/courseC_artist_prog7.level index 1a408d6aa32a9..9c09375c4a6e3 100644 --- a/dashboard/config/scripts/levels/courseC_artist_prog7.level +++ b/dashboard/config/scripts/levels/courseC_artist_prog7.level @@ -39,6 +39,7 @@ "video_key": "CSF_artist_angles", "hide_share_and_remix": "false", "disable_if_else_editing": "false", + "solution_image_url": "https://d3p74s6bwmy6t9.cloudfront.net/8cbbc4899e479126d6c97114489d398f=development/967.png", "contained_level_names": null }, "published": true, @@ -256,4 +257,4 @@ - \ No newline at end of file + From afeb5e7bab1ff111b6bc86690a7e343c81d0765a Mon Sep 17 00:00:00 2001 From: David Bailey Date: Fri, 4 Aug 2017 13:09:21 -0700 Subject: [PATCH 07/11] extract default_update_blocks_params in LevelsControllerTest --- .../controllers/levels_controller_test.rb | 46 ++++++++----------- 1 file changed, 18 insertions(+), 28 deletions(-) diff --git a/dashboard/test/controllers/levels_controller_test.rb b/dashboard/test/controllers/levels_controller_test.rb index 27b05a49c96b3..f4b7f23f87a2a 100644 --- a/dashboard/test/controllers/levels_controller_test.rb +++ b/dashboard/test/controllers/levels_controller_test.rb @@ -3,6 +3,8 @@ class LevelsControllerTest < ActionController::TestCase include Devise::Test::ControllerHelpers + default_update_blocks_params = nil + setup do Rails.application.config.stubs(:levelbuilder_mode).returns true Level.any_instance.stubs(:write_to_file?).returns(false) # don't write to level files @@ -20,6 +22,13 @@ class LevelsControllerTest < ActionController::TestCase CDO.stubs(:disable_s3_image_uploads).returns(false) LevelSourceImage.any_instance.expects(:save_to_s3).never create(:level_source, :with_image, level: @level, data: @program) + + default_update_blocks_params = { + level_id: @level.id, + game_id: @level.game.id, + type: 'toolbox_blocks', + program: @program, + } end test "should get index" do @@ -296,12 +305,7 @@ class LevelsControllerTest < ActionController::TestCase end test "should update blocks" do - post :update_blocks, params: { - level_id: @level.id, - game_id: @level.game.id, - type: 'toolbox_blocks', - program: @program - } + post :update_blocks, params: default_update_blocks_params assert_response :success level = assigns(:level) assert_equal level.properties[:toolbox_blocks.to_s], @program @@ -309,13 +313,10 @@ class LevelsControllerTest < ActionController::TestCase end test "should update solution image when updating solution blocks" do - post :update_blocks, params: { - level_id: @level.id, - game_id: @level.game.id, + post :update_blocks, params: default_update_blocks_params.merge( type: 'solution_blocks', - program: @program, image: 'stub-image-data', - } + ) assert_response :success level = assigns(:level) puts "level.properties #{level.properties}" @@ -324,28 +325,19 @@ class LevelsControllerTest < ActionController::TestCase end test "should not update solution image when updating toolbox blocks" do - post :update_blocks, params: { - level_id: @level.id, - game_id: @level.game.id, - type: 'toolbox_blocks', - program: @program, + post :update_blocks, params: default_update_blocks_params.merge( image: 'stub-image-data', - } + ) assert_response :success level = assigns(:level) - assert_equal level.properties[:toolbox_blocks.to_s], @program + assert_equal @program, level.properties[:toolbox_blocks.to_s] assert_nil level.properties[:solution_image_url.to_s] end test "should not update blocks if not levelbuilder" do [@not_admin, @admin].each do |user| sign_in user - post :update_blocks, params: { - level_id: @level.id, - game_id: @level.game.id, - type: 'toolbox_blocks', - program: @program - } + post :update_blocks, params: default_update_blocks_params assert_response :forbidden end end @@ -355,12 +347,10 @@ class LevelsControllerTest < ActionController::TestCase can_edit = Ability.new(@levelbuilder).can? :edit, level assert_equal false, can_edit - post :update_blocks, params: { + post :update_blocks, params: default_update_blocks_params.merge( level_id: level.id, game_id: level.game.id, - type: 'toolbox_blocks', - program: @program - } + ) assert_response :forbidden end From be2d6e01876f6633a0c3d70a756259edea8479a1 Mon Sep 17 00:00:00 2001 From: David Bailey Date: Fri, 4 Aug 2017 14:02:29 -0700 Subject: [PATCH 08/11] code review feedback --- .../app/controllers/activities_controller.rb | 2 +- .../app/controllers/levels_controller.rb | 2 +- dashboard/app/helpers/levels_helper.rb | 10 +++++- .../controllers/levels_controller_test.rb | 35 ++++++++++++------- 4 files changed, 34 insertions(+), 15 deletions(-) diff --git a/dashboard/app/controllers/activities_controller.rb b/dashboard/app/controllers/activities_controller.rb index 6755b216c2edd..ff3f89c4eec33 100644 --- a/dashboard/app/controllers/activities_controller.rb +++ b/dashboard/app/controllers/activities_controller.rb @@ -87,7 +87,7 @@ def milestone params[:lines] = MAX_LINES_OF_CODE if params[:lines] > MAX_LINES_OF_CODE end - @level_source_image = get_level_source_image(params[:image], @level_source.try(:id)) + @level_source_image = find_or_create_level_source_image(params[:image], @level_source.try(:id)) @new_level_completed = false if current_user diff --git a/dashboard/app/controllers/levels_controller.rb b/dashboard/app/controllers/levels_controller.rb index a130e2d94cfae..4a0e6b96ef70c 100644 --- a/dashboard/app/controllers/levels_controller.rb +++ b/dashboard/app/controllers/levels_controller.rb @@ -296,7 +296,7 @@ def set_solution_image_url(level) level, params[:program].strip_utf8mb4 ) - level_source_image = get_level_source_image(params[:image], level_source.try(:id)) + level_source_image = find_or_create_level_source_image(params[:image], level_source.try(:id)) @level.properties['solution_image_url'] = level_source_image.s3_url if level_source_image end end diff --git a/dashboard/app/helpers/levels_helper.rb b/dashboard/app/helpers/levels_helper.rb index b14c14c80a745..f6be7f4595064 100644 --- a/dashboard/app/helpers/levels_helper.rb +++ b/dashboard/app/helpers/levels_helper.rb @@ -771,7 +771,15 @@ def include_multi_answers?(standalone) standalone || current_user.try(:should_see_inline_answer?, @script_level) end - def get_level_source_image(level_image, level_source_id) + # Finds the existing LevelSourceImage corresponding to the specified level + # source id if one exists, otherwise creates and returns a new + # LevelSourceImage using the image data in level_image. + # + # @param level_image [String] A base64-encoded image. + # @param level_source_id [Integer, nil] The id of a LevelSource or nil. + # @returns [LevelSourceImage] A level source image, or nil if one was not + # created or found. + def find_or_create_level_source_image(level_image, level_source_id) level_source_image = nil # Store the image only if the image is set, and the image has not been saved if level_image && level_source_id diff --git a/dashboard/test/controllers/levels_controller_test.rb b/dashboard/test/controllers/levels_controller_test.rb index f4b7f23f87a2a..bdb5512b4dc16 100644 --- a/dashboard/test/controllers/levels_controller_test.rb +++ b/dashboard/test/controllers/levels_controller_test.rb @@ -16,12 +16,7 @@ class LevelsControllerTest < ActionController::TestCase sign_in(@levelbuilder) @program = '' - # Ensure that we get a real S3 url for the level source image when - # requested, and that we never try to upload an image to S3. - - CDO.stubs(:disable_s3_image_uploads).returns(false) - LevelSourceImage.any_instance.expects(:save_to_s3).never - create(:level_source, :with_image, level: @level, data: @program) + enable_level_source_image_s3_urls default_update_blocks_params = { level_id: @level.id, @@ -308,8 +303,8 @@ class LevelsControllerTest < ActionController::TestCase post :update_blocks, params: default_update_blocks_params assert_response :success level = assigns(:level) - assert_equal level.properties[:toolbox_blocks.to_s], @program - assert_nil level.properties[:solution_image_url.to_s] + assert_equal @program, level.properties['toolbox_blocks'] + assert_nil level.properties['solution_image_url'] end test "should update solution image when updating solution blocks" do @@ -320,8 +315,8 @@ class LevelsControllerTest < ActionController::TestCase assert_response :success level = assigns(:level) puts "level.properties #{level.properties}" - assert_equal level.properties[:solution_blocks.to_s], @program - assert_s3_image_url(level.properties[:solution_image_url.to_s]) + assert_equal @program, level.properties['solution_blocks'] + assert_s3_image_url level.properties['solution_image_url'] end test "should not update solution image when updating toolbox blocks" do @@ -330,8 +325,8 @@ class LevelsControllerTest < ActionController::TestCase ) assert_response :success level = assigns(:level) - assert_equal @program, level.properties[:toolbox_blocks.to_s] - assert_nil level.properties[:solution_image_url.to_s] + assert_equal @program, level.properties['toolbox_blocks'] + assert_nil level.properties['solution_image_url'] end test "should not update blocks if not levelbuilder" do @@ -743,4 +738,20 @@ def assert_s3_image_url(url) "expected #{url.inspect} to be an S3 URL" ) end + + # Allow our update_blocks tests to verify that real S3 urls are being + # generated when solution images are uploaded. We don't want to actually + # upload any S3 images in our tests, so just enable the codepath where an + # existing LevelSourceImage is found based on the program contents. + def enable_level_source_image_s3_urls + # Allow LevelSourceImage to return real S3 urls. + CDO.stubs(:disable_s3_image_uploads).returns(false) + + # Make sure there is a LevelSourceImage associated with the program. + create(:level_source, :with_image, level: @level, data: @program) + + # Because we cleared disable_s3_image_uploads, there's a chance we'll + # accidentally try to upload an image to S3. Make sure this never happens. + LevelSourceImage.any_instance.expects(:save_to_s3).never + end end From 11132e79337302b5938d05836df40633976b2fc8 Mon Sep 17 00:00:00 2001 From: David Bailey Date: Fri, 4 Aug 2017 14:31:16 -0700 Subject: [PATCH 09/11] rename default_update_blocks_params to @default_update_blocks_params --- .../test/controllers/levels_controller_test.rb | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/dashboard/test/controllers/levels_controller_test.rb b/dashboard/test/controllers/levels_controller_test.rb index bdb5512b4dc16..7ef0a11b74572 100644 --- a/dashboard/test/controllers/levels_controller_test.rb +++ b/dashboard/test/controllers/levels_controller_test.rb @@ -3,8 +3,6 @@ class LevelsControllerTest < ActionController::TestCase include Devise::Test::ControllerHelpers - default_update_blocks_params = nil - setup do Rails.application.config.stubs(:levelbuilder_mode).returns true Level.any_instance.stubs(:write_to_file?).returns(false) # don't write to level files @@ -18,7 +16,7 @@ class LevelsControllerTest < ActionController::TestCase enable_level_source_image_s3_urls - default_update_blocks_params = { + @default_update_blocks_params = { level_id: @level.id, game_id: @level.game.id, type: 'toolbox_blocks', @@ -300,7 +298,7 @@ class LevelsControllerTest < ActionController::TestCase end test "should update blocks" do - post :update_blocks, params: default_update_blocks_params + post :update_blocks, params: @default_update_blocks_params assert_response :success level = assigns(:level) assert_equal @program, level.properties['toolbox_blocks'] @@ -308,7 +306,7 @@ class LevelsControllerTest < ActionController::TestCase end test "should update solution image when updating solution blocks" do - post :update_blocks, params: default_update_blocks_params.merge( + post :update_blocks, params: @default_update_blocks_params.merge( type: 'solution_blocks', image: 'stub-image-data', ) @@ -320,7 +318,7 @@ class LevelsControllerTest < ActionController::TestCase end test "should not update solution image when updating toolbox blocks" do - post :update_blocks, params: default_update_blocks_params.merge( + post :update_blocks, params: @default_update_blocks_params.merge( image: 'stub-image-data', ) assert_response :success @@ -332,7 +330,7 @@ class LevelsControllerTest < ActionController::TestCase test "should not update blocks if not levelbuilder" do [@not_admin, @admin].each do |user| sign_in user - post :update_blocks, params: default_update_blocks_params + post :update_blocks, params: @default_update_blocks_params assert_response :forbidden end end @@ -342,7 +340,7 @@ class LevelsControllerTest < ActionController::TestCase can_edit = Ability.new(@levelbuilder).can? :edit, level assert_equal false, can_edit - post :update_blocks, params: default_update_blocks_params.merge( + post :update_blocks, params: @default_update_blocks_params.merge( level_id: level.id, game_id: level.game.id, ) From 9c8934f395cf7ca39c586bbd7bbdd20f7d83222c Mon Sep 17 00:00:00 2001 From: David Bailey Date: Fri, 4 Aug 2017 15:48:40 -0700 Subject: [PATCH 10/11] generate a solution image for one playlab level [ci skip] --- dashboard/config/scripts/levels/courseC_PlayLab_events1.level | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/dashboard/config/scripts/levels/courseC_PlayLab_events1.level b/dashboard/config/scripts/levels/courseC_PlayLab_events1.level index 720d50e9534e8..36181514db7c3 100644 --- a/dashboard/config/scripts/levels/courseC_PlayLab_events1.level +++ b/dashboard/config/scripts/levels/courseC_PlayLab_events1.level @@ -41,11 +41,12 @@ "hide_share_and_remix": "false", "disable_if_else_editing": "false", "authored_hints": "[{\"hint_class\":\"content\",\"hint_markdown\":\"Attach this block to the `when run` block:\\n\\n![](https://images.code.org/24043f33cb433506679d27acf991b7c1-image-1499792847837.06.43 AM.png)\",\"hint_id\":\"courseC_PlayLab_events1_a\",\"hint_type\":\"general\",\"tts_url\":\"https://tts.code.org/sharon22k/180/100/b7c0dffa28e40475021b7f070fc4aceb/courseC_PlayLab_events1.mp3\"}]", + "solution_image_url": "https://d3p74s6bwmy6t9.cloudfront.net/af4338d3357b7926d7966836de647c0d=development/952.png", "contained_level_names": null }, "published": true, "notes": "", - "audit_log": "[{\"changed_at\":\"2017-06-14 20:07:10 +0000\",\"changed\":[\"start_blocks\",\"toolbox_blocks\",\"solution_blocks\",\"success_condition\",\"contained_level_names\"],\"changed_by_id\":302,\"changed_by_email\":\"mara.downing@code.org\"},{\"changed_at\":\"2017-07-11 17:07:39 +0000\",\"changed\":[\"start_blocks\",\"toolbox_blocks\",\"solution_blocks\",\"contained_level_names\"],\"changed_by_id\":302,\"changed_by_email\":\"mara.downing@code.org\"}]", + "audit_log": "[{\"changed_at\":\"2017-06-14 20:07:10 +0000\",\"changed\":[\"start_blocks\",\"toolbox_blocks\",\"solution_blocks\",\"success_condition\",\"contained_level_names\"],\"changed_by_id\":302,\"changed_by_email\":\"mara.downing@code.org\"},{\"changed_at\":\"2017-07-11 17:07:39 +0000\",\"changed\":[\"start_blocks\",\"toolbox_blocks\",\"solution_blocks\",\"contained_level_names\"],\"changed_by_id\":302,\"changed_by_email\":\"mara.downing@code.org\"},{\"changed_at\":\"2017-08-04 15:16:23 -0700\",\"changed\":[],\"changed_by_id\":1,\"changed_by_email\":\"dave@code.org\"}]", "level_concept_difficulty": { } }]]> From 2cf4f22df0eb1d1f9b7f4a84713623678f0e5f3a Mon Sep 17 00:00:00 2001 From: David Bailey Date: Fri, 4 Aug 2017 16:24:57 -0700 Subject: [PATCH 11/11] remove stray puts [ci skip] --- dashboard/test/controllers/levels_controller_test.rb | 1 - 1 file changed, 1 deletion(-) diff --git a/dashboard/test/controllers/levels_controller_test.rb b/dashboard/test/controllers/levels_controller_test.rb index 7ef0a11b74572..eeac0f9c5faef 100644 --- a/dashboard/test/controllers/levels_controller_test.rb +++ b/dashboard/test/controllers/levels_controller_test.rb @@ -312,7 +312,6 @@ class LevelsControllerTest < ActionController::TestCase ) assert_response :success level = assigns(:level) - puts "level.properties #{level.properties}" assert_equal @program, level.properties['solution_blocks'] assert_s3_image_url level.properties['solution_image_url'] end