안드로이드 개발 정보
(글 수 1,064)
가끔 앱배포시에 DB파일을 함께 배포하는 방법을 문의하는 분들이 계셔서
제가 가지고 있는 정보를 공유하려고 합니다.
DB파일을 배포하는 방법에는 여러가지가 있겠지만(http://www.androidpub.com/7629 회색님 댓글 참조)
제가 공유하는 방법은 apk파일속에 넣어서 배포하는 방법입니다.
순서
1. 1MB가 넘는 DB파일은 900KB씩 잘라서 assets 폴더에 넣는다.
(assets 폴더에 1MB이상 되는 파일을 넣고 읽으려면 에러가 발생합니다.)
2. 어플이 맨처음 실행될때 assets 폴더에 있는 DB파일을 순서대로 읽어서
/data/data/패키지명/databases/DB파일명.db 로 하나의 DB파일을 만든다.
먼저 DB파일을 900KB씩 자르는 소스는
위와 같이 900KB씩 자른 DB파일을 assets 폴더에 넣습니다.
그리고 어플이 맨처음 실행될때 아래와 같이 /data/data/패키지명/databases/생성될 DB명.db 로 만들어줍니다.
제가 가지고 있는 정보를 공유하려고 합니다.
DB파일을 배포하는 방법에는 여러가지가 있겠지만(http://www.androidpub.com/7629 회색님 댓글 참조)
제가 공유하는 방법은 apk파일속에 넣어서 배포하는 방법입니다.
순서
1. 1MB가 넘는 DB파일은 900KB씩 잘라서 assets 폴더에 넣는다.
(assets 폴더에 1MB이상 되는 파일을 넣고 읽으려면 에러가 발생합니다.)
2. 어플이 맨처음 실행될때 assets 폴더에 있는 DB파일을 순서대로 읽어서
/data/data/패키지명/databases/DB파일명.db 로 하나의 DB파일을 만든다.
먼저 DB파일을 900KB씩 자르는 소스는
FileInputStream fis = new FileInputStream("경로/DB파일명.db"); BufferedInputStream bis = new BufferedInputStream(fis); FileOutputStream fos = fos = new FileOutputStream("경로/잘라진 DB파일명1.db");; BufferedOutputStream bos = bos = new BufferedOutputStream(fos);; byte[] b = new byte[1024]; int read = -1; int count = 1; int count2 = 1; while((read = bis.read(b, 0, 1024)) != -1) { bos.write(b, 0, read); bos.flush(); if(count2 % 900 == 0) { count++; if(fos != null) fos.close(); if(bos != null) bos.close(); fos = new FileOutputStream("경로/잘라진 DB파일명" + count + ".db"); bos = new BufferedOutputStream(fos); } count2++; } fis.close(); bis.close(); if(fos != null) fos.close(); if(bos != null) bos.close();
위와 같이 900KB씩 자른 DB파일을 assets 폴더에 넣습니다.
그리고 어플이 맨처음 실행될때 아래와 같이 /data/data/패키지명/databases/생성될 DB명.db 로 만들어줍니다.
if(어플이 맨처음 실행이면) { AssetManager am = null; InputStream[] arrIs = new InputStream[5]; // assets 폴더에 있는 DB파일 갯수 5개 BufferedInputStream[] arrBis = new BufferedInputStream[5]; // assets 폴더에 있는 DB파일 갯수 5개 FileOutputStream fos = null; BufferedOutputStream bos = null; try { File f = new File("/data/data/패키지명/databases/생성될 DB명.db"); // 혹시나 DB가 있으면 지우고 0바이트의 DB파일을 새로 만든다. if(f.exists()) { f.delete(); f.createNewFile(); } am = this.getResources().getAssets(); for(int i = 0; i < arrIs.length; i++) { arrIs[i] = am.open("assets 폴더에 있는 DB명" + (i + 1) + ".db"); arrBis[i] = new BufferedInputStream(arrIs[i]); } fos = new FileOutputStream(f); bos = new BufferedOutputStream(fos); int read = -1; byte[] buffer = new byte[1024]; for(int i = 0; i < arrIs.length; i++) { while((read = arrBis[i].read(buffer, 0, 1024)) != -1) { bos.write(buffer, 0, read); } bos.flush(); } } catch(Exception e){} finally { for(int i = 0; i < arrIs.length; i++) { try{if(arrIs[i] != null) arrIs[i].close();}catch(Exception e){} try{if(arrBis[i] != null) arrBis[i].close();}catch(Exception e){} } try{if(fos != null) fos.close();}catch(Exception e){} try{if(bos != null) bos.close();}catch(Exception e){} arrIs = null; arrBis = null; } }
이상입니다.
그리고 assets 폴더에 있는 파일을 삭제하려고
여기저기 알아봤는데 결국에는 못찾았습니다.
불가능하다는 답변만......
불가능하지 않은 방법을 아시는 분은 말씀해주시면 감사드리겠습니다.
약 1년전쯤 SDK 1.0에서 만든 소스인데 2.0에서도 잘 돌아가고
모토로이에서도 잘 돌아가네요..^^
2011.12.28 추가
위의 소스코드는 db 파일을 900kb 씩 자르는 방식을 사용했는데요..
저건 제가 아는게 없을때 사용했던 방법이고
현재는 1MB 이상인 파일일 경우 900kb 씩 자르지 않고 'DB파일명.mp3' 같이 확장자만 mp3로 바꿔서
assets 폴더에 넣고 프로그램이 실행될때 mp3 확장자만 db 확장자로 바꿔주고
/data/data/패키지명/databases/DB파일명.db 로 저장하면 된다고 하네요..
귀차니즘 때문에 해보지는 않았다는......
2010.07.18 02:04:16
알려주신 소스로 약 1.5MB 가량의 DB를 둘로 나누어 합쳤는데 디비가 깨지는 것 같습니다.
sqlite3로 읽어오면 압호화되었거나 데이터베이스가 아니라고 나오네요..
나누는건 자바프로젝트로 만들고 합치는건 당연히 안드로이드 프로젝트에서 진행하였습니다.
합친후 용량과 원본용량을 비교해 보니 원본용량이 좀더 크더군요..
나누고 나서는 합친 용량이 원본과 일치하는데 합치고나서의 용량이 일치하지 않는군요..
참고로 assets폴더에 추가할 때는 New->File->파일이름쓰고확인->디비파일을메모장에서내용복사 하는 식으로 했습니다.
같은 소스로 했는데 왜 이런 현상이 생기는 걸까요 ㅠ 답변주시면 감사하겠습니다
2010.08.07 07:39:06
잘 보았습니다! 현제 저에게 매우 중요한 글이네요! 한가지 질문이 있습니다.
쓰신 대로 열심히 따라했구요 DB 파일은 300정도라서 나누지 않았습니다.
문제는 DB에 한글이 들어갔다는 건데요
저렇게 파일출력을 하니 한글이 깨져버리네요 ㅠ
자바 초보라서 그런데 한글 깨질때 어찌 해야 할지 알려주실수있나요?
쓰신 대로 열심히 따라했구요 DB 파일은 300정도라서 나누지 않았습니다.
문제는 DB에 한글이 들어갔다는 건데요
저렇게 파일출력을 하니 한글이 깨져버리네요 ㅠ
자바 초보라서 그런데 한글 깨질때 어찌 해야 할지 알려주실수있나요?
질문좀 해도 괜찮을까요? ^^
1. 만약 DB의 용량이 계속 커지는 경우는 프로그램이 종료될 때 1메가를 넘었는지를 체크해서 잘라줘야 하는건가요?
2. 읽어온 버퍼의 데이터를 SQLiteDatabase 객체로 바꾸려면 어떻게 해야 하나요?