private static Loader getCustomLoaderInstance(DataLoader testData) {
   Loader dataLoader = null;
   LOG.info("User specified to use custom Loader. Trying to get the custom loader.");
   if (testData.loader() == null) {
     Assert.fail(
         "Specified the LoaderType as CUSTOM but did not specify loader"
             + " attribute. A loaderType of CUSTOM requires the loader "
             + "attribute specifying "
             + "the Custom Loader Class which implements Loader interface.");
   } else {
     try {
       Class<? extends Loader> loaderClass = testData.loader();
       dataLoader = loaderClass.newInstance();
     } catch (Exception e) {
       throw new RuntimeException(
           "Exception occured while trying to instantiate a class of type :" + testData.loader(),
           e);
     }
   }
   return dataLoader;
 }
 /**
  * Determine the Loader Type to load the test data
  *
  * @param testData the {@link DataLoader} annotation instance
  * @param dataFiles the list of test data Files
  * @return {@link LoaderType} to use
  */
 private static final LoaderType determineLoaderType(DataLoader testData, String[] dataFiles) {
   LoaderType loaderType = testData.loaderType();
   if (LoaderType.NONE.equals(loaderType)) {
     // Identify the file extension
     if (dataFiles == null || dataFiles.length == 0) {
       // assume it is custom loader and return
       return LoaderType.CUSTOM;
     }
     // Since we currently support only a single file type in the FilePaths attribute,
     // we can safely pick one of the file, determine its extension and assume that other files
     // have the same
     // extension
     return resolveFileExtension(dataFiles[0]);
   }
   return loaderType;
 }
 /**
  * Method that determines the right Loader and the right Data Files for the "write output data"
  * functionality supported by the EasyTest Framework.
  *
  * @param testData an instance of {@link DataLoader} that helps in identifying the right {@link
  *     Loader} to write the data back to the file.
  * @param testClass the class that the {@link TestInfo} object will be associated with
  * @return {@link TestInfo} an instance of {@link TestInfo} containing information about the
  *     currently executing test.
  */
 public static TestInfo determineLoader(DataLoader testData, TestClass testClass) {
   TestInfo result = new TestInfo(testClass);
   // String[] dataFiles = testData.filePaths();
   String[] dataFiles = determineFilePaths(testData);
   LoaderType loaderType = determineLoaderType(testData, dataFiles);
   // Loader
   Loader dataLoader = null;
   if (LoaderType.CUSTOM.equals(loaderType) || dataFiles.length == 0) {
     dataLoader = getCustomLoaderInstance(testData);
   } else {
     // user has specified data files and the data fileType is also
     // not custom.
     if (loaderType != null) {
       dataLoader = LoaderFactory.getLoader(loaderType);
     }
   }
   result.setDataLoader(dataLoader);
   result.setFilePaths(dataFiles);
   result.setWriteData(testData.writeData());
   return result;
 }
 /**
  * Determine the Path of the test data files
  *
  * @param dataLoader the {@link DataLoader} annotation
  * @return an array of resolved file names
  */
 private static String[] determineFilePaths(DataLoader dataLoader) {
   String[] filePaths = dataLoader.filePaths();
   String[] result = new String[filePaths.length];
   result = handleSystemProperty();
   if (result == null) {
     // filePaths cannot be null as the default is an empty array
     if (filePaths.length == 0) {
       LOG.info(
           "Neither System Property 'testDataFiles' nor the attribute 'filePaths' is specified.");
     } else {
       result = new String[filePaths.length];
       for (int i = 0; i < filePaths.length; i++) {
         if (isVariablePath(filePaths[i])) {
           result[i] = getTestDataFileExpression(filePaths[i]);
         } else {
           result[i] = filePaths[i];
         }
       }
     }
   }
   return result;
 }