Skip to content

Commit

Permalink
added initial nightly-builder app
Browse files Browse the repository at this point in the history
  • Loading branch information
rvagg committed Apr 11, 2015
1 parent 94c2c20 commit 9b1c6d0
Show file tree
Hide file tree
Showing 8 changed files with 266 additions and 0 deletions.
1 change: 1 addition & 0 deletions tools/nightly-builder/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
node_modules
49 changes: 49 additions & 0 deletions tools/nightly-builder/build-required.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
"use strict"

const strftime = require('strftime').timezone(0)
, after = require('after')
, latestBuild = require('./latest-build')
, latestCommit = require('./latest-commit')

const dateFormat = '%Y%m%d'


function timeString () {
return strftime(dateFormat)
}


function buildRequired (type, callback) {
let done = after(2, onData)
, build
, commit

function onData (err) {
if (err)
return callback(err)

let buildCommit = build.commit.substr(0, 10)
, buildDate = strftime(dateFormat, build.date)
, nowDate = timeString()

commit = commit.substr(0, 10)

if (buildCommit != commit) // only need to compare commit
return callback(null, { type: type, commit: commit, date: nowDate })

return callback()
}

latestBuild(type, function (err, data) {
build = data
done(err)
})

latestCommit(type, function (err, data) {
commit = data
done(err)
})
}


module.exports = buildRequired
36 changes: 36 additions & 0 deletions tools/nightly-builder/latest-build.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
"use strict"

const jsonist = require('jsonist')

const indexUrl = 'https://iojs.org/download/{type}/index.json'


function latestBuild (type, callback) {
let url = indexUrl.replace(/\{type\}/, type)

function onGet (err, data) {
if (err)
return callback(err)

let i = -1

while (data[++i]) {
let m = data[i].version.match(/nightly(20\d\d)(\d\d)(\d\d)(\w{10,})/)
, date = new Date(m && `${m[1]}-${m[2]}-${m[3]}` || data[i].date)
, commit = m && m[4]

return callback(null, {
version : data[i].version
, date : date
, commit : commit
})
}

return callback(new Error(`no latest version for "${type}"`))
}

jsonist.get(url, onGet)
}


module.exports = latestBuild
27 changes: 27 additions & 0 deletions tools/nightly-builder/latest-commit.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
"use strict"

const ghrepos = require('ghrepos')

const nightlyRef = 'heads/v1.x'
, nightlyNextRef = 'heads/next'


function latestCommit (type, callback) {
let ref = type == 'nightly' ? nightlyRef : type == 'next-nightly' ? nightlyNextRef : null

if (!ref)
throw new Error(`Unknown type "${type}"`)

ghrepos.getRef(null, 'iojs', 'io.js', ref, function (err, data) {
if (err)
return callback(err)

if (!data || !data.object)
return callback(new Error(`Got unexpected data from GitHub: ${JSON.stringify(data)}`))

return callback(null, data.object.sha)
})
}


module.exports = latestCommit
30 changes: 30 additions & 0 deletions tools/nightly-builder/nightly-builder.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
"use strict"

const argv = require('minimist')(process.argv.slice(2))
, inspect = require('util').inspect
, buildRequired = require('./build-required')
, triggerBuild = require('./trigger-build')


if (typeof argv.type != 'string'
|| !/^(nightly|next-nightly)$/.test(argv.type)
|| typeof argv.token != 'string') {

console.error('Usage: nightly-builder --type <nightly|next-nightly> --token <jenkins job token>')
return process.exit(1)
}

buildRequired(argv.type, function (err, data) {
if (err)
throw err

if (!data)
return console.log('No build required')

triggerBuild(argv.token, data, function (err) {
if (err)
throw err

console.log(`Build triggered: ${inspect(data)}`)
})
})
23 changes: 23 additions & 0 deletions tools/nightly-builder/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
{
"name": "nightly-builder",
"version": "1.0.0",
"description": "nightly builder for io.js dist",
"main": "nightly-builder.js",
"author": "Rod Vagg <rod@vagg.org>",
"license": "MIT",
"scripts": {
"test": "node ./test.js"
},
"dependencies": {
"after": "~0.8.1",
"bl": "~0.9.4",
"ghrepos": "~1.0.2",
"hyperquest": "~1.0.1",
"jsonist": "~1.0.0",
"minimist": "~1.1.1",
"strftime": "~0.9.0"
},
"devDependencies": {
"tape": "~4.0.0"
}
}
47 changes: 47 additions & 0 deletions tools/nightly-builder/test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
"use strict"

const test = require('tape')
, latestCommit = require('./latest-commit')
, latestBuild = require('./latest-build')


test('latest-build', function (t) {
t.plan(14)
var other = null

function verify (type) {
return function (err, data) {
t.error(err, 'no error')
t.ok(data, 'got data')
let m = data.version && data.version.match(/v\d+\.\d+\.\d+-((?:next-)?nightly)20\d{6}\w{10,}/)
t.ok(m, `version (${data.version}) looks correct`)
t.equal(m && m[1], type, 'correct type')
t.ok(data.date < new Date(), `date (${data.date.toISOString()}) looks correct`)
t.ok(data.commit && data.commit.length >= 10, `commit (${data.commit}) looks right`)
t.notEqual(data.commit, other, 'commit not the same as other type of commit')
other = data.commit // who's gonna be first??
}
}

latestBuild('nightly', verify('nightly'))
latestBuild('next-nightly', verify('next-nightly'))
})


test('latest-commit', function (t) {
t.plan(8)
var other = null

function verify (type) {
return function (err, sha) {
t.error(err, 'no error')
t.equal(typeof sha, 'string', 'got sha')
t.equal(sha.length, 40, `sha looks good (${sha})`)
t.notEqual(sha, other, 'sha not the same as other type of sha')
other = sha // who's gonna be first??
}
}

latestCommit('nightly', verify('nightly'))
latestCommit('next-nightly', verify('next-nightly'))
})
53 changes: 53 additions & 0 deletions tools/nightly-builder/trigger-build.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
"use strict";

const hyperquest = require('hyperquest')
, bl = require('bl')
, qs = require('querystring')


const urlbase = 'https://jenkins-iojs.nodesource.com/job/iojs+release+nightly/build?token='
, buildUser = 'iojs'
, buildProject = 'io.js'


function triggerBuild(token, options, callback) {
let url = `${urlbase}${token}`
, data = {
parameter : [
{
name : 'user'
, value : buildUser
}
, {
name : 'project'
, value : buildProject
}
, {
name : 'commit'
, value : options.commit
}
, {
name : 'datestring'
, value : options.date
}
, {
name : 'buildtype'
, value : options.type
}
]
}
, post = qs.encode({
token : token
, json : JSON.stringify(data)
})

let req = hyperquest(url, {
method: 'post'
, headers: { 'content-type': 'application/x-www-form-urlencoded' }
})
req.end(post)
req.pipe(bl(callback))
}


module.exports = triggerBuild

0 comments on commit 9b1c6d0

Please sign in to comment.