Snippets

Fantom-Factory Zip Utils

Created by Steve Eynon
** A collection of Zip / File utilities.
class ZipUtils {
	
	** Compresses the given file and returns the compressed .zip file.
	** 'toCompress' may be a directory.
	** 
	** If 'destFile' is null, it defaults to '${toCompress.basename}.zip' 
	** 
	** The options map is used to customise zipping:
	**  - bufferSize: an 'Int' that defines the stream buffer size. Defaults to 16Kb.
	**  - incFolderName: set to 'true' to include the containing folder name in the zip path
	static File zip(File toCompress, File? destFile := null, [Str:Obj]? options := null) {
		if (destFile != null && destFile.isDir)
			throw ArgErr("Destination can not be a directory - ${destFile}")

		bufferSize	:= options?.get("bufferSize") ?: 16*1024
		dstFile		:= destFile ?: toCompress.parent + `${toCompress.basename}.zip` 
		zip			:= Zip.write(dstFile.out(false, bufferSize))		
		parentUri 	:= toCompress.isDir && options?.get("incFolderName") == true ? toCompress.parent.uri : toCompress.uri
		
		try {
			toCompress.walk |src| {
				if (src.isDir) return
				path := src.uri.relTo(parentUri)
				out  := zip.writeNext(path)
				try {
					src.in(bufferSize).pipe(out)
				} finally
					out.close
			}
		} finally
			zip.close

		return dstFile
	}

	** Decompresses the given file and returns the directory it was unzipped to.
	** 
	** The options map is used to customise zipping:
	**  - bufferSize: an 'Int' that defines the stream buffer size. Defaults to 16Kb.
	static File unzip(File toDecompress, File? destDir := null, [Str:Obj]? options := null) {
		if (toDecompress.isDir)
			throw ArgErr("Destination can not be a directory - ${toDecompress}")
		if (destDir != null && !destDir.isDir)
			throw ArgErr("Destination must be a directory - ${destDir}")
		
		bufferSize	:= options?.get("bufferSize") ?: 16*1024
		dstDir		:= destDir ?: toDecompress.parent
		zip			:= Zip.read(toDecompress.in(bufferSize))
		try {
			File? entry
			while ((entry = zip.readNext) != null) {
				entry.copyTo(dstDir + entry.uri.relTo(`/`), ["overwrite":true])
			}
		} finally {
			zip.close
		}
		
		return dstDir
	}
	
	** Create a temporary directory which is guaranteed to be a new, empty
	** directory with a unique name.  The dir name will be generated using
	** the specified prefix and suffix.  
	** 
	** If dir is non-null then it is used as the file's parent directory,
	** otherwise the system's default temporary directory is used.
	** 
	** Examples:
	**   File.createTemp("x", "-etc") => `/tmp/x67392-etc/`
	**   File.createTemp.deleteOnExit => `/tmp/fan-5284/`
	**
	** See the Fantom forum topic [File.createTempDir()]`http://fantom.org/forum/topic/2424`.
	static File createTempDir(Str prefix := "fan-", Str suffix := "", File? dir := null) {
		tempFile := File.createTemp(prefix, suffix, dir ?: Env.cur.tempDir)
		dirName  := tempFile.name
		tempFile.delete
		tempDir  := tempFile.parent.createDir(dirName)
		return tempDir
	}
}

Comments (0)