본문 바로가기

Server Oriented/Java & JSP

모바일에서 Base64 로 encode 하고 이를 String 으로 전달받은후 DB 처리


import java.io.BufferedInputStream;

import java.io.ByteArrayInputStream;

import com.sun.org.apache.xerces.internal.impl.dv.util.Base64;

public class ClassMng{

  /**

   * 모바일에서 올려질 때 Base64 로 encode 하고 이를 String 으로 전달받아왔는데,

   * 이를 Base64 로 docode 하면서 byte 로 전환하고 ByteArrayInputStream 에 담았다가 차후 작업을 생각해서 다시 BufferedInputStream 에 담다

   * @param   ClassInfo1 작업할 대상

   * @return    boolean 성공 여부

   * @throws  Exception

   */

  public void setString2Base64Byte2Bis(ClassInfo1 info) throws Exception{


    ByteArrayInputStream bais = null;

    BufferedInputStream   bis  = null;


    try{


      String  str = info.getString1(); // Base64 로 decode 하고 byte[] 를 ByteArrayInputStream 과 BufferedInputStream 으로 전환

      if(str!=null){

        byte[]  b   = Base64.decode(str);         // decode 결과물이 String 인 클래스의 메소드도 존재하지만 이곳에선 byte[] 사용

        info.setLength(b.length);                     // File.length(), 파일 사이즈를 배열 크기로.. 파일로 저장한 다음 파일 사이즈를 재도 동일한지는..

        bais        = new ByteArrayInputStream(b);

        bis          = new BufferedInputStream(bais); // 버퍼 작업을 하기 위해서.. I/O 를 위해서 나중에 쓰임새가 있을지 몰라서..

      }

      info.setBis(bis);                                        // return 하는 것 보다는 파라미터로 전달받은 Object 에 넘기는 것도 좋아요..


    }catch(Exception e){

      StringBuffer sbLog  = new StringBuffer();

      sbLog.append("\n---.Class1.setString2Base64Byte2Bis(ClassInfo1 Info)\n");

      sbLog.append("---.Exception:" +e.toString()+    "..\n");

      System.out.println(sbLog); // println 이기 때문에 맨 뒤에는 sbLog.append("\n"); 불필요.

      sbLog.delete(0, sbLog.length()); // 명시적 GC

      throw e; // throw 할 건데 왜 try 문을 썼느냐..? 물론 필요하지 않을 수도 있는데, 오류가 발생한 곳이 어디인지 명확히 하려고..

    }finally{ // 파라미터로 넘겨진 ClassInfo1 에 Object 형태로 세팅해 주기 때문에, 여기서 Stream 을 close() 할 수가 없네요..

    }

  }




  /**
   * 모바일에서 올려질 때 Base64 로 encode 하고 이를 String 으로 전달받아왔는데..
   * 이를 DB 에 넣으려는 메소드, DB 는 LongRaw 형태..
   * @param   ClassInfo1 작업할 대상
   * @return    boolean 성공 여부
   * @throws   Exception
   */
  public boolean saveInfo1(ClassInfo1 info) throws Exception{

    boolean     result      = false;
    BufferedInputStream bis   = null;                         // 작업 종료후 스트림 폐쇄를 위해..

    try{

      String      str       = info.getString1();
      if(str !=null && str .length()>0){                     // 기존 홈페이지에서는 부가정보 수정시 사진은 별도 프로세스를 태운다
        this.setString2Base64Byte2Bis(info);            // 모바일에서 올려진 Base64 String 을 BufferedInputStream 으로 전환
        bis                    = info.getBis();                 // 작업 종료후 스트림 폐쇄를 위해..
        result        = dao.modtInfo1(info);                // select 로 존재성 체크 또는, 쿼리 하나로 update 와 insert 를 구분하는 것도 좋지만 이 방법도 ok
        if(!result)   result = dao.addInfo1(info);
        if(!result)   info.setReturnMessage("오류1");
      }

    }catch(Exception e){
      StringBuffer sbLog  = new StringBuffer();
      sbLog.append("\n---.Class1.saveInfo1(ClassInfo1  Info)\n");
      sbLog.append("---.Exception:" +e.toString()+    "..\n");
      sbLog.append("---.info     :" +info.toString()+ "..\n");
      System.out.println(sbLog); // println 이기 때문에 맨 뒤에는 sbLog.append("\n"); 불필요.
      sbLog.delete(0, sbLog.length());
      throw e;
    }finally{
      String          rm      = Utils.getValue(info.getReturnMessage());
      if(rm.length()>0){      // 오류 발생시 시스템에 표시
        StringBuffer sbLog    = new StringBuffer();
        sbLog.append("\n---.Class1.saveInfo1(ClassInfo1 Info)\n");
        sbLog.append("---.error:" +rm+    "..\n");
        sbLog.append("---.info :" +info.toString()+ "..\n");
        System.out.println(sbLog); // println 이기 때문에 맨 뒤에는 sbLog.append("\n"); 불필요.
        sbLog.delete(0, sbLog.length());
      }
      if(bis  !=null) try{ bis.close();   }finally{ bis   =null; } // setString2Base64Byte2Bis 이 아니라 이곳에서 스트림을 close 함
    }

    return result;
  }
}




public class ClassDao{


   ...


  /**

   * LongRaw 를 수정

   * @param   ClassInfo1 작업할 대상

   * @return    boolean 성공 여부

   * @throws  Exception

   */

  protected boolean modFga114tInfo(ClassInfo1 info) throws Exception{


    PreparedStatement pstmt   = null;

    boolean         result  = false;

    StringBuffer      query   = new StringBuffer();     // DB Query 사용후 명시적 GC 를 하기 위해


    try{


      query.append("update table1                 \n");

      query.append("   set longraw1  = ?,        \n");

      query.append("       updt_id      = ?,        \n");

      query.append("       updt_date  = sysdate \n");

      query.append(" where user_id  = ?          \n");


      pstmt   = dao.m_conn.prepareStatement(query.toString()); // connection 과 기본 Dao 는 다른 곳에서 처리..

      int   i = 1;

      pstmt.setBinaryStream(i++, info.getBis(), info.getLength());

      pstmt.setString(i++, info.getUserId());

      pstmt.setString(i++, info.getUserId());

      i       = pstmt.executeUpdate();


      if(i==1)  result  = true;


    }catch(Exception e){

      throw e; // ClassMng 안에서 ClassDao 를 정의하고, SQL 문제인 경우 Exception 에 찍히기 때문에 이곳에선 그냥 throw

    }finally{

      if(pstmt!=null) try{ pstmt.close();                   }finally{ pstmt =null; }         // connection 도 여기서 해 주는 것이 좋은데, 여기선 생략

      if(query!=null) try{ query.delete(0, query.length()); }finally{ query = null; } // 여기서 리셋해 주3..

    }


    return result;

  }


}