diff --git a/lib/constants/data-binary-source.ts b/lib/constants/data-binary-source.ts
index 46021a4454e04d15eefa7bbc803acc4aa4d66663..726d6a00dfae2bd6ab6a25499b1af2fbfed8091b 100644
--- a/lib/constants/data-binary-source.ts
+++ b/lib/constants/data-binary-source.ts
@@ -3,12 +3,12 @@ export const DATASOURCE_CARGO = 'cargo';
 export const DATASOURCE_CDNJS = 'cdnjs';
 export const DATASOURCE_DART = 'dart';
 export const DATASOURCE_DOCKER = 'docker';
-export const DATASOURCE_GIT_SUBMODULES = 'gitSubmodules';
-export const DATASOURCE_GIT_TAGS = 'gitTags';
+export const DATASOURCE_GIT_SUBMODULES = 'git-submodules';
+export const DATASOURCE_GIT_TAGS = 'git-tags';
 export const DATASOURCE_GITHUB = 'github';
 export const DATASOURCE_GITLAB = 'gitlab';
 export const DATASOURCE_GO = 'go';
-export const DATASOURCE_GRADLE_VERSION = 'gradleVersion';
+export const DATASOURCE_GRADLE_VERSION = 'gradle-version';
 export const DATASOURCE_HELM = 'helm';
 export const DATASOURCE_HEX = 'hex';
 export const DATASOURCE_MAVEN = 'maven';
@@ -18,7 +18,7 @@ export const DATASOURCE_ORB = 'orb';
 export const DATASOURCE_PACKAGIST = 'packagist';
 export const DATASOURCE_PYPI = 'pypi';
 export const DATASOURCE_RUBYGEMS = 'rubygems';
-export const DATASOURCE_RUBY_VERSION = 'rubyVersion';
+export const DATASOURCE_RUBY_VERSION = 'ruby-version';
 export const DATASOURCE_SBT = 'sbt';
 export const DATASOURCE_TERRAFORM = 'terraform';
-export const DATASOURCE_TERRAFORM_PROVIDER = 'terraformProvider';
+export const DATASOURCE_TERRAFORM_PROVIDER = 'terraform-provider';
diff --git a/lib/datasource/index.ts b/lib/datasource/index.ts
index 392642d3aab5b83d01eec3163b78cfbe5eb29355..9f3612683952cf5a2b8e02e405bc74b4b8859672 100644
--- a/lib/datasource/index.ts
+++ b/lib/datasource/index.ts
@@ -1,30 +1,8 @@
+import fs from 'fs';
 import { logger } from '../logger';
 import { addMetaData } from './metadata';
 import * as versioning from '../versioning';
 
-import * as cargo from './cargo';
-import * as cdnjs from './cdnjs';
-import * as dart from './dart';
-import * as docker from './docker';
-import * as hex from './hex';
-import * as github from './github';
-import * as gitlab from './gitlab';
-import * as gitTags from './git-tags';
-import * as gitSubmodules from './git-submodules';
-import * as go from './go';
-import * as gradleVersion from './gradle-version';
-import * as helm from './helm';
-import * as maven from './maven';
-import * as npm from './npm';
-import * as nuget from './nuget';
-import * as orb from './orb';
-import * as packagist from './packagist';
-import * as pypi from './pypi';
-import * as rubygems from './rubygems';
-import * as rubyVersion from './ruby-version';
-import * as sbt from './sbt';
-import * as terraform from './terraform';
-import * as terraformProvider from './terraform-provider';
 import {
   Datasource,
   PkgReleaseConfig,
@@ -36,31 +14,33 @@ import { VERSION_SCHEME_SEMVER } from '../constants/version-schemes';
 
 export * from './common';
 
-const datasources: Record<string, Datasource> = {
-  cargo,
-  cdnjs,
-  dart,
-  docker,
-  helm,
-  hex,
-  github,
-  gitlab,
-  gitTags,
-  gitSubmodules,
-  go,
-  gradleVersion,
-  maven,
-  npm,
-  nuget,
-  orb,
-  packagist,
-  pypi,
-  rubygems,
-  rubyVersion,
-  sbt,
-  terraform,
-  terraformProvider,
-};
+const datasources: Record<string, Datasource> = {};
+
+function isValidDatasourceModule(
+  datasourceName: string,
+  module: unknown
+): module is Datasource {
+  return !!module;
+}
+
+function loadDatasources(): void {
+  const datasourceDirs = fs
+    .readdirSync(__dirname, { withFileTypes: true })
+    .filter(dirent => dirent.isDirectory())
+    .map(dirent => dirent.name)
+    .filter(name => !name.startsWith('__'))
+    .sort();
+  for (const datasourceName of datasourceDirs) {
+    const module = require(`./${datasourceName}`); // eslint-disable-line
+    if (isValidDatasourceModule(datasourceName, module)) {
+      datasources[datasourceName] = module;
+    } /* istanbul ignore next */ else {
+      throw new Error(`Datasource module "${datasourceName}" is invalid.`);
+    }
+  }
+}
+
+loadDatasources();
 
 const cacheNamespace = 'datasource-releases';
 
diff --git a/lib/manager/composer/__snapshots__/extract.spec.ts.snap b/lib/manager/composer/__snapshots__/extract.spec.ts.snap
index a67ddb617b3a644409bab762f98b3765641ae9ad..f594e1f25b3af3dc87c63b3b4f4c8e8b00c1fc80 100644
--- a/lib/manager/composer/__snapshots__/extract.spec.ts.snap
+++ b/lib/manager/composer/__snapshots__/extract.spec.ts.snap
@@ -549,7 +549,7 @@ Object {
     },
     Object {
       "currentValue": "dev-trunk",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "awesome/vcs",
       "depType": "require",
       "lockedVersion": "1.1.0",
@@ -558,7 +558,7 @@ Object {
     },
     Object {
       "currentValue": ">=7.0.2",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "awesome/git",
       "depType": "require",
       "lockedVersion": "1.2.0",
@@ -621,7 +621,7 @@ Object {
     },
     Object {
       "currentValue": "dev-trunk",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "awesome/vcs",
       "depType": "require",
       "lookupName": "https://my-vcs.example/my-vcs-repo",
@@ -629,7 +629,7 @@ Object {
     },
     Object {
       "currentValue": ">=7.0.2",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "awesome/git",
       "depType": "require",
       "lookupName": "https://my-git.example/my-git-repo",
diff --git a/lib/manager/gradle-wrapper/__snapshots__/extract.spec.ts.snap b/lib/manager/gradle-wrapper/__snapshots__/extract.spec.ts.snap
index e624bc353c6ad0b9026191426ade45f940ba015f..866baef318d315b9c6c2728faca7c3bae1c15696 100644
--- a/lib/manager/gradle-wrapper/__snapshots__/extract.spec.ts.snap
+++ b/lib/manager/gradle-wrapper/__snapshots__/extract.spec.ts.snap
@@ -4,7 +4,7 @@ exports[`lib/manager/gradle-wrapper/extract extractPackageFile() extracts all ve
 Array [
   Object {
     "currentValue": "4.10.3",
-    "datasource": "gradleVersion",
+    "datasource": "gradle-version",
     "depName": "gradle",
     "depType": "gradle-wrapper",
     "managerData": Object {
@@ -21,7 +21,7 @@ exports[`lib/manager/gradle-wrapper/extract extractPackageFile() extracts bin ve
 Array [
   Object {
     "currentValue": "4.8.0",
-    "datasource": "gradleVersion",
+    "datasource": "gradle-version",
     "depName": "gradle",
     "depType": "gradle-wrapper",
     "managerData": Object {
diff --git a/lib/manager/ruby-version/__snapshots__/extract.spec.ts.snap b/lib/manager/ruby-version/__snapshots__/extract.spec.ts.snap
index 266c3ca0863a1d567f51d9994b638891a17ae9cb..3b796324f0adfbf256829d297bf8284edaefd0f9 100644
--- a/lib/manager/ruby-version/__snapshots__/extract.spec.ts.snap
+++ b/lib/manager/ruby-version/__snapshots__/extract.spec.ts.snap
@@ -4,7 +4,7 @@ exports[`lib/manager/ruby-version/extract extractPackageFile() returns a result
 Array [
   Object {
     "currentValue": "8.4.0",
-    "datasource": "rubyVersion",
+    "datasource": "ruby-version",
     "depName": "ruby",
   },
 ]
@@ -14,7 +14,7 @@ exports[`lib/manager/ruby-version/extract extractPackageFile() skips non ranges
 Array [
   Object {
     "currentValue": "latestn",
-    "datasource": "rubyVersion",
+    "datasource": "ruby-version",
     "depName": "ruby",
     "skipReason": "unsupported-version",
   },
@@ -25,7 +25,7 @@ exports[`lib/manager/ruby-version/extract extractPackageFile() supports ranges 1
 Array [
   Object {
     "currentValue": "8.4",
-    "datasource": "rubyVersion",
+    "datasource": "ruby-version",
     "depName": "ruby",
   },
 ]
diff --git a/lib/manager/swift/__snapshots__/index.spec.ts.snap b/lib/manager/swift/__snapshots__/index.spec.ts.snap
index 9605f6e5abbc6e935998aba17b691679f106eee4..2185e7f08d46cb30190bf6f30ae0cd03452309c8 100644
--- a/lib/manager/swift/__snapshots__/index.spec.ts.snap
+++ b/lib/manager/swift/__snapshots__/index.spec.ts.snap
@@ -5,35 +5,35 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "0.1.0",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "avito-tech/GraphiteClient",
       "fileReplacePosition": 1177,
       "lookupName": "https://github.com/avito-tech/GraphiteClient.git",
     },
     Object {
       "currentValue": "1.0.16",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "IBM-Swift/BlueSignals",
       "fileReplacePosition": 1268,
       "lookupName": "https://github.com/IBM-Swift/BlueSignals.git",
     },
     Object {
       "currentValue": "3.0.6",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "daltoniam/Starscream",
       "fileReplacePosition": 1439,
       "lookupName": "https://github.com/daltoniam/Starscream.git",
     },
     Object {
       "currentValue": "1.4.6",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "httpswift/swifter",
       "fileReplacePosition": 1523,
       "lookupName": "https://github.com/httpswift/swifter.git",
     },
     Object {
       "currentValue": "from : \\"0.9.6\\"",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "weichsel/ZIPFoundation",
       "fileReplacePosition": 1626,
       "lookupName": "https://github.com/weichsel/ZIPFoundation/",
@@ -48,7 +48,7 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "from:\\"1.2.3\\"",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "vapor/vapor",
       "fileReplacePosition": 64,
       "lookupName": "https://github.com/vapor/vapor.git",
@@ -63,7 +63,7 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "\\"1.2.3\\"...",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "vapor/vapor",
       "fileReplacePosition": 64,
       "lookupName": "https://github.com/vapor/vapor.git",
@@ -78,7 +78,7 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "\\"1.2.3\\"...\\"1.2.4\\"",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "vapor/vapor",
       "fileReplacePosition": 64,
       "lookupName": "https://github.com/vapor/vapor.git",
@@ -93,7 +93,7 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "\\"1.2.3\\"..<\\"1.2.4\\"",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "vapor/vapor",
       "fileReplacePosition": 64,
       "lookupName": "https://github.com/vapor/vapor.git",
@@ -108,7 +108,7 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "...\\"1.2.3\\"",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "vapor/vapor",
       "fileReplacePosition": 64,
       "lookupName": "https://github.com/vapor/vapor.git",
@@ -123,7 +123,7 @@ Object {
   "deps": Array [
     Object {
       "currentValue": "..<\\"1.2.3\\"",
-      "datasource": "gitTags",
+      "datasource": "git-tags",
       "depName": "vapor/vapor",
       "fileReplacePosition": 64,
       "lookupName": "https://github.com/vapor/vapor.git",
diff --git a/lib/manager/terraform/__snapshots__/extract.spec.ts.snap b/lib/manager/terraform/__snapshots__/extract.spec.ts.snap
index b26136f8c5bcbbf7ca0be2a2806b0f000c7d21e4..438e0d4d246050d2bb3d46e9d4a9711d5274a5bb 100644
--- a/lib/manager/terraform/__snapshots__/extract.spec.ts.snap
+++ b/lib/manager/terraform/__snapshots__/extract.spec.ts.snap
@@ -183,7 +183,7 @@ Object {
     },
     Object {
       "currentValue": "1.36.1",
-      "datasource": "terraformProvider",
+      "datasource": "terraform-provider",
       "depName": "azurerm",
       "depNameShort": "azurerm",
       "depType": "terraform",
@@ -195,7 +195,7 @@ Object {
     },
     Object {
       "currentValue": "=2.4",
-      "datasource": "terraformProvider",
+      "datasource": "terraform-provider",
       "depName": "gitlab",
       "depNameShort": "gitlab",
       "depType": "terraform",
@@ -207,7 +207,7 @@ Object {
     },
     Object {
       "currentValue": "=1.3",
-      "datasource": "terraformProvider",
+      "datasource": "terraform-provider",
       "depName": "gitlab",
       "depNameShort": "gitlab",
       "depType": "terraform",
@@ -218,7 +218,7 @@ Object {
       "moduleName": "gitlab",
     },
     Object {
-      "datasource": "terraformProvider",
+      "datasource": "terraform-provider",
       "depName": "helm",
       "depNameShort": "helm",
       "depType": "terraform",
@@ -231,7 +231,7 @@ Object {
     },
     Object {
       "currentValue": "V1.9",
-      "datasource": "terraformProvider",
+      "datasource": "terraform-provider",
       "depName": "newrelic",
       "depNameShort": "newrelic",
       "depType": "terraform",