Use webdriverio, not selenium-webdriver

This commit is contained in:
Max Brunsfeld 2015-02-06 10:38:40 -08:00
parent 6430bbb460
commit 56a4e6b7bf
3 changed files with 133 additions and 88 deletions

View File

@ -31,11 +31,11 @@
"request": "~2.27.0",
"rimraf": "~2.2.2",
"runas": "~1.0.1",
"selenium-webdriver": "^2.44.0",
"tello": "1.0.4",
"temp": "~0.8.1",
"underscore-plus": "1.x",
"unzip": "~0.1.9",
"vm-compatibility-layer": "~0.1.0"
"vm-compatibility-layer": "~0.1.0",
"webdriverio": "^2.4.5"
}
}

View File

@ -0,0 +1,86 @@
os = require "os"
path = require "path"
temp = require("temp").track()
remote = require "remote"
{spawn, spawnSync} = require "child_process"
webdriverio = require "../../../build/node_modules/webdriverio"
async = require "async"
AtomPath = remote.process.argv[0]
AtomLauncherPath = path.join(__dirname, "..", "helpers", "atom-launcher.sh")
SocketPath = path.join(os.tmpdir(), "atom-integration-test.sock")
ChromedriverPort = 9515
module.exports =
driverTest: (fn) ->
chromedriver = spawn("chromedriver", [
"--verbose",
"--port=#{ChromedriverPort}",
"--url-base=/wd/hub"
])
logs = []
errorCode = null
chromedriver.on "exit", (code, signal) ->
errorCode = code unless signal?
chromedriver.stderr.on "data", (log) ->
logs.push(log.toString())
chromedriver.stderr.on "close", ->
if errorCode?
jasmine.getEnv().currentSpec.fail "Chromedriver exited. code: #{errorCode}. Logs: #{logs.join("\n")}"
waitsFor "webdriver steps to complete", (done) ->
fn()
.catch((error) -> jasmine.getEnv().currentSpec.fail(err.message))
.end()
.call(done)
, 30000
runs -> chromedriver.kill()
# Start Atom using chromedriver.
startAtom: (args...) ->
webdriverio.remote(
host: 'localhost'
port: ChromedriverPort
desiredCapabilities:
browserName: "atom"
chromeOptions:
binary: AtomLauncherPath
args: [
"atom-path=#{AtomPath}"
"atom-args=#{args.join(" ")}"
"dev"
"safe"
"user-data-dir=#{temp.mkdirSync('integration-spec-')}"
"socket-path=#{SocketPath}"
])
.init()
.addCommand "waitForCondition", (conditionFn, timeout, cb) ->
timedOut = succeeded = false
pollingInterval = Math.min(timeout, 100)
setTimeout((-> timedOut = true), timeout)
async.until(
(-> succeeded or timedOut),
((next) =>
setTimeout(=>
conditionFn.call(this).then(
((result) ->
succeeded = result
next()),
((err) -> next(err))
)
, pollingInterval)),
((err) -> cb(err, succeeded))
)
# Once one `Atom` window is open, subsequent invocations of `Atom` will exit
# immediately.
startAnotherAtom: (args...) ->
spawnSync(AtomPath, args.concat([
"--dev",
"--safe",
"--socket-path=#{SocketPath}"
]))

View File

@ -3,105 +3,64 @@
# ATOM_INTEGRATION_TESTS_ENABLED=true apm test
return unless process.env.ATOM_INTEGRATION_TESTS_ENABLED
os = require "os"
fs = require "fs"
path = require "path"
remote = require "remote"
temp = require("temp").track()
{spawn, spawnSync} = require "child_process"
{Builder, By} = require "../../build/node_modules/selenium-webdriver"
AtomPath = remote.process.argv[0]
AtomLauncherPath = path.join(__dirname, "helpers", "atom-launcher.sh")
SocketPath = path.join(os.tmpdir(), "atom-integration-test.sock")
ChromeDriverPort = 9515
{startAtom, startAnotherAtom, driverTest} = require("./helpers/start-atom")
describe "Starting Atom", ->
[chromeDriver, driver, tempDirPath] = []
beforeEach ->
tempDirPath = temp.mkdirSync("empty-dir")
jasmine.useRealClock()
waitsFor "chromedriver to start", (done) ->
chromeDriver = spawn "chromedriver", ["--verbose", "--port=#{ChromeDriverPort}"]
chromeDriver.on "error", (error) ->
throw new Error("chromedriver failed to start: #{error.message}")
chromeDriver.stdout.on "data", -> done()
afterEach ->
waitsForPromise -> driver.quit().thenFinally(-> chromeDriver.kill())
startAtom = (args...) ->
driver = new Builder()
.usingServer("http://localhost:#{ChromeDriverPort}")
.withCapabilities(
chromeOptions:
binary: AtomLauncherPath
args: [
"atom-path=#{AtomPath}"
"atom-args=#{args.join(" ")}"
"dev"
"safe"
"user-data-dir=#{temp.mkdirSync('integration-spec-')}"
"socket-path=#{SocketPath}"
]
)
.forBrowser('atom')
.build()
waitsForPromise ->
driver.wait ->
driver.getTitle().then (title) -> title.indexOf("Atom") >= 0
startAnotherAtom = (args...) ->
spawnSync(AtomPath, args.concat([
"--dev",
"--safe",
"--socket-path=#{SocketPath}"
]))
describe "when given the name of a file that doesn't exist", ->
tempFilePath = null
describe "opening paths via commmand-line arguments", ->
[tempDirPath, tempFilePath] = []
beforeEach ->
tempDirPath = temp.mkdirSync("empty-dir")
tempFilePath = path.join(tempDirPath, "an-existing-file")
fs.writeFileSync(tempFilePath, "This was already here.")
startAtom(path.join(tempDirPath, "new-file"))
it "opens a new window with an empty text editor", ->
waitsForPromise ->
driver.getAllWindowHandles().then (handles) ->
expect(handles.length).toBe 1
driver.executeScript(-> atom.workspace.getActivePane().getItems().length).then (length) ->
expect(length).toBe 1
driver.executeScript(-> atom.workspace.getActiveTextEditor().getText()).then (text) ->
expect(text).toBe("")
driver.findElement(By.tagName("atom-text-editor")).sendKeys("Hello world!")
driver.executeScript(-> atom.workspace.getActiveTextEditor().getText()).then (text) ->
expect(text).toBe "Hello world!"
it "reuses existing windows when directories are reopened", ->
driverTest ->
# Opening another existing file in the same directory reuses the window,
# and opens a new tab for the file.
waitsForPromise ->
startAnotherAtom(tempFilePath)
driver.wait ->
driver.executeScript(-> atom.workspace.getActivePane().getItems().length).then (length) ->
length is 2
driver.executeScript(-> atom.workspace.getActiveTextEditor().getText()).then (text) ->
expect(text).toBe "This was already here."
# Opening a new file creates one window with one empty text editor.
startAtom(path.join(tempDirPath, "new-file"))
.waitForExist("atom-text-editor", 5000)
.then((exists) -> expect(exists).toBe true)
.windowHandles()
.then(({value}) -> expect(value.length).toBe 1)
.execute(-> atom.workspace.getActivePane().getItems().length)
.then(({value}) -> expect(value).toBe 1)
# Opening a different directory creates a new window.
waitsForPromise ->
startAnotherAtom(temp.mkdirSync("another-empty-dir"))
driver.wait ->
driver.getAllWindowHandles().then (handles) ->
handles.length is 2
# Typing in the editor changes its text.
.execute(-> atom.workspace.getActiveTextEditor().getText())
.then(({value}) -> expect(value).toBe "")
.click("atom-text-editor")
.keys("Hello!")
.execute(-> atom.workspace.getActiveTextEditor().getText())
.then(({value}) -> expect(value).toBe "Hello!")
describe "when given the name of a directory that exists", ->
beforeEach ->
startAtom(tempDirPath)
# Opening an existing file in the same directory reuses the window and
# adds a new tab for the file.
.call(-> startAnotherAtom(tempFilePath))
.waitForCondition(
(-> @execute((-> atom.workspace.getActivePane().getItems().length)).then ({value}) -> value is 2),
5000)
.then((result) -> expect(result).toBe(true))
.execute(-> atom.workspace.getActiveTextEditor().getText())
.then(({value}) -> expect(value).toBe "This was already here.")
it "opens a new window no text editors open", ->
waitsForPromise ->
driver.executeScript(-> atom.workspace.getActiveTextEditor()).then (editor) ->
expect(editor).toBeNull()
# Opening a different directory creates a second window with no
# tabs open.
.call(-> startAnotherAtom(temp.mkdirSync("another-empty-dir")))
.waitForCondition(
(-> @windowHandles().then(({value}) -> value.length is 2)),
5000)
.then((result) -> expect(result).toBe(true))
.windowHandles()
.then(({value}) ->
@window(value[1])
.waitForExist("atom-workspace", 5000)
.then((exists) -> expect(exists).toBe true)
.execute(-> atom.workspace.getActivePane().getItems().length)
.then(({value}) -> expect(value).toBe 0))