public GenericStructureInfo structureInfoFromZip(ZipInputStream zipInputStream)
      throws StructureLoadException {
    try {
      String json = null;
      NBTTagCompound worldData = null;

      ZipEntry zipEntry;

      while ((zipEntry = zipInputStream.getNextEntry()) != null) {
        byte[] bytes = completeByteArray(zipInputStream);

        if (bytes != null) {
          if (STRUCTURE_INFO_JSON_FILENAME.equals(zipEntry.getName())) json = new String(bytes);
          else if (WORLD_DATA_NBT_FILENAME.equals(zipEntry.getName()))
            worldData = CompressedStreamTools.func_152457_a(bytes, NBTSizeTracker.field_152451_a);
        }

        zipInputStream.closeEntry();
      }
      zipInputStream.close();

      if (json == null || worldData == null)
        throw new StructureInvalidZipException(json != null, worldData != null);

      GenericStructureInfo genericStructureInfo = registry.createStructureFromJSON(json);
      genericStructureInfo.worldDataCompound = worldData;

      return genericStructureInfo;
    } catch (IOException e) {
      throw new StructureLoadException(e);
    }
  }
  public boolean saveGenericStructure(
      GenericStructureInfo info, String structureName, boolean activeFolder) {
    File parent = RCFileTypeRegistry.getStructuresDirectory(activeFolder);
    if (parent != null) {
      String json = registry.createJSONFromStructure(info);

      if (RecurrentComplex.USE_ZIP_FOR_STRUCTURE_FILES) {
        File newFile = new File(parent, structureName + "." + FILE_SUFFIX);
        boolean failed = false;

        try {
          ZipOutputStream zipOutputStream = new ZipOutputStream(new FileOutputStream(newFile));

          addZipEntry(zipOutputStream, STRUCTURE_INFO_JSON_FILENAME, json.getBytes());
          addZipEntry(
              zipOutputStream,
              WORLD_DATA_NBT_FILENAME,
              CompressedStreamTools.compress(info.worldDataCompound));

          zipOutputStream.close();
        } catch (Exception ex) {
          RecurrentComplex.logger.error("Could not write structure to zip file", ex);
          failed = true;
        }

        return !failed && newFile.exists();
      } else {
        File newFile = new File(parent, structureName + ".json");
        boolean failed = false;

        try {
          FileUtils.writeStringToFile(newFile, json);
        } catch (Exception e) {
          RecurrentComplex.logger.error("Could not write structure zip to folder", e);
          failed = true;
        }

        return !failed && newFile.exists();
      }
    }

    return false;
  }
  @Override
  public boolean loadFile(Path path, FileLoadContext context) {
    try {
      GenericStructureInfo genericStructureInfo = readGenericStructure(path);

      String structureID =
          context.customID != null
              ? context.customID
              : FilenameUtils.getBaseName(path.getFileName().toString());

      if (registry.registerStructure(
          genericStructureInfo, structureID, context.domain, context.active, context.custom))
        return true;
    } catch (IOException | StructureLoadException e) {
      RecurrentComplex.logger.warn("Error reading structure", e);
    }

    return false;
  }