Protractor tests hung up after finishing tests - jenkins

I have configured grunt tasks to start the protractor webdriver and then run the protractor tests with protractor-runner, grunt config is like
.....
protractor_webdriver: {
start: {
options: {
path: 'node_modules/protractor/bin/',
command: 'webdriver-manager start --standalone'
}
}
},
protractor: {
options: {
configFile: proctatorConf,
noColor: false,
args: {
}
},
auto: {
options: {
keepAlive: true,
args: {
}
}
},
singlerun: {
options: {
keepAlive: false,
args: {
}
}
}
}
....
grunt.registerTask('test:e2e', [
'shell:update_webdriver',
'protractor_webdriver:start',
'protractor:singlerun'
]);
and in Jenkins i installed xvfb-plugin and said on the job configuration to startup Xvfb screen and shutdown after job finish,
And what is the problem is that when jenkins execute grunt test:e2e command, it executes all test, give me failure information like
Finished in 16.455 seconds
[31m4 tests, 6 assertions, 4 failures
and jenkins job hungs on that, what could be the problem for this?

Related

Does Jenkins GitLab plugin supports the feature like allow_failure in GitLab CI?

I'm using Jenkins GitLab Plugin, and I used gitlabBuild() to tell GitLab that the pipeline will succeed only if all three tasks are successful.
gitlabBuilds(builds: ['First', 'Second', 'Third']) {}
And I need the unexecuted task be cancelled when any task fails, the default behaviour is all the unexecuted task will hang on pending state.
Looks like the allow_failure: false in GitLab CI is indeed what I want:
Use allow_failure to determine whether a pipeline should continue running when a job fails.
To let the pipeline continue running subsequent jobs, use allow_failure: true.
To stop the pipeline from running subsequent jobs, use allow_failure: false.
Does Jenkins GitLab plugin support the feature like allow_failure in GitLab CI?
I've found a workaround which is cancelling the follow stages manually, but it's a little ugly:
stage('First') {
steps {
gitlabCommitStatus(name: 'First') {
script {
gitlabBuilds(builds: ['First', 'Second', 'Third']) {}
}
}
}
post {
failure {
updateGitlabCommitStatus name: 'Second', state: 'canceled'
updateGitlabCommitStatus name: 'Third', state: 'canceled'
}
}
}
stage('Second') {
steps {
gitlabCommitStatus(name: 'Second') {
script {
}
}
}
post {
failure {
updateGitlabCommitStatus name: 'Third', state: 'canceled'
}
}
}
stage('Third') {
steps {
gitlabCommitStatus(name: 'First') {
script {
}
}
}
}
Does someone have a better solution? Thanks.

Jenkinsfile with Dockerfile: How to call a method before the Docker image is built?

I have a Jenkinsfile that looks something like the following:
void setBuildStatus(String message, String state) {
step([
$class: "GitHubCommitStatusSetter",
reposSource: [$class: "ManuallyEnteredRepositorySource", url: "https://github.com/my-user/my-repo"],
contextSource: [$class: "ManuallyEnteredCommitContextSource", context: "ci/jenkins/build-status"],
errorHandlers: [[$class: "ChangingBuildStatusErrorHandler", result: "UNSTABLE"]],
statusResultSource: [ $class: "ConditionalStatusResultSource", results: [[$class: "AnyBuildResult", message: message, state: state]] ]
]);
}
pipeline {
environment {
DATABASE_URL = credentials('database-url')
}
agent {
dockerfile {
args '-e DATABASE_URL=$DATABASE_URL'
}
}
stages {
stage('test') {
steps {
setBuildStatus("Running rspec", "PENDING");
sh 'bundle exec rspec'
}
}
}
post {
success {
setBuildStatus("Build succeeded", "SUCCESS");
}
failure {
setBuildStatus("Build failed", "FAILURE");
}
}
}
... and a Dockerfile that looks like this:
FROM ruby:2.6.7
WORKDIR /usr/src/app
# bundle install
RUN gem install bundler:2.2.26
COPY Gemfile Gemfile.lock ./
RUN bundle install --jobs 5
Which is pretty standard for a Ruby app.
This all works as expected: it sets the GitHub status to pending once the specs start to run and to Success or Failure when they're done. But if I change a gem it rebuilds the Docker image, which takes about 3:30 minutes on my Jenkins machine. During this time there's no update to GitHub's status, on GitHub it looks like nothing is happening.
Can I somehow call setBuildStatus("Starting build", "PENDING"); immediately when I enter the pipeline?
You can probably do something like the one below. Simply create two stages, the first one will run on Any agent and just set the status, and the next stage will do the actual ruby-build.
pipeline {
agent any
environment {
DATABASE_URL = credentials('database-url')
}
stages {
stage('Set State') {
steps {
setBuildStatus("Build started", "PENDING");
}
}
stage('test') {
agent {
dockerfile {
args '-e DATABASE_URL=$DATABASE_URL'
}
}
steps {
sh 'bundle exec rspec'
}
}
}
post {
success {
setBuildStatus("Build succeeded", "SUCCESS");
}
failure {
setBuildStatus("Build failed", "FAILURE");
}
}
}

What is the proper way to stop and remove a docker container in Jenkins when using Docker Pipeline Plugin?

I have a Jenkins pipeline that builds and runs a Docker machine, not as an agent, but using a scripting block along with the Docker Pipeline Plugin methods docker.build() and Image.run(). This works fine but if the build fails, the docker container is left running! I currently have Container.stop() in a post{ always{} } block but it doesn't seem to work. I don't want ssh into my Jenkins server to delete the container after every build and I can't just leave it because it has a specific and necessary name. How do I stop and rm the container regardless of failure of the build?
My pipeline:
pipeline {
agent none
stages {
stage('Checkout') {
agent any
steps {
checkout([$class: 'GitSCM', branches: [[name: '*/master']], doGenerateSubmoduleConfigurations: false, extensions: [], submoduleCfg: [], userRemoteConfigs: [[credentialsId: '<some credentials>', url: '<a git repo>']]])
}
}
stage('Spin Up Receiver') {
agent any
steps {
script {
def receiver = docker.build("receiver", "--rm centos7_receiver")
def receiver_container = receiver.run("-d -v ${PWD}/realtime_files/station_name/201707/f/20170710_191:/DSK1/SSN/LOG0_f/17001 --network='rsync_test' --name='test_receiver'")
}
}
}
stage('Run Tests') {
agent { dockerfile { args '-v /etc/passwd:/etc/passwd --network="rsync_test"' } }
steps {
sh "python ./rsyncUnitTests.py"
}
}
}
post {
always {
script {
receiver_container.stop()
}
}
failure {
sendEmail('foo#bar.com')
}
changed {
sendEmail('foo#bar.com')
}
}
}
Here is a working solution. You simply have to define a variable for the container outside the main pipeline. Then you can use it anywhere in the pipeline to start or stop the container. In particular, you can remove the container in post{ always{ } }.
def receiver_container
pipeline {
agent any
stages {
stage('Checkout') {
agent any
steps {
checkout([$class: 'GitSCM', branches: [[name: '*/master']], doGenerateSubmoduleConfigurations: false, extensions: [], submoduleCfg: [], userRemoteConfigs: [[credentialsId: '<some credentials>', url: '<a git repo>']]])
}
}
stage('Spin Up Receiver') {
agent any
steps {
script {
def receiver = docker.build("receiver", "--rm receiver_docker")
receiver_container = receiver.run("-d -u 0:0 -v /var/lib/jenkins/workspace/RsyncRealtime/jenkins_rt:/DSK1/SSN/LOG5_F/17191 --network='rsync_test' --name='test_receiver'")
}
}
}
stage('Run Unit Tests') {
agent {
dockerfile {
args '-u 0:0 -v /etc/passwd:/etc/passwd --network="rsync_test"'
}
}
steps {
sh "sshpass -p 'test' ssh anonymous#test_receiver ls -l /DSK1/SSN/LOG5_F/17191"
sh "python ./rsyncUnitTests.py"
}
}
}
post {
always {
script {
receiver_container.stop()
}
}
failure {
sendEmail('foo#bar.com')
}
changed {
sendEmail('foo#bar.com')
}
}
}
You can use Image.withRun() instead of Image.run().
Image.withRun[(args[, command])] {…}
Like run but stops the container as soon as its body exits, so you do not need a try-finally block.
Here other useful commands:
https://qa.nuxeo.org/jenkins/pipeline-syntax/globals#docker

Running protractor on Jenkins doesn't fail the build when there is an error

I have set up Jenkins Slave on Windows VM. when there are failures in my tests , the build status always shows succeeded.
Here is how I run protractor tests on jenkins
Windows PowerShell command :
cd conf
protractor ConfProd.js
My Conf file:
var HtmlReporter = require('protractor-html-screenshot-reporter');
exports.config = {
seleniumAddress: 'http://localhost:4444/wd/hub', //desktop
allScriptsTimeout: 60000,
baseUrl: 'https://myTest.com',
params: {
empUrl: 'https://employeeurl.com/',
},
// frameworks to use
frameworks: 'jasmine2',
directConnect: 'true',
//Capabilities to be passed to the webdriver instance.
multiCapabilities: [{
'browserName': 'chrome',
'chromeOptions' : {
args: ['--window-size=1200,1200']
},
specs: [
'../tests/*.spec.js'
],
},
{
'browserName': 'firefox',
'firefoxOptions' : {
args: ['--window-size=900,900']
},
specs: [
'../tests/*.spec.js'
],
exclude: ['../tests/EmployeeTests.spec.js'],
}],
onPrepare: function () {
jasmine.getEnv().addReporter(new HtmlReporter({
baseDirectory: '/tmp/screenshots',
docTitle: 'TestReports',
takeScreenShotsOnlyForFailedSpecs: true
}));
},
jasmineNodeOpts: {
showColors: true,
isVerbose: true,
includeStackTrace: true,
}
};
This is the message from console output on Jenkins:
[launcher] chrome #1 failed 4 test(s)
[launcher] firefox #2 failed 4 test(s)
[launcher] overall: 8 failed spec(s)
Checking for post-build
Performing post-build step
Checking if email needs to be generated
No emails were triggered.
Finished: SUCCESS

Set up Protractor tests with Jenkins

I need to get my protractor tests to run using Jenkins. I know this has been asked before, and this seems like a really good answer. But I'm confused about where the bash script comes from and how to move forward. Here's what I've got:
Protractor config file:
var HtmlScreenshotReporter = require('protractor-jasmine2-screenshot-reporter');
require('jasmine-reporters');
exports.config = {
seleniumAddress: 'http://localhost:4444/wd/hub',
capabilities: {
'browserName': 'chrome'
},
framework: 'jasmine2',
suites: {...},
jasmineNodeOpts: {
showColors: true,
defaultTimeoutInterval: 10000
},
onPrepare: function() {
global.isAngularSite = function(flag) {
browser.ignoreSynchronization = !flag;
};
browser.manage().window().setPosition(0,0);
browser.manage().window().setSize(1280, 1024);
}
jasmine.getEnv().addReporter(
new jasmine.JUnitXmlReporter('protractor_output', true, true)
);
}
How can I get my tests to run with Jenkins? Please help

Resources