{"id":549,"date":"2016-04-19T11:39:19","date_gmt":"2016-04-19T10:39:19","guid":{"rendered":"http:\/\/www.haxed.me.uk\/?p=549"},"modified":"2016-04-19T15:36:47","modified_gmt":"2016-04-19T14:36:47","slug":"creating-next-generation-server-image-first-generation-server","status":"publish","type":"post","link":"https:\/\/haxed.me.uk\/index.php\/2016\/04\/19\/creating-next-generation-server-image-first-generation-server\/","title":{"rendered":"Creating a Next Generation Server image from a First Generation Server"},"content":{"rendered":"<p>So we had a customer today that wanted to create a next generation cloud-server using a first generation server image. Since the first gen platform uses cloud files, it&#8217;s possible to do manually, downloading from cloud files , concatenating and untar to access the filesystem.<\/p>\n<p>Like so;<\/p>\n<pre>\r\ncat receiverTar1.tar receivedTar2.tar >> alltars.tar\r\ntar -itvf alltars.tar\r\n<\/pre>\n<p>Although I used on my mac:<\/p>\n<pre>\r\ntar -vxf alltars.tar \r\n<\/pre>\n<p>This gives us the VHD files extracted into an &#8216;image&#8217; folder;<\/p>\n<pre>\r\n$ ls -al image\/\r\ntotal 79851760\r\ndrwxr-xr-x   6 adam9261  RACKSPACE\\Domain Users          204 Apr 19 12:17 .\r\ndrwxr-xr-x  11 adam9261  RACKSPACE\\Domain Users          374 Apr 19 11:47 ..\r\n-rw-r--r--   1 adam9261  RACKSPACE\\Domain Users  40884003328 Jan  4 07:05 image.vhd\r\n-rwxr-xr-x   1 adam9261  RACKSPACE\\Domain Users         1581 Apr 19 12:15 import-container.sh\r\n-rw-r--r--   1 adam9261  RACKSPACE\\Domain Users            8 Jan  4 07:05 manifest.ovf\r\n-rw-r--r--   1 adam9261  RACKSPACE\\Domain Users        84480 Jan  4 07:05 snap.vhd\r\n<\/pre>\n<p>We are interested in the image.vhd file. Now lets upload it to cloud files to IMPORT it into Glance, which is what is used by the next generation platform to create a new server. The problem of course was that the first gen image format wasn&#8217;t compatible. Next gen builds need to retrieve the VHD image from glance.<\/p>\n<p>Also, lets ensure we use Transfer-Encoding: chunked&#8221; as a host -H header. This tells Cloud Files that the .vhd exceeds 5G and it will create a multi-part manifest for us for the main file. Splitting it up for us into multiple objects spanned across 5Gig Files!<\/p>\n<pre>\r\n\r\n# Username used to login to control panel\r\nUSERNAME='mycloudusername'\r\n# Find the APIKey in the 'account settings' part of the menu of the control panel\r\nAPIKEY='mycloudapikey'\r\n# Find the image ID you'd like to make available on cloud files\r\nCUSTOMER_ID=10001010\r\n\r\nIMPORT_CF_ENDPOINT=\"https:\/\/storage101.lon3.clouddrive.com\/v1\/MossoCloudFS_50441c7a-dc22-4287-8e8c-b9844df\"\r\n\r\n# This section simply retrieves the TOKEN\r\nTOKEN=`curl https:\/\/identity.api.rackspacecloud.com\/v2.0\/tokens -X POST -d '{ \"auth\":{\"RAX-KSKEY:apiKeyCredentials\": { \"username\":\"'$USERNAME'\", \"apiKey\": \"'$APIKEY'\" }} }' -H \"Content-type: application\/json\" |  python -mjson.tool | grep -A5 token | grep id | cut -d '\"' -f4`\r\n\r\n# Upload VHD\r\ncurl -X PUT -T image.vhd \\\r\n-H \"X-Auth-Token: $TOKEN\" \\\r\n-H \"Transfer-Encoding: chunked\" \\\r\n\"$IMPORT_CF_ENDPOINT\/import\/image.vhd\"\r\n\r\n<\/pre>\n<p>Update: <\/p>\n<p>Something in curl transmission caused it to sadly, mess up. So I used swiftly instead.<\/p>\n<pre>\r\n$ swiftly put -i image.vhd import\/image.vhd\r\n<\/pre>\n<p>The problem with swiftly was it didn&#8217;t like my .swiftly file in my ~ as should work 100% without problems, but it didn&#8217;t. With help of my friend Jake this is what I did, to get round that and set manually in the environment (as opposed to using the .swiftly file)<\/p>\n<pre>\r\nabull-mb:~ adam9261$ export SWIFTLY_AUTH_URL=https:\/\/identity.api.rackspacecloud.com\/v2.0\r\nabull-mb:~ adam9261$ export SWIFTLY_AUTH_USER=cloudusernamehere\r\nabull-mb:~ adam9261$ export SWIFTLY_AUTH_KEY=apikeyhere\r\nabull-mb:~ adam9261$ swiftly auth\r\n<\/pre>\n<p>Next stage import to glance <\/p>\n<pre>\r\n#!\/bin\/bash\r\n\r\n# Username used to login to control panel\r\nUSERNAME='mycloudusername'\r\n# Find the APIKey in the 'account settings' part of the menu of the control panel\r\nAPIKEY='mycloudapikey'\r\n# Find the image ID you'd like to make available on cloud files\r\nCUSTOMER_ID=10001010\r\nIMPORT_CF_ENDPOINT=\"https:\/\/storage101.lon3.clouddrive.com\/v1\/MossoCloudFS_50441c7a-dc22-4287-8e8c-b6d76b237da\"\r\nIMPORT_IMAGE_ENDPOINT=https:\/\/LON.images.api.rackspacecloud.com\/v2\/$CUSTOMER_ID\r\n\r\n\r\n# This section simply retrieves the TOKEN\r\nTOKEN=`curl https:\/\/identity.api.rackspacecloud.com\/v2.0\/tokens -X POST -d '{ \"auth\":{\"RAX-KSKEY:apiKeyCredentials\": { \"username\":\"'$USERNAME'\", \"apiKey\": \"'$APIKEY'\" }} }' -H \"Content-type: application\/json\" |  python -mjson.tool | grep -A5 token | grep id | cut -d '\"' -f4`\r\n\r\n\r\nVHD-NOTES=TESTING-RACKSPACE-IMAGE-IMPORT\r\nIMPORT_CONTAINER=import\r\n\r\ncurl -X POST \"$IMPORT_IMAGE_ENDPOINT\/tasks\" \\\r\n      -H \"X-Auth-Token: $TOKEN\" \\\r\n      -H \"Content-Type: application\/json\" \\\r\n      -d \"{\\\"type\\\":\\\"import\\\",\\\"input\\\":{\\\"image_properties\\\":{\\\"name\\\":\\\"$VHD_NOTES\\\"},\\\"import_from\\\":\\\"$IMPORT_CONTAINER\/image.vhd\\\"}}\" |\\\r\n      python -mjson.tool\r\n<\/pre>\n<p>Please note that image.vhd is hardcoded into the curl import. Also see VHD-NOTES variable which is passed to the task. This is just to identify the image more easily.<\/p>\n<p><strong> Response: <\/strong><\/p>\n<pre>\r\n{\r\n    \"created_at\": \"2016-04-19T13:12:57Z\",\r\n    \"id\": \"ff7d8c09-9dd7-43ed-824f-338201681b12\",\r\n    \"input\": {\r\n        \"image_properties\": {\r\n            \"name\": \"\"\r\n        },\r\n        \"import_from\": \"import\/image.vhd\"\r\n    },\r\n    \"message\": \"\",\r\n    \"owner\": \"10001010\",\r\n    \"result\": null,\r\n    \"schema\": \"\/v2\/schemas\/task\",\r\n    \"self\": \"\/v2\/tasks\/ff7d8c09-9dd7-43ed-815f-338201681ba7\",\r\n    \"status\": \"pending\",\r\n    \"type\": \"import\",\r\n    \"updated_at\": \"2016-04-19T13:12:57Z\"\r\n}\r\n<\/pre>\n<p>I then retrieved the Task details: (code not included yet). In this case I used pitchfork.cloudapi.co. A rackspace service that allows you to make API calls using a web frontend. <\/p>\n<p>I was in a rush to get this done for the customer as soon as possible.<\/p>\n<pre>\r\n{\r\n    \"status\": \"processing\", \r\n    \"created_at\": \"2016-04-19T13:12:57Z\", \r\n    \"updated_at\": \"2016-04-19T13:12:58Z\", \r\n    \"id\": \"ff7d8c09-9dd7-43ed-824f-338201681b12\", \r\n    \"result\": null, \r\n    \"owner\": \"10009158\", \r\n    \"input\": {\r\n        \"image_properties\": {\r\n            \"name\": \"\"\r\n        }, \r\n        \"import_from\": \"import\/image.vhd\"\r\n    }, \r\n    \"message\": \"\", \r\n    \"type\": \"import\", \r\n    \"self\": \"\/v2\/tasks\/ff7d8c09-9dd7-43ed-815f-338201681ba7\", \r\n    \"schema\": \"\/v2\/schemas\/task\"\r\n}\r\n\r\n<\/pre>\n<p>We can now see that the status is processing. When it has completed, it will tell us whether it failed or not <\/p>\n<p>After waiting 30 minutes or so:<\/p>\n<pre>\r\n{\r\n    \"status\": \"success\", \r\n    \"created_at\": \"2016-04-19T13:12:57Z\", \r\n    \"updated_at\": \"2016-04-19T14:22:53Z\", \r\n    \"expires_at\": \"2016-04-21T14:22:53Z\", \r\n    \"id\": \"ff7d8c09-9dd7-43ed-815f-338201681ba7\", \r\n    \"result\": {\r\n        \"image_id\": \"826bbb51-0f83-4278-b0ad-702aba088aae\"\r\n    }, \r\n    \"owner\": \"10009158\", \r\n    \"input\": {\r\n        \"image_properties\": {\r\n            \"name\": \"\"\r\n        }, \r\n        \"import_from\": \"import\/image.vhd\"\r\n    }, \r\n    \"message\": \"\", \r\n    \"type\": \"import\", \r\n    \"self\": \"\/v2\/tasks\/ff7d8c09-9dd7-43ed-815f-338201681ba7\", \r\n    \"schema\": \"\/v2\/schemas\/task\"\r\n}\r\n<\/pre>\n<p>It worked!<\/p>\n","protected":false},"excerpt":{"rendered":"<p>So we had a customer today that wanted to create a next generation cloud-server using a first generation server image. Since the first gen platform uses cloud files, it&#8217;s possible to do manually, downloading from cloud files , concatenating and &hellip; <a href=\"https:\/\/haxed.me.uk\/index.php\/2016\/04\/19\/creating-next-generation-server-image-first-generation-server\/\">Continue reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[13,19,15,30,7,36],"tags":[],"class_list":["post-549","post","type-post","status-publish","format-standard","hentry","category-api","category-bash","category-cloud","category-glance-api","category-management-tools","category-migration"],"_links":{"self":[{"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/posts\/549","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/comments?post=549"}],"version-history":[{"count":9,"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/posts\/549\/revisions"}],"predecessor-version":[{"id":558,"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/posts\/549\/revisions\/558"}],"wp:attachment":[{"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/media?parent=549"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/categories?post=549"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/haxed.me.uk\/index.php\/wp-json\/wp\/v2\/tags?post=549"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}