184 lines
5.9 KiB
TypeScript
Executable File
184 lines
5.9 KiB
TypeScript
Executable File
require("chromedriver");
|
|
import seleniumWebdriver = require("selenium-webdriver");
|
|
import {setWorldConstructor, After} from "cucumber";
|
|
import Fs = require("fs");
|
|
import Speakeasy = require("speakeasy");
|
|
import Assert = require("assert");
|
|
import Request = require("request-promise");
|
|
import BluebirdPromise = require("bluebird");
|
|
|
|
process.env.NODE_TLS_REJECT_UNAUTHORIZED = "0"
|
|
|
|
function CustomWorld() {
|
|
const that = this;
|
|
this.driver = new seleniumWebdriver.Builder()
|
|
.forBrowser("chrome")
|
|
.build();
|
|
|
|
this.totpSecrets = {};
|
|
this.configuration = {};
|
|
|
|
this.visit = function (link: string) {
|
|
return this.driver.get(link);
|
|
};
|
|
|
|
this.setFieldTo = function (fieldName: string, content: string) {
|
|
const that = this;
|
|
return this.driver.findElement(seleniumWebdriver.By.id(fieldName))
|
|
.sendKeys(content);
|
|
};
|
|
|
|
this.clearField = function (fieldName: string) {
|
|
return this.driver.findElement(seleniumWebdriver.By.id(fieldName)).clear();
|
|
};
|
|
|
|
this.getErrorPage = function (code: number) {
|
|
const that = this;
|
|
return this.driver.wait(seleniumWebdriver.until.elementLocated(seleniumWebdriver.By.tagName("h1")), 5000)
|
|
.then(function () {
|
|
return that.driver
|
|
.findElement(seleniumWebdriver.By.tagName("h1")).getText();
|
|
})
|
|
.then(function (txt: string) {
|
|
try {
|
|
Assert.equal(txt, "Error " + code);
|
|
} catch (e) {
|
|
console.log(txt);
|
|
throw e;
|
|
}
|
|
})
|
|
};
|
|
|
|
this.clickOnButton = function (buttonText: string) {
|
|
const that = this;
|
|
return this.driver.wait(seleniumWebdriver.until.elementLocated(seleniumWebdriver.By.tagName("button")), 5000)
|
|
.then(function () {
|
|
return that.driver
|
|
.findElement(seleniumWebdriver.By.tagName("button"))
|
|
.findElement(seleniumWebdriver.By.xpath("//button[contains(.,'" + buttonText + "')]"))
|
|
.click();
|
|
});
|
|
};
|
|
|
|
this.waitUntilUrlContains = function (url: string) {
|
|
const that = this;
|
|
return this.driver.wait(seleniumWebdriver.until.urlIs(url), 15000)
|
|
.then(function () {return BluebirdPromise.resolve(); }, function (err: Error) {
|
|
that.driver.getCurrentUrl()
|
|
.then(function (current: string) {
|
|
console.error("====> Error due to: %s (current) != %s (expected)", current, url);
|
|
});
|
|
return BluebirdPromise.reject(err);
|
|
});
|
|
};
|
|
|
|
this.loginWithUserPassword = function (username: string, password: string) {
|
|
return that.driver.wait(seleniumWebdriver.until.elementLocated(seleniumWebdriver.By.id("username")), 5000)
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.id("username"))
|
|
.sendKeys(username);
|
|
})
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.id("password"))
|
|
.clear();
|
|
})
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.id("password"))
|
|
.sendKeys(password);
|
|
})
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.tagName("button"))
|
|
.click();
|
|
});
|
|
};
|
|
|
|
this.retrieveLatestMail = function () {
|
|
return Request({
|
|
method: "GET",
|
|
uri: "http://localhost:8085/messages",
|
|
json: true
|
|
})
|
|
.then(function (data: any) {
|
|
const messageId = data[data.length - 1].id;
|
|
return Request({
|
|
method: "GET",
|
|
uri: `http://localhost:8085/messages/${messageId}.html`
|
|
});
|
|
})
|
|
.then(function (data: any) {
|
|
const regexp = new RegExp(/<a href="(.+)" class="button">Continue<\/a>/);
|
|
const match = regexp.exec(data);
|
|
const link = match[1];
|
|
return BluebirdPromise.resolve(link);
|
|
});
|
|
};
|
|
|
|
this.registerTotpSecret = function (totpSecretHandle: string) {
|
|
return that.driver.wait(seleniumWebdriver.until.elementLocated(seleniumWebdriver.By.className("register-totp")), 5000)
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.className("register-totp")).click();
|
|
})
|
|
.then(function () {
|
|
return that.retrieveLatestMail();
|
|
})
|
|
.then(function (url: string) {
|
|
return that.driver.get(url);
|
|
})
|
|
.then(function () {
|
|
return that.driver.wait(seleniumWebdriver.until.elementLocated(seleniumWebdriver.By.id("secret")), 5000);
|
|
})
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.id("secret")).getText();
|
|
})
|
|
.then(function (secret: string) {
|
|
that.totpSecrets[totpSecretHandle] = secret;
|
|
});
|
|
};
|
|
|
|
this.useTotpTokenHandle = function (totpSecretHandle: string) {
|
|
if (!this.totpSecrets[totpSecretHandle])
|
|
throw new Error("No available TOTP token handle " + totpSecretHandle);
|
|
|
|
const token = Speakeasy.totp({
|
|
secret: this.totpSecrets[totpSecretHandle],
|
|
encoding: "base32"
|
|
});
|
|
return this.useTotpToken(token);
|
|
};
|
|
|
|
this.useTotpToken = function (totpSecret: string) {
|
|
return that.driver.wait(seleniumWebdriver.until.elementLocated(seleniumWebdriver.By.id("token")), 5000)
|
|
.then(function () {
|
|
return that.driver.findElement(seleniumWebdriver.By.id("token"))
|
|
.sendKeys(totpSecret);
|
|
});
|
|
};
|
|
|
|
this.registerTotpAndSignin = function (username: string, password: string) {
|
|
const totpHandle = "HANDLE";
|
|
const authUrl = "https://login.example.com:8080/";
|
|
const that = this;
|
|
return this.visit(authUrl)
|
|
.then(function () {
|
|
return that.loginWithUserPassword(username, password);
|
|
})
|
|
.then(function () {
|
|
return that.registerTotpSecret(totpHandle);
|
|
})
|
|
.then(function () {
|
|
return that.visit(authUrl);
|
|
})
|
|
.then(function () {
|
|
return that.loginWithUserPassword(username, password);
|
|
})
|
|
.then(function () {
|
|
return that.useTotpTokenHandle(totpHandle);
|
|
})
|
|
.then(function () {
|
|
return that.clickOnButton("Sign in");
|
|
});
|
|
};
|
|
}
|
|
|
|
setWorldConstructor(CustomWorld);
|