code: public final void setAppsRootDirectory(final String directory) throws URISyntaxException, IOException {
          this.appsRootDirectory = directory;
  
          final File realRoot;
          if (!directory.contains(":/")) {
              realRoot = new File(directory);
          } else {
              final Optional<File> fileOptional = this.configFileLoader.toFile(new URI(directory));
              if (fileOptional.isPresent()) {
                  realRoot = fileOptional.get();
              } else {
                  throw new IllegalArgumentException(
                          directory + " does not refer to a file on the current system.");
              }
          }
  
          final AppWalker walker = new AppWalker();
          for (File child: walker.getAppDirs(realRoot)) {
              final File configFile = new File(child, CONFIG_YAML);
              String appName = realRoot.toURI().relativize(child.toURI()).getPath().replace('/', ':');
              if (appName.endsWith(":")) {
                  appName = appName.substring(0, appName.length() - 1);
              }
              this.configurationFiles.put(appName, configFile.toURI());
          }
          if (this.configurationFiles.isEmpty()) {
              return;
          }
  
          // ensure there is a "default" app
          if (!this.configurationFiles.containsKey(DEFAULT_CONFIGURATION_FILE_KEY)) {
              pickDefaultApp();
          }
      }
docs: Set a single directory that contains one or more subdirectories, each one that contains a config.yaml
  file will be considered a print app.
  <p>
  This can be called multiple times and each directory will add to the apps found in the other
  directories.  However the appId is based on the directory names so if there are 2 directories with the
  same name the second will overwrite the first encounter.
  
  @param directory the root directory containing the sub-app-directories.  This must resolve to a
  file with the