log4sql을 사용하면 I,U,D,S 쿼리문과 쿼리 수행시간, parameter까지 확인을 할 수 있습니다.
사용방법은 간단합니다.
라이브러리만 추가해준후 driver class만 변경해주면 됩니다.
보다 자세한 사용법 및 jar파일은 아래 URL에서 확인하시면 됩니다.
log4sql을 사용하면 I,U,D,S 쿼리문과 쿼리 수행시간, parameter까지 확인을 할 수 있습니다.
사용방법은 간단합니다.
라이브러리만 추가해준후 driver class만 변경해주면 됩니다.
보다 자세한 사용법 및 jar파일은 아래 URL에서 확인하시면 됩니다.
out 객체는 JSP 페이지의 결과를 웹 브라우저에 전송해 주는 출력 스트림을 나타내며 JSP페이지가 웹 브라우저에게 보내는 모든 정보는 out객체로 통해서 전달이 된다.
out객체는 java.io.Writer 클래스를 상송 받은 javax.servlet.jsp.JspWriter클래스 타입의 객체이며 out객체로 사용한다.
주로 많이 사용되는 메소드는 웹 브라우저에 출력을 하기 위한 println() 메소드이다.
out 내부 객체의 메소드
boolean isAutoFlush() 출력버퍼가 다 채워진 경우에 자동으로 flush했을 경우는 true를 리턴, 그렇지 않은 경우는 false 를 리턴한다.
int getBufferSize() 출력 버퍼의 전체의 크기를 바이트 단위로 리턴한다.
int getRemaining() 출력 버퍼의 남은 양을 바이트 단위로 리턴한다.
void clearBuffer() 현재 출력 버퍼에 저장된 내용을 취소한다.(비운다.)
String println(string) 현재 출력 버퍼에 저장된 내용르 웹 브라우저로 전송하고 버퍼를 비운다.
void close() 출력 버퍼의 내용을 flush하고 스트림을 닫는다.
리턴타입 |
메소드명 |
설명 |
없음 | clear() |
출력버퍼에 저장된 내용을 버림. 비었을 경우 예외발생 |
없음 | clearBuffer() |
clear()메소드와 같은 역할이지만, 버퍼가 빈경우에도 예외발생않고 현재 버퍼를 비움 |
없음 | flush() |
현재 버퍼에 저장된 내용을 클라이언트로 전송하고 버퍼를 비움. |
없음 | close() |
출력 버퍼를 클라이언트로 전송하고 출력스트림 종료 |
boolean | isAutoFlush() | page지시어의 autoFlush속성으로 지정된 값을 리턴 |
int | getBufferSize() | 출력 버퍼의 크기를 바이트 단위 |
int | getRemaining() | 출력 버퍼의 남은 양 |
없음 | print(String str ) | 출력 스트림으로 str 문자열 출력 |
tomcat/common/lib/ 아래에
ojdbc14라이브러리 추가
아울러 jdk1.5/lib 안에도 꼭 있어야 함..
jdk1.5/jre/lib/ext 안에는 있으나 마나이다..
==========================================
위 작업 끝난 다음에...도 jdbc 드라이버가 인식이 안됫었는데 알보고니 철자가 틀려서 그런거였다;;
ㅠㅠ;;;
'oracle.jdbc.dirver.OracleDriver' 로 써 있었던 것이였다 =>'oracle.jdbc.driver.OracleDriver' 로 바꿔야 햇는데;;
org.apache.tomcat.dbcp.dbcp.SQLNestedException: Cannot load JDBC driver class 'oracle.jdbc.driver.OracleDriver'
at org.apache.tomcat.dbcp.dbcp.BasicDataSource.createDataSource(BasicDataSource.java:766)
at org.apache.tomcat.dbcp.dbcp.BasicDataSource.getConnection(BasicDataSource.java:540)
at org.apache.jsp.index_jsp._jspService(index_jsp.java:62)
at org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:98)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
at org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:328)
at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:315)
at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:265)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:269)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:210)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:174)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:117)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:108)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:151)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:870)
at org.apache.coyote.http11.Http11BaseProtocol$Http11ConnectionHandler.processConnection(Http11BaseProtocol.java:665)
at org.apache.tomcat.util.net.PoolTcpEndpoint.processSocket(PoolTcpEndpoint.java:528)
at org.apache.tomcat.util.net.LeaderFollowerWorkerThread.runIt(LeaderFollowerWorkerThread.java:81)
at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:685)
at java.lang.Thread.run(Unknown Source)
Caused by: java.lang.ClassNotFoundException: oracle.jdbc.driver.OracleDriver
at java.net.URLClassLoader$1.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.ClassLoader.loadClassInternal(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Unknown Source)
at org.apache.tomcat.dbcp.dbcp.BasicDataSource.createDataSource(BasicDataSource.java:760)
... 22 more
Logging Messages from Servlets and JSPs
웹 어플리케이션에서 로그를 기록하는 법은 크게 2가지가 있습니다.
하나는 ServletContext.log() 를 이용하는 것이고 다른 하나는 Log4j 를 이용하는 것입니다. 먼저 ServletContext.log()를 사용해서 로그를 남기는 방법을 보겠습니다.
import javax.servlet.*;
import javax.servlet.http.*;
public class MyLog extends HttpServlet {
public void goGet( HttpServletRequest request, HttpServeltResponse response ) throws SevletException, java.io.IOException {
ServletContext context = getServletContext();
context.log("에러가 발생했습니다.");
context.log("에러가 발생했습니다.",new IllegalStateException("잘못된 파라메터입니다."));
}
}
log 메서드는 2개가 있는데 하나는 String 변수만 받고 다른 하나는 String와 Throwable을 받습니다.
Log4j 를 사용하는 방법은 좀더 자세히 보겠습니다. 요것은 아주 유용하기 때문에 자세히 봐야 합니다.^^
먼저 Log4j를 셋업하는 방법부터 보겠습니다. 일단 셋업을 하기전에 다운받아 설치를 해야합니다.
http://jakarta.apache.org/log4j/docs/download.html
여기서 다운받아 톰켓의 WEB-INF/lib 에 가져다 놓습니다. 압축을 풀면 jakarta-log4j-1.2.8 파일이 나옵니다. 파일이름은 버젼마다 틀려집니다. 참고하세요. 압축을 풀고 WEB-INF/lib 에다가 가져다 놓았으면 properties 파일을 만들어야 합니다. 이는 단순히 text파일로 키,값으로 이루어져 로그파일에 대한 각종 정보들을 담아둡니다. 이 프로퍼티 파일로 log4j를 서블릿에서 사용하기 위해선 2개의 패키지를 import 해야 합니다.
import org.apache.log4j.Logger;
import org.apache.log4j.PropertyCofigurator;
하지만 이 프로퍼티 파일을 이용하지 않고 싶을때는 log4j에서 지원하는 default configurator를 이용할 수 있습니다. 이때는 PropertyCofigurator 대신 BasicConfigurator를 임포트 합니다. 사용법은 약간 다르니 주의하세요.
import org.apache.log4j.Logger;
import org.apache.log4j.BasicConfigurator;
import javax.servlet.*;
import javax.servlet.http.*;
public class LoggerDefaultConfig extends HttpServelt {
private Logger log = null;
public void init(){
log = Logger.getRootLogger();
BasicConfigurator.configurator();
}
public void goGet( HttpSevletRequest req, HttpServletResponse res ) throws ServletException, java.io.IOException {
log.debug("디버깅 메시지입니다.");
log.info("정보 메시지입니다.");
}
}
다음은 configuration file 을 이용한 로그 사용법을 보겠습니다.
먼저 log4j.properties 파일을 만들고 web-inf/classes 폴더에다가 넣습니다. 그리고 사용하고자 하는 서블릿에다가 org.apache.log4j.Logger 를 import를 합니다. 그런다음 정적 메소드인 Logger.getRootLogger() 를 사용하여 레퍼런스를 얻어와서 로그를 남김니다.
이 로그파일에는 org.apache.log4j.ConsoleAppender 타입의 이름을 붙입니다. 여기서는 hans로 정하겠습니다.
log4j.rootLogger=DEBUG, hans
log4j.appender.hans=org.apache.log4j.ConsoleAppender
log4j.appender.hans.layout=org.apache.log4j.SimpleLayout
BasicConfigurator.configure( ) 이게 호출되지 않으면 자동으로 web-inf/classes 에서 log4j.properties 파일을 찾아 설정하게 됩니다.
log4j.rootLogger=DEBUG, cons
log4j.logger.com.jspservletcookbook=, myAppender
#the root logger's appender
log4j.appender.cons=org.apache.log4j.ConsoleAppender
#the com.jspservletcookbook logger's appender log4j.appender.myAppender=org.apache.log4j.RollingFileAppender
log4j.appender.myAppender.File=h:/home/example.log
log4j.appender.myAppender.MaxBackupIndex=1
log4j.appender.myAppender.MaxFileSize=1MB
#the root logger's layout
log4j.appender.cons.layout=org.apache.log4j.SimpleLayout
#the com.jspservletcookbook logger's layout
log4j.appender.myAppender.layout=org.apache.log4j.PatternLayout
log4j.appender.myAppender.layout.ConversionPattern=%-5p
Logger:%c{1} Date: %d{ISO8601} - %m%n
위 코드는 myAppender라는 이름으로 rootLogger를 상속하여 다양한 로그를 남기는 법을 보여줍니다.
the log4j Javadoc page: http://jakarta.apache.org/log4j/docs/api/index.html [출처] log 남기기 ( with log4j )|작성자 달콤인생
the log4j project documentation page: http://jakarta.apache.org/log4j/docs/documentation.html
개발자 생존 가이드 발표하기 전 자바서비스넷의 이원영님이 추천해주셨던 내용이기도 했습니다. http://www.inter-sections.net/2007/11/13/how-to-recognise-a-good-programmer/
6가지 요소를 얘기합니다. 물론 여러 요소들이 많겠지만, 6가지 소양은 다음과 같습니다.
#1 : Passion
#2 : Self-teaching and love of learning
#3 : Intelligence
#4 : Hidden experience
#5 : Variety of technologies
#6 : Formal qualifications
물론 변명의 여지도 Disclaimer에 남겨놓았습니다. 저 조건을 만족하는 것이 모두 좋은 프로그래머는 아니고, 또한 일부 조건에 맞는 형편없는 프로그래머도 있다고. 하지만 비즈니스맨 입장에서 좋은 프로그래머는 알아놓을 필요가 있다고 얘기합니다.
하단에 있는 긍정적인 지표와 부정적인 지표들로 내용을 마무리짓습니다.
Positive indicators:
* Passionate about technology
* Programs as a hobby
* Will talk your ear off on a technical subject if encouraged
* Significant (and often numerous) personal side-projects over the years
* Learns new technologies on his/her own
* Opinionated about which technologies are better for various usages
* Very uncomfortable about the idea of working with a technology he doesn’t believe to be “right”
* Clearly smart, can have great conversations on a variety of topics
* Started programming long before university/work
* Has some hidden “icebergs”, large personal projects under the CV radar
* Knowledge of a large variety of unrelated technologies (may not be on CV)
Negative indicators:
* Programming is a day job
* Don’t really want to “talk shop”, even when encouraged to
* Learns new technologies in company-sponsored courses
* Happy to work with whatever technology you’ve picked, “all technologies are good”
* Doesn’t seem too smart
* Started programming at university
* All programming experience is on the CV
* Focused mainly on one or two technology stacks (e.g. everything to do with developing a java application), with no experience outside of it
사람을 뽑는 입장이라면 자신과 같은 사람을 뽑을까요? 대답이 "Yes"라면 이제 비즈니스맨을 잘 만나는 일만 남았군요. 제리 맥과이어 같은 사람말이죠.
6. 입력값 수집 [출처] Struts1 VS Struts2|작성자 슬레이어
스트럿츠1은 사용자의 입력값을 받기 위해 ActionForm 오브젝트를 사용합니다. 그리고 모든 ActionForm들은 프레임웍에 의존적인 기반 클래스를 extend 하도록 되어 있습니다. JavaBean이 ActionForm으로 사용될 수 없기 때문에 개발자들은 입력값을 받기 위해 과다한 클래스들을 생성해야 합니다.
그러나 스트럿츠2는 Action클래스의 프러퍼티들(프레임웍에 독립적인 입력 프러퍼티로서)을 사용함으로써 추가적인 입력값 처리 관련 오브젝트들의 필요성을 제거했고 그리하여 과다하게 클래스가 생성되는것을 방지합니다. 추가적으로 스트럿츠2에서 Action클래스의 프러퍼티들은 웹페이지 상에서 태그라이브러리로 접근이 됩니다. 스트럿츠2는 POJO 폼오브젝트와 POJO Action을 지원할 뿐만 아니라 ActionForm형태의 사용도 지원합니다. 비즈니스 오브젝트나 도메인 오브젝트와 같은 타입들 역시 입력/출력값 관련 오브젝트로 사용이 가능합니다.
7. 표현식(Expression Language)
스트럿츠1은 JSTL과 통합되기 때문이 보통 JSTL을 EL로 사용합니다. 스트럿츠1은 기본적인 수준의 오브젝트내의 값에 대한 처리/순회를 지원하지만 상대적으로 컬렉션과 인덱스가 지정된 프러퍼티에 대한 지원이 약합니다. 스트럿츠2 또한 JSTL을 사용합니다만 보다 강력하고 유연한 Expression Langugae인 OGNL(Object Graph Notation Language)을 지원합니다.
8. 값을 뷰에 연결하기
뷰의 관점에서 보면 스트럿츠1은 오브젝트(Model에서 처리된 결과값을 담은)을 페이지 컨텍스트에 바인딩하기 위해 표준적인 JSP 메커니즘을 사용합니다.
하지만 스트럿츠2는 "Value Stack" 이란 기술을 사용하므로 View와 View가 렌더링할 오브젝트를 연결해놓지 않고도 태그라이브러리를 사용하여 값에 접근할 수 있습니다. Value Stack를 사용하여 값을 프로퍼티명을 사용하지만 그 타입이 다를 수도 있는 항목들을 가진 View들의 경우 해당 View를 재사용할 수 있습니다.
9. 형변환
보통 스트럿츠1에 있어 ActionForm의 프러퍼티값들은 모두 String형입니다. 스트럿츠1은 형변환시에 Commons-Beanutils를 사용합니다. 이런 타입컨버터들은 클래스당 하나씩 할당되고 인스턴트당 하나씩으로 설정할 수 없습니다.
하지만 스트럿츠2는 형변환에 OGNL을 사용합니다. OGNL의 구조는 기본적이고 공통적인 오브젝트의 타입과 프리미티브 타입에 대한 컨버터를 포함하고 있습니다.
10. Action의 실행에 대한 제어
스트럿츠1은 각 모듈당 별개의 RequestProcessors(라이프사이클)을 지원하지만 동일한 모듈내의 모든 Action들은 동일한 라이프사이클을 공유해야하만 합니다. 그러나 스트럿츠2는 Interceptor Stack을 사용하여 Action당 다른 라이프사이클을 가질 수 있도록 지원하고 있습니다. 필요하다면 커스텀 스택도 생성/사용할 수 있습니다.
[출처] [EJB] EJB 는 왜 사용하는가 ?|작성자 슬레이어