Site Search :
Standard Enterprise XML Methodology Pattern Setting Tunning Other
Article Contributors
GuestBook
Javapattern Maven
XSourceGen Dev
JetSpeed Test
JLook Image
jLook Family Site


Extracting zip or jar file
 
보통 자바측에서도 zip file or jar파일에 대한 압축포맷에 대한 핸들링이 필요한 시점이 있다.
javabrain사이트의 article에 적용되었던 압축된 아티클의 관리방법의 가장 기초선상에 선 프로그램을 소개한다. ( 2003/03/01 ) 146
Written by ienvyou - 최지웅
1 of 1
 
여기서는 zip파일 또는 jar파일을 api를 이용하여 푸는 방법에 대하여 설명한다. 
여기서 가져야할 기본적인 지식은 스트림에 대한 이해가 필수이며, 파일에 대한 read, 
write 메소드와 그것들을 필터링할 수 있는 능력이 필요한다.
간단하게 소개하자면 자바에서 IO란 여러분들이 수도로 들어온 물을 정수기로 걸러
직접 마실수 있느냐 없느냐의 문제이며, 또한 수도꼭지를 잠그는것이 close이고 여는것이
read이며, 정수기의 필터를 이용하여 물을 걸러 마시는 것을 필터링이라 한다.

여기서는 java.io.ZipInputStream등을 통하여 입력받은 zip or jar파일 포맷의 압축파일을 
풀도록 한다. jar파일이 zip파일의 형태라는 것은 여러분도 익히 알고 있을 것이다.
당연히 zip파일이 풀리면 jar파일도 풀리는 것이다.

핵심적인 코드는 아래와 같다.

	FileInputStream fis=new FileInputStream(args[0]);
	BufferedInputStream bis=new BufferedInputStream(fis);
	ZipInputStream zis=new ZipInputStream(bis);

입력받은 파일을 읽어들이는 역할을 하며 ZipEntry를 통하여 해당 파일의 압축되어진 
엔트리를 확인 할 수 있다.

또한 압축이 풀릴 위치를 지정할 수 있어야 하므로 getDirectory라는 메소드를 통하여
입력받은 값을 이용하여 압축이 풀릴수 있도록 사용한다.

우선 디렉토리입력을 받을 수 있는 MakeDirectory클래스를 보도록 하자.

public static String getDirectory(String target){
		File f = new File(target);
		if(f.exists()) return target;
		Vector v = new Vector();
		boolean END=false;
		while(!END){
			if(!f.exists()) {
				v.addElement(f);
				f = new File(f.getParent());
			}
			else END=!END;
		}

		for(int i=v.size()-1 ; i>=0 ;i--){
			((File)v.elementAt(i)).mkdir();
		}
		return target;
	}
}

위의 메소드에서는 압축을 풀 디렉토리를 찾아본후 만약 존재하지 않는다면 입력받은 
위치에 디렉토리를 recursive하게 생성한다.

mkdir -r 옵션같은 경우라 생각하면 무방하겠다.

자, 그러면 이 파일의 전체 소스를 보도록 하자.

import java.util.zip.*;
import java.util.jar.*;
import java.io.*;
import java.util.*;

class JarTarget {
public static void main(String[] args) {
if( args.length < 2 ) {
System.out.println("Usage : java JarTarget source_jar target_directory");
System.exit(0);
}
try{
	FileInputStream fis=new FileInputStream(args[0]);
	BufferedInputStream bis=new BufferedInputStream(fis);
	ZipInputStream zis=new ZipInputStream(bis);
	ZipEntry ze=null;

	int count = 0;
	while ((ze=zis.getNextEntry())!=null){
		// if it is a directory then we do nothing

	//	System.out.println("[Extracting the file] " + ze.getName());

	String zeName = ze.getName().replace('/', File.separatorChar);
	File path = new File(args[1] + File.separator + zeName);

	makeDirectory(
	path.toString().substring(0,path.toString().lastIndexOf(File.separator)));

	if (ze.isDirectory())	{
		path.mkdir();
		continue;
	}

	System.out.println(path.toString());
	FileOutputStream fos =new FileOutputStream(path.toString());
	int size=(int) ze.getSize();
	if (size==-1) {
		// ZipEntry.getSize()얻는 부분 쓸라면 쓰고..
	}

	// 핵심부분...

	byte[] b=new byte[(int)size];
	int rb=0;
	int chunk=0;
	while (((int)size - rb) > 0)	{
		chunk=zis.read(b,rb,(int)size - rb);
		fos.write(b, 0, chunk);
		if (chunk==-1) {
			break;
		}
		rb+=chunk;
	}

	++count;
}
}catch(Exception e) {
	e.printStackTrace();
}


}

public static String makeDirectory(String target){
	File f = new File(target);
	if(f.exists()) return target;
	Vector v = new Vector();
	boolean END=false;
	while(!END){
		if(!f.exists()) {
			v.addElement(f);
			f = new File(f.getParent());
		}
		else END=!END;
	}

	for(int i=v.size()-1 ; i>=0 ;i--){
		((File)v.elementAt(i)).mkdir();
	}
	return target;
}
}

위의 코드정도를 이해할 수 있다면 IO에는 어느정도 기본기가 갖춰졌다고 해도 무방하다
일반적으로 개발자들이 약한 부분이 IO/Thread/Network이 아닐까 한다.

Written by carouser 2001-07-12
 
1
References
 
Java Standard Documentation
This article source code : ZipExtract.zip
Copyright ⓒ 2003 www.javapattern.info & www.jlook.com, an jLOOK co.,LTD