diff --git a/src/apptask.js b/src/apptask.js index 53695c29a..c05753424 100644 --- a/src/apptask.js +++ b/src/apptask.js @@ -50,6 +50,7 @@ var addons = require('./addons.js'), subdomains = require('./subdomains.js'), superagent = require('superagent'), sysinfo = require('./sysinfo.js'), + tld = require('tldjs'), util = require('util'), _ = require('underscore'); @@ -307,7 +308,16 @@ function waitForAltDomainDnsPropagation(app, callback) { // try for 10 minutes before giving up. this allows the user to "reconfigure" the app in the case where // an app has an external domain and cloudron is migrated to custom domain. - subdomains.waitForDns(app.altDomain, config.appFqdn(app.location), 'CNAME', { interval: 10000, times: 60 }, callback); + var isNakedDomain = tld.getDomain(app.altDomain) === app.altDomain; + if (isNakedDomain) { // check naked domains with A record since CNAME records don't work there + sysinfo.getPublicIp(function (error, ip) { + if (error) return callback(error); + + subdomains.waitForDns(app.altDomain, ip, 'A', { interval: 10000, times: 60 }, callback); + }); + } else { + subdomains.waitForDns(app.altDomain, config.appFqdn(app.location), 'CNAME', { interval: 10000, times: 60 }, callback); + } } // updates the app object and the database @@ -404,7 +414,7 @@ function install(app, callback) { updateApp.bind(null, app, { installationProgress: '85, Waiting for DNS propagation' }), exports._waitForDnsPropagation.bind(null, app), - updateApp.bind(null, app, { installationProgress: '90, Waiting for External Domain CNAME setup' }), + updateApp.bind(null, app, { installationProgress: '90, Waiting for External Domain setup' }), exports._waitForAltDomainDnsPropagation.bind(null, app), // required when restoring and !lastBackupId updateApp.bind(null, app, { installationProgress: '95, Configure nginx' }), @@ -492,7 +502,7 @@ function configure(app, callback) { updateApp.bind(null, app, { installationProgress: '80, Waiting for DNS propagation' }), exports._waitForDnsPropagation.bind(null, app), - updateApp.bind(null, app, { installationProgress: '85, Waiting for External Domain CNAME setup' }), + updateApp.bind(null, app, { installationProgress: '85, Waiting for External Domain setup' }), exports._waitForAltDomainDnsPropagation.bind(null, app), updateApp.bind(null, app, { installationProgress: '90, Configuring Nginx' }), diff --git a/webadmin/src/3rdparty/js/angular-tld.js b/webadmin/src/3rdparty/js/angular-tld.js index 2540603b1..bf232145b 100644 --- a/webadmin/src/3rdparty/js/angular-tld.js +++ b/webadmin/src/3rdparty/js/angular-tld.js @@ -1,6 +1,7 @@ // !!! // This module is manually patched by us to not only report valid domains, but verify that subdomains are not accepted // !!! +'use strict'; angular.module('ngTld', []) .factory('ngTld', ngTld) @@ -16,9 +17,14 @@ function ngTld() { return (path.slice(-1) !== '.') && !!tld.getDomain(path) && path !== tld.getDomain(path); } + function isNakedDomain(path) { + return (path.slice(-1) !== '.') && !!tld.getDomain(path) && path === tld.getDomain(path); + } + return { tldExists: tldExists, - isSubdomain: isSubdomain + isSubdomain: isSubdomain, + isNakedDomain: isNakedDomain }; } @@ -37,4 +43,3 @@ function checkTld(ngTld) { } }; } - diff --git a/webadmin/src/views/apps.html b/webadmin/src/views/apps.html index 4753300dc..62d17b8d8 100644 --- a/webadmin/src/views/apps.html +++ b/webadmin/src/views/apps.html @@ -50,11 +50,16 @@ -

+

Add a CNAME record for {{ appConfigure.location }} to {{ appConfigure.app.cnameTarget || appConfigure.app.fqdn }}

+

+ Add an A record for {{ appConfigure.location }} to this Cloudron's public IP +
+

+

Do not forget, to add an A record for {{ appConfigure.location }}.{{ config.fqdn }}
diff --git a/webadmin/src/views/apps.js b/webadmin/src/views/apps.js index 897fd77f8..27a650db8 100644 --- a/webadmin/src/views/apps.js +++ b/webadmin/src/views/apps.js @@ -1,7 +1,7 @@ 'use strict'; -angular.module('Application').controller('AppsController', ['$scope', '$location', '$timeout', 'Client', 'AppStore', function ($scope, $location, $timeout, Client, AppStore) { +angular.module('Application').controller('AppsController', ['$scope', '$location', '$timeout', 'Client', 'ngTld', 'AppStore', function ($scope, $location, $timeout, Client, ngTld, AppStore) { $scope.HOST_PORT_MIN = 1024; $scope.HOST_PORT_MAX = 65535; $scope.installedApps = Client.getInstalledApps(); @@ -42,8 +42,15 @@ angular.module('Application').controller('AppsController', ['$scope', '$location }, isAltDomainValid: function () { - if (!$scope.appConfigure.usingAltDomain) return true; - return /.+\..+\..+/.test($scope.appConfigure.location); // 2 dots + return ngTld.tldExists($scope.appConfigure.location); + }, + + isAltDomainSubdomain: function () { + return ngTld.isSubdomain($scope.appConfigure.location); + }, + + isAltDomainNaked: function () { + return ngTld.isNakedDomain($scope.appConfigure.location); } };