{"action":"created","comment":{"url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/comments/24509223","id":24509223,"diff_hunk":"@@ -0,0 +1,88 @@\n+\"\"\"\n+The mentoring XBlock is currently designed to be edited using XML.\n+\n+Until it is re-written to allow creating children with a nice GUI in Studio,\n+this file contains a hack that allows us to parse the XML and create blocks in\n+Studio from the parsed XML.\n+\n+It works by parsing the XML and creating XBlocks in a temporary runtime\n+environment, so that the blocks' fields can be read and copied into Studio.\n+\"\"\"\n+from xblock.fields import Scope\n+from xblock.runtime import Runtime, DictKeyValueStore, KvsFieldData, MemoryIdManager, ScopeIds\n+\n+\n+class TransientRuntime(Runtime):\n+    \"\"\"\n+    An XBlock runtime designed to have no persistence and no ability to render views/handlers.\n+    \"\"\"\n+    def __init__(self):\n+        id_manager = MemoryIdManager()\n+        field_data = KvsFieldData(DictKeyValueStore())\n+        super(TransientRuntime, self).__init__(\n+            id_reader=id_manager,\n+            id_generator=id_manager,\n+            field_data=field_data,\n+        )\n+\n+    def create_block_from_node(self, node):\n+        \"\"\"\n+        Parse an XML node representing an XBlock (and children), and return the XBlock.\n+        \"\"\"\n+        block_type = node.tag\n+        def_id = self.id_generator.create_definition(block_type)\n+        usage_id = self.id_generator.create_usage(def_id)\n+        keys = ScopeIds(None, block_type, def_id, usage_id)\n+        block_class = self.mixologist.mix(self.load_block_type(block_type))\n+        block = block_class.parse_xml(node, self, keys, self.id_generator)\n+        block.save()\n+        return block\n+\n+    def handler_url(self, *args, **kwargs):\n+        raise RuntimeError(\"TransientRuntime does not support handler_url.\")","path":"mentoring/studio_xml_utils.py","position":42,"original_position":42,"commit_id":"24f648fccfc934d384cd6acfa02b5e83fff9b12a","original_commit_id":"24f648fccfc934d384cd6acfa02b5e83fff9b12a","user":{"login":"Kelketek","id":1099483,"avatar_url":"https://avatars.githubusercontent.com/u/1099483?v=3","gravatar_id":"","url":"https://api.github.com/users/Kelketek","html_url":"https://github.com/Kelketek","followers_url":"https://api.github.com/users/Kelketek/followers","following_url":"https://api.github.com/users/Kelketek/following{/other_user}","gists_url":"https://api.github.com/users/Kelketek/gists{/gist_id}","starred_url":"https://api.github.com/users/Kelketek/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/Kelketek/subscriptions","organizations_url":"https://api.github.com/users/Kelketek/orgs","repos_url":"https://api.github.com/users/Kelketek/repos","events_url":"https://api.github.com/users/Kelketek/events{/privacy}","received_events_url":"https://api.github.com/users/Kelketek/received_events","type":"User","site_admin":false},"body":"Could we make these NotSupportedErrors?","created_at":"2015-02-11T16:35:17Z","updated_at":"2015-02-11T16:35:17Z","html_url":"https://github.com/open-craft/xblock-mentoring/pull/5#discussion_r24509223","pull_request_url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5","_links":{"self":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/comments/24509223"},"html":{"href":"https://github.com/open-craft/xblock-mentoring/pull/5#discussion_r24509223"},"pull_request":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5"}}},"pull_request":{"url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5","id":29067865,"html_url":"https://github.com/open-craft/xblock-mentoring/pull/5","diff_url":"https://github.com/open-craft/xblock-mentoring/pull/5.diff","patch_url":"https://github.com/open-craft/xblock-mentoring/pull/5.patch","issue_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/5","number":5,"state":"open","locked":false,"title":"Fix so real children work in studio and LMS (OC-513)","user":{"login":"bradenmacdonald","id":945577,"avatar_url":"https://avatars.githubusercontent.com/u/945577?v=3","gravatar_id":"","url":"https://api.github.com/users/bradenmacdonald","html_url":"https://github.com/bradenmacdonald","followers_url":"https://api.github.com/users/bradenmacdonald/followers","following_url":"https://api.github.com/users/bradenmacdonald/following{/other_user}","gists_url":"https://api.github.com/users/bradenmacdonald/gists{/gist_id}","starred_url":"https://api.github.com/users/bradenmacdonald/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/bradenmacdonald/subscriptions","organizations_url":"https://api.github.com/users/bradenmacdonald/orgs","repos_url":"https://api.github.com/users/bradenmacdonald/repos","events_url":"https://api.github.com/users/bradenmacdonald/events{/privacy}","received_events_url":"https://api.github.com/users/bradenmacdonald/received_events","type":"User","site_admin":false},"body":"This branch fixes two things:\r\n\r\n1. The \"real children\" conversion (#1) was not compatible with Studio, due to the way mentoring is designed to be edited as XML, which Studio doesn't really support when it comes to child XBlocks. See the extensive discussion in [OC-513](http://tasks.opencraft.com/browse/OC-513) and [on the ML](https://groups.google.com/forum/#!topic/edx-code/1fKZvkwgBVg).\r\n  * Fix: I added some questionable hacks (contained within a new file, `studio_xml_utils.py`). Since Studio provides no mechanism for instantiating XBlocks from XML, the workaround is to create our own in-memory XBlock runtime and instantiate temporary XBlocks from XML using that temporary runtime. We can then see all the XBlocks as they are created from the XML and tell Studio to create similar ones and make them children of the mentoring block.\r\n  * Problems with this fix:\r\n    - It's definitely a bit of a hack, but that *may* be considered acceptable until we get around to implementing a new way of editing the block in Studio that doesn't require XML.\r\n    - The child XBlocks can't expect to persist data to their XBlock fields. This is fine as none of them are currently designed to do this.\r\n    - `studio_xml_utils.py` needs to access the modulestore directly. This is not ideal but isn't horrible since we already know we're being used in edX Studio. (This only ever occurs from the `studio_submit` view handler).\r\n    - **The XBlock must be edited and saved in Studio** before it will work properly. This means that if you update an existing course or even just add a new block, you have to click \"Edit > Save\" on each XBlock before they will work. This is the only problem that I see being a big deal. I'm still thinking about what to do about this.\r\n\r\n2. edx-platform already has an `html` XBlock which conflicts with the html block we include in this repository. I fixed this by renaming all of the XBlocks to e.g. `mentoring-html` instead of `html`. I added some magic so that inside a `<mentoring>` element, the new `mentoring-` prefix can be left out.","created_at":"2015-02-11T04:33:33Z","updated_at":"2015-02-11T16:35:17Z","closed_at":null,"merged_at":null,"merge_commit_sha":"8a4b6852d3e9fd0c3b30a9c51a7d6da023d80a11","assignee":null,"milestone":null,"commits_url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5/commits","review_comments_url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5/comments","review_comment_url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/comments/{number}","comments_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/5/comments","statuses_url":"https://api.github.com/repos/open-craft/xblock-mentoring/statuses/24f648fccfc934d384cd6acfa02b5e83fff9b12a","head":{"label":"open-craft:real-children-studio","ref":"real-children-studio","sha":"24f648fccfc934d384cd6acfa02b5e83fff9b12a","user":{"login":"open-craft","id":7414786,"avatar_url":"https://avatars.githubusercontent.com/u/7414786?v=3","gravatar_id":"","url":"https://api.github.com/users/open-craft","html_url":"https://github.com/open-craft","followers_url":"https://api.github.com/users/open-craft/followers","following_url":"https://api.github.com/users/open-craft/following{/other_user}","gists_url":"https://api.github.com/users/open-craft/gists{/gist_id}","starred_url":"https://api.github.com/users/open-craft/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/open-craft/subscriptions","organizations_url":"https://api.github.com/users/open-craft/orgs","repos_url":"https://api.github.com/users/open-craft/repos","events_url":"https://api.github.com/users/open-craft/events{/privacy}","received_events_url":"https://api.github.com/users/open-craft/received_events","type":"Organization","site_admin":false},"repo":{"id":29684458,"name":"xblock-mentoring","full_name":"open-craft/xblock-mentoring","owner":{"login":"open-craft","id":7414786,"avatar_url":"https://avatars.githubusercontent.com/u/7414786?v=3","gravatar_id":"","url":"https://api.github.com/users/open-craft","html_url":"https://github.com/open-craft","followers_url":"https://api.github.com/users/open-craft/followers","following_url":"https://api.github.com/users/open-craft/following{/other_user}","gists_url":"https://api.github.com/users/open-craft/gists{/gist_id}","starred_url":"https://api.github.com/users/open-craft/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/open-craft/subscriptions","organizations_url":"https://api.github.com/users/open-craft/orgs","repos_url":"https://api.github.com/users/open-craft/repos","events_url":"https://api.github.com/users/open-craft/events{/privacy}","received_events_url":"https://api.github.com/users/open-craft/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/open-craft/xblock-mentoring","description":"Mentoring XBlock for edX","fork":true,"url":"https://api.github.com/repos/open-craft/xblock-mentoring","forks_url":"https://api.github.com/repos/open-craft/xblock-mentoring/forks","keys_url":"https://api.github.com/repos/open-craft/xblock-mentoring/keys{/key_id}","collaborators_url":"https://api.github.com/repos/open-craft/xblock-mentoring/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/open-craft/xblock-mentoring/teams","hooks_url":"https://api.github.com/repos/open-craft/xblock-mentoring/hooks","issue_events_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/events{/number}","events_url":"https://api.github.com/repos/open-craft/xblock-mentoring/events","assignees_url":"https://api.github.com/repos/open-craft/xblock-mentoring/assignees{/user}","branches_url":"https://api.github.com/repos/open-craft/xblock-mentoring/branches{/branch}","tags_url":"https://api.github.com/repos/open-craft/xblock-mentoring/tags","blobs_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/refs{/sha}","trees_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/trees{/sha}","statuses_url":"https://api.github.com/repos/open-craft/xblock-mentoring/statuses/{sha}","languages_url":"https://api.github.com/repos/open-craft/xblock-mentoring/languages","stargazers_url":"https://api.github.com/repos/open-craft/xblock-mentoring/stargazers","contributors_url":"https://api.github.com/repos/open-craft/xblock-mentoring/contributors","subscribers_url":"https://api.github.com/repos/open-craft/xblock-mentoring/subscribers","subscription_url":"https://api.github.com/repos/open-craft/xblock-mentoring/subscription","commits_url":"https://api.github.com/repos/open-craft/xblock-mentoring/commits{/sha}","git_commits_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/commits{/sha}","comments_url":"https://api.github.com/repos/open-craft/xblock-mentoring/comments{/number}","issue_comment_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/comments/{number}","contents_url":"https://api.github.com/repos/open-craft/xblock-mentoring/contents/{+path}","compare_url":"https://api.github.com/repos/open-craft/xblock-mentoring/compare/{base}...{head}","merges_url":"https://api.github.com/repos/open-craft/xblock-mentoring/merges","archive_url":"https://api.github.com/repos/open-craft/xblock-mentoring/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/open-craft/xblock-mentoring/downloads","issues_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues{/number}","pulls_url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls{/number}","milestones_url":"https://api.github.com/repos/open-craft/xblock-mentoring/milestones{/number}","notifications_url":"https://api.github.com/repos/open-craft/xblock-mentoring/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/open-craft/xblock-mentoring/labels{/name}","releases_url":"https://api.github.com/repos/open-craft/xblock-mentoring/releases{/id}","created_at":"2015-01-22T15:11:16Z","updated_at":"2015-02-06T07:36:33Z","pushed_at":"2015-02-11T04:23:18Z","git_url":"git://github.com/open-craft/xblock-mentoring.git","ssh_url":"git@github.com:open-craft/xblock-mentoring.git","clone_url":"https://github.com/open-craft/xblock-mentoring.git","svn_url":"https://github.com/open-craft/xblock-mentoring","homepage":null,"size":1716,"stargazers_count":0,"watchers_count":0,"language":"Python","has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":2,"forks":0,"open_issues":2,"watchers":0,"default_branch":"master"}},"base":{"label":"open-craft:master","ref":"master","sha":"00778d0326dee10e9aaea684063b0151b9a818e1","user":{"login":"open-craft","id":7414786,"avatar_url":"https://avatars.githubusercontent.com/u/7414786?v=3","gravatar_id":"","url":"https://api.github.com/users/open-craft","html_url":"https://github.com/open-craft","followers_url":"https://api.github.com/users/open-craft/followers","following_url":"https://api.github.com/users/open-craft/following{/other_user}","gists_url":"https://api.github.com/users/open-craft/gists{/gist_id}","starred_url":"https://api.github.com/users/open-craft/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/open-craft/subscriptions","organizations_url":"https://api.github.com/users/open-craft/orgs","repos_url":"https://api.github.com/users/open-craft/repos","events_url":"https://api.github.com/users/open-craft/events{/privacy}","received_events_url":"https://api.github.com/users/open-craft/received_events","type":"Organization","site_admin":false},"repo":{"id":29684458,"name":"xblock-mentoring","full_name":"open-craft/xblock-mentoring","owner":{"login":"open-craft","id":7414786,"avatar_url":"https://avatars.githubusercontent.com/u/7414786?v=3","gravatar_id":"","url":"https://api.github.com/users/open-craft","html_url":"https://github.com/open-craft","followers_url":"https://api.github.com/users/open-craft/followers","following_url":"https://api.github.com/users/open-craft/following{/other_user}","gists_url":"https://api.github.com/users/open-craft/gists{/gist_id}","starred_url":"https://api.github.com/users/open-craft/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/open-craft/subscriptions","organizations_url":"https://api.github.com/users/open-craft/orgs","repos_url":"https://api.github.com/users/open-craft/repos","events_url":"https://api.github.com/users/open-craft/events{/privacy}","received_events_url":"https://api.github.com/users/open-craft/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/open-craft/xblock-mentoring","description":"Mentoring XBlock for edX","fork":true,"url":"https://api.github.com/repos/open-craft/xblock-mentoring","forks_url":"https://api.github.com/repos/open-craft/xblock-mentoring/forks","keys_url":"https://api.github.com/repos/open-craft/xblock-mentoring/keys{/key_id}","collaborators_url":"https://api.github.com/repos/open-craft/xblock-mentoring/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/open-craft/xblock-mentoring/teams","hooks_url":"https://api.github.com/repos/open-craft/xblock-mentoring/hooks","issue_events_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/events{/number}","events_url":"https://api.github.com/repos/open-craft/xblock-mentoring/events","assignees_url":"https://api.github.com/repos/open-craft/xblock-mentoring/assignees{/user}","branches_url":"https://api.github.com/repos/open-craft/xblock-mentoring/branches{/branch}","tags_url":"https://api.github.com/repos/open-craft/xblock-mentoring/tags","blobs_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/refs{/sha}","trees_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/trees{/sha}","statuses_url":"https://api.github.com/repos/open-craft/xblock-mentoring/statuses/{sha}","languages_url":"https://api.github.com/repos/open-craft/xblock-mentoring/languages","stargazers_url":"https://api.github.com/repos/open-craft/xblock-mentoring/stargazers","contributors_url":"https://api.github.com/repos/open-craft/xblock-mentoring/contributors","subscribers_url":"https://api.github.com/repos/open-craft/xblock-mentoring/subscribers","subscription_url":"https://api.github.com/repos/open-craft/xblock-mentoring/subscription","commits_url":"https://api.github.com/repos/open-craft/xblock-mentoring/commits{/sha}","git_commits_url":"https://api.github.com/repos/open-craft/xblock-mentoring/git/commits{/sha}","comments_url":"https://api.github.com/repos/open-craft/xblock-mentoring/comments{/number}","issue_comment_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/comments/{number}","contents_url":"https://api.github.com/repos/open-craft/xblock-mentoring/contents/{+path}","compare_url":"https://api.github.com/repos/open-craft/xblock-mentoring/compare/{base}...{head}","merges_url":"https://api.github.com/repos/open-craft/xblock-mentoring/merges","archive_url":"https://api.github.com/repos/open-craft/xblock-mentoring/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/open-craft/xblock-mentoring/downloads","issues_url":"https://api.github.com/repos/open-craft/xblock-mentoring/issues{/number}","pulls_url":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls{/number}","milestones_url":"https://api.github.com/repos/open-craft/xblock-mentoring/milestones{/number}","notifications_url":"https://api.github.com/repos/open-craft/xblock-mentoring/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/open-craft/xblock-mentoring/labels{/name}","releases_url":"https://api.github.com/repos/open-craft/xblock-mentoring/releases{/id}","created_at":"2015-01-22T15:11:16Z","updated_at":"2015-02-06T07:36:33Z","pushed_at":"2015-02-11T04:23:18Z","git_url":"git://github.com/open-craft/xblock-mentoring.git","ssh_url":"git@github.com:open-craft/xblock-mentoring.git","clone_url":"https://github.com/open-craft/xblock-mentoring.git","svn_url":"https://github.com/open-craft/xblock-mentoring","homepage":null,"size":1716,"stargazers_count":0,"watchers_count":0,"language":"Python","has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":2,"forks":0,"open_issues":2,"watchers":0,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5"},"html":{"href":"https://github.com/open-craft/xblock-mentoring/pull/5"},"issue":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/5"},"comments":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/issues/5/comments"},"review_comments":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5/comments"},"review_comment":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/comments/{number}"},"commits":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/pulls/5/commits"},"statuses":{"href":"https://api.github.com/repos/open-craft/xblock-mentoring/statuses/24f648fccfc934d384cd6acfa02b5e83fff9b12a"}}}}