From 7d1d87d6ec1a500ba47a263d05f6abeb0872781e Mon Sep 17 00:00:00 2001
From: Ainar Garipov <a.garipov@adguard.com>
Date: Tue, 1 Dec 2020 15:51:35 +0300
Subject: [PATCH] Pull request: + client: 2358 Make the mobileconfig API
 parameterized and more robust

Merge in DNS/adguard-home from feature/2358 to master

Updates #2358.

Squashed commit of the following:

commit b2b91ee3b7303d20b94265d43d785e77260b2210
Author: Artem Baskal <a.baskal@adguard.com>
Date:   Tue Dec 1 14:54:35 2020 +0300

    + client: 2358 Make the mobileconfig API parameterized and more robust
---
 client/src/components/ui/Guide.js | 218 ++++++++++++++++--------------
 client/src/reducers/encryption.js |   4 +
 2 files changed, 121 insertions(+), 101 deletions(-)

diff --git a/client/src/components/ui/Guide.js b/client/src/components/ui/Guide.js
index cef1c6f8..a06af83b 100644
--- a/client/src/components/ui/Guide.js
+++ b/client/src/components/ui/Guide.js
@@ -2,22 +2,25 @@ import React, { useState } from 'react';
 import PropTypes from 'prop-types';
 import { Trans, useTranslation } from 'react-i18next';
 import i18next from 'i18next';
+import { useSelector } from 'react-redux';
 import Tabs from './Tabs';
 import Icons from './Icons';
+import { getPathWithQueryString } from '../../helpers/helpers';
 
 const MOBILE_CONFIG_LINKS = {
     DOT: '/apple/dot.mobileconfig',
     DOH: '/apple/doh.mobileconfig',
 };
-
-const renderMobileconfigInfo = ({ label, components }) => <li key={label}>
+const renderMobileconfigInfo = ({ label, components, server_name }) => <li key={label}>
     <Trans components={components}>{label}</Trans>
     <ul>
         <li>
-            <a href={MOBILE_CONFIG_LINKS.DOT} download>{i18next.t('download_mobileconfig_dot')}</a>
+            <a href={getPathWithQueryString(MOBILE_CONFIG_LINKS.DOT, { host: server_name })}
+               download>{i18next.t('download_mobileconfig_dot')}</a>
         </li>
         <li>
-            <a href={MOBILE_CONFIG_LINKS.DOH} download>{i18next.t('download_mobileconfig_doh')}</a>
+            <a href={getPathWithQueryString(MOBILE_CONFIG_LINKS.DOH, { host: server_name })}
+               download>{i18next.t('download_mobileconfig_doh')}</a>
         </li>
     </ul>
 </li>;
@@ -38,37 +41,8 @@ const renderLi = ({ label, components }) => <li key={label}>
     </Trans>
 </li>;
 
-const dnsPrivacyList = [{
-    title: 'Android',
-    list: [
-        {
-            label: 'setup_dns_privacy_android_1',
-        },
-        {
-            label: 'setup_dns_privacy_android_2',
-            components: [
-                {
-                    key: 0,
-                    href: 'https://adguard.com/adguard-android/overview.html',
-                },
-                <code key="1">text</code>,
-            ],
-        },
-        {
-            label: 'setup_dns_privacy_android_3',
-            components: [
-                {
-                    key: 0,
-                    href: 'https://getintra.org/',
-                },
-                <code key="1">text</code>,
-            ],
-        },
-    ],
-},
-{
-    title: 'iOS',
-    list: [
+const getDnsPrivacyList = (server_name) => {
+    const iosList = [
         {
             label: 'setup_dns_privacy_ios_2',
             components: [
@@ -79,13 +53,6 @@ const dnsPrivacyList = [{
                 <code key="1">text</code>,
             ],
         },
-        {
-            label: 'setup_dns_privacy_4',
-            components: {
-                highlight: <code />,
-            },
-            renderComponent: renderMobileconfigInfo,
-        },
         {
             label: 'setup_dns_privacy_ios_1',
             components: [
@@ -93,68 +60,114 @@ const dnsPrivacyList = [{
                     key: 0,
                     href: 'https://itunes.apple.com/app/id1452162351',
                 },
-                    <code key="1">text</code>,
-                    {
-                        key: 2,
-                        href: 'https://dnscrypt.info/stamps',
-                    },
+                <code key="1">text</code>,
+                {
+                    key: 2,
+                    href: 'https://dnscrypt.info/stamps',
+                },
 
             ],
-        },
-    ],
-},
-{
-    title: 'setup_dns_privacy_other_title',
-    list: [
-        {
-            label: 'setup_dns_privacy_other_1',
-        },
-        {
-            label: 'setup_dns_privacy_other_2',
-            components: [
-                {
-                    key: 0,
-                    href: 'https://github.com/AdguardTeam/dnsproxy',
-                },
-            ],
-        },
-        {
-            href: 'https://github.com/jedisct1/dnscrypt-proxy',
-            label: 'setup_dns_privacy_other_3',
-            components: [
-                {
-                    key: 0,
-                    href: 'https://github.com/jedisct1/dnscrypt-proxy',
-                },
+        }];
+    /* Insert second element if can generate .mobileconfig links */
+    if (server_name) {
+        iosList.splice(1, 0, {
+            label: 'setup_dns_privacy_4',
+            components: {
+                highlight: <code />,
+            },
+            renderComponent: ({ label, components }) => renderMobileconfigInfo({
+                label,
+                components,
+                server_name,
+            }),
+        });
+    }
+
+    return [{
+        title: 'Android',
+        list: [
+            {
+                label: 'setup_dns_privacy_android_1',
+            },
+            {
+                label: 'setup_dns_privacy_android_2',
+                components: [
+                    {
+                        key: 0,
+                        href: 'https://adguard.com/adguard-android/overview.html',
+                    },
                     <code key="1">text</code>,
-            ],
-        },
-        {
-            label: 'setup_dns_privacy_other_4',
-            components: [
-                {
-                    key: 0,
-                    href: 'https://support.mozilla.org/kb/firefox-dns-over-https',
-                },
+                ],
+            },
+            {
+                label: 'setup_dns_privacy_android_3',
+                components: [
+                    {
+                        key: 0,
+                        href: 'https://getintra.org/',
+                    },
                     <code key="1">text</code>,
-            ],
-        },
-        {
-            label: 'setup_dns_privacy_other_5',
-            components: [
-                {
-                    key: 0,
-                    href: 'https://dnscrypt.info/implementations',
-                },
-                {
-                    key: 1,
-                    href: 'https://dnsprivacy.org/wiki/display/DP/DNS+Privacy+Clients',
-                },
-            ],
-        },
-    ],
-},
-];
+                ],
+            },
+        ],
+    },
+    {
+        title: 'iOS',
+        list: iosList,
+    },
+    {
+        title: 'setup_dns_privacy_other_title',
+        list: [
+            {
+                label: 'setup_dns_privacy_other_1',
+            },
+            {
+                label: 'setup_dns_privacy_other_2',
+                components: [
+                    {
+                        key: 0,
+                        href: 'https://github.com/AdguardTeam/dnsproxy',
+                    },
+                ],
+            },
+            {
+                href: 'https://github.com/jedisct1/dnscrypt-proxy',
+                label: 'setup_dns_privacy_other_3',
+                components: [
+                    {
+                        key: 0,
+                        href: 'https://github.com/jedisct1/dnscrypt-proxy',
+                    },
+                        <code key="1">text</code>,
+                ],
+            },
+            {
+                label: 'setup_dns_privacy_other_4',
+                components: [
+                    {
+                        key: 0,
+                        href: 'https://support.mozilla.org/kb/firefox-dns-over-https',
+                    },
+                        <code key="1">text</code>,
+                ],
+            },
+            {
+                label: 'setup_dns_privacy_other_5',
+                components: [
+                    {
+                        key: 0,
+                        href: 'https://dnscrypt.info/implementations',
+                    },
+                    {
+                        key: 1,
+                        href: 'https://dnsprivacy.org/wiki/display/DP/DNS+Privacy+Clients',
+                    },
+                ],
+            },
+        ],
+    },
+    ];
+};
 
 const renderDnsPrivacyList = ({ title, list }) => <div className="tab__paragraph" key={title}>
     <strong><Trans>{title}</Trans></strong>
@@ -172,6 +185,7 @@ const getTabs = ({
     tlsAddress,
     httpsAddress,
     showDnsPrivacyNotice,
+    server_name,
     t,
 }) => ({
     Router: {
@@ -277,7 +291,7 @@ const getTabs = ({
                                 setup_dns_privacy_3
                             </Trans>
                         </div>
-                        {dnsPrivacyList.map(renderDnsPrivacyList)}
+                        {getDnsPrivacyList(server_name).map(renderDnsPrivacyList)}
                     </>}
             </div>
         </div>;
@@ -299,6 +313,7 @@ const renderContent = ({ title, list, getTitle }) => <div key={title} label={i18
 
 const Guide = ({ dnsAddresses }) => {
     const { t } = useTranslation();
+    const server_name = useSelector((state) => state.encryption.server_name);
     const tlsAddress = dnsAddresses?.filter((item) => item.includes('tls://')) ?? '';
     const httpsAddress = dnsAddresses?.filter((item) => item.includes('https://')) ?? '';
     const showDnsPrivacyNotice = httpsAddress.length < 1 && tlsAddress.length < 1;
@@ -309,6 +324,7 @@ const Guide = ({ dnsAddresses }) => {
         tlsAddress,
         httpsAddress,
         showDnsPrivacyNotice,
+        server_name,
         t,
     });
 
diff --git a/client/src/reducers/encryption.js b/client/src/reducers/encryption.js
index a5cd7cbf..8fe9a2cb 100644
--- a/client/src/reducers/encryption.js
+++ b/client/src/reducers/encryption.js
@@ -9,6 +9,8 @@ const encryption = handleActions({
         const newState = {
             ...state,
             ...payload,
+            /* TODO: handle property delete on api refactor */
+            server_name: payload.server_name || '',
             processing: false,
         };
         return newState;
@@ -20,6 +22,7 @@ const encryption = handleActions({
         const newState = {
             ...state,
             ...payload,
+            server_name: payload.server_name || '',
             processingConfig: false,
         };
         return newState;
@@ -49,6 +52,7 @@ const encryption = handleActions({
             subject,
             warning_validation,
             dns_names,
+            server_name: payload.server_name || '',
             processingValidate: false,
         };
         return newState;