Skip to content

Commit

Permalink
AGENT-280: Clean up the code some and add additional ds-options
Browse files Browse the repository at this point in the history
  • Loading branch information
orlandov committed Aug 22, 2011
1 parent c4cdb6b commit 88e4acf
Show file tree
Hide file tree
Showing 4 changed files with 116 additions and 68 deletions.
149 changes: 93 additions & 56 deletions lib/cli.js
@@ -1,34 +1,75 @@
var DatasetManifest = require('./dataset_manifest');
var DiskImage = require('./disk_image');
var async = require('async');
var crypto = require('crypto');
var execFile = require('child_process').execFile;
var fs = require('fs');
var fs = require('fs');
var optparse = require('optparse');
var path = require('path');
var util = require('util');
var xml2js = require('xml2js');
var crypto = require('crypto');
var fs = require('fs');
var uuid = require('node-uuid');
var xml2js = require('xml2js');

var DatasetManifest = require('./dataset_manifest');
function sha1file (filename, callback) {
var shasum = crypto.createHash('sha1');
var s = fs.ReadStream(filename);
s.on('data', function(d) {
shasum.update(d);
});

s.on('end', function() {
var d = shasum.digest('hex');
return callback(null, d);
});
}

function replaceFilenameExtension (filename, newExt) {
return ( path.join
( path.dirname(filename)
, path.basename
( filename
, path.extname(filename)
) + newExt
)
);
}

var CLI = module.exports = function () {}

CLI.prototype.parseOptions = function () {
var self = this;
var switches
= [ ['-h', '--help', 'This help message.']
, ['-n', '--ds-name VALUE', 'Short name for the dataset.']
, ['-v', '--ds-version VALUE', 'Semantic version of dataset.']
, ['-d', '--ds-description VALUE', 'Short description of dataset (to max. of 255 bytes).']
, ['-u', '--assets-url VALUE', 'Assets location url']
= [ ['-h', '--help', 'This help message']
, ['-n', '--ds-name VALUE', 'Short name for the dataset']
, ['-v', '--ds-version VALUE', 'Semantic version of dataset']
, ['-d', '--ds-description VALUE',
'Short description of dataset (to max. of 255 bytes)']
, ['-o', '--ds-os VALUE',
'The dataset operating system. (ie. linux, smartos, etc)']
, ['-a', '--assets-url VALUE', 'Assets location url']
, ['-D', '--ds-disk-driver VALUE', 'Set the VM\'s disk driver (default: virtio)']
, ['-N', '--ds-nic-driver VALUE', 'Set the VM\'s NIC driver (default: virtio)']
];

var examples
= [
{ description:
"bleh"
, example:
"$0 --assets-url http://10.99.99.6/datasets/ --dataset-os linux" +
"--name mylinux ./vms/mylinux.ovf /usbkey/datasets"
}
]

var options = this.options = {};
var parser = new optparse.OptionParser(switches);
parser.banner
= [ "Usage:"
, " " + [process.argv[0], process.argv[1], "[options] <vm.ovf> [output-directory]"].join(' ')
, " " + [ process.argv[0]
, process.argv[1]
, "[options] <vm.ovf> [output-directory]"
].join(' ')
].join("\n");

parser.on(2, function (value) {
Expand All @@ -43,18 +84,22 @@ CLI.prototype.parseOptions = function () {
self.displayHelp(parser.toString());
});

parser.on('ds-name', function (ds_name) {
parser.on('ds-name', function (name, ds_name) {
options.ds_name = ds_name;
});

parser.on('ds-version', function (ds_version) {
parser.on('ds-version', function (name, ds_version) {
options.ds_version = ds_version;
});

parser.on('ds-uuid', function (ds_uuid) {
parser.on('ds-uuid', function (name, ds_uuid) {
options.ds_uuid = ds_uuid;
});

parser.on('ds-os', function (name, ds_os) {
options.ds_os = ds_os;
});

parser.on('assets-url', function (name, assets_url) {
options.assets_url = assets_url;
});
Expand All @@ -68,6 +113,12 @@ CLI.prototype.parseOptions = function () {
process.exit(1);
}

if (!options.ds_os) {
console.error("Error: --ds-os must be specified\n");
self.displayHelp(parser.toString());
process.exit(1);
}

self.ovfFilename = options.input;
if (!options.outputDir) {
options.outputDir = '.';
Expand Down Expand Up @@ -95,7 +146,6 @@ CLI.prototype.start = function () {
, self.writeDatasetManifest.bind(self)
]
, function (error) {
console.dir(error);
console.log("All done!");
}
);
Expand Down Expand Up @@ -123,7 +173,7 @@ CLI.prototype.mkdir = function (callback) {
callback();
}
else {
fs.mkdir(self.options.outputDir, 0755, function (error) {
fs.mkdir(self.options.outputDir, parseInt('0755', 8), function (error) {
if (error) {
throw new Error(error.toString);
}
Expand Down Expand Up @@ -164,7 +214,7 @@ CLI.prototype.verifyFiles = function (callback) {
console.error("Digest mismatch for file " + filename);
process.exit(1);
}
fileDigests[filename] = computedDigest;
self.fileDigests[filename] = computedDigest;
callback();
});
}
Expand Down Expand Up @@ -196,23 +246,24 @@ CLI.prototype.createDatasetManifest = function (callback) {
var VirtualSystem = ovf.VirtualSystem;

self.parseDisks(ovf);
self.parseVirtualSytemSection(ovf);
// self.parseVirtualSytemSection(ovf);
self.parseNetworkSection(ovf);

manifest.name = this.options.ds_name || VirtualSystem['@']['ovf:id'];
manifest.requirements = {};
manifest.type = 'vmimage';
manifest.type = 'zvol';
manifest.uuid = this.options.ds_uuid || uuid().toLowerCase();
manifest.version = this.options.ds_version || '1.0.0';
manifest.os = this.options.ds_os || manifest.name;
manifest.disk_driver = this.options.disk_driver || 'virtio';
manifest.nic_driver = this.options.nic_driver || 'virtio';

return callback();
}

CLI.prototype.populateFiles = function (callback) {
var self = this;

console.dir(self.files);

async.forEach
( Object.keys(self.files)
, function (file, callback) {
Expand All @@ -234,7 +285,7 @@ CLI.prototype.populateFiles = function (callback) {
, function (callback) {
console.log("Verifying file " + outputFile);
sha1file(outputFile, function (error, sha) {
self.fileDigests[file] = record.sha = sha;
self.fileDigests[file] = record.sha1 = sha;
callback();
});
}
Expand All @@ -251,19 +302,8 @@ CLI.prototype.populateFiles = function (callback) {
);
}

function sha1file (filename, callback) {
var shasum = crypto.createHash('sha1');
var s = fs.ReadStream(filename);
s.on('data', function(d) {
shasum.update(d);
});

s.on('end', function() {
var d = shasum.digest('hex');
return callback(null, d);
});
}

/*
CLI.prototype.parseVirtualSytemSection = function (obj, callback) {
var self = this;
var VirtualHardwareSection = obj.VirtualSystem.VirtualHardwareSection;
Expand All @@ -277,12 +317,13 @@ CLI.prototype.parseVirtualSytemSection = function (obj, callback) {
break;
}
});
}
} */

CLI.prototype.parseNetworkSection = function (obj) {
var self = this;
var NetworkSection = obj.NetworkSection;
var Network;
var nets = [];

if (NetworkSection.Network) {
if (Array.isArray(NetworkSection.Network)) {
Expand All @@ -292,12 +333,11 @@ CLI.prototype.parseNetworkSection = function (obj) {
Network = [ NetworkSection.Network ];
}

var nets = [];
var count = 0;
var count = 0;

Network.forEach(function (n) {
nets.push({ name: 'net'+count++, description: n.Description });
});
Network.forEach(function (n) {
nets.push({ name: 'net'+count++, description: n.Description });
});
}

// Scan Networks
Expand Down Expand Up @@ -326,6 +366,11 @@ CLI.prototype.parseDisks = function () {
var Files = self.getAsArray(ovf.References, 'File');
var Disks = self.getAsArray(ovf.DiskSection, 'Disk');

if (Disks.length > 1) {
throw new Error(
"sdc-convertm does not support .ovf's describing multiple disks");
}

Files.forEach(function (File) {
var file
= files[File['@']['ovf:id']]
Expand All @@ -335,11 +380,16 @@ CLI.prototype.parseDisks = function () {
var href = File['@']['ovf:href'];
var m = href.match(/^(\w+):\/\//);
if (m) {
throw new Error ("OVF disk referenced file with unsupported href type: " + m[1]);
throw new Error(
"OVF disk referenced file with unsupported href type: " + m[1]);
}
file.path = path.join(dirname, href);
file.href = href;
file.outputFile = path.join(self.options.outputDir, replaceFilenameExtension(href, '.zfs.bz2'));
file.outputFile
= path.join
( self.options.outputDir
, replaceFilenameExtension(href, '.zfs.bz2')
);
});

Disks.forEach(function (Disk) {
Expand All @@ -365,6 +415,8 @@ CLI.prototype.parseDisks = function () {
+ allocUnits);
}
}

self.manifest.image_size = disk.capacityBytes / (1024*1024);
});
}

Expand All @@ -387,21 +439,17 @@ CLI.prototype.createDiskImages = function (callback) {
( Object.keys(self.disks)
, function (diskId, callback) {
var disk = self.disks[diskId];
console.dir(self.disks[disk]);
var diskImage = new DiskImage();

console.dir(disk);
var opts
= { inputFile: disk.file.path
, outputFile: disk.file.outputFile
, capacityBytes: disk.capacityBytes
, zpool: self.options.zpool
, format: disk.format
};
console.dir(opts);

diskImage.convertToZfsStream(opts, function (error) {
console.dir(arguments);
console.log("Done converting " + disk);
callback();
});
Expand All @@ -412,17 +460,6 @@ CLI.prototype.createDiskImages = function (callback) {
);
}

function replaceFilenameExtension (filename, newExt) {
return ( path.join
( path.dirname(filename)
, path.basename
( filename
, path.extname(filename)
) + newExt
)
);
}

var OVF = function () {}

OVF.prototype.parse = function (opts) {
Expand Down
4 changes: 3 additions & 1 deletion lib/dataset_manifest.js
@@ -1,6 +1,8 @@
var DatasetManifest = module.exports = function () {
var self = this;
var simpleKeys = 'name type uuid version files'.split(' ');
var simpleKeys =
[ 'name', 'type', 'uuid', 'version', 'image_size', 'files', 'os'
, 'disk_driver', 'nic_driver'];

this.manifest = { files: [], requirements: { networks : [] }};
var requirements = this.manifest.requirements;
Expand Down

0 comments on commit 88e4acf

Please sign in to comment.