gt: 		try (InputStream in = Files.newInputStream(world) ) {
context: package org.erikaredmark.monkeyshines.encoder;
  
  import static com.google.common.base.Preconditions.checkArgument;
  
  import java.io.FileInputStream;
  import java.io.IOException;
  import java.io.InputStream;
  import java.io.OutputStream;
  import java.nio.file.Files;
  import java.nio.file.LinkOption;
  import java.nio.file.Path;
  
  import org.erikaredmark.monkeyshines.editor.WorldEditor;
  import org.erikaredmark.monkeyshines.encoder.exception.WorldRestoreException;
  import org.erikaredmark.monkeyshines.encoder.exception.WorldSaveException;
  
  /**
   * Provides utility methods for saving and restoring worlds. Used as a saving mechanism for the level editor; changes to a world
   * during gameplay should never be encoded and saved!
   * 
   * @author Erika Redmark
   * 
   */
  public final class WorldIO {
  	private WorldIO() { }
  	
  	private static final String WORLD_EXTENSION = ".world";
  	
  	/**
  	 * 
  	 * Takes a world editor and translates the underlying world, and ALL data making it up into a persistable format.
  	 * This only saves the logical level data (placement of tiles and their underlying types and data) and does not hold
  	 * any resource data.
  	 * <p/>
  	 * This method is blocking until the file is saved. The file is always saved as the name of the world with a .world
  	 * extension.
  	 * 
  	 * @param worldEditor
  	 * 		a world editor that needs to be encoded
  	 * 
  	 * @param path
  	 * 		a location to save the world to. The encoder will generate the save format at that location. This does not include
  	 * 		the file name, and should point to a folder
  	 * @throws IOException 
  	 * 
  	 * @throws IlegalArgumentException
  	 * 		if the given path points to anything other than a valid folder
  	 * 
  	 * @throws WorldSaveException
  	 * 		if an error occurs during saving the world due to high level issues (such as world corruption)
  	 * 
  	 * @throws IOException
  	 * 		if an error occurs saving the world due to low level I/O issues
  	 * 
  	 */
  	public static void saveWorld( WorldEditor worldEditor, Path path ) throws WorldSaveException, IOException {
  		if (Files.isDirectory(path, LinkOption.NOFOLLOW_LINKS) == false)
  			throw new IllegalArgumentException("Path " + path + " must point to a valid folder");
  		
  		EncodedWorld encoded = EncodedWorld.fromMemory(worldEditor.getWorld() );
  		final Path outputPath = path.resolve(worldEditor.getWorldName() + WorldIO.WORLD_EXTENSION);
  		
  		try (OutputStream out = Files.newOutputStream(outputPath) ) {
  			encoded.save(out);
  		} 
  		
  	}
  	
  	/**
  	 * 
  	 * Takes the world editor's underlying world ONLY and saves that to the file pointed to by path. This method differs
  	 * from the basic {@link #saveWorld(WorldEditor, Path)} in that it only updates the .world file and leaves the 
  	 * resource pack as is. This is the default operation for when the user is saving changes to the world in the basic
  	 * editor.
  	 * 
  	 * @param worldEditor
  	 * 		a world editor that needs to be encoded
  	 * 
  	 * @param path
  	 * 		a location to save the world to. Unlike the other save method, this must point to an existing file in which
  	 * 		to overwrite (the original world)
  	 * 
  	 * @throws IlegalArgumentException
  	 * 		if the given path points to anything other than a valid file
  	 * 
  	 * @throws WorldSaveException
  	 * 		if an error occurs during saving the world due to high level issues (such as world corruption)
  	 * 
  	 * @throws IOException
  	 * 		if an error occurs saving the world due to low level I/O issues
  	 * 
  	 */
  	public static void saveOnlyWorld( WorldEditor worldEditor, Path path ) throws WorldSaveException, IOException {
  		if (Files.isRegularFile(path, LinkOption.NOFOLLOW_LINKS) == false)
  			throw new IllegalArgumentException("Path " + path + " must point to the .world file to overwrite");
  		
  		EncodedWorld encoded = EncodedWorld.fromMemory(worldEditor.getWorld() );
  		try (OutputStream out = Files.newOutputStream(path) ) {
  			encoded.save(out);
  		} 
  	}
  	
  	/**
  	 * 
  	 * Creates a new world folder at the given location with the given name. The default resources pack is used by copying
  	 * it to that location and renaming it to the given world name. Additionally, a clean-slate 'worldName'.world file is
  	 * created with empty content ready for the editor.
  	 * <p/>
  	 * This method is guaranteed to have created the folder if it does not throw an exception.
  	 * 
  	 * @param newWorldFolder
  	 * 		the location to create the new world folder. This location's parent must exist, but the actually folder should
  	 * 		not as this method will create a new one
  	 * 
  	 * @param worldName
  	 * 		the name of the world, which will be the name of the .world file as well as the name of the resource pack
  	 * @throws IOException 
  	 * 
  	 * @throws IllegalArgumentException	
  	 * 		if the path to the new world folder already exists, or if the parent of the path (all folders leading up)
  	 * 		do not exist
  	 * 
  	 * @throws IOException
  	 * 		if something occurs during folder and/or file creation that prevents the full creation of this world
  	 * 
  	 */
  	public static void newWorldWithDefault(Path newWorldFolder, String worldName) throws WorldSaveException, IOException {
  	    // Don't create the world data until we first verify the resource pack is valid
  		InputStream resourceSource = WorldIO.class.getResourceAsStream("/resources/standard/default.zip");
  	    if (resourceSource == null) throw new RuntimeException("Bad .jar file, default resource pack unavailable");
  	    
  		newWorldData(newWorldFolder, worldName);
  		
  		// Copy resources and create <worldName>.zip file
  
  	    Path resourceDestination = newWorldFolder.resolve(worldName + ".zip");
  	    Files.copy(resourceSource, resourceDestination);
  	}
  	
  	/**
  	 * 
  	 * Creates a new world folder at the given location with the given name, copying the contents of the resource pack
  	 * pointed to to the new folder with the world.
  	 * <p/>
  	 * This method is guaranteed to have created the folder if it does not throw an exception.
  	 * 
  	 * @param newWorldFolder
  	 * 		the location to create the new world folder. This location's parent must exist, but the actually folder should
  	 * 		not as this method will create a new one
  	 * 
  	 * @param worldName
  	 * 		the name of the world, which will be the name of the .world file as well as the name of the resource pack
  	 * 
  	 * @throws IOException 
  	 * 
  	 * @throws IllegalArgumentException	
  	 * 		if the path to the new world folder already exists, or if the parent of the path (all folders leading up)
  	 * 		do not exist, or if the given resource pack does not exist
  	 * 
  	 * @throws IOException
  	 * 		if something occurs during folder and/or file creation that prevents the full creation of this world
  	 * 
  	 */
  	public static void newWorldWithResources(Path newWorldFolder, String worldName, Path rsrcPack) throws WorldSaveException, IOException {
  		checkArgument(Files.exists(rsrcPack, LinkOption.NOFOLLOW_LINKS) );
  		newWorldData(newWorldFolder, worldName);
  		
  		// Copy resources from target into <worldName>.zip file
  		InputStream resourceSource = new FileInputStream(rsrcPack.toFile() );
  	    Path resourceDestination = newWorldFolder.resolve(worldName + ".zip");
  	    Files.copy(resourceSource, resourceDestination);
  	}
  	
  	/** Common code to both newWorldYYY functions. Makes the .world file, does not handle resources.					*/
  	private static void newWorldData(Path newWorldFolder, String worldName) throws WorldSaveException, IOException {
  		checkArgument(Files.exists(newWorldFolder, LinkOption.NOFOLLOW_LINKS) == false );    // child must not exist
  		checkArgument(Files.exists(newWorldFolder.getParent(), LinkOption.NOFOLLOW_LINKS) ); // ... but parent must
  		
  		Files.createDirectory(newWorldFolder);
  	    
  		// Create .world file
  		EncodedWorld newWorld = EncodedWorld.fresh(worldName);
  		Path worldLocation = newWorldFolder.resolve(worldName + WorldIO.WORLD_EXTENSION);
  		try (OutputStream out = Files.newOutputStream(worldLocation) ) {
  			newWorld.save(out);
  		}
  	}
  	
  	/**
  	 * 
  	 * Restores a world saved at a given location. This only loads world data, and not resources (graphics) for the world
  	 * which are loaded separately.
  	 * <p/>
  	 * The returned object represents an immutable version of the starting state of the world for either the world editor
  	 * or game to blow into a full world world with operational real-time.
  	 * 
  	 * @param world
  	 * 		path to the .world file
  	 * 
  	 * @throws IllegalArgumentException
  	 * 		if the given path does not point to an actual file
  	 * 
  	 * @throws WorldRestoreException
  	 * 		if the given file cannot be read due to world corruption resulting in an inability to
  	 * 		generate a world from it
  	 * 
  	 * @throws IOException
  	 * 		if a low level I/O error prevents read
  	 * 
  	 */
  	public static EncodedWorld restoreWorld(Path world) throws WorldRestoreException, IOException {
  		if (Files.isRegularFile(world, LinkOption.NOFOLLOW_LINKS) == false)
  			throw new IllegalArgumentException("Path " + world + " must point to a valid file.");
  		
  