gitlab-qa 5.14.0 → 5.17.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitlab-ci.yml +43 -2
- data/README.md +52 -5
- data/docs/what_tests_can_be_run.md +102 -5
- data/lib/gitlab/qa.rb +1 -1
- data/lib/gitlab/qa/component/base.rb +27 -6
- data/lib/gitlab/qa/component/specs.rb +43 -11
- data/lib/gitlab/qa/docker/command.rb +15 -3
- data/lib/gitlab/qa/docker/engine.rb +5 -1
- data/lib/gitlab/qa/docker/shellout.rb +2 -2
- data/lib/gitlab/qa/release.rb +17 -4
- data/lib/gitlab/qa/runner.rb +23 -15
- data/lib/gitlab/qa/runtime/env.rb +15 -6
- data/lib/gitlab/qa/scenario/test/instance/geo.rb +0 -3
- data/lib/gitlab/qa/scenario/test/integration/geo.rb +4 -2
- data/lib/gitlab/qa/scenario/test/integration/gitaly_cluster.rb +201 -0
- data/lib/gitlab/qa/scenario/test/integration/praefect.rb +20 -8
- data/lib/gitlab/qa/scenario/test/sanity/version.rb +1 -1
- data/lib/gitlab/qa/version.rb +1 -1
- metadata +3 -3
- data/lib/gitlab/qa/scenario/test/integration/gitaly_ha.rb +0 -166
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: d14680b847d514a92a3db02e62d17566d165c3aa2fa7772cbf4cdb5eb3746d6f
|
4
|
+
data.tar.gz: f8669ae124311588e59bd52f743b5aafb41a2f7ca40073f12eae28f860e7f54a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: be1aa1c90f7bbfe3e9fab71640f14517d212d5dbfcd5d412e2576b1c6553ad445a2530088f9999fee9fa02cf3bc813f3ee23ae1f2474b2d48a4e2979710163c6
|
7
|
+
data.tar.gz: 138a8b071f801af2bf9db1bed412976ba29be624352bef902f97d5a041ecb6cb45e1e1e32373af6c17e47847900aef791fe3e7219a53736781035fa143425449
|
data/.gitlab-ci.yml
CHANGED
@@ -31,6 +31,8 @@ workflow:
|
|
31
31
|
- if: '$CI_COMMIT_BRANCH == "master"'
|
32
32
|
# For tags, create a pipeline.
|
33
33
|
- if: '$CI_COMMIT_TAG'
|
34
|
+
# For triggers from GitLab MR pipelines (and pipelines from other projects), create a pipeline
|
35
|
+
- if: '$CI_PIPELINE_SOURCE == "pipeline"'
|
34
36
|
|
35
37
|
.default-rules:
|
36
38
|
rules:
|
@@ -92,7 +94,7 @@ release:
|
|
92
94
|
- exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS || test_run_exit_code=$?
|
93
95
|
- exe/gitlab-qa-report --update-screenshot-path "gitlab-qa-run-*/**/rspec-*.xml"
|
94
96
|
- export GITLAB_QA_ACCESS_TOKEN="$GITLAB_QA_PRODUCTION_ACCESS_TOKEN"
|
95
|
-
- if [ "$TOP_UPSTREAM_SOURCE_REF" == "master" ]; then exe/gitlab-qa-report --report-in-issues "gitlab-qa-run-*/**/rspec-*.xml" --project "$QA_TESTCASES_REPORTING_PROJECT"; fi
|
97
|
+
- if [ "$TOP_UPSTREAM_SOURCE_REF" == "master" ]; then $(exe/gitlab-qa-report --report-in-issues "gitlab-qa-run-*/**/rspec-*.xml" --project "$QA_TESTCASES_REPORTING_PROJECT") || true; fi
|
96
98
|
- exit $test_run_exit_code
|
97
99
|
|
98
100
|
.ce-qa:
|
@@ -830,6 +832,44 @@ ee:praefect-quarantine:
|
|
830
832
|
QA_CAN_TEST_PRAEFECT: "true"
|
831
833
|
QA_RSPEC_TAGS: "--tag quarantine --tag ~orchestrated"
|
832
834
|
|
835
|
+
ce:gitaly-cluster:
|
836
|
+
extends:
|
837
|
+
- .test
|
838
|
+
- .high-capacity
|
839
|
+
- .ce-qa
|
840
|
+
- .rspec-report-opts
|
841
|
+
variables:
|
842
|
+
QA_SCENARIO: "Test::Integration::GitalyCluster"
|
843
|
+
|
844
|
+
ce:gitaly-cluster-quarantine:
|
845
|
+
extends:
|
846
|
+
- .test
|
847
|
+
- .high-capacity
|
848
|
+
- .ce-qa
|
849
|
+
- .quarantine
|
850
|
+
- .rspec-report-opts
|
851
|
+
variables:
|
852
|
+
QA_SCENARIO: "Test::Integration::GitalyCluster"
|
853
|
+
|
854
|
+
ee:gitaly-cluster:
|
855
|
+
extends:
|
856
|
+
- .test
|
857
|
+
- .high-capacity
|
858
|
+
- .ee-qa
|
859
|
+
- .rspec-report-opts
|
860
|
+
variables:
|
861
|
+
QA_SCENARIO: "Test::Integration::GitalyCluster"
|
862
|
+
|
863
|
+
ee:gitaly-cluster-quarantine:
|
864
|
+
extends:
|
865
|
+
- .test
|
866
|
+
- .high-capacity
|
867
|
+
- .ee-qa
|
868
|
+
- .quarantine
|
869
|
+
- .rspec-report-opts
|
870
|
+
variables:
|
871
|
+
QA_SCENARIO: "Test::Integration::GitalyCluster"
|
872
|
+
|
833
873
|
ce:smtp:
|
834
874
|
extends:
|
835
875
|
- .test
|
@@ -891,7 +931,8 @@ ee:jira-quarantine:
|
|
891
931
|
staging:
|
892
932
|
script:
|
893
933
|
- unset EE_LICENSE
|
894
|
-
- exe/gitlab-qa Test::Instance::Staging
|
934
|
+
- 'echo "Running: exe/gitlab-qa Test::Instance::Staging ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS"'
|
935
|
+
- exe/gitlab-qa Test::Instance::Staging ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS
|
895
936
|
extends:
|
896
937
|
- .test
|
897
938
|
- .high-capacity
|
data/README.md
CHANGED
@@ -121,11 +121,58 @@ All the scenarios you can run are described in the
|
|
121
121
|
|
122
122
|
Note: The GitLab QA tool requires that [Docker](https://docs.docker.com/install/) is installed.
|
123
123
|
|
124
|
-
###
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
124
|
+
### Command-line options
|
125
|
+
|
126
|
+
In addition to the [arguments you can use to specify the scenario and
|
127
|
+
tests to run](/docs/what_tests_can_be_run.md), you can use the
|
128
|
+
following options to control the tool's behavior.
|
129
|
+
|
130
|
+
**Note:** These are `gitlab-qa` options so if you specify RSpec
|
131
|
+
options as well, including test file paths, be sure to add these
|
132
|
+
options before the `--` that indicates that subsequent arguments are
|
133
|
+
intended for RSpec.
|
134
|
+
|
135
|
+
| Option | Description |
|
136
|
+
| ------ | ----------- |
|
137
|
+
| `--no-teardown` | Skip teardown of containers after the scenario completes |
|
138
|
+
| `--no-tests` | Orchestrates the docker containers but does not run the tests. Implies `--no-teardown` |
|
139
|
+
|
140
|
+
For example, the following command would start an EE GitLab Docker
|
141
|
+
container and would leave the instance running, but would not run the
|
142
|
+
tests:
|
143
|
+
|
144
|
+
```plaintext
|
145
|
+
$ gitlab-qa Test::Instance::Image EE --no-tests
|
146
|
+
```
|
147
|
+
|
148
|
+
GitLab QA will have automatically run the `docker ps` command to show
|
149
|
+
the port that container is running on, for example:
|
150
|
+
|
151
|
+
```plaintext
|
152
|
+
...
|
153
|
+
Skipping tests.
|
154
|
+
The orchestrated docker containers have not been removed.
|
155
|
+
Docker shell command: `docker ps`
|
156
|
+
CONTAINER ID IMAGE ... PORTS
|
157
|
+
fdeffd791b69 gitlab/gitlab-ee:nightly 22/tcp, 443/tcp, 0.0.0.0:32768->80/tcp
|
158
|
+
```
|
159
|
+
|
160
|
+
You could then run tests against that instance in a similar way to
|
161
|
+
[running tests against GDK](/docs/run_qa_against_gdk.md). This can be
|
162
|
+
useful if you want to run and debug a specific test, for example:
|
163
|
+
|
164
|
+
```plaintext
|
165
|
+
# From /path/to/gdk/gitlab/qa
|
166
|
+
$ bundle exec bin/qa Test::Instance::All http://localhost:32768 -- qa/specs/features/browser_ui/3_create/merge_request/create_merge_request_spec.rb
|
167
|
+
```
|
168
|
+
|
169
|
+
### How to add new tests
|
170
|
+
|
171
|
+
Please see the [Beginner's guide to writing end-to-end tests](https://docs.gitlab.com/ee/development/testing_guide/end_to_end/beginners_guide.html).
|
172
|
+
|
173
|
+
Test cases and scripts to run them are located in the
|
174
|
+
[GitLab FOSS](https://gitlab.com/gitlab-org/gitlab-foss/tree/master/qa) and
|
175
|
+
[GitLab](https://gitlab.com/gitlab-org/gitlab/tree/master/qa)
|
129
176
|
repositories under the `qa/` directory, so please also check the documentation
|
130
177
|
there.
|
131
178
|
|
@@ -1,5 +1,6 @@
|
|
1
|
-
# What tests can be run?
|
2
1
|
|
2
|
+
# What tests can be run?
|
3
|
+
[[_TOC_]]
|
3
4
|
## The two types of QA tests
|
4
5
|
|
5
6
|
First of all, the first thing to choose is whether you want to run orchestrated
|
@@ -28,6 +29,8 @@ For more details on the internals, please read the
|
|
28
29
|
|
29
30
|
## Supported GitLab environment variables
|
30
31
|
|
32
|
+
All environment variables used by GitLab QA should be defined in [`lib/gitlab/qa/runtime/env.rb`](https://gitlab.com/gitlab-org/gitlab-qa/-/blob/master/lib/gitlab/qa/runtime/env.rb).
|
33
|
+
|
31
34
|
| Variable | Default | Description | Required |
|
32
35
|
|-----------------------|-----------|-----------------------|----------|
|
33
36
|
| `GITLAB_USERNAME` | `root` | Username to use when signing into GitLab. | Yes|
|
@@ -53,7 +56,8 @@ For more details on the internals, please read the
|
|
53
56
|
| `GITLAB_SANDBOX_NAME` | `gitlab-qa-sandbox` | The sandbox group name the test suite is going to use. | No|
|
54
57
|
| `GITLAB_QA_ACCESS_TOKEN`|- | A valid personal access token with the `api` scope. This is used for API access during tests, and is used in the version that staging is currently running. An existing token that is valid on [`Test::Instance::Staging`](#testinstancestaging) scenario to retrieve the staging can be found in the shared 1Password vault. |No|
|
55
58
|
| `GITLAB_QA_ADMIN_ACCESS_TOKEN` |- | A valid personal access token with the `api` scope from a user with admin access. Used for API access as an admin during tests. | No|
|
56
|
-
| `
|
59
|
+
| `GITLAB_QA_CONTAINER_REGISTRY_ACCESS_TOKEN` | - | A valid personal access token with the `read_registry` scope. Used to [access the container registry on `registry.gitlab.com` when tests run in a CI job that _is not_ triggered via another pipeline](https://gitlab.com/gitlab-org/gitlab-qa/-/blob/364addb83e7b136ff0f9d8719ca9553d290aa9ab/lib/gitlab/qa/release.rb#L152). For example, if you manually run a [new Staging pipeline](https://ops.gitlab.net/gitlab-org/quality/staging/-/pipelines/new), this token will be used. | No |
|
60
|
+
| `EE_LICENSE` |- | Enterprise Edition license. | No|
|
57
61
|
| `QA_ARTIFACTS_DIR` |`/tmp/gitlab-qa`| Path to a directory where artifacts (logs and screenshots) for failing tests will be saved. | No|
|
58
62
|
| `DOCKER_HOST` |`http://localhost`| Docker host to run tests against. | No|
|
59
63
|
| `CHROME_HEADLESS` |- | When running locally, set to `false` to allow Chrome tests to be visible - watch your tests being run. | No|
|
@@ -83,8 +87,27 @@ For more details on the internals, please read the
|
|
83
87
|
|
84
88
|
## Running tests with a feature flag enabled
|
85
89
|
|
86
|
-
It is possible to enable a feature flag before running tests.
|
87
|
-
|
90
|
+
It is possible to enable or disable a feature flag before running tests.
|
91
|
+
To test a Gitlab image with a feature flag enabled, run this command:
|
92
|
+
```
|
93
|
+
$ gitlab-qa Test::Instance::Image gitlab/gitlab-ee:12.4.0-ee.0 --enable-feature feature_flag_name
|
94
|
+
```
|
95
|
+
|
96
|
+
To run a test with feature flag disabled, run this command:
|
97
|
+
```
|
98
|
+
$ gitlab-qa Test::Instance::Image gitlab/gitlab-ee:12.4.0-ee.0 --disable-feature feature_flag_name
|
99
|
+
```
|
100
|
+
|
101
|
+
You an also test a GitLab image multiple times with different feature flag settings:
|
102
|
+
```
|
103
|
+
$ gitlab-qa Test::Instance::Image gitlab/gitlab-ee:12.4.0-ee.0 --disable-feature feature_flag_name --enable-feature feature_flag_name
|
104
|
+
```
|
105
|
+
This will first disable `feature_flag_name` flag and run the tests and then enable it and run the tests again.
|
106
|
+
|
107
|
+
You can pass any number of feature flag settings. The tests will run once for each setting.
|
108
|
+
|
109
|
+
See the [QA framework documentation](https://gitlab.com/gitlab-org/gitlab-ce/blob/master/qa/README.md#running-tests-with-a-feature-flag-enabled)
|
110
|
+
for information on running the tests with different feature flag settings from the QA framework.
|
88
111
|
|
89
112
|
## Specifying the GitLab version
|
90
113
|
|
@@ -217,6 +240,26 @@ $ gitlab-qa Test::Integration::Geo EE
|
|
217
240
|
|
218
241
|
[test-geo]: https://gitlab.com/gitlab-org/gitlab-ee/blob/master/qa/qa/ee/scenario/test/geo.rb
|
219
242
|
|
243
|
+
### `Test::Integration::GitalyCluster CE|EE|<full image address>`
|
244
|
+
|
245
|
+
This tests [Gitaly Cluster](https://docs.gitlab.com/ee/administration/gitaly/praefect.html),
|
246
|
+
a clustered configuration of the Gitaly repository storage service.
|
247
|
+
|
248
|
+
The scenario configures and starts several docker containers to
|
249
|
+
represent the [recommended minimum configuration](https://docs.gitlab.com/ee/administration/gitaly/praefect.html#requirements-for-configuring-a-gitaly-cluster)
|
250
|
+
of a Gitaly Cluster.
|
251
|
+
|
252
|
+
To run tests against the GitLab container, a GitLab QA (`gitlab/gitlab-qa`)
|
253
|
+
container is spun up and tests are run from it by running the
|
254
|
+
`Test::Integration::GitalyHA` scenario, which includes tests written
|
255
|
+
specifically to test Gitaly Cluster features.
|
256
|
+
|
257
|
+
Example:
|
258
|
+
|
259
|
+
```
|
260
|
+
$ gitlab-qa Test::Integration::GitalyCluster EE
|
261
|
+
```
|
262
|
+
|
220
263
|
### `Test::Integration::LDAPNoTLS CE|EE|<full image address>`
|
221
264
|
|
222
265
|
This tests that a GitLab instance works as expected with an external
|
@@ -545,7 +588,7 @@ in the GitLab CE project).
|
|
545
588
|
|
546
589
|
- `GITLAB_QA_DEV_ACCESS_TOKEN`: A valid personal access token for the
|
547
590
|
`gitlab-qa-bot` on `dev.gitlab.org` with the `registry` scope.
|
548
|
-
This is used to pull the QA Docker from the Omnibus GitLab `dev` Container Registry.
|
591
|
+
This is used to pull the QA Docker image from the Omnibus GitLab `dev` Container Registry.
|
549
592
|
If the variable isn't present, the QA image from Docker Hub will be used.
|
550
593
|
This can be found in the shared 1Password vault.
|
551
594
|
|
@@ -560,6 +603,41 @@ $ export GITLAB_PASSWORD="$GITLAB_QA_PASSWORD"
|
|
560
603
|
$ gitlab-qa Test::Instance::Staging
|
561
604
|
```
|
562
605
|
|
606
|
+
### `Test::Instance::StagingGeo`
|
607
|
+
|
608
|
+
This scenario tests that the Geo staging deployment (with [`staging.gitlab.com`](https://staging.gitlab.com) as the primary site and [`geo.staging.gitlab.com`](https://geo.staging.gitlab.com) as the secondary site) works as expected by running tests tagged `:geo` against it. This is done by spinning up a GitLab QA (`gitlab/gitlab-qa`) container and running the `QA::EE::Scenario::Test::Geo` scenario. Note that the Geo setup steps in the `QA::EE::Scenario::Test::Geo` scenario are skipped when testing a live Geo deployment.
|
609
|
+
|
610
|
+
**Required user properties:**
|
611
|
+
|
612
|
+
- The user must provide OAuth authorization on the secondary site before running Geo tests. This can be done via the authorization modal that appears after logging into the secondary node for the first time.
|
613
|
+
|
614
|
+
- Some Geo tests require the user to have Admin access level (for example, the Geo Nodes API tests)
|
615
|
+
|
616
|
+
**Required environment variables:**
|
617
|
+
|
618
|
+
- `GITLAB_QA_ACCESS_TOKEN`: A valid personal access token with the `api` scope.
|
619
|
+
This is used to retrieve the version that staging is currently running.
|
620
|
+
This can be found in the shared 1Password vault.
|
621
|
+
|
622
|
+
**Optional environment variables:**
|
623
|
+
|
624
|
+
- `GITLAB_QA_DEV_ACCESS_TOKEN`: A valid personal access token for the
|
625
|
+
`gitlab-qa-bot` on `dev.gitlab.org` with the `registry` scope.
|
626
|
+
This is used to pull the QA Docker image from the Omnibus GitLab `dev` Container Registry.
|
627
|
+
If the variable isn't present, the QA image from Docker Hub will be used.
|
628
|
+
This can be found in the shared 1Password vault.
|
629
|
+
|
630
|
+
Example:
|
631
|
+
|
632
|
+
```
|
633
|
+
$ export GITLAB_QA_ACCESS_TOKEN=your_api_access_token
|
634
|
+
$ export GITLAB_QA_DEV_ACCESS_TOKEN=your_dev_registry_access_token
|
635
|
+
$ export GITLAB_USERNAME="gitlab-qa"
|
636
|
+
$ export GITLAB_PASSWORD="$GITLAB_QA_PASSWORD"
|
637
|
+
|
638
|
+
$ gitlab-qa Test::Instance::StagingGeo
|
639
|
+
```
|
640
|
+
|
563
641
|
### `Test::Instance::Production`
|
564
642
|
|
565
643
|
This scenario functions the same as `Test::Instance::Staging`
|
@@ -633,6 +711,25 @@ $ export EE_LICENSE=$(cat /path/to/gitlab_license)
|
|
633
711
|
$ gitlab-qa Test::Instance::Airgapped EE -- --tag smoke
|
634
712
|
```
|
635
713
|
|
714
|
+
### `Test::Instance::Geo EE|<full image address>:nightly|latest|any_tag http://geo-primary.gitlab http://geo-secondary.gitlab`
|
715
|
+
|
716
|
+
This scenario will run tests tagged `:geo` against a live Geo deployment, by spinning up a GitLab QA (`gitlab/gitlab-qa`)
|
717
|
+
container and running the `QA::EE::Scenario::Test::Geo` scenario. Note that the Geo setup steps in the `QA::EE::Scenario::Test::Geo` scenario are skipped when testing a live Geo deployment. The URLs for the primary site and secondary site of the live Geo deployment must be provided as command line arguments.
|
718
|
+
|
719
|
+
**Required user properties:**
|
720
|
+
|
721
|
+
- The user must provide OAuth authorization on the secondary site before running Geo tests. This can be done via the authorization modal that appears after signing into the secondary node for the first time.
|
722
|
+
|
723
|
+
- Some Geo tests require the user to have Admin access level (for example, the Geo Nodes API tests)
|
724
|
+
|
725
|
+
Example:
|
726
|
+
|
727
|
+
```
|
728
|
+
$ export GITLAB_USERNAME="gitlab-qa"
|
729
|
+
$ export GITLAB_PASSWORD="$GITLAB_QA_PASSWORD"
|
730
|
+
|
731
|
+
$ gitlab-qa Test::Instance::Geo EE https://primary.gitlab.com https://secondary.gitlab.com
|
732
|
+
```
|
636
733
|
----
|
637
734
|
|
638
735
|
[Back to README.md](../README.md)
|
data/lib/gitlab/qa.rb
CHANGED
@@ -54,7 +54,7 @@ module Gitlab
|
|
54
54
|
autoload :Praefect, 'gitlab/qa/scenario/test/integration/praefect'
|
55
55
|
autoload :Elasticsearch, 'gitlab/qa/scenario/test/integration/elasticsearch'
|
56
56
|
autoload :SMTP, 'gitlab/qa/scenario/test/integration/smtp'
|
57
|
-
autoload :
|
57
|
+
autoload :GitalyCluster, 'gitlab/qa/scenario/test/integration/gitaly_cluster'
|
58
58
|
autoload :Jira, 'gitlab/qa/scenario/test/integration/jira'
|
59
59
|
end
|
60
60
|
|
@@ -42,6 +42,16 @@ module Gitlab
|
|
42
42
|
end
|
43
43
|
|
44
44
|
def instance
|
45
|
+
instance_no_teardown do
|
46
|
+
yield self if block_given?
|
47
|
+
end
|
48
|
+
ensure
|
49
|
+
teardown
|
50
|
+
end
|
51
|
+
|
52
|
+
alias_method :launch_and_teardown_instance, :instance
|
53
|
+
|
54
|
+
def instance_no_teardown
|
45
55
|
prepare
|
46
56
|
start
|
47
57
|
reconfigure
|
@@ -49,20 +59,14 @@ module Gitlab
|
|
49
59
|
process_exec_commands
|
50
60
|
|
51
61
|
yield self if block_given?
|
52
|
-
ensure
|
53
|
-
teardown
|
54
62
|
end
|
55
63
|
|
56
|
-
alias_method :launch_and_teardown_instance, :instance
|
57
|
-
|
58
64
|
def prepare
|
59
65
|
prepare_docker_image
|
60
66
|
prepare_network
|
61
67
|
end
|
62
68
|
|
63
69
|
def prepare_docker_image
|
64
|
-
return if Runtime::Env.skip_pull?
|
65
|
-
|
66
70
|
pull
|
67
71
|
end
|
68
72
|
|
@@ -106,6 +110,17 @@ module Gitlab
|
|
106
110
|
end
|
107
111
|
|
108
112
|
def teardown
|
113
|
+
unless teardown?
|
114
|
+
puts "The orchestrated docker containers have not been removed."
|
115
|
+
docker.ps
|
116
|
+
|
117
|
+
return
|
118
|
+
end
|
119
|
+
|
120
|
+
teardown!
|
121
|
+
end
|
122
|
+
|
123
|
+
def teardown!
|
109
124
|
assert_name!
|
110
125
|
|
111
126
|
return unless docker.running?(name)
|
@@ -115,6 +130,8 @@ module Gitlab
|
|
115
130
|
end
|
116
131
|
|
117
132
|
def pull
|
133
|
+
return if Runtime::Env.skip_pull?
|
134
|
+
|
118
135
|
docker.pull(image, tag)
|
119
136
|
end
|
120
137
|
|
@@ -129,6 +146,10 @@ module Gitlab
|
|
129
146
|
def assert_name!
|
130
147
|
raise 'Invalid instance name!' unless name
|
131
148
|
end
|
149
|
+
|
150
|
+
def teardown?
|
151
|
+
!Runtime::Scenario.attributes.include?(:teardown) || Runtime::Scenario.teardown
|
152
|
+
end
|
132
153
|
end
|
133
154
|
end
|
134
155
|
end
|
@@ -17,6 +17,8 @@ module Gitlab
|
|
17
17
|
end
|
18
18
|
|
19
19
|
def perform # rubocop:disable Metrics/AbcSize
|
20
|
+
return puts "Skipping tests." if skip_tests?
|
21
|
+
|
20
22
|
raise ArgumentError unless [suite, release].all?
|
21
23
|
|
22
24
|
@docker.login(**release.login_params) if release.login_params
|
@@ -25,23 +27,53 @@ module Gitlab
|
|
25
27
|
|
26
28
|
name = "#{release.project_name}-qa-#{SecureRandom.hex(4)}"
|
27
29
|
|
28
|
-
|
29
|
-
command << "-t --rm --net=#{network || 'bridge'}"
|
30
|
+
feature_flag_sets = []
|
30
31
|
|
31
|
-
|
32
|
-
|
33
|
-
|
32
|
+
# When `args` includes `[..., "--disable-feature", "a", "--enable-feature", "b", ...]`
|
33
|
+
# `feature_flag_sets` will be set to `[["--disable-feature", "a"], ["--enable-feature", "b"]]`
|
34
|
+
# This will result in tests running twice, once with each feature.
|
35
|
+
while (index = args&.index { |x| x =~ /--.*-feature/ })
|
36
|
+
feature_flag_sets << args.slice!(index, 2)
|
37
|
+
end
|
34
38
|
|
35
|
-
|
36
|
-
|
39
|
+
# When `args` do not have either "--disable-feature" or "--enable-feature", we
|
40
|
+
# add [] so that test is run exactly once.
|
41
|
+
feature_flag_sets << [] unless feature_flag_sets.any?
|
37
42
|
|
38
|
-
|
39
|
-
|
40
|
-
|
43
|
+
feature_flag_sets.each do |feature_flag_set|
|
44
|
+
@docker.run(release.qa_image, release.qa_tag, suite, *args_with_flags(args, feature_flag_set)) do |command|
|
45
|
+
command << "-t --rm --net=#{network || 'bridge'}"
|
41
46
|
|
42
|
-
|
47
|
+
env.merge(Runtime::Env.variables).each do |key, value|
|
48
|
+
command.env(key, value)
|
49
|
+
end
|
50
|
+
|
51
|
+
command.volume('/var/run/docker.sock', '/var/run/docker.sock')
|
52
|
+
command.volume(File.join(Runtime::Env.host_artifacts_dir, name), File.join(Docker::Volumes::QA_CONTAINER_WORKDIR, 'tmp'))
|
53
|
+
|
54
|
+
@volumes.to_h.each do |to, from|
|
55
|
+
command.volume(to, from)
|
56
|
+
end
|
57
|
+
|
58
|
+
command.name(name)
|
59
|
+
end
|
43
60
|
end
|
44
61
|
end
|
62
|
+
|
63
|
+
private
|
64
|
+
|
65
|
+
def args_with_flags(args, feature_flag_set)
|
66
|
+
return args if feature_flag_set.empty?
|
67
|
+
|
68
|
+
puts "Running with feature flag: #{feature_flag_set.join(' ')}"
|
69
|
+
|
70
|
+
args_with_f = args.dup
|
71
|
+
args_with_f.insert(1, *feature_flag_set)
|
72
|
+
end
|
73
|
+
|
74
|
+
def skip_tests?
|
75
|
+
Runtime::Scenario.attributes.include?(:run_tests) && !Runtime::Scenario.run_tests
|
76
|
+
end
|
45
77
|
end
|
46
78
|
end
|
47
79
|
end
|
@@ -4,8 +4,9 @@ module Gitlab
|
|
4
4
|
class Command
|
5
5
|
attr_reader :args
|
6
6
|
|
7
|
-
def initialize(cmd = nil)
|
7
|
+
def initialize(cmd = nil, mask_secrets: nil)
|
8
8
|
@args = Array(cmd)
|
9
|
+
@mask_secrets = Array(mask_secrets)
|
9
10
|
end
|
10
11
|
|
11
12
|
def <<(*args)
|
@@ -28,6 +29,17 @@ module Gitlab
|
|
28
29
|
"docker #{@args.join(' ')}"
|
29
30
|
end
|
30
31
|
|
32
|
+
# Returns a masked string form of a Command
|
33
|
+
#
|
34
|
+
# @example
|
35
|
+
# Command.new('a docker command', mask_secrets: 'command').mask_secrets #=> 'a docker *****'
|
36
|
+
# Command.new('a docker command', mask_secrets: %w[docker command]).mask_secrets #=> 'a ***** *****'
|
37
|
+
#
|
38
|
+
# @return [String] The masked command string
|
39
|
+
def mask_secrets
|
40
|
+
@mask_secrets.each_with_object(to_s) { |secret, s| s.gsub!(secret, '*****') }
|
41
|
+
end
|
42
|
+
|
31
43
|
def ==(other)
|
32
44
|
to_s == other.to_s
|
33
45
|
end
|
@@ -36,8 +48,8 @@ module Gitlab
|
|
36
48
|
Docker::Shellout.new(self).execute!(&block)
|
37
49
|
end
|
38
50
|
|
39
|
-
def self.execute(cmd, &block)
|
40
|
-
new(cmd).execute!(&block)
|
51
|
+
def self.execute(cmd, mask_secrets: nil, &block)
|
52
|
+
new(cmd, mask_secrets: mask_secrets).execute!(&block)
|
41
53
|
end
|
42
54
|
end
|
43
55
|
end
|
@@ -10,7 +10,7 @@ module Gitlab
|
|
10
10
|
end
|
11
11
|
|
12
12
|
def login(username:, password:, registry:)
|
13
|
-
Docker::Command.execute(%(login --username "#{username}" --password "#{password}" #{registry}))
|
13
|
+
Docker::Command.execute(%(login --username "#{username}" --password "#{password}" #{registry}), mask_secrets: password)
|
14
14
|
end
|
15
15
|
|
16
16
|
def pull(image, tag)
|
@@ -82,6 +82,10 @@ module Gitlab
|
|
82
82
|
def running?(name)
|
83
83
|
Docker::Command.execute("ps -f name=#{name}").include?(name)
|
84
84
|
end
|
85
|
+
|
86
|
+
def ps(name = nil)
|
87
|
+
Docker::Command.execute(['ps', name].compact.join(' '))
|
88
|
+
end
|
85
89
|
end
|
86
90
|
end
|
87
91
|
end
|
@@ -10,7 +10,7 @@ module Gitlab
|
|
10
10
|
@command = command
|
11
11
|
@output = []
|
12
12
|
|
13
|
-
puts "Docker shell command: `#{@command}`"
|
13
|
+
puts "Docker shell command: `#{@command.mask_secrets}`"
|
14
14
|
end
|
15
15
|
|
16
16
|
def execute!
|
@@ -28,7 +28,7 @@ module Gitlab
|
|
28
28
|
end
|
29
29
|
|
30
30
|
if wait.value.exited? && wait.value.exitstatus.nonzero?
|
31
|
-
raise StatusError, "Docker command `#{@command}` failed!"
|
31
|
+
raise StatusError, "Docker command `#{@command.mask_secrets}` failed!"
|
32
32
|
end
|
33
33
|
end
|
34
34
|
|
data/lib/gitlab/qa/release.rb
CHANGED
@@ -136,6 +136,8 @@ module Gitlab
|
|
136
136
|
end
|
137
137
|
|
138
138
|
def login_params
|
139
|
+
return if Runtime::Env.skip_pull?
|
140
|
+
|
139
141
|
if dev_gitlab_org?
|
140
142
|
Runtime::Env.require_qa_dev_access_token!
|
141
143
|
|
@@ -145,11 +147,18 @@ module Gitlab
|
|
145
147
|
registry: DEV_REGISTRY
|
146
148
|
}
|
147
149
|
elsif omnibus_mirror?
|
148
|
-
Runtime::Env.
|
149
|
-
|
150
|
+
username, password = if Runtime::Env.ci_job_token && Runtime::Env.ci_pipeline_source == 'pipeline'
|
151
|
+
['gitlab-ci-token', Runtime::Env.ci_job_token]
|
152
|
+
elsif Runtime::Env.qa_container_registry_access_token
|
153
|
+
[Runtime::Env.gitlab_username, Runtime::Env.qa_container_registry_access_token]
|
154
|
+
else
|
155
|
+
Runtime::Env.require_qa_access_token!
|
156
|
+
|
157
|
+
[Runtime::Env.gitlab_username, Runtime::Env.qa_access_token]
|
158
|
+
end
|
150
159
|
{
|
151
|
-
username:
|
152
|
-
password:
|
160
|
+
username: username,
|
161
|
+
password: password,
|
153
162
|
registry: COM_REGISTRY
|
154
163
|
}
|
155
164
|
end
|
@@ -167,6 +176,10 @@ module Gitlab
|
|
167
176
|
canonical? || release.match?(CUSTOM_GITLAB_IMAGE_REGEX)
|
168
177
|
end
|
169
178
|
|
179
|
+
def api_project_name
|
180
|
+
project_name.gsub('ce', 'foss').gsub('-ee', '')
|
181
|
+
end
|
182
|
+
|
170
183
|
private
|
171
184
|
|
172
185
|
def canonical?
|
data/lib/gitlab/qa/runner.rb
CHANGED
@@ -4,22 +4,20 @@ module Gitlab
|
|
4
4
|
module QA
|
5
5
|
# rubocop:disable Metrics/AbcSize
|
6
6
|
class Runner
|
7
|
-
# These options are implemented in the QA framework (i.e., in the CE/EE codebase)
|
8
|
-
# They're included here so that gitlab-qa treats them as valid options
|
9
|
-
PASS_THROUGH_OPTS = [
|
10
|
-
['--address URL', 'Address of the instance to test'],
|
11
|
-
['--enable-feature FEATURE_FLAG', 'Enable a feature before running tests'],
|
12
|
-
['--mattermost-address URL', 'Address of the Mattermost server'],
|
13
|
-
['--parallel', 'Execute tests in parallel'],
|
14
|
-
['--loop', 'Execute tests in a loop']
|
15
|
-
].freeze
|
16
|
-
|
17
7
|
def self.run(args)
|
18
|
-
|
8
|
+
Runtime::Scenario.define(:teardown, true)
|
9
|
+
Runtime::Scenario.define(:run_tests, true)
|
10
|
+
|
11
|
+
@options = OptionParser.new do |opts|
|
19
12
|
opts.banner = 'Usage: gitlab-qa [options] Scenario URL [[--] path] [rspec_options]'
|
20
13
|
|
21
|
-
|
22
|
-
|
14
|
+
opts.on('--no-teardown', 'Skip teardown of containers after the scenario completes.') do
|
15
|
+
Runtime::Scenario.define(:teardown, false)
|
16
|
+
end
|
17
|
+
|
18
|
+
opts.on('--no-tests', 'Orchestrates the docker containers but does not run the tests. Implies --no-teardown') do
|
19
|
+
Runtime::Scenario.define(:run_tests, false)
|
20
|
+
Runtime::Scenario.define(:teardown, false)
|
23
21
|
end
|
24
22
|
|
25
23
|
opts.on_tail('-v', '--version', 'Show the version') do
|
@@ -33,19 +31,29 @@ module Gitlab
|
|
33
31
|
exit
|
34
32
|
end
|
35
33
|
|
36
|
-
|
34
|
+
begin
|
35
|
+
opts.parse(args)
|
36
|
+
rescue OptionParser::InvalidOption
|
37
|
+
# Ignore invalid options and options that are passed through to the tests
|
38
|
+
end
|
37
39
|
end
|
38
40
|
|
41
|
+
args.reject! { |arg| gitlab_qa_options.include?(arg) }
|
42
|
+
|
39
43
|
if args.size >= 1
|
40
44
|
Scenario
|
41
45
|
.const_get(args.shift)
|
42
46
|
.perform(*args)
|
43
47
|
else
|
44
|
-
puts options
|
48
|
+
puts @options
|
45
49
|
exit 1
|
46
50
|
end
|
47
51
|
end
|
48
52
|
# rubocop:enable Metrics/AbcSize
|
53
|
+
|
54
|
+
def self.gitlab_qa_options
|
55
|
+
@gitlab_qa_options ||= @options.top.list.map(&:long).flatten
|
56
|
+
end
|
49
57
|
end
|
50
58
|
end
|
51
59
|
end
|
@@ -6,6 +6,8 @@ module Gitlab
|
|
6
6
|
module Env
|
7
7
|
extend self
|
8
8
|
|
9
|
+
# Variables that are used in tests and are passed through to the docker container that executes the tests.
|
10
|
+
# These variables should be listed in /docs/what_tests_can_be_run.md#supported-gitlab-environment-variables
|
9
11
|
ENV_VARIABLES = {
|
10
12
|
'QA_REMOTE_GRID' => :remote_grid,
|
11
13
|
'QA_REMOTE_GRID_USERNAME' => :remote_grid_username,
|
@@ -38,6 +40,7 @@ module Gitlab
|
|
38
40
|
'SIGNUP_DISABLED' => :signup_disabled,
|
39
41
|
'QA_ADDITIONAL_REPOSITORY_STORAGE' => :qa_additional_repository_storage,
|
40
42
|
'QA_PRAEFECT_REPOSITORY_STORAGE' => :qa_praefect_repository_storage,
|
43
|
+
'QA_GITALY_NON_CLUSTER_STORAGE' => :qa_gitaly_non_cluster_storage,
|
41
44
|
'QA_COOKIES' => :qa_cookie,
|
42
45
|
'QA_DEBUG' => :qa_debug,
|
43
46
|
'QA_LOG_PATH' => :qa_log_path,
|
@@ -104,10 +107,18 @@ module Gitlab
|
|
104
107
|
ENV['CI_JOB_NAME']
|
105
108
|
end
|
106
109
|
|
110
|
+
def ci_job_token
|
111
|
+
ENV['CI_JOB_TOKEN']
|
112
|
+
end
|
113
|
+
|
107
114
|
def ci_job_url
|
108
115
|
ENV['CI_JOB_URL']
|
109
116
|
end
|
110
117
|
|
118
|
+
def ci_pipeline_source
|
119
|
+
ENV['CI_PIPELINE_SOURCE']
|
120
|
+
end
|
121
|
+
|
111
122
|
def ci_project_name
|
112
123
|
ENV['CI_PROJECT_NAME']
|
113
124
|
end
|
@@ -144,6 +155,10 @@ module Gitlab
|
|
144
155
|
ENV['GITLAB_QA_DEV_ACCESS_TOKEN']
|
145
156
|
end
|
146
157
|
|
158
|
+
def qa_container_registry_access_token
|
159
|
+
ENV['GITLAB_QA_CONTAINER_REGISTRY_ACCESS_TOKEN']
|
160
|
+
end
|
161
|
+
|
147
162
|
def host_artifacts_dir
|
148
163
|
@host_artifacts_dir ||= File.join(ENV['QA_ARTIFACTS_DIR'] || '/tmp/gitlab-qa', Runtime::Env.run_id)
|
149
164
|
end
|
@@ -207,12 +222,6 @@ module Gitlab
|
|
207
222
|
end
|
208
223
|
end
|
209
224
|
|
210
|
-
def require_gitlab_bot_multi_project_pipeline_polling_token!
|
211
|
-
return unless ENV['GITLAB_BOT_MULTI_PROJECT_PIPELINE_POLLING_TOKEN'].to_s.strip.empty?
|
212
|
-
|
213
|
-
raise ArgumentError, "Please provide GITLAB_BOT_MULTI_PROJECT_PIPELINE_POLLING_TOKEN"
|
214
|
-
end
|
215
|
-
|
216
225
|
def skip_pull?
|
217
226
|
enabled?(ENV['QA_SKIP_PULL'], default: false)
|
218
227
|
end
|
@@ -8,9 +8,6 @@ module Gitlab
|
|
8
8
|
|
9
9
|
class Geo < Scenario::Template
|
10
10
|
def perform(release, primary_address, secondary_address, *rspec_args)
|
11
|
-
# Geo requires an EE license
|
12
|
-
Runtime::Env.require_license!
|
13
|
-
|
14
11
|
Component::Specs.perform do |specs|
|
15
12
|
specs.suite = 'QA::EE::Scenario::Test::Geo'
|
16
13
|
specs.release = QA::Release.new(release)
|
@@ -27,13 +27,14 @@ module Gitlab
|
|
27
27
|
gitlab_rails['db_pool'] = 5;
|
28
28
|
gitlab_rails['geo_node_name'] = '#{primary.name}';
|
29
29
|
gitlab_rails['monitoring_whitelist'] = ['0.0.0.0/0'];
|
30
|
+
gitlab_rails['packages_enabled'] = true;
|
30
31
|
postgresql['listen_address'] = '0.0.0.0';
|
31
32
|
postgresql['max_replication_slots'] = 1;
|
32
33
|
postgresql['md5_auth_cidr_addresses'] = ['0.0.0.0/0'];
|
33
34
|
postgresql['sql_user_password'] = 'e1d1469ec5f533651918b4567a3ed1ae';
|
34
35
|
postgresql['trust_auth_cidr_addresses'] = ['0.0.0.0/0','0.0.0.0/0'];
|
35
36
|
sidekiq['concurrency'] = 2;
|
36
|
-
|
37
|
+
puma['worker_processes'] = 2;
|
37
38
|
OMNIBUS
|
38
39
|
primary.exec_commands = fast_ssh_key_lookup_commands + git_lfs_install_commands
|
39
40
|
|
@@ -50,11 +51,12 @@ module Gitlab
|
|
50
51
|
gitlab_rails['db_pool'] = 5;
|
51
52
|
gitlab_rails['geo_node_name'] = '#{secondary.name}';
|
52
53
|
gitlab_rails['monitoring_whitelist'] = ['0.0.0.0/0'];
|
54
|
+
gitlab_rails['packages_enabled'] = true;
|
53
55
|
postgresql['listen_address'] = '0.0.0.0';
|
54
56
|
postgresql['md5_auth_cidr_addresses'] = ['0.0.0.0/0'];
|
55
57
|
postgresql['sql_user_password'] = 'e1d1469ec5f533651918b4567a3ed1ae';
|
56
58
|
sidekiq['concurrency'] = 2;
|
57
|
-
|
59
|
+
puma['worker_processes'] = 2;
|
58
60
|
OMNIBUS
|
59
61
|
secondary.exec_commands = fast_ssh_key_lookup_commands + git_lfs_install_commands
|
60
62
|
|
@@ -0,0 +1,201 @@
|
|
1
|
+
module Gitlab
|
2
|
+
module QA
|
3
|
+
module Scenario
|
4
|
+
module Test
|
5
|
+
module Integration
|
6
|
+
class GitalyCluster < Scenario::Template
|
7
|
+
attr_reader :gitlab_name, :spec_suite
|
8
|
+
|
9
|
+
def initialize
|
10
|
+
@gitlab_name = 'gitlab-gitaly-ha'
|
11
|
+
@primary_node_name = 'gitaly1'
|
12
|
+
@secondary_node_name = 'gitaly2'
|
13
|
+
@tertiary_node_name = 'gitaly3'
|
14
|
+
@praefect_node_name = 'praefect'
|
15
|
+
@database = 'postgres'
|
16
|
+
@spec_suite = 'Test::Integration::GitalyHA'
|
17
|
+
@network = 'test'
|
18
|
+
end
|
19
|
+
|
20
|
+
# rubocop:disable Metrics/AbcSize
|
21
|
+
def perform(release, *rspec_args)
|
22
|
+
gitaly_primary_node = gitaly(@primary_node_name, release)
|
23
|
+
gitaly_secondary_node = gitaly(@secondary_node_name, release)
|
24
|
+
gitaly_tertiary_node = gitaly(@tertiary_node_name, release)
|
25
|
+
|
26
|
+
sql_node = Component::PostgreSQL.new.tap do |sql|
|
27
|
+
sql.name = @database
|
28
|
+
sql.network = @network
|
29
|
+
sql.instance_no_teardown do
|
30
|
+
sql.run_psql '-d template1 -c "CREATE DATABASE praefect_production OWNER postgres"'
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
praefect_node = Component::Gitlab.new.tap do |praefect|
|
35
|
+
praefect.release = QA::Release.new(release)
|
36
|
+
praefect.name = @praefect_node_name
|
37
|
+
praefect.network = @network
|
38
|
+
praefect.skip_availability_check = true
|
39
|
+
|
40
|
+
praefect.omnibus_config = praefect_omnibus_configuration
|
41
|
+
|
42
|
+
praefect.instance_no_teardown
|
43
|
+
end
|
44
|
+
|
45
|
+
Component::Gitlab.perform do |gitlab|
|
46
|
+
gitlab.release = QA::Release.new(release)
|
47
|
+
gitlab.name = gitlab_name
|
48
|
+
gitlab.network = @network
|
49
|
+
|
50
|
+
gitlab.omnibus_config = gitlab_omnibus_configuration
|
51
|
+
gitlab.instance do
|
52
|
+
puts "Running Gitaly HA specs!"
|
53
|
+
|
54
|
+
Component::Specs.perform do |specs|
|
55
|
+
specs.suite = spec_suite
|
56
|
+
specs.release = gitlab.release
|
57
|
+
specs.network = gitlab.network
|
58
|
+
specs.args = [gitlab.address, *rspec_args]
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
ensure
|
63
|
+
praefect_node&.teardown
|
64
|
+
sql_node&.teardown
|
65
|
+
gitaly_primary_node&.teardown
|
66
|
+
gitaly_secondary_node&.teardown
|
67
|
+
gitaly_tertiary_node&.teardown
|
68
|
+
end
|
69
|
+
# rubocop:enable Metrics/AbcSize
|
70
|
+
|
71
|
+
private
|
72
|
+
|
73
|
+
def disable_other_services
|
74
|
+
<<~OMNIBUS
|
75
|
+
postgresql['enable'] = false;
|
76
|
+
redis['enable'] = false;
|
77
|
+
nginx['enable'] = false;
|
78
|
+
prometheus['enable'] = false;
|
79
|
+
grafana['enable'] = false;
|
80
|
+
puma['enable'] = false;
|
81
|
+
sidekiq['enable'] = false;
|
82
|
+
gitlab_workhorse['enable'] = false;
|
83
|
+
gitlab_rails['rake_cache_clear'] = false;
|
84
|
+
gitlab_rails['auto_migrate'] = false;
|
85
|
+
OMNIBUS
|
86
|
+
end
|
87
|
+
|
88
|
+
def praefect_omnibus_configuration
|
89
|
+
<<~OMNIBUS
|
90
|
+
#{disable_other_services}
|
91
|
+
gitaly['enable'] = false;
|
92
|
+
praefect['enable'] = true;
|
93
|
+
praefect['listen_addr'] = '0.0.0.0:2305';
|
94
|
+
praefect['prometheus_listen_addr'] = '0.0.0.0:9652';
|
95
|
+
praefect['auth_token'] = 'PRAEFECT_EXTERNAL_TOKEN';
|
96
|
+
praefect['database_host'] = '#{@database}.#{@network}';
|
97
|
+
praefect['database_user'] = 'postgres';
|
98
|
+
praefect['database_port'] = 5432;
|
99
|
+
praefect['database_password'] = 'SQL_PASSWORD';
|
100
|
+
praefect['database_dbname'] = 'praefect_production';
|
101
|
+
praefect['database_sslmode'] = 'disable';
|
102
|
+
praefect['postgres_queue_enabled'] = true;
|
103
|
+
praefect['failover_enabled'] = true;
|
104
|
+
praefect['virtual_storages'] = {
|
105
|
+
'default' => {
|
106
|
+
'#{@primary_node_name}' => {
|
107
|
+
'address' => 'tcp://#{@primary_node_name}.#{@network}:8075',
|
108
|
+
'token' => 'PRAEFECT_INTERNAL_TOKEN',
|
109
|
+
'primary' => true
|
110
|
+
},
|
111
|
+
'#{@secondary_node_name}' => {
|
112
|
+
'address' => 'tcp://#{@secondary_node_name}.#{@network}:8075',
|
113
|
+
'token' => 'PRAEFECT_INTERNAL_TOKEN'
|
114
|
+
},
|
115
|
+
'#{@tertiary_node_name}' => {
|
116
|
+
'address' => 'tcp://#{@tertiary_node_name}.#{@network}:8075',
|
117
|
+
'token' => 'PRAEFECT_INTERNAL_TOKEN'
|
118
|
+
}
|
119
|
+
}
|
120
|
+
};
|
121
|
+
OMNIBUS
|
122
|
+
end
|
123
|
+
|
124
|
+
def gitaly_omnibus_configuration
|
125
|
+
<<~OMNIBUS
|
126
|
+
#{disable_other_services}
|
127
|
+
prometheus['enable'] = true;
|
128
|
+
prometheus_monitoring['enable'] = false;
|
129
|
+
gitaly['enable'] = true;
|
130
|
+
gitaly['listen_addr'] = '0.0.0.0:8075';
|
131
|
+
gitaly['prometheus_listen_addr'] = '0.0.0.0:9236';
|
132
|
+
gitaly['auth_token'] = 'PRAEFECT_INTERNAL_TOKEN';
|
133
|
+
gitlab_shell['secret_token'] = 'GITLAB_SHELL_SECRET_TOKEN';
|
134
|
+
gitlab_rails['internal_api_url'] = 'http://#{@gitlab_name}.#{@network}';
|
135
|
+
git_data_dirs({
|
136
|
+
'#{@primary_node_name}' => {
|
137
|
+
'path' => '/var/opt/gitlab/git-data'
|
138
|
+
},
|
139
|
+
'#{@secondary_node_name}' => {
|
140
|
+
'path' => '/var/opt/gitlab/git-data'
|
141
|
+
},
|
142
|
+
'#{@tertiary_node_name}' => {
|
143
|
+
'path' => '/var/opt/gitlab/git-data'
|
144
|
+
}
|
145
|
+
});
|
146
|
+
OMNIBUS
|
147
|
+
end
|
148
|
+
|
149
|
+
def gitlab_omnibus_configuration
|
150
|
+
<<~OMNIBUS
|
151
|
+
external_url 'http://#{@gitlab_name}.#{@network}';
|
152
|
+
|
153
|
+
git_data_dirs({
|
154
|
+
'default' => {
|
155
|
+
'gitaly_address' => 'tcp://#{@praefect_node_name}.#{@network}:2305',
|
156
|
+
'gitaly_token' => 'PRAEFECT_EXTERNAL_TOKEN'
|
157
|
+
}
|
158
|
+
});
|
159
|
+
gitaly['listen_addr'] = '0.0.0.0:8075';
|
160
|
+
gitlab_shell['secret_token'] = 'GITLAB_SHELL_SECRET_TOKEN';
|
161
|
+
prometheus['scrape_configs'] = [
|
162
|
+
{
|
163
|
+
'job_name' => 'praefect',
|
164
|
+
'static_configs' => [
|
165
|
+
'targets' => [
|
166
|
+
'#{@praefect_node_name}.#{@network}:9652'
|
167
|
+
]
|
168
|
+
]
|
169
|
+
},
|
170
|
+
{
|
171
|
+
'job_name' => 'praefect-gitaly',
|
172
|
+
'static_configs' => [
|
173
|
+
'targets' => [
|
174
|
+
'#{@primary_node_name}.#{@network}:9236',
|
175
|
+
'#{@secondary_node_name}.#{@network}:9236',
|
176
|
+
'#{@tertiary_node_name}.#{@network}:9236'
|
177
|
+
]
|
178
|
+
]
|
179
|
+
}
|
180
|
+
];
|
181
|
+
grafana['disable_login_form'] = false;
|
182
|
+
grafana['admin_password'] = 'GRAFANA_ADMIN_PASSWORD';
|
183
|
+
OMNIBUS
|
184
|
+
end
|
185
|
+
|
186
|
+
def gitaly(name, release)
|
187
|
+
Component::Gitlab.new.tap do |gitaly|
|
188
|
+
gitaly.release = QA::Release.new(release)
|
189
|
+
gitaly.name = name
|
190
|
+
gitaly.network = @network
|
191
|
+
gitaly.skip_availability_check = true
|
192
|
+
gitaly.omnibus_config = gitaly_omnibus_configuration
|
193
|
+
gitaly.instance_no_teardown
|
194
|
+
end
|
195
|
+
end
|
196
|
+
end
|
197
|
+
end
|
198
|
+
end
|
199
|
+
end
|
200
|
+
end
|
201
|
+
end
|
@@ -13,7 +13,11 @@ module Gitlab
|
|
13
13
|
gitlab.name = 'gitlab'
|
14
14
|
gitlab.network = 'test'
|
15
15
|
gitlab.volumes = volumes
|
16
|
-
gitlab.exec_commands = [
|
16
|
+
gitlab.exec_commands = [
|
17
|
+
'gitlab-psql -d template1 -c "CREATE DATABASE praefect_production OWNER gitlab"',
|
18
|
+
'mkdir -p /var/opt/gitlab/git-data/repositories/praefect',
|
19
|
+
'chown -R git:root /var/opt/gitlab/git-data/repositories'
|
20
|
+
]
|
17
21
|
|
18
22
|
gitlab.act do
|
19
23
|
prepare
|
@@ -21,7 +25,7 @@ module Gitlab
|
|
21
25
|
reconfigure
|
22
26
|
process_exec_commands
|
23
27
|
wait
|
24
|
-
teardown
|
28
|
+
teardown!
|
25
29
|
end
|
26
30
|
end
|
27
31
|
|
@@ -61,21 +65,26 @@ module Gitlab
|
|
61
65
|
def omnibus_config_with_praefect
|
62
66
|
<<~OMNIBUS
|
63
67
|
gitaly['enable'] = true;
|
64
|
-
gitaly['
|
68
|
+
gitaly['listen_addr'] = '0.0.0.0:8075';
|
69
|
+
gitaly['auth_token'] = 'secret-token';
|
65
70
|
gitaly['storage'] = [
|
66
71
|
{
|
67
72
|
'name' => 'praefect-gitaly-0',
|
68
|
-
'path' => '/var/opt/gitlab/git-data/repositories'
|
73
|
+
'path' => '/var/opt/gitlab/git-data/repositories/praefect'
|
74
|
+
},
|
75
|
+
{
|
76
|
+
'name' => 'gitaly',
|
77
|
+
'path' => '/var/opt/gitlab/git-data/repositories/gitaly'
|
69
78
|
}
|
70
79
|
];
|
71
80
|
praefect['enable'] = true;
|
72
81
|
praefect['listen_addr'] = '0.0.0.0:2305';
|
73
|
-
praefect['auth_token'] = '
|
82
|
+
praefect['auth_token'] = 'secret-token';
|
74
83
|
praefect['virtual_storages'] = {
|
75
84
|
'default' => {
|
76
85
|
'praefect-gitaly-0' => {
|
77
|
-
'address' => '
|
78
|
-
'token' => '
|
86
|
+
'address' => 'tcp://localhost:8075',
|
87
|
+
'token' => 'secret-token',
|
79
88
|
'primary' => true
|
80
89
|
}
|
81
90
|
}
|
@@ -84,10 +93,13 @@ module Gitlab
|
|
84
93
|
praefect['database_user'] = 'gitlab';
|
85
94
|
praefect['database_dbname'] = 'praefect_production';
|
86
95
|
praefect['postgres_queue_enabled'] = true;
|
87
|
-
gitlab_rails['gitaly_token'] = '
|
96
|
+
gitlab_rails['gitaly_token'] = 'secret-token';
|
88
97
|
git_data_dirs({
|
89
98
|
'default' => {
|
90
99
|
'gitaly_address' => 'tcp://localhost:2305'
|
100
|
+
},
|
101
|
+
'gitaly' => {
|
102
|
+
'path' => '/var/opt/gitlab/git-data/repositories/gitaly'
|
91
103
|
}
|
92
104
|
});
|
93
105
|
OMNIBUS
|
data/lib/gitlab/qa/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gitlab-qa
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 5.
|
4
|
+
version: 5.17.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Grzegorz Bizon
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-
|
11
|
+
date: 2020-08-10 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: climate_control
|
@@ -284,7 +284,7 @@ files:
|
|
284
284
|
- lib/gitlab/qa/scenario/test/instance/staging_geo.rb
|
285
285
|
- lib/gitlab/qa/scenario/test/integration/elasticsearch.rb
|
286
286
|
- lib/gitlab/qa/scenario/test/integration/geo.rb
|
287
|
-
- lib/gitlab/qa/scenario/test/integration/
|
287
|
+
- lib/gitlab/qa/scenario/test/integration/gitaly_cluster.rb
|
288
288
|
- lib/gitlab/qa/scenario/test/integration/group_saml.rb
|
289
289
|
- lib/gitlab/qa/scenario/test/integration/instance_saml.rb
|
290
290
|
- lib/gitlab/qa/scenario/test/integration/jira.rb
|
@@ -1,166 +0,0 @@
|
|
1
|
-
module Gitlab
|
2
|
-
module QA
|
3
|
-
module Scenario
|
4
|
-
module Test
|
5
|
-
module Integration
|
6
|
-
class GitalyHA < Scenario::Template
|
7
|
-
attr_reader :gitlab_name, :spec_suite
|
8
|
-
|
9
|
-
def initialize
|
10
|
-
@gitlab_name = 'gitlab-gitaly-ha'
|
11
|
-
@primary_node = 'gitaly1'
|
12
|
-
@secondary_node = 'gitaly2'
|
13
|
-
@praefect_node = 'praefect'
|
14
|
-
@database = 'postgres'
|
15
|
-
@spec_suite = 'Test::Integration::GitalyHA'
|
16
|
-
@network = 'test'
|
17
|
-
end
|
18
|
-
|
19
|
-
# rubocop:disable Metrics/AbcSize
|
20
|
-
def perform(release, *rspec_args)
|
21
|
-
gitaly(@primary_node, release) do
|
22
|
-
gitaly(@secondary_node, release) do
|
23
|
-
Component::PostgreSQL.perform do |sql|
|
24
|
-
sql.name = @database
|
25
|
-
sql.network = @network
|
26
|
-
|
27
|
-
sql.instance do
|
28
|
-
sql.run_psql '-d template1 -c "CREATE DATABASE praefect_production OWNER postgres"'
|
29
|
-
|
30
|
-
Component::Gitlab.perform do |praefect|
|
31
|
-
praefect.release = QA::Release.new(release)
|
32
|
-
praefect.name = @praefect_node
|
33
|
-
praefect.network = @network
|
34
|
-
praefect.skip_availability_check = true
|
35
|
-
|
36
|
-
praefect.omnibus_config = praefect_omnibus_configuration
|
37
|
-
|
38
|
-
praefect.instance do
|
39
|
-
Component::Gitlab.perform do |gitlab|
|
40
|
-
gitlab.release = QA::Release.new(release)
|
41
|
-
gitlab.name = gitlab_name
|
42
|
-
gitlab.network = @network
|
43
|
-
|
44
|
-
gitlab.omnibus_config = gitlab_omnibus_configuration
|
45
|
-
gitlab.instance do
|
46
|
-
puts "Running Gitaly HA specs!"
|
47
|
-
|
48
|
-
Component::Specs.perform do |specs|
|
49
|
-
specs.suite = spec_suite
|
50
|
-
specs.release = gitlab.release
|
51
|
-
specs.network = gitlab.network
|
52
|
-
specs.args = [gitlab.address, *rspec_args]
|
53
|
-
end
|
54
|
-
end
|
55
|
-
end
|
56
|
-
end
|
57
|
-
end
|
58
|
-
end
|
59
|
-
end
|
60
|
-
end
|
61
|
-
end
|
62
|
-
end
|
63
|
-
# rubocop:enable Metrics/AbcSize
|
64
|
-
|
65
|
-
private
|
66
|
-
|
67
|
-
def disable_other_services
|
68
|
-
<<~OMNIBUS
|
69
|
-
postgresql['enable'] = false;
|
70
|
-
redis['enable'] = false;
|
71
|
-
nginx['enable'] = false;
|
72
|
-
prometheus['enable'] = false;
|
73
|
-
grafana['enable'] = false;
|
74
|
-
unicorn['enable'] = false;
|
75
|
-
sidekiq['enable'] = false;
|
76
|
-
gitlab_workhorse['enable'] = false;
|
77
|
-
gitlab_rails['rake_cache_clear'] = false;
|
78
|
-
gitlab_rails['auto_migrate'] = false;
|
79
|
-
OMNIBUS
|
80
|
-
end
|
81
|
-
|
82
|
-
def praefect_omnibus_configuration
|
83
|
-
<<~OMNIBUS
|
84
|
-
#{disable_other_services}
|
85
|
-
gitaly['enable'] = false;
|
86
|
-
praefect['enable'] = true;
|
87
|
-
praefect['listen_addr'] = '0.0.0.0:2305';
|
88
|
-
praefect['prometheus_listen_addr'] = '0.0.0.0:9652';
|
89
|
-
praefect['auth_token'] = 'PRAEFECT_EXTERNAL_TOKEN';
|
90
|
-
praefect['database_host'] = '#{@database}.#{@network}';
|
91
|
-
praefect['database_user'] = 'postgres';
|
92
|
-
praefect['database_port'] = 5432;
|
93
|
-
praefect['database_password'] = 'SQL_PASSWORD';
|
94
|
-
praefect['database_dbname'] = 'praefect_production';
|
95
|
-
praefect['database_sslmode'] = 'disable';
|
96
|
-
praefect['postgres_queue_enabled'] = true;
|
97
|
-
praefect['failover_enabled'] = true;
|
98
|
-
praefect['virtual_storages'] = {
|
99
|
-
'default' => {
|
100
|
-
'#{@primary_node}' => {
|
101
|
-
'address' => 'tcp://#{@primary_node}.#{@network}:8075',
|
102
|
-
'token' => 'PRAEFECT_INTERNAL_TOKEN',
|
103
|
-
'primary' => true
|
104
|
-
},
|
105
|
-
'#{@secondary_node}' => {
|
106
|
-
'address' => 'tcp://#{@secondary_node}.#{@network}:8075',
|
107
|
-
'token' => 'PRAEFECT_INTERNAL_TOKEN'
|
108
|
-
}
|
109
|
-
}
|
110
|
-
};
|
111
|
-
OMNIBUS
|
112
|
-
end
|
113
|
-
|
114
|
-
def gitaly_omnibus_configuration
|
115
|
-
<<~OMNIBUS
|
116
|
-
#{disable_other_services}
|
117
|
-
prometheus_monitoring['enable'] = false;
|
118
|
-
gitaly['enable'] = true;
|
119
|
-
gitaly['listen_addr'] = '0.0.0.0:8075';
|
120
|
-
gitaly['prometheus_listen_addr'] = '0.0.0.0:9236';
|
121
|
-
gitaly['auth_token'] = 'PRAEFECT_INTERNAL_TOKEN';
|
122
|
-
gitlab_shell['secret_token'] = 'GITLAB_SHELL_SECRET_TOKEN';
|
123
|
-
gitlab_rails['internal_api_url'] = 'http://#{@gitlab_name}.#{@network}';
|
124
|
-
git_data_dirs({
|
125
|
-
'#{@primary_node}' => {
|
126
|
-
'path' => '/var/opt/gitlab/git-data'
|
127
|
-
},
|
128
|
-
'#{@secondary_node}' => {
|
129
|
-
'path' => '/var/opt/gitlab/git-data'
|
130
|
-
}
|
131
|
-
});
|
132
|
-
OMNIBUS
|
133
|
-
end
|
134
|
-
|
135
|
-
def gitlab_omnibus_configuration
|
136
|
-
<<~OMNIBUS
|
137
|
-
git_data_dirs({
|
138
|
-
'default' => {
|
139
|
-
'gitaly_address' => 'tcp://#{@praefect_node}.#{@network}:2305',
|
140
|
-
'gitaly_token' => 'PRAEFECT_EXTERNAL_TOKEN'
|
141
|
-
}
|
142
|
-
});
|
143
|
-
gitlab_shell['secret_token'] = 'GITLAB_SHELL_SECRET_TOKEN';
|
144
|
-
OMNIBUS
|
145
|
-
end
|
146
|
-
|
147
|
-
def gitaly(name, release)
|
148
|
-
Component::Gitlab.perform do |gitaly|
|
149
|
-
gitaly.release = QA::Release.new(release)
|
150
|
-
gitaly.name = name
|
151
|
-
gitaly.network = @network
|
152
|
-
gitaly.skip_availability_check = true
|
153
|
-
|
154
|
-
gitaly.omnibus_config = gitaly_omnibus_configuration
|
155
|
-
|
156
|
-
gitaly.instance do
|
157
|
-
yield self
|
158
|
-
end
|
159
|
-
end
|
160
|
-
end
|
161
|
-
end
|
162
|
-
end
|
163
|
-
end
|
164
|
-
end
|
165
|
-
end
|
166
|
-
end
|