2023. 2. 17. 23:55ㆍJava
프로젝트 내 src 내 javabasic 패키지 내 DbConn.java
package javabasic;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.Statement;
public class DbConn { // DbManager 역할하는 클래스
private static Connection dbConn; // 멤버로 선언
public static Connection getConnection() {
if (dbConn == null) {
try {
String url = "jdbc:oracle:thin:@localhost:1521:orcl";
String user = "scott";
String pwd = "a1234";
Class.forName("oracle.jdbc.driver.OracleDriver"); // 클래스에 동적으로 바인딩하는 부분
dbConn = DriverManager.getConnection(url, user, pwd);
} catch (Exception e) {
// TODO Auto-generated catch block
System.out.println(e.toString());
}
} // end of if
return dbConn;
}// getConnection()
public static Connection getConnection(String url, String user, String pwd) {
if (dbConn != null) {
try {
Class.forName("oracle.jdbc.driver.OracleDriver");
dbConn = DriverManager.getConnection(url, user, pwd);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return dbConn;
}
public static void dbClose() {
if (dbConn != null) {
try {
if (!dbConn.isClosed())
dbConn.close();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
dbConn = null; // 초기화하지 않으면 다시 사용할 수가 없기 때문에 꼭 실행함
}
public static void dbClose(PreparedStatement ps, Connection conn) {
try {
if (ps != null)
ps.close();
if (conn != null)
conn.close();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
conn = null;
ps = null; // 항상 자원을 반납 후 널값 처리 해줌
}
public static void dbClose(Statement st, Connection conn) {
try {
if (st != null)
st.close();
if (conn != null)
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
conn = null;
st = null;
}
public static void dbClose(ResultSet rs, PreparedStatement ps, Connection conn) {
try {
if (rs != null)
rs.close();
if (ps != null)
ps.close();
if (conn != null)
conn.close();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
rs = null;
ps = null;
conn = null; // 항상 자원을 반납 후 널값 처리 해줌
}
public static void dbClose(ResultSet rs, Statement st, Connection conn) {
try {
if (rs != null)
rs.close();
if (st != null)
st.close();
if (conn != null)
conn.close();
} catch (Exception e) {
e.printStackTrace();
}
conn = null;
st = null;
rs = null;
}
}
Eclipse IDE 에서 Package Explorer 에 프로젝트 이름을 선택하고 마우스 오른쪽 버튼을 누른다.
Properties > Java Build PathLibraries Tab 선택한다.Add External JARs...를 누른다.다운로드 받은 ojdbc6.jar 를 선택하고 열기 버튼을 누른다.Apply > Apply and Close 를 선택한다.
프로젝트 내 src 내 javabasic 패키지 내 ClobFile.java
package javabasic;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.Reader;
import java.io.Writer;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.Statement;
import oracle.jdbc.OracleResultSet;
import oracle.sql.CLOB;
public class ClobFile {
public static void main(String[] args) throws Exception {
// TODO Auto-generated method stub
// 데이타베이스 접속 Connection 얻어오기
Connection conn = DbConn.getConnection();
conn.setAutoCommit(false);
//CLOB 타입 멤버 선언
CLOB clob = null;
Statement stmt = conn.createStatement();
//clob_table에 lock건다.for update절 처리한다.
// String query = "select * from clob_table for update";
// ResultSet rs = stmt.executeQuery(query);
//
// while(rs.next()) {
// clob = ((OracleResultSet)rs).getCLOB(4);
// }//while
//
// readFromFile(clob);//clob 파일을 읽어온다
// stmt.execute("commit");//데이타베이스에 반영한다
//쿼리문을 실행한다.
//파일에 출력하기 위한 clob_table 레코드의 값을 가져온다.
//clob_table 필드명이 contents 필드내용을 불러와야한다.
// ResultSet rs = stmt.executeQuery("select * from clob_table where no=2");
ResultSet rs = stmt.executeQuery("select * from clob_table where no=1");
//rs데이타값들을 파일에저장하도록 처리한다. 커서 설정해줘야 한다
if(rs.next()) {
//위치시켜준 커서에서 필드중에 4번째 필드가 필요한데, 그 값을 이용해서
//clob 를 얻어와야 한다.
clob = ((OracleResultSet)rs).getCLOB(4);//rs에서 가져올때 CLOB 객체로 받는데
//이 CLOB 객체는오라클사의 객체이다.RESULTSET을 오라클사의 RESULTSET
//으로 형변환시켜야한다.
String str = rs.getString(4);//clob 컬럼을 문자열로 가져온다.
//값이 있다면...
if(clob != null) System.out.println("clobe 길이 :" + clob.length());
}
writeToFile(clob);
}//main
//파일을 Clob 컬럼에 저장하는 메서드
static void readFromFile(CLOB clob) throws Exception {
//파일읽어와야하므로 파일객체생성
File file = new File("C:\\lobFile\\eula.txt");
//파일읽을수있는 스트림 생성
FileReader in = new FileReader(file);
//읽어온 내용을 clob에다 저장한다
@SuppressWarnings("deprecation")
Writer out = clob.getCharacterOutputStream();
//clob의 사이즈 구한다 해당 clob사이즈만큼 문자를 읽어올수있는 버퍼를 생성한다.
int chunk = clob.getChunkSize();
System.out.println("청크 사이즈 : " + chunk);
//청크 사이즈 만큼 버퍼 만들어줘야 한다 버퍼는 캐릭터형을 읽어와야 한다.
char[] buffer = new char[chunk];
//chunk는 오라클에 대한 메모리, 오라클 저장공간 만들때, 테이블스페이스가 있다.
//데이타를 저장하기 위한 하나의 공간인 테이블스페이스. 테이블스페이스는
//segment,오라클객체들이 segment 단위로 들어가 있다. 하나의 db를 만들면
//그 안에는 segment 단위로 들어간다.segment들은 각각 extent를 갖고 있다.
//extent는 데이타 블록 형태로 잘개 쪼개져 저장되어있다. 데이타블록이 모여서
//extend.extent가 모여서 segment.세그먼트가 모여서 테이블스페이스가된다.
//chunk는 데이타 블럭을 의미한다.
//하나의 저장공간.하드디스크는 데이터를 젖아할때 잘게 쪼개져서
//블록형태로 저장되어있을 것이다. 묶여진 데이타 블럭의 공간을
//chunk라고 한다.데이타가 저장되어있는 공간이 연속적인 공간이
//있을 것이다.어떤 공간은 비어있는 연속적인 공간이 있다고 하자.
//chunk는 한덩어리 라고 한다. 데이타블럭이 모여있는것이
//chunk인데 비워져있지않고 채워져있는 연속적인 모임 덩어리를
//used chunk 라고 한다. 비어있는 것은 free chunk혹은
//chunk 라고 한다. clob라는 것은 최대 지원할수있는 사이즈가
//4gb이다. clob 설정시 비어있는 공간 덩어리 크기를 구해올 수
//있는데 그것이 chunk 이다.
int length;//읽어온 데이타의 길잇값크깃값을 알아오는 부분
//읽어온 만큼 버퍼에 담아두겠다.
//처음위치=오프셋은 0 으로 설정한다 처음부터 차근차근 읽어오겠다.크기는
//청크크기만큼읽어오겠다.
//read()메소드가 읽어왔을 때 더이상 읽어올 데이타가 없다면 -1 이 반환된다.
//-1을 만났을 때 버퍼에 더이상 데이타가 없다라는 의미다.
//-1이 아닐때까지 버퍼에 데이타가 계속 있을 때 까지 반복해서 반복문을 돌린다.
while((length = in.read(buffer,0,chunk)) != -1) {
// clob에 있는 아웃풋스트림을 통해서 데이타를 쓰고 저장한다.
out.write(buffer,0,length);//스트림버퍼에있는읽어온크기만큼을 가져와 그 데이타를 out에 쓰겠다.
}//while
out.close();
in.close();
}
//Clob컬럼에 있는 데이터의 내용을 File에 출력하는 메소드
static void writeToFile(CLOB clob) throws Exception {
//clob 의 크기를 얻어온다.
int chunk = clob.getChunkSize();
//길이값얻어온다.
int length;
//buffer에 거쳐서 데이타값을 파일에 출력해야한다.
//char형 버퍼를 생성한다. 청크 길이만큼 배열길이를 설정한다.
char[] buffer = new char[chunk];
//파일에 출력하기 위해 캐릭터형 아웃풋스트림 생성한다.
FileWriter outFile = null;
outFile = new FileWriter("C:\\lobFile\\outFile.txt");//어디에다 어떤파일로 해서 생성하는 것인지를 정해야 한다.
//파일라이터를 이용해 아웃풋스트림에다가 outFile.txt 파일을 연결시켜준것이다.
//우리가 파일라이터로 내용을 출력하게 되면 자동으로 outFile.txt에 저장이 되는것이다.
//clob 에서 데이타 내용을 불러와야 한다. 인풋스트림이 필요하다.
//clob에 있는 내용을 읽어올 수 있는 Reader가 인풋스트림 일종의 캐릭터스트림이면서 입력스트림이다.
Reader in = clob.getCharacterStream();
//clob에 있는 내용을 얻어와서 그 내용을 버퍼에 저장시켰다가 버퍼에 있는 내용을 다시
//outFile.txt에 FileWriter를 이용해서 출력해주는 과정이다.
while((length = in.read(buffer)) != -1) {
//인풋스트림으로부터 데이타를 읽어와서 buffere에 기록을 하게 된다.
//읽어온 수 만큼의 길잇값을 얻어온다. 그 길잇값이 -1이면 더이상 읽을게 없다.
outFile.write(buffer,0,length);//buffer로 부터 length크기만큼 읽어온다.
//읽어온바이트수만큼 파일에다가 출력하겠다.
}//while
in.close();
outFile.close();
}
}
ClobFile.java 파일을 실행한다.
실행 결과
clobe 길이 :67
ORACLE SQL 에서 SELECT ~ FOR UPDATE 가 있다.
선택된 행들에 대해 배타적인 LOCK 을 설정한다.
커서 결과 집합의 레코드를 잠글 수 있다.
일반적인 SELECT 문장은 SHARED LOCK 이다. 즉, 다른 사람도 동시에 접근 할 수 있다.
오라클에서 LOCK 은 TABLE 단위 LOCK 이 아니라, 처리할 데이타 ROW 레벨 LOCK 이라고 한다.
FOR UPDATE 를 쓰는 용도는 은행의 예금 및 통장의 잔액 변경의 일관성을 유지하기 위해서 그리고 영화 및 공연장의 특정 좌석을 예약하려고 할 때 쓴다고 한다.
https://tyrionlife.tistory.com/41
[ORACLE] SELECT ~ FOR UPDATE 기능 및 용도
SELECT ~ FOR UPDATE 정의 선택된 행들에 대해 배타적인 LOCK을 설정하는 기능이다. SELECT FOR UPDATE 문을 통해 커서 결과 집합의 레코드를 잠글 수 있다. 이 문을 사용하기 위해 레코드를 변경할 필요는
tyrionlife.tistory.com
void java.io.OutputStreamWriter.write(char[] cbuf, int off, int len) throws IOException
write(char[] cbuf, int off, int len) 메서드는 문자열 배열의 한 부분을 쓴다.
파라메터 char[] cbuf 는 문자들이 저장될 버퍼이다.
파라메터 int off 는 문자들을 쓰기 시작할 출발지점으로 처음이라는 기준이 되는 0번째 공간(지점) 부터 얼마나 떨어져서 시작할지를 나타내는 정수이다.
파라메터 int len 은 쓸 문자들의 수 이다.
'Java' 카테고리의 다른 글
Java LocalDateTime (0) | 2023.02.19 |
---|---|
Java BasicDataSource (0) | 2023.02.18 |
Java CallableStatement (0) | 2023.02.17 |
Java static block 과 instance block (0) | 2023.02.17 |
Java addBatch() (0) | 2023.02.17 |