Commit 25a42a56 authored by Dmitriy Zaporozhets's avatar Dmitriy Zaporozhets

Merge pull request #8439 from glasspelican/Teamcity

Teamcity integration using 8.1 rest api
parents 19c6951c 1fa19401
v 7.7.0
-
-
-
- Add Jetbrains Teamcity CI service (Jason Lippert)
-
-
-
......
......@@ -42,7 +42,7 @@ class Projects::ServicesController < Projects::ApplicationController
:title, :token, :type, :active, :api_key, :subdomain,
:room, :recipients, :project_url, :webhook,
:user_key, :device, :priority, :sound, :bamboo_url, :username, :password,
:build_key, :server
:build_key, :server, :teamcity_url, :build_type
)
end
end
......@@ -66,6 +66,7 @@ class Project < ActiveRecord::Base
has_one :slack_service, dependent: :destroy
has_one :buildbox_service, dependent: :destroy
has_one :bamboo_service, dependent: :destroy
has_one :teamcity_service, dependent: :destroy
has_one :pushover_service, dependent: :destroy
has_one :forked_project_link, dependent: :destroy, foreign_key: "forked_to_project_id"
has_one :forked_from_project, through: :forked_project_link
......@@ -314,7 +315,8 @@ class Project < ActiveRecord::Base
end
def available_services_names
%w(gitlab_ci campfire hipchat pivotaltracker flowdock assembla emails_on_push gemnasium slack pushover buildbox bamboo)
%w(gitlab_ci campfire hipchat pivotaltracker flowdock assembla
emails_on_push gemnasium slack pushover buildbox bamboo teamcity)
end
def gitlab_ci?
......
class TeamcityService < CiService
include HTTParty
prop_accessor :teamcity_url, :build_type, :username, :password
validates :teamcity_url, presence: true,
format: { with: URI::regexp }, if: :activated?
validates :build_type, presence: true, if: :activated?
validates :username, presence: true,
if: ->(service) { service.password? }, if: :activated?
validates :password, presence: true,
if: ->(service) { service.username? }, if: :activated?
attr_accessor :response
after_save :compose_service_hook, if: :activated?
def compose_service_hook
hook = service_hook || build_service_hook
hook.save
end
def title
'JetBrains TeamCity CI'
end
def description
'A continuous integration and build server'
end
def help
'The build configuration in Teamcity must use the build format '\
'number %build.vcs.number% '\
'you will also want to configure monitoring of all branches so merge '\
'requests build, that setting is in the vsc root advanced settings.'
end
def to_param
'teamcity'
end
def fields
[
{ type: 'text', name: 'teamcity_url',
placeholder: 'TeamCity root URL like https://teamcity.example.com' },
{ type: 'text', name: 'build_type',
placeholder: 'Build configuration ID' },
{ type: 'text', name: 'username',
placeholder: 'A user with permissions to trigger a manual build' },
{ type: 'password', name: 'password' },
]
end
def build_info(sha)
url = URI.parse("#{teamcity_url}/httpAuth/app/rest/builds/"\
"branch:unspecified:any,number:#{sha}")
auth = {
username: username,
password: password,
}
@response = HTTParty.get("#{url}", verify: false, basic_auth: auth)
end
def build_page(sha)
build_info(sha) if @response.nil? || !@response.code
if @response.code != 200
# If actual build link can't be determined,
# send user to build summary page.
"#{teamcity_url}/viewLog.html?buildTypeId=#{build_type}"
else
# If actual build link is available, go to build result page.
built_id = @response['build']['id']
"#{teamcity_url}/viewLog.html?buildId=#{built_id}"\
"&buildTypeId=#{build_type}"
end
end
def commit_status(sha)
build_info(sha) if @response.nil? || !@response.code
return :error unless @response.code == 200 || @response.code == 404
status = if @response.code == 404
'Pending'
else
@response['build']['status']
end
if status.include?('SUCCESS')
'success'
elsif status.include?('FAILURE')
'failed'
elsif status.include?('Pending')
'pending'
else
:error
end
end
def execute(data)
auth = {
username: username,
password: password,
}
branch = data[:ref]
self.class.post("#{teamcity_url}/httpAuth/app/rest/buildQueue",
body: "<build branchName=\"#{branch}\">"\
"<buildType id=\"#{build_type}\"/>"\
'</build>',
headers: { 'Content-type' => 'application/xml' },
basic_auth: auth
)
end
end
......@@ -16,3 +16,4 @@ __Project integrations with external services for continuous integration and mor
- PivotalTracker
- Pushover
- Slack
- TeamCity
\ No newline at end of file
......@@ -66,3 +66,10 @@ Feature: Project Services
And I click Atlassian Bamboo CI service link
And I fill Atlassian Bamboo CI settings
Then I should see Atlassian Bamboo CI service settings saved
Scenario: Activate jetBrains TeamCity CI service
When I visit project "Shop" services page
And I click jetBrains TeamCity CI service link
And I fill jetBrains TeamCity CI settings
Then I should see jetBrains TeamCity CI service settings saved
......@@ -15,6 +15,7 @@ class Spinach::Features::ProjectServices < Spinach::FeatureSteps
page.should have_content 'Assembla'
page.should have_content 'Pushover'
page.should have_content 'Atlassian Bamboo'
page.should have_content 'JetBrains TeamCity'
end
step 'I click gitlab-ci service link' do
......@@ -168,4 +169,23 @@ class Spinach::Features::ProjectServices < Spinach::FeatureSteps
find_field('Build key').value.should == 'KEY'
find_field('Username').value.should == 'user'
end
step 'I click JetBrains TeamCity CI service link' do
click_link 'JetBrains TeamCity CI'
end
step 'I fill JetBrains TeamCity CI settings' do
check 'Active'
fill_in 'Teamcity url', with: 'http://teamcity.example.com'
fill_in 'Build type', with: 'GitlabTest_Build'
fill_in 'Username', with: 'user'
fill_in 'Password', with: 'verySecret'
click_button 'Save'
end
step 'I should see JetBrains TeamCity CI service settings saved' do
find_field('Teamcity url').value.should == 'http://teamcity.example.com'
find_field('Build type').value.should == 'GitlabTest_Build'
find_field('Username').value.should == 'user'
end
end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment