Add Windows support to device init command

This commit is contained in:
Juan Cruz Viotti 2015-01-28 08:33:50 -04:00
parent f67cdaee43
commit db3d4292f4
2 changed files with 45 additions and 33 deletions

View File

@ -2,10 +2,9 @@ _ = require('lodash-contrib')
async = require('async')
resin = require('resin-sdk')
os = require('os')
fs = require('fs')
progressStream = require('progress-stream')
visuals = require('resin-cli-visuals')
commandOptions = require('./command-options')
drive = require('../drive/drive')
exports.list =
signature: 'devices'
@ -166,18 +165,6 @@ exports.init =
options: [ commandOptions.yes ]
permission: 'user'
action: (params, options, done) ->
if os.platform() is 'win32'
error = new Error('This functionality is only available on UNIX based systems for now.')
return done(error)
if not fs.existsSync(params.image)
error = new Error("Invalid OS image: #{params.image}")
return done(error)
if not fs.existsSync(params.device)
error = new Error("Invalid device: #{params.device}")
return done(error)
async.waterfall([
(callback) ->
@ -190,27 +177,14 @@ exports.init =
(confirmed, callback) ->
return done() if not confirmed
imageFile = fs.createReadStream(params.image)
deviceFile = fs.createWriteStream(params.device)
imageFileSize = fs.statSync(params.image).size
progressBar = null
progress = progressStream
length: imageFileSize
time: 500
if not options.quiet
progressBar = new visuals.widgets.Progress('Writing device OS', imageFileSize)
progress.on 'progress', (status) ->
drive.writeImage params.device, params.image,
progress: not options.quiet
onProgress: (status) ->
progressBar ?= new visuals.widgets.Progress('Writing device OS', status.length)
progressBar.tick(status.delta)
imageFile
.pipe(progress)
.pipe(deviceFile)
.on 'error', (error) ->
if error.code is 'EBUSY'
error.message = "Try umounting #{error.path} first."
return callback(error)
.on('close', callback)
, callback
], done)

38
lib/drive/drive.coffee Normal file
View File

@ -0,0 +1,38 @@
fs = require('fs')
progressStream = require('progress-stream')
exports.writeImage = (devicePath, imagePath, options = {}, callback = _.noop) ->
if not fs.existsSync(imagePath)
return callback(new Error("Invalid OS image: #{imagePath}"))
if not fs.existsSync(devicePath)
return callback(new Error("Invalid device: #{devicePath}"))
imageFile = fs.createReadStream(imagePath)
deviceFile = fs.createWriteStream devicePath,
# Required by Windows to work correctly
flags: 'r+'
imageFileSize = fs.statSync(imagePath).size
progress = progressStream
length: imageFileSize
time: 500
if options.progress
progress.on('progress', options.onProgress)
imageFile
.pipe(progress)
.pipe(deviceFile)
# TODO: We should make use of nodewindows.elevate()
# if we get an EPERM error.
.on 'error', (error) ->
if error.code is 'EBUSY'
error.message = "Try umounting #{error.path} first."
return callback(error)
.on('close', callback)