{"action":"created","issue":{"url":"https://api.github.com/repos/midasplatform/Midas/issues/146","labels_url":"https://api.github.com/repos/midasplatform/Midas/issues/146/labels{/name}","comments_url":"https://api.github.com/repos/midasplatform/Midas/issues/146/comments","events_url":"https://api.github.com/repos/midasplatform/Midas/issues/146/events","html_url":"https://github.com/midasplatform/Midas/pull/146","id":113530035,"number":146,"title":"uploadGeneratetoken: Add support to optionally create new revision","user":{"login":"jcfr","id":219043,"avatar_url":"https://avatars.githubusercontent.com/u/219043?v=3","gravatar_id":"","url":"https://api.github.com/users/jcfr","html_url":"https://github.com/jcfr","followers_url":"https://api.github.com/users/jcfr/followers","following_url":"https://api.github.com/users/jcfr/following{/other_user}","gists_url":"https://api.github.com/users/jcfr/gists{/gist_id}","starred_url":"https://api.github.com/users/jcfr/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/jcfr/subscriptions","organizations_url":"https://api.github.com/users/jcfr/orgs","repos_url":"https://api.github.com/users/jcfr/repos","events_url":"https://api.github.com/users/jcfr/events{/privacy}","received_events_url":"https://api.github.com/users/jcfr/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":1,"created_at":"2015-10-27T08:25:50Z","updated_at":"2015-10-27T08:31:55Z","closed_at":null,"pull_request":{"url":"https://api.github.com/repos/midasplatform/Midas/pulls/146","html_url":"https://github.com/midasplatform/Midas/pull/146","diff_url":"https://github.com/midasplatform/Midas/pull/146.diff","patch_url":"https://github.com/midasplatform/Midas/pull/146.patch"},"body":"This commit updates the \"uploadGeneratetoken\" API introducing the new\r\nparameter \"create_additional_revision\" allowing to optionally change\r\nthe default behavior and ensure a new revision is created when:\r\n  - a bitstream associated with the file already exists on the server\r\n  - and the checksum parameter is specified\r\n  - and the item updated has at least one revision\r\n\r\nSince the http uploader doesn't specify the \"checksum\" parameter, the\r\nproblem is only reproducible using the web API.\r\n\r\nFor example, considering the following configuration:\r\n\r\n```\r\n folder\r\n   |--- item1 --- revision1\r\n   |                 |--- bitstream1 (filename1)\r\n   |\r\n   |--- item2 --- revision1\r\n   |                 |--- bitstream2 (filename2)\r\n```\r\n\r\nBy default, trying to associate bitstream1 with item2 will result in\r\nthis configuration:\r\n\r\n```\r\n folder\r\n   |--- item1 --- revision1\r\n   |                 |--- bitstream1 (filename1)\r\n   |\r\n   |--- item2 --- revision1\r\n   |                 |--- bitstream2 (filename2)\r\n   |                 |--- bitstream1 (filename1)\r\n```\r\n\r\nBy setting the option \"create_additional_revision\" to True, the\r\nfollowing configuration will be obtained:\r\n\r\n```\r\n folder\r\n   |--- item1 --- revision1\r\n   |                 |--- bitstream1 (filename1)\r\n   |\r\n   |--- item2 -|--- revision1\r\n   |           |     |--- bitstream2 (filename2)\r\n   |           |\r\n   |           |--- revision2\r\n   |           |     |--- bitstream1 (filename1)\r\n```"},"comment":{"url":"https://api.github.com/repos/midasplatform/Midas/issues/comments/151413387","html_url":"https://github.com/midasplatform/Midas/pull/146#issuecomment-151413387","issue_url":"https://api.github.com/repos/midasplatform/Midas/issues/146","id":151413387,"user":{"login":"jcfr","id":219043,"avatar_url":"https://avatars.githubusercontent.com/u/219043?v=3","gravatar_id":"","url":"https://api.github.com/users/jcfr","html_url":"https://github.com/jcfr","followers_url":"https://api.github.com/users/jcfr/followers","following_url":"https://api.github.com/users/jcfr/following{/other_user}","gists_url":"https://api.github.com/users/jcfr/gists{/gist_id}","starred_url":"https://api.github.com/users/jcfr/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/jcfr/subscriptions","organizations_url":"https://api.github.com/users/jcfr/orgs","repos_url":"https://api.github.com/users/jcfr/repos","events_url":"https://api.github.com/users/jcfr/events{/privacy}","received_events_url":"https://api.github.com/users/jcfr/received_events","type":"User","site_admin":false},"created_at":"2015-10-27T08:31:55Z","updated_at":"2015-10-27T08:31:55Z","body":"The following snippet allow to reproduce the problem: \r\n\r\n```\r\n%reload_ext autoreload\r\n%autoreload 1\r\n%aimport pydas\r\nimport hashlib\r\nimport os\r\nimport time\r\n\r\nmidas_url = 'http://slicer.kitware.com/midas3'\r\nemail = os.environ[\"MIDAS_PACKAGE_EMAIL\"]\r\napikey = os.environ[\"MIDAS_PACKAGE_API_KEY\"]\r\ncommunicator = pydas.core.Communicator(midas_url)\r\n\r\nfolder_id = 1654 # Update this with a folder you have write access\r\n\r\ndef token(email, apikey):\r\n    return communicator.login_with_api_key(email, apikey)\r\n\r\ndef md5(fname):\r\n    hash = hashlib.md5()\r\n    with open(fname) as f:\r\n        for chunk in iter(lambda: f.read(4096), \"\"):\r\n            hash.update(chunk)\r\n    return hash.hexdigest()\r\n\r\ndef generate_file(filepath):\r\n    with open(filepath, 'wb') as fout:\r\n        fout.write(os.urandom(1024))\r\n    filename = os.path.basename(filepath)\r\n    checksum = md5(filepath)\r\n    print(\"filepath: %s, md5: %s\" % (filepath, checksum))\r\n    return (filename, checksum)\r\n\r\nprefix = str(int(time.time()))\r\n\r\n# Create original file for item #1\r\nfilepath_item1 = './%s-bistream-1.bin' % prefix\r\n(filename_item1, checksum_item1) = generate_file(filepath_item1)\r\n\r\n# Create item #1\r\nitem = communicator.create_item(token(email, apikey), '%s-item1' % prefix, folder_id)\r\nitem_id = item['item_id']\r\nprint(\"item #1 created: %s\" % (item_id))\r\n\r\n# Upload initial revision into item #1\r\nupload_token = communicator.generate_upload_token(token(email, apikey), item_id, filename_item1)\r\ncommunicator.perform_upload(upload_token, filename_item1, item_id=item_id, filepath=filepath_item1)\r\nprint(\"item #1: initial revision created\")\r\n\r\n# Create original file for item #2\r\nfilepath_item2 = './%s-bistream-2.bin' % prefix\r\n(filename_item2, checksum_item2) = generate_file(filepath_item2)\r\n\r\n# Create item #2\r\nitem = communicator.create_item(token(email, apikey), '%s-item2' % prefix, folder_id)\r\nitem_id = item['item_id']\r\nprint(\"item #2 created: %s\" % (item_id))\r\n\r\n# Upload initial revision into item #2\r\nupload_token = communicator.generate_upload_token(token(email, apikey), item_id, filename_item2)\r\ncommunicator.perform_upload(upload_token, filename_item2, item_id=item_id, filepath=filepath_item2)\r\nprint(\"item #2: initial revision created\")\r\n\r\n# Upload an other revision into item #2 associating bitstream created for item #1\r\nupload_token = communicator.generate_upload_token(token(email, apikey), item_id, filename_item1, checksum=checksum_item1)\r\nprint(\"item #2: other revision created\")\r\nif upload_token:\r\n    raise Exception('item #2: upload_token is expected to be empty')\r\n```\r\n\r\nItem1:\r\n\r\n![item1-before-pr-update-uploadgeneratetoken-with-create-additional-revision](https://cloud.githubusercontent.com/assets/219043/10752900/9689e632-7c63-11e5-8b63-bcaf5ade98c6.png)\r\n\r\n\r\nItem2:\r\n\r\n![item2-before-pr-update-uploadgeneratetoken-with-create-additional-revision](https://cloud.githubusercontent.com/assets/219043/10752905/9a962c4a-7c63-11e5-8324-dda0a1f3ff48.png)\r\n\r\n\r\n"}}