fix: Better DNS check to prevent errors
This commit is contained in:
@@ -4,6 +4,8 @@ import { dev } from '$app/env';
|
|||||||
import * as Sentry from '@sentry/node';
|
import * as Sentry from '@sentry/node';
|
||||||
import { uniqueNamesGenerator, adjectives, colors, animals } from 'unique-names-generator';
|
import { uniqueNamesGenerator, adjectives, colors, animals } from 'unique-names-generator';
|
||||||
import type { Config } from 'unique-names-generator';
|
import type { Config } from 'unique-names-generator';
|
||||||
|
import { promises as dns } from 'dns';
|
||||||
|
import { isIP } from 'is-ip';
|
||||||
|
|
||||||
import * as db from '$lib/database';
|
import * as db from '$lib/database';
|
||||||
import { buildLogQueue } from './queues';
|
import { buildLogQueue } from './queues';
|
||||||
@@ -14,6 +16,7 @@ import Cookie from 'cookie';
|
|||||||
import os from 'os';
|
import os from 'os';
|
||||||
import type { RequestEvent } from '@sveltejs/kit/types/internal';
|
import type { RequestEvent } from '@sveltejs/kit/types/internal';
|
||||||
import type { Job } from 'bullmq';
|
import type { Job } from 'bullmq';
|
||||||
|
import { t } from './translations';
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (!dev) {
|
if (!dev) {
|
||||||
@@ -179,3 +182,98 @@ export function getDomain(domain: string): string {
|
|||||||
export function getOsArch() {
|
export function getOsArch() {
|
||||||
return os.arch();
|
return os.arch();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export async function isDNSValid(event: any, domain: string): Promise<any> {
|
||||||
|
let resolves = [];
|
||||||
|
try {
|
||||||
|
if (isIP(event.url.hostname)) {
|
||||||
|
resolves = [event.url.hostname];
|
||||||
|
} else {
|
||||||
|
resolves = await dns.resolve4(event.url.hostname);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
throw {
|
||||||
|
message:
|
||||||
|
"Could not resolve domain or it's not pointing to the server IP address. <br><br>Please check your domain name and try again."
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
let ipDomainFound = false;
|
||||||
|
dns.setServers(['1.1.1.1', '8.8.8.8']);
|
||||||
|
const dnsResolve = await dns.resolve4(domain);
|
||||||
|
if (dnsResolve.length > 0) {
|
||||||
|
for (const ip of dnsResolve) {
|
||||||
|
if (resolves.includes(ip)) {
|
||||||
|
ipDomainFound = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!ipDomainFound) throw false;
|
||||||
|
} catch (error) {
|
||||||
|
throw {
|
||||||
|
message: t.get('application.domain_not_valid')
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function checkDomainsIsValidInDNS({ event, fqdn, dualCerts }): Promise<any> {
|
||||||
|
const domain = getDomain(fqdn);
|
||||||
|
const domainDualCert = domain.includes('www.') ? domain.replace('www.', '') : `www.${domain}`;
|
||||||
|
dns.setServers(['1.1.1.1', '8.8.8.8']);
|
||||||
|
let resolves = [];
|
||||||
|
try {
|
||||||
|
if (isIP(event.url.hostname)) {
|
||||||
|
resolves = [event.url.hostname];
|
||||||
|
} else {
|
||||||
|
resolves = await dns.resolve4(event.url.hostname);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
throw {
|
||||||
|
message: t.get('application.dns_not_set_error', { domain: domain })
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
if (dualCerts) {
|
||||||
|
try {
|
||||||
|
const ipDomain = await dns.resolve4(domain);
|
||||||
|
const ipDomainDualCert = await dns.resolve4(domainDualCert);
|
||||||
|
|
||||||
|
let ipDomainFound = false;
|
||||||
|
let ipDomainDualCertFound = false;
|
||||||
|
|
||||||
|
for (const ip of ipDomain) {
|
||||||
|
if (resolves.includes(ip)) {
|
||||||
|
ipDomainFound = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (const ip of ipDomainDualCert) {
|
||||||
|
if (resolves.includes(ip)) {
|
||||||
|
ipDomainDualCertFound = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (ipDomainFound && ipDomainDualCertFound) return { status: 200 };
|
||||||
|
throw false;
|
||||||
|
} catch (error) {
|
||||||
|
throw {
|
||||||
|
message: t.get('application.dns_not_set_error', { domain })
|
||||||
|
};
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
const ipDomain = await dns.resolve4(domain);
|
||||||
|
let ipDomainFound = false;
|
||||||
|
for (const ip of ipDomain) {
|
||||||
|
if (resolves.includes(ip)) {
|
||||||
|
ipDomainFound = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (ipDomainFound) return { status: 200 };
|
||||||
|
throw false;
|
||||||
|
} catch (error) {
|
||||||
|
throw {
|
||||||
|
message: t.get('application.dns_not_set_error', { domain })
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@@ -178,9 +178,11 @@
|
|||||||
"delete_application": "Delete application",
|
"delete_application": "Delete application",
|
||||||
"permission_denied_delete_application": "You do not have permission to delete this application",
|
"permission_denied_delete_application": "You do not have permission to delete this application",
|
||||||
"domain_already_in_use": "Domain {{domain}} is already used.",
|
"domain_already_in_use": "Domain {{domain}} is already used.",
|
||||||
"dns_not_set_error": "DNS not set or propogated for {{domain}}.<br><br>Please check your DNS settings.",
|
"dns_not_set_error": "DNS not set correctly or propogated for {{domain}}.<br><br>Please check your DNS settings.",
|
||||||
|
"domain_required": "Domain is required.",
|
||||||
"settings_saved": "Settings saved.",
|
"settings_saved": "Settings saved.",
|
||||||
"dns_not_set_partial_error": "DNS not set",
|
"dns_not_set_partial_error": "DNS not set",
|
||||||
|
"domain_not_valid": "Domain is not valid.",
|
||||||
"git_source": "Git Source",
|
"git_source": "Git Source",
|
||||||
"git_repository": "Git Repository",
|
"git_repository": "Git Repository",
|
||||||
"build_pack": "Build Pack",
|
"build_pack": "Build Pack",
|
||||||
|
@@ -117,7 +117,7 @@ const cron = async (): Promise<void> => {
|
|||||||
await queue.ssl.add('ssl', {}, { repeat: { every: dev ? 10000 : 60000 } });
|
await queue.ssl.add('ssl', {}, { repeat: { every: dev ? 10000 : 60000 } });
|
||||||
if (!dev) await queue.cleanup.add('cleanup', {}, { repeat: { every: 300000 } });
|
if (!dev) await queue.cleanup.add('cleanup', {}, { repeat: { every: 300000 } });
|
||||||
if (!dev) await queue.sslRenew.add('sslRenew', {}, { repeat: { every: 1800000 } });
|
if (!dev) await queue.sslRenew.add('sslRenew', {}, { repeat: { every: 1800000 } });
|
||||||
await queue.autoUpdater.add('autoUpdater', {}, { repeat: { every: 60000 } });
|
if (!dev) await queue.autoUpdater.add('autoUpdater', {}, { repeat: { every: 60000 } });
|
||||||
};
|
};
|
||||||
cron().catch((error) => {
|
cron().catch((error) => {
|
||||||
console.log('cron failed to start');
|
console.log('cron failed to start');
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
import { dev } from '$app/env';
|
import { dev } from '$app/env';
|
||||||
import { getDomain, getUserDetails } from '$lib/common';
|
import { checkDomainsIsValidInDNS, getDomain, getUserDetails, isDNSValid } from '$lib/common';
|
||||||
import * as db from '$lib/database';
|
import * as db from '$lib/database';
|
||||||
import { ErrorHandler } from '$lib/database';
|
import { ErrorHandler } from '$lib/database';
|
||||||
import type { RequestHandler } from '@sveltejs/kit';
|
import type { RequestHandler } from '@sveltejs/kit';
|
||||||
@@ -7,16 +7,38 @@ import { promises as dns } from 'dns';
|
|||||||
import getPort from 'get-port';
|
import getPort from 'get-port';
|
||||||
import { t } from '$lib/translations';
|
import { t } from '$lib/translations';
|
||||||
|
|
||||||
|
export const get: RequestHandler = async (event) => {
|
||||||
|
const { status, body } = await getUserDetails(event);
|
||||||
|
if (status === 401) return { status, body };
|
||||||
|
const domain = event.url.searchParams.get('domain');
|
||||||
|
if (!domain) {
|
||||||
|
return {
|
||||||
|
status: 500,
|
||||||
|
body: {
|
||||||
|
message: t.get('application.domain_required')
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
await isDNSValid(event, domain);
|
||||||
|
return {
|
||||||
|
status: 200
|
||||||
|
};
|
||||||
|
} catch (error) {
|
||||||
|
return ErrorHandler(error);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
export const post: RequestHandler = async (event) => {
|
export const post: RequestHandler = async (event) => {
|
||||||
const { status, body } = await getUserDetails(event);
|
const { status, body } = await getUserDetails(event);
|
||||||
if (status === 401) return { status, body };
|
if (status === 401) return { status, body };
|
||||||
|
|
||||||
const { id } = event.params;
|
const { id } = event.params;
|
||||||
let { exposePort, fqdn, forceSave } = await event.request.json();
|
let { exposePort, fqdn, forceSave, dualCerts } = await event.request.json();
|
||||||
fqdn = fqdn.toLowerCase();
|
fqdn = fqdn.toLowerCase();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const domain = getDomain(fqdn);
|
const { isDNSCheckEnabled } = await db.prisma.setting.findFirst({});
|
||||||
const found = await db.isDomainConfigured({ id, fqdn });
|
const found = await db.isDomainConfigured({ id, fqdn });
|
||||||
if (found) {
|
if (found) {
|
||||||
throw {
|
throw {
|
||||||
@@ -25,26 +47,6 @@ export const post: RequestHandler = async (event) => {
|
|||||||
})
|
})
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
if (!dev && !forceSave) {
|
|
||||||
let ip = [];
|
|
||||||
let localIp = [];
|
|
||||||
dns.setServers(['1.1.1.1', '8.8.8.8']);
|
|
||||||
|
|
||||||
try {
|
|
||||||
localIp = await dns.resolve4(event.url.hostname);
|
|
||||||
} catch (error) {}
|
|
||||||
try {
|
|
||||||
ip = await dns.resolve4(domain);
|
|
||||||
} catch (error) {}
|
|
||||||
|
|
||||||
if (localIp?.length > 0) {
|
|
||||||
if (ip?.length === 0 || !ip.includes(localIp[0])) {
|
|
||||||
throw {
|
|
||||||
message: t.get('application.dns_not_set_error', { domain: domain })
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (exposePort) {
|
if (exposePort) {
|
||||||
exposePort = Number(exposePort);
|
exposePort = Number(exposePort);
|
||||||
@@ -59,6 +61,10 @@ export const post: RequestHandler = async (event) => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (isDNSCheckEnabled && !forceSave) {
|
||||||
|
return await checkDomainsIsValidInDNS({ event, fqdn, dualCerts });
|
||||||
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
status: 200
|
status: 200
|
||||||
};
|
};
|
||||||
|
@@ -45,9 +45,9 @@
|
|||||||
import Explainer from '$lib/components/Explainer.svelte';
|
import Explainer from '$lib/components/Explainer.svelte';
|
||||||
import Setting from '$lib/components/Setting.svelte';
|
import Setting from '$lib/components/Setting.svelte';
|
||||||
import type Prisma from '@prisma/client';
|
import type Prisma from '@prisma/client';
|
||||||
import { notNodeDeployments, staticDeployments } from '$lib/components/common';
|
import { getDomain, notNodeDeployments, staticDeployments } from '$lib/components/common';
|
||||||
import { toast } from '@zerodevx/svelte-toast';
|
import { toast } from '@zerodevx/svelte-toast';
|
||||||
import { post } from '$lib/api';
|
import { get, post } from '$lib/api';
|
||||||
import cuid from 'cuid';
|
import cuid from 'cuid';
|
||||||
import { browser } from '$app/env';
|
import { browser } from '$app/env';
|
||||||
import { disabledButton } from '$lib/store';
|
import { disabledButton } from '$lib/store';
|
||||||
@@ -63,6 +63,8 @@
|
|||||||
let dualCerts = application.settings.dualCerts;
|
let dualCerts = application.settings.dualCerts;
|
||||||
let autodeploy = application.settings.autodeploy;
|
let autodeploy = application.settings.autodeploy;
|
||||||
|
|
||||||
|
let nonWWWDomain = application.fqdn && getDomain(application.fqdn).replace(/^www\./, '');
|
||||||
|
|
||||||
let wsgis = [
|
let wsgis = [
|
||||||
{
|
{
|
||||||
value: 'None',
|
value: 'None',
|
||||||
@@ -127,13 +129,16 @@
|
|||||||
async function handleSubmit() {
|
async function handleSubmit() {
|
||||||
loading = true;
|
loading = true;
|
||||||
try {
|
try {
|
||||||
|
nonWWWDomain = application.fqdn && getDomain(application.fqdn).replace(/^www\./, '');
|
||||||
await post(`/applications/${id}/check.json`, {
|
await post(`/applications/${id}/check.json`, {
|
||||||
fqdn: application.fqdn,
|
fqdn: application.fqdn,
|
||||||
forceSave,
|
forceSave,
|
||||||
|
dualCerts,
|
||||||
exposePort: application.exposePort
|
exposePort: application.exposePort
|
||||||
});
|
});
|
||||||
await post(`/applications/${id}.json`, { ...application });
|
await post(`/applications/${id}.json`, { ...application });
|
||||||
$disabledButton = false;
|
$disabledButton = false;
|
||||||
|
forceSave = false;
|
||||||
return toast.push('Configurations saved.');
|
return toast.push('Configurations saved.');
|
||||||
} catch ({ error }) {
|
} catch ({ error }) {
|
||||||
if (error?.startsWith($t('application.dns_not_set_partial_error'))) {
|
if (error?.startsWith($t('application.dns_not_set_partial_error'))) {
|
||||||
@@ -155,6 +160,14 @@
|
|||||||
application.baseBuildImage = event.detail.value;
|
application.baseBuildImage = event.detail.value;
|
||||||
await handleSubmit();
|
await handleSubmit();
|
||||||
}
|
}
|
||||||
|
async function isDNSValid(domain) {
|
||||||
|
try {
|
||||||
|
await get(`/applications/${id}/check.json?domain=${domain}`);
|
||||||
|
toast.push('Domain is valid in DNS.');
|
||||||
|
} catch ({ error }) {
|
||||||
|
return errorNotification(error);
|
||||||
|
}
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="flex items-center space-x-2 p-5 px-6 font-bold">
|
<div class="flex items-center space-x-2 p-5 px-6 font-bold">
|
||||||
@@ -387,6 +400,7 @@
|
|||||||
{/if}
|
{/if}
|
||||||
<Explainer text={$t('application.https_explainer')} />
|
<Explainer text={$t('application.https_explainer')} />
|
||||||
</div>
|
</div>
|
||||||
|
<div>
|
||||||
<input
|
<input
|
||||||
readonly={!$session.isAdmin || isRunning}
|
readonly={!$session.isAdmin || isRunning}
|
||||||
disabled={!$session.isAdmin || isRunning}
|
disabled={!$session.isAdmin || isRunning}
|
||||||
@@ -397,6 +411,23 @@
|
|||||||
pattern="^https?://([a-z0-9]+(-[a-z0-9]+)*\.)+[a-z]{'{'}2,{'}'}$"
|
pattern="^https?://([a-z0-9]+(-[a-z0-9]+)*\.)+[a-z]{'{'}2,{'}'}$"
|
||||||
placeholder="eg: https://coollabs.io"
|
placeholder="eg: https://coollabs.io"
|
||||||
/>
|
/>
|
||||||
|
{#if forceSave}
|
||||||
|
<div class="pt-4">
|
||||||
|
<button
|
||||||
|
class="bg-coollabs hover:bg-coollabs-100"
|
||||||
|
on:click|preventDefault={() => isDNSValid(getDomain(nonWWWDomain))}
|
||||||
|
>Check {nonWWWDomain} DNS Record</button
|
||||||
|
>
|
||||||
|
{#if dualCerts}
|
||||||
|
<button
|
||||||
|
class="bg-coollabs hover:bg-coollabs-100"
|
||||||
|
on:click|preventDefault={() => isDNSValid(getDomain(`www.${nonWWWDomain}`))}
|
||||||
|
>Check www.{nonWWWDomain} DNS Record</button
|
||||||
|
>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="grid grid-cols-2 items-center pb-8">
|
<div class="grid grid-cols-2 items-center pb-8">
|
||||||
<Setting
|
<Setting
|
||||||
|
@@ -1,11 +1,31 @@
|
|||||||
import { dev } from '$app/env';
|
import { dev } from '$app/env';
|
||||||
import { asyncExecShell, getDomain, getEngine, getUserDetails } from '$lib/common';
|
import { checkDomainsIsValidInDNS, getDomain, getUserDetails, isDNSValid } from '$lib/common';
|
||||||
import * as db from '$lib/database';
|
import * as db from '$lib/database';
|
||||||
import { ErrorHandler } from '$lib/database';
|
import { ErrorHandler } from '$lib/database';
|
||||||
import { t } from '$lib/translations';
|
import { t } from '$lib/translations';
|
||||||
import { promises as dns } from 'dns';
|
|
||||||
import type { RequestHandler } from '@sveltejs/kit';
|
import type { RequestHandler } from '@sveltejs/kit';
|
||||||
import { isIP } from 'is-ip';
|
|
||||||
|
export const get: RequestHandler = async (event) => {
|
||||||
|
const { status, body } = await getUserDetails(event);
|
||||||
|
if (status === 401) return { status, body };
|
||||||
|
const domain = event.url.searchParams.get('domain');
|
||||||
|
if (!domain) {
|
||||||
|
return {
|
||||||
|
status: 500,
|
||||||
|
body: {
|
||||||
|
message: t.get('application.domain_required')
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
await isDNSValid(event, domain);
|
||||||
|
return {
|
||||||
|
status: 200
|
||||||
|
};
|
||||||
|
} catch (error) {
|
||||||
|
return ErrorHandler(error);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
export const post: RequestHandler = async (event) => {
|
export const post: RequestHandler = async (event) => {
|
||||||
const { status, body } = await getUserDetails(event);
|
const { status, body } = await getUserDetails(event);
|
||||||
@@ -14,11 +34,9 @@ export const post: RequestHandler = async (event) => {
|
|||||||
|
|
||||||
let { fqdn, forceSave, dualCerts, isDNSCheckEnabled } = await event.request.json();
|
let { fqdn, forceSave, dualCerts, isDNSCheckEnabled } = await event.request.json();
|
||||||
if (fqdn) fqdn = fqdn.toLowerCase();
|
if (fqdn) fqdn = fqdn.toLowerCase();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const domain = getDomain(fqdn);
|
|
||||||
const domainDualCert = domain.includes('www.') ? domain.replace('www.', '') : `www.${domain}`;
|
|
||||||
const found = await db.isDomainConfigured({ id, fqdn });
|
const found = await db.isDomainConfigured({ id, fqdn });
|
||||||
|
console.log(found);
|
||||||
if (found) {
|
if (found) {
|
||||||
throw {
|
throw {
|
||||||
message: t.get('application.domain_already_in_use', {
|
message: t.get('application.domain_already_in_use', {
|
||||||
@@ -26,111 +44,9 @@ export const post: RequestHandler = async (event) => {
|
|||||||
})
|
})
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
if (isDNSCheckEnabled) {
|
if (isDNSCheckEnabled && !forceSave) {
|
||||||
if (!forceSave) {
|
return await checkDomainsIsValidInDNS({ event, fqdn, dualCerts });
|
||||||
dns.setServers(['1.1.1.1', '8.8.8.8']);
|
|
||||||
if (dualCerts) {
|
|
||||||
try {
|
|
||||||
const ipDomain = await dns.resolve4(domain);
|
|
||||||
const ipDomainDualCert = await dns.resolve4(domainDualCert);
|
|
||||||
console.log({ ipDomain, ipDomainDualCert });
|
|
||||||
// TODO: Check if ipDomain and ipDomainDualCert are the same, but not like this
|
|
||||||
if (
|
|
||||||
ipDomain.length === ipDomainDualCert.length &&
|
|
||||||
ipDomain.every((v) => ipDomainDualCert.indexOf(v) >= 0)
|
|
||||||
) {
|
|
||||||
let resolves = [];
|
|
||||||
if (isIP(event.url.hostname)) {
|
|
||||||
resolves = [event.url.hostname];
|
|
||||||
} else {
|
|
||||||
resolves = await dns.resolve4(event.url.hostname);
|
|
||||||
}
|
}
|
||||||
console.log({ resolves });
|
|
||||||
for (const ip of ipDomain) {
|
|
||||||
if (resolves.includes(ip)) {
|
|
||||||
return {
|
|
||||||
status: 200
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
for (const ip of ipDomainDualCert) {
|
|
||||||
if (resolves.includes(ip)) {
|
|
||||||
return {
|
|
||||||
status: 200
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
throw false;
|
|
||||||
} else {
|
|
||||||
throw false;
|
|
||||||
}
|
|
||||||
} catch (error) {
|
|
||||||
console.log(error);
|
|
||||||
throw {
|
|
||||||
message: t.get('application.dns_not_set_error', { domain })
|
|
||||||
};
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
let resolves = [];
|
|
||||||
try {
|
|
||||||
const ipDomain = await dns.resolve4(domain);
|
|
||||||
console.log({ ipDomain });
|
|
||||||
if (isIP(event.url.hostname)) {
|
|
||||||
resolves = [event.url.hostname];
|
|
||||||
} else {
|
|
||||||
resolves = await dns.resolve4(event.url.hostname);
|
|
||||||
}
|
|
||||||
console.log({ resolves });
|
|
||||||
for (const ip of ipDomain) {
|
|
||||||
if (resolves.includes(ip)) {
|
|
||||||
return {
|
|
||||||
status: 200
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
throw false;
|
|
||||||
} catch (error) {
|
|
||||||
console.log(error);
|
|
||||||
throw {
|
|
||||||
message: t.get('application.dns_not_set_error', { domain })
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// let localReverseDomains = [];
|
|
||||||
// let newIps = [];
|
|
||||||
// let newIpsWWW = [];
|
|
||||||
// let localIps = [];
|
|
||||||
// try {
|
|
||||||
// localReverseDomains = await dns.reverse(event.url.hostname)
|
|
||||||
// } catch (error) { }
|
|
||||||
// try {
|
|
||||||
// localIps = await dns.resolve4(event.url.hostname);
|
|
||||||
// } catch (error) { }
|
|
||||||
// try {
|
|
||||||
// newIps = await dns.resolve4(domain);
|
|
||||||
// if (dualCerts) {
|
|
||||||
// newIpsWWW = await dns.resolve4(`${isWWW ? nonWWW : domain}`)
|
|
||||||
// }
|
|
||||||
// console.log(newIps)
|
|
||||||
// } catch (error) { }
|
|
||||||
// console.log({ localIps, newIps, localReverseDomains, dualCerts, isWWW, nonWWW })
|
|
||||||
// if (localReverseDomains?.length > 0) {
|
|
||||||
// if ((newIps?.length === 0 || !newIps.includes(event.url.hostname)) || (dualCerts && newIpsWWW?.length === 0 && !newIpsWWW.includes(`${isWWW ? nonWWW : domain}`))) {
|
|
||||||
// throw {
|
|
||||||
// message: t.get('application.dns_not_set_error', { domain })
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// if (localIps?.length > 0) {
|
|
||||||
// if (newIps?.length === 0 || !localIps.includes(newIps[0])) {
|
|
||||||
// throw {
|
|
||||||
// message: t.get('application.dns_not_set_error', { domain })
|
|
||||||
// };
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
status: 200
|
status: 200
|
||||||
};
|
};
|
||||||
|
@@ -31,7 +31,7 @@
|
|||||||
import Setting from '$lib/components/Setting.svelte';
|
import Setting from '$lib/components/Setting.svelte';
|
||||||
import Explainer from '$lib/components/Explainer.svelte';
|
import Explainer from '$lib/components/Explainer.svelte';
|
||||||
import { errorNotification } from '$lib/form';
|
import { errorNotification } from '$lib/form';
|
||||||
import { del, post } from '$lib/api';
|
import { del, get, post } from '$lib/api';
|
||||||
import CopyPasswordField from '$lib/components/CopyPasswordField.svelte';
|
import CopyPasswordField from '$lib/components/CopyPasswordField.svelte';
|
||||||
import { browser } from '$app/env';
|
import { browser } from '$app/env';
|
||||||
import { getDomain } from '$lib/components/common';
|
import { getDomain } from '$lib/components/common';
|
||||||
@@ -49,6 +49,7 @@
|
|||||||
|
|
||||||
let forceSave = false;
|
let forceSave = false;
|
||||||
let fqdn = settings.fqdn;
|
let fqdn = settings.fqdn;
|
||||||
|
let nonWWWDomain = fqdn && getDomain(fqdn).replace(/^www\./, '');
|
||||||
let isFqdnSet = !!settings.fqdn;
|
let isFqdnSet = !!settings.fqdn;
|
||||||
let loading = {
|
let loading = {
|
||||||
save: false,
|
save: false,
|
||||||
@@ -96,6 +97,7 @@
|
|||||||
async function handleSubmit() {
|
async function handleSubmit() {
|
||||||
try {
|
try {
|
||||||
loading.save = true;
|
loading.save = true;
|
||||||
|
nonWWWDomain = fqdn && getDomain(fqdn).replace(/^www\./, '');
|
||||||
if (fqdn !== settings.fqdn) {
|
if (fqdn !== settings.fqdn) {
|
||||||
await post(`/settings/check.json`, { fqdn, forceSave, dualCerts, isDNSCheckEnabled });
|
await post(`/settings/check.json`, { fqdn, forceSave, dualCerts, isDNSCheckEnabled });
|
||||||
await post(`/settings.json`, { fqdn });
|
await post(`/settings.json`, { fqdn });
|
||||||
@@ -106,6 +108,7 @@
|
|||||||
settings.minPort = minPort;
|
settings.minPort = minPort;
|
||||||
settings.maxPort = maxPort;
|
settings.maxPort = maxPort;
|
||||||
}
|
}
|
||||||
|
forceSave = false;
|
||||||
} catch ({ error }) {
|
} catch ({ error }) {
|
||||||
if (error?.startsWith($t('application.dns_not_set_partial_error'))) {
|
if (error?.startsWith($t('application.dns_not_set_partial_error'))) {
|
||||||
forceSave = true;
|
forceSave = true;
|
||||||
@@ -123,6 +126,14 @@
|
|||||||
return errorNotification(error);
|
return errorNotification(error);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
async function isDNSValid(domain) {
|
||||||
|
try {
|
||||||
|
await get(`/settings/check.json?domain=${domain}`);
|
||||||
|
toast.push('Domain is valid in DNS.');
|
||||||
|
} catch ({ error }) {
|
||||||
|
return errorNotification(error);
|
||||||
|
}
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="flex space-x-1 p-6 font-bold">
|
<div class="flex space-x-1 p-6 font-bold">
|
||||||
@@ -176,6 +187,23 @@
|
|||||||
pattern="^https?://([a-z0-9]+(-[a-z0-9]+)*\.)+[a-z]{'{'}2,{'}'}$"
|
pattern="^https?://([a-z0-9]+(-[a-z0-9]+)*\.)+[a-z]{'{'}2,{'}'}$"
|
||||||
placeholder="{$t('forms.eg')}: https://coolify.io"
|
placeholder="{$t('forms.eg')}: https://coolify.io"
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
{#if forceSave}
|
||||||
|
<div class="pt-4">
|
||||||
|
<button
|
||||||
|
class="bg-coollabs hover:bg-coollabs-100"
|
||||||
|
on:click|preventDefault={() => isDNSValid(getDomain(nonWWWDomain))}
|
||||||
|
>Check {nonWWWDomain} DNS Record</button
|
||||||
|
>
|
||||||
|
{#if dualCerts}
|
||||||
|
<button
|
||||||
|
class="bg-coollabs hover:bg-coollabs-100"
|
||||||
|
on:click|preventDefault={() => isDNSValid(getDomain(`www.${nonWWWDomain}`))}
|
||||||
|
>Check www.{nonWWWDomain} DNS Record</button
|
||||||
|
>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="grid grid-cols-2 items-start py-6">
|
<div class="grid grid-cols-2 items-start py-6">
|
||||||
|
Reference in New Issue
Block a user