Commit 0af8fa9e authored by Catalin Irimie's avatar Catalin Irimie

Expose internal_url setting for Geo secondaries

This enables admins to set an internal URL for Geo secondaries.

The field already existed in the backend but was intentionally
not exposed to the frontend for simplicity.

This is a pre-requisite to enable the primary to query the
secondaries data directly through this URL.

Changelog: added
EE: true
parent 35ff3879
...@@ -55,14 +55,21 @@ you can increase the values to complete backfill in a shorter time. If it's ...@@ -55,14 +55,21 @@ you can increase the values to complete backfill in a shorter time. If it's
under heavy load and backfill reduces its availability for normal requests, under heavy load and backfill reduces its availability for normal requests,
you can decrease them. you can decrease them.
## Using a different URL for synchronization ## Set up the internal URLs
> Setting up internal URLs in secondary sites was [introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/77179) in GitLab 14.7.
You can set up a different URL for synchronization between the primary and secondary site.
The **primary** site's Internal URL is used by **secondary** sites to contact it The **primary** site's Internal URL is used by **secondary** sites to contact it
(to sync repositories, for example). The name Internal URL distinguishes it from (to sync repositories, for example). The name Internal URL distinguishes it from
[External URL](https://docs.gitlab.com/omnibus/settings/configuration.html#configuring-the-external-url-for-gitlab), [External URL](https://docs.gitlab.com/omnibus/settings/configuration.html#configuring-the-external-url-for-gitlab),
which is used by users. Internal URL does not need to be a private address. which is used by users. Internal URL does not need to be a private address.
Internal URL defaults to external URL, but you can also customize it: When [Geo secondary proxying](../../administration/geo/secondary_proxy/index.md) is enabled,
the primary uses the secondary's internal URL to contact it directly.
The internal URL defaults to external URL. To change it:
1. On the top bar, select **Menu > Admin**. 1. On the top bar, select **Menu > Admin**.
1. On the left sidebar, select **Geo > Nodes**. 1. On the left sidebar, select **Geo > Nodes**.
...@@ -70,6 +77,9 @@ Internal URL defaults to external URL, but you can also customize it: ...@@ -70,6 +77,9 @@ Internal URL defaults to external URL, but you can also customize it:
1. Edit the internal URL. 1. Edit the internal URL.
1. Select **Save changes**. 1. Select **Save changes**.
When enabled, the Admin Area for Geo shows replication details for each site directly
from the primary site's UI, and through the Geo secondary proxy, if enabled.
WARNING: WARNING:
We recommend using an HTTPS connection while configuring the Geo sites. To avoid We recommend using an HTTPS connection while configuring the Geo sites. To avoid
breaking communication between **primary** and **secondary** sites when using breaking communication between **primary** and **secondary** sites when using
......
<script> <script>
import { GlFormGroup, GlFormInput, GlSprintf, GlLink } from '@gitlab/ui'; import { GlFormGroup, GlFormInput, GlSprintf, GlLink } from '@gitlab/ui';
import { mapActions, mapState } from 'vuex'; import { mapActions, mapState } from 'vuex';
import { s__ } from '~/locale';
import { import {
VALIDATION_FIELD_KEYS, VALIDATION_FIELD_KEYS,
NODE_NAME_MORE_INFO, NODE_NAME_MORE_INFO,
...@@ -24,6 +25,15 @@ export default { ...@@ -24,6 +25,15 @@ export default {
}, },
computed: { computed: {
...mapState(['formErrors']), ...mapState(['formErrors']),
internalUrlDescription() {
return this.nodeData.primary
? s__(
'AdminGeo|The URL of the primary site that is used internally by the secondary sites.',
)
: s__(
'AdminGeo|The URL of the secondary site that is used internally by the primary site.',
);
},
}, },
methods: { methods: {
...mapActions(['setError']), ...mapActions(['setError']),
...@@ -126,21 +136,14 @@ export default { ...@@ -126,21 +136,14 @@ export default {
</div> </div>
</gl-form-group> </gl-form-group>
<gl-form-group <gl-form-group
v-if="nodeData.primary"
class="col-12 col-sm-6" class="col-12 col-sm-6"
:label="__('Internal URL (optional)')" :label="__('Internal URL (optional)')"
label-for="node-internal-url-field" label-for="node-internal-url-field"
:description=" :description="internalUrlDescription"
__('The URL defined on the primary node that secondary nodes should use to contact it.')
"
> >
<template #description> <template #description>
<gl-sprintf <gl-sprintf
:message=" :message="`${internalUrlDescription} ${__('%{linkStart}Learn more.%{linkEnd}')}`"
__(
'The URL defined on the primary node that secondary nodes should use to contact it. %{linkStart}Learn more%{linkEnd}',
)
"
> >
<template #link="{ content }"> <template #link="{ content }">
<gl-link <gl-link
......
...@@ -17,7 +17,7 @@ export const NODE_NAME_MORE_INFO = helpPagePath('user/admin_area/geo_nodes.html' ...@@ -17,7 +17,7 @@ export const NODE_NAME_MORE_INFO = helpPagePath('user/admin_area/geo_nodes.html'
}); });
export const NODE_INTERNAL_URL_MORE_INFO = helpPagePath('user/admin_area/geo_nodes.html', { export const NODE_INTERNAL_URL_MORE_INFO = helpPagePath('user/admin_area/geo_nodes.html', {
anchor: 'using-a-different-url-for-synchronization', anchor: 'set-up-the-internal-urls',
}); });
export const SELECTIVE_SYNC_MORE_INFO = helpPagePath( export const SELECTIVE_SYNC_MORE_INFO = helpPagePath(
......
...@@ -52,7 +52,7 @@ export default { ...@@ -52,7 +52,7 @@ export default {
<gl-icon name="external-link" class="gl-ml-1" /> <gl-icon name="external-link" class="gl-ml-1" />
</gl-link> </gl-link>
</div> </div>
<div v-if="node.primary" class="gl-display-flex gl-flex-direction-column gl-lg-my-5"> <div class="gl-display-flex gl-flex-direction-column gl-lg-my-5">
<span>{{ $options.i18n.internalUrl }}</span> <span>{{ $options.i18n.internalUrl }}</span>
<span class="gl-font-weight-bold" data-testid="node-internal-url">{{ <span class="gl-font-weight-bold" data-testid="node-internal-url">{{
node.internalUrl node.internalUrl
......
...@@ -95,7 +95,7 @@ RSpec.describe 'admin Geo Nodes', :js, :geo do ...@@ -95,7 +95,7 @@ RSpec.describe 'admin Geo Nodes', :js, :geo do
end end
describe 'node form fields' do describe 'node form fields' do
primary_only_fields = %w(node-internal-url-field node-reverification-interval-field) primary_only_fields = %w(node-reverification-interval-field)
secondary_only_fields = %w(node-selective-synchronization-field node-repository-capacity-field node-file-capacity-field node-object-storage-field) secondary_only_fields = %w(node-selective-synchronization-field node-repository-capacity-field node-file-capacity-field node-object-storage-field)
it 'when primary renders only primary fields' do it 'when primary renders only primary fields' do
......
...@@ -74,10 +74,10 @@ describe('GeoNodeFormCore', () => { ...@@ -74,10 +74,10 @@ describe('GeoNodeFormCore', () => {
}); });
describe.each` describe.each`
primaryNode | showInternalUrl primaryNode
${true} | ${true} ${true}
${false} | ${false} ${false}
`(`conditional fields`, ({ primaryNode, showInternalUrl }) => { `('internal URL', ({ primaryNode }) => {
describe(`when node is ${primaryNode ? 'primary' : 'secondary'}`, () => { describe(`when node is ${primaryNode ? 'primary' : 'secondary'}`, () => {
beforeEach(() => { beforeEach(() => {
createComponent({ createComponent({
...@@ -85,17 +85,15 @@ describe('GeoNodeFormCore', () => { ...@@ -85,17 +85,15 @@ describe('GeoNodeFormCore', () => {
}); });
}); });
it(`${showInternalUrl ? 'shows' : 'hides'} the Internal URL Field`, () => { it('shows the Internal URL Field', () => {
expect(findGeoNodeInternalUrlField().exists()).toBe(showInternalUrl); expect(findGeoNodeInternalUrlField().exists()).toBe(true);
}); });
it(`${showInternalUrl ? 'shows' : 'hides'} the Internal URL More Information Link`, () => { it('shows the Internal URL More Information Link', () => {
expect(findGeoNodeFormInternalUrlMoreInformation().exists()).toBe(showInternalUrl); expect(findGeoNodeFormInternalUrlMoreInformation().exists()).toBe(true);
if (showInternalUrl) { expect(findGeoNodeFormInternalUrlMoreInformation().attributes('href')).toBe(
expect(findGeoNodeFormInternalUrlMoreInformation().attributes('href')).toBe( NODE_INTERNAL_URL_MORE_INFO,
NODE_INTERNAL_URL_MORE_INFO, );
);
}
}); });
}); });
}); });
......
...@@ -67,17 +67,17 @@ describe('GeoNodeCoreDetails', () => { ...@@ -67,17 +67,17 @@ describe('GeoNodeCoreDetails', () => {
}); });
describe.each` describe.each`
node | showInternalUrl node
${MOCK_NODES[0]} | ${true} ${MOCK_NODES[0]}
${MOCK_NODES[1]} | ${false} ${MOCK_NODES[1]}
`(`conditionally`, ({ node, showInternalUrl }) => { `('internal URL', ({ node }) => {
beforeEach(() => { beforeEach(() => {
createComponent(null, { node }); createComponent(null, { node });
}); });
describe(`when primary is ${node.primary}`, () => { describe(`when primary is ${node.primary}`, () => {
it(`does ${showInternalUrl ? '' : 'not '}render node internal url`, () => { it(`does render node internal url`, () => {
expect(findNodeInternalUrl().exists()).toBe(showInternalUrl); expect(findNodeInternalUrl().exists()).toBe(true);
}); });
}); });
}); });
......
...@@ -722,6 +722,9 @@ msgstr "" ...@@ -722,6 +722,9 @@ msgstr ""
msgid "%{level_name} is not allowed since the fork source project has lower visibility." msgid "%{level_name} is not allowed since the fork source project has lower visibility."
msgstr "" msgstr ""
msgid "%{linkStart}Learn more.%{linkEnd}"
msgstr ""
msgid "%{link_start}Learn more%{link_end} about roles." msgid "%{link_start}Learn more%{link_end} about roles."
msgstr "" msgstr ""
...@@ -2498,6 +2501,12 @@ msgstr "" ...@@ -2498,6 +2501,12 @@ msgstr ""
msgid "AdminDashboard|Error loading the statistics. Please try again" msgid "AdminDashboard|Error loading the statistics. Please try again"
msgstr "" msgstr ""
msgid "AdminGeo|The URL of the primary site that is used internally by the secondary sites."
msgstr ""
msgid "AdminGeo|The URL of the secondary site that is used internally by the primary site."
msgstr ""
msgid "AdminLabels|Define your default set of project labels" msgid "AdminLabels|Define your default set of project labels"
msgstr "" msgstr ""
...@@ -35301,12 +35310,6 @@ msgstr "" ...@@ -35301,12 +35310,6 @@ msgstr ""
msgid "The Snowplow cookie domain." msgid "The Snowplow cookie domain."
msgstr "" msgstr ""
msgid "The URL defined on the primary node that secondary nodes should use to contact it."
msgstr ""
msgid "The URL defined on the primary node that secondary nodes should use to contact it. %{linkStart}Learn more%{linkEnd}"
msgstr ""
msgid "The URL of the Jenkins server." msgid "The URL of the Jenkins server."
msgstr "" msgstr ""
......
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