function watchProjectFiles() {
		if (!broker.started || (!process.mainModule && !require.main)) return;

		cache.clear();
		prevProjectFiles = projectFiles;
		projectFiles = new Map();

		// Read the main module
		const mainModule = process.mainModule || require.main;

		// Process the whole module tree
		processModule(mainModule, null, 0, null);

		if (extraFiles != null) {
			Object.entries(extraFiles).forEach(([fName, restartType]) => {
				const watchItem = getWatchItem(fName);
				if (restartType == "broker") watchItem.brokerRestart = true;
				else if (restartType == "allServices") watchItem.allServices = true;
				else if (isString(restartType)) watchItem.services.push(restartType);
				else if (Array.isArray(restartType)) watchItem.services.push(...restartType);
			});
		}

		const needToReload = new Set();

		// Debounced Service reloader function
		const reloadServices = _.debounce(() => {
			const needToReloadDedup = _.uniqWith([...needToReload], (a, b) => {
				const ac = typeof a == "string" ? a : a.__filename;
				const bc = typeof b == "string" ? b : b.__filename;
				return ac == bc;
			});

			broker.logger.info(
				kleur.bgMagenta().white().bold(`Reload ${needToReloadDedup.length} service(s)`)
			);

			needToReloadDedup.forEach(svc => {
				if (typeof svc == "string")
					if (fs.existsSync(svc)) return broker.loadService(svc);
					else return;

				return hotReloadService(svc);
			});
			needToReload.clear();
		}, 500);

		// Close previous watchers
		stopAllFileWatcher(prevProjectFiles);

		// Watching project files
		broker.logger.debug("");
		broker.logger.debug(kleur.yellow().bold("Watching the following project files:"));

		projectFiles.forEach((watchItem, fName) => {
			// Delete if file doesn't exist anymore
			if (!fs.existsSync(fName)) projectFiles.delete(fName);
		});

		projectFiles.forEach((watchItem, fName) => {
			const relPath = path.relative(process.cwd(), fName);
			if (watchItem.brokerRestart)
				broker.logger.debug(`  ${relPath}:`, kleur.grey("restart broker."));
			else if (watchItem.allServices)
				broker.logger.debug(`  ${relPath}:`, kleur.grey("reload all services."));
			else if (watchItem.services.length > 0) {
				broker.logger.debug(
					`  ${relPath}:`,
					kleur.grey(
						`reload ${watchItem.services.length} service(s) & ${watchItem.others.length} other(s).`
					) /*, watchItem.services, watchItem.others*/
				);
				watchItem.services.forEach(svcFullname =>
					broker.logger.debug(kleur.grey(`    ${svcFullname}`))
				);
				watchItem.others.forEach(filename =>
					broker.logger.debug(kleur.grey(`    ${path.relative(process.cwd(), filename)}`))
				);
			}
			// Create watcher
			watchItem.watcher = fs.watch(fName, eventType => {
				const relPath = path.relative(process.cwd(), fName);
				broker.logger.info(
					kleur.magenta().bold(`The '${relPath}' file is changed. (Event: ${eventType})`)
				);

				// Clear from require cache
				clearRequireCache(fName);
				if (watchItem.others.length > 0) {
					watchItem.others.forEach(f => clearRequireCache(f));
				}

				if (
					watchItem.brokerRestart &&
					broker.runner &&
					isFunction(broker.runner.restartBroker)
				) {
					broker.logger.info(kleur.bgMagenta().white().bold("Action: Restart broker..."));
					stopAllFileWatcher(projectFiles);
					// Clear the whole require cache
					Object.keys(require.cache).forEach(key => delete require.cache[key]);

					return broker.runner.restartBroker();
				} else if (watchItem.allServices) {
					// Reload all services
					broker.services.forEach(svc => {
						if (svc.__filename) needToReload.add(svc);
					});
					reloadServices();
				} else if (watchItem.services.length > 0) {
					// Reload certain services
					broker.services.forEach(svc => {
						if (watchItem.services.indexOf(svc.fullName) !== -1) needToReload.add(svc);
					});

					if (needToReload.size == 0) {
						// It means, it's a crashed reloaded service, so we
						// didn't find it in the loaded services because
						// the previous hot-reload failed. We should load it
						// broker.loadService
						needToReload.add(relPath);
					}
					reloadServices();
				}
			});
		});

		if (projectFiles.size == 0) broker.logger.debug(kleur.grey("  No files."));
	}
Detect service dependency graph & watch all dependent files & services.