posted by 동건이 2011. 10. 6. 17:06

N-Screen 이란?

모바일업계에서 오랫동안 일해오면서 가장 싫어했던 단어들이 Seamless, Ubiqutous, 3-Screen 등이었다. 이러한 단어들은 실제 정의와 무관하게 '서로 다른 Screen Device에서 하나의 서비스를 동일한 사용성으로 제공한다'는 의미로 통용되었다. 개인적으로는 크기, 플랫폼, H/W 성능, 목적에 따라 Device의 고유한 사용성이 있는데 그것을 무시한다는 것을 받아드리기 힘들었다. 이러한 Multi Screen Device들에 대한 해석은 오랫동안 모바일 산업을 지배하였고 지금까지 사용되고 있다.

사용자 삽입 이미지

최근에는 'N-Screen 전략' 이라는 단어가 많이 사용된다. 혹자는 기존 3-Screen에서 Screen이 좀 더 다양해진 개념으로 사용하기도 하고, 일부 통신사나 언론기관에서는 Cloud와 혼용하여 사용하기도 한다. 하지만, 'N-Screen 전략'은 기존 Seamless한 3-Screen 전략과는 아주 큰 차이가 있다.

사용자 삽입 이미지

N-Screen 전략은 Online Activity가 더 이상 Single Task가 아니라는 것에서 시작한다. H/W와 Network 성능이 좋아지고 사용자들의 인터넷 사용이 익숙해지면서 다양한 인터넷 서비스들을 동시에 사용하는 것이 일반화되고 있다. 특히, 인터넷 서비스를 사용하면서 TV를 보거나 음악을 듣는 비율은 매우 높은 것으로 조사되고 있다.

사용자 삽입 이미지

이러한 Multi Tasking 현상은 모바일 Device의 발전과 함께 더욱 심화되고 있다. Yahoo의 최근 자료에 의하면 86%의 사용자가 TV를 시청하면서 Mobile Internet에 접속한다고 한다. n-Screen은 이렇게 서로 다른 Screen Device를 통해 하나의 서비스에 새로운 가치를 만들어 내는데에 목적이 있다.



위 영상(광고가 끝난 후에 플레이 된다)은 삼성전자가 2009년 9월에 발표한 LED TV와 세트인 Tablet 이다. 802.11n Wi-Fi를 통해 TV를 제어할 수 있고 TV 영상을 Preview 하거나 Widget을 통해 일부 Internet 서비스를 사용할 수도 있다. Apple iPad가 2010년 1월 28일에 발표되었으니 약 4개월이나 앞선 Device이다. 하지만, 이 Tablet의 아쉬움은 TV와 서로 연동되어 편리함은 전해주었지만 새로운 가치를 만들어내지는 못했다.

참고로 위 삼성 LED TV과 Tablet 세트는 $3,399로 판매될 예정이었으나 실제 시장에 나오지는 못한 것으로 보인다. TV과 Tablet으로 구성된 2-Screen 상품은 2003년에 소니가 WEGA PDP에서 최초로 시도하였다.



n-Screen은 서로 다른 Screen Device들이 각자의 특성에 맞는 기능(Feature)를 제공하면서 새로운 가치를 만들어 내야 한다. n-Screen 전략에서 Xfinity가 가장 많은 예로 등장하는 것이 바로 이 때문이다. Xfinity는 ‘2010 케이블쇼’에서 Comcast가 발표한 iPad App 인데, 기본적인 기능은 삼성전자 Tablet과 매우 유사하다. 하지만 Xfinity는 단순히 고도화된 리모콘에 멈춘 것이 아니라 친구를 초대하여 같은 TV 프로그램을 볼 수 있고 친구들과 채팅까지 할 수 있는 새로운 Communication 서비스를 만들어 냈다.

사용자 삽입 이미지

Yahoo의 최근 자료에 의하면 TV 시청 중에 40%는 SNS를, 37%는 인터넷 브라우저를, 33%를 모바일앱을 사용할만큼 Mobile Device를 많이 사용한다고 한다. 현재 이러한 사용자들의 Multi Tasking은 TV 내용과는 무관한 경우가 많다. 만일 Smart Phone이나 Smart Pad를 통해 TV내용과 관련있는 컨텐츠를 자연스럽게 노출할 수 있다면 새로운 서비스가 만들어지지 않을까?

과거 3-Screen이나 Ubiqutous는 Serial한 사용자 활동에 Seamless를 강조하였다. N-Screen 전략은 Parallel한 사용자 활동에서 서로 다른 Screen Device간의 Interaction이 가장 중요하다. 물론, 그 Interaction을 통해 새로운 가치를 만들어내어야 한다. 개인적으로 가장 큰 고민거리이자 관심의 대상이다.

댓글을 달아 주세요

posted by 동건이 2011. 9. 21. 21:05

웹서비스 프레임워크 비교(Comparision of WS) Apache Axis2, CXF and Sun JAX-WS


Apache Axis2

Axis2 is the follow-up of the popular Axis1 framework. Axis2 is based on a completely new architecture and has been rewritten from scratch. That makes Axis2 very flexible. For instance the databinding that is responsible for the serialization of Java objects into XML is not limited to one technology. For instance the following databindings are available:

Data BindingDescription
ADB The Axis2 Databinding Framework is leightweight and simple but doesn't cover all XML Schema functions.
JiBX Allows the use of pojos without any modifications. A mapping defines how the pojos are serialized to XML.
XMLBeans Offers the most comprehensive XML Schema support.

Table 1: Axis2 Databindings

Asynchronous Web Services are well supported by Axis2. An Axis2 service accepts also asynchronous requests without any changes to the service. The service can use an endpoint reference delivered in the request to address a callback after finishing an asynchronous request.

Asynchronous Web Service Invocation
Figure 1: Asynchronous Web Service Invocation

The deployment of services for Axis1 has often been criticized. Therefore Axis2 has a completely new deployment model. An Axis2 runtime is a Web application and can be installed on every JEE compliant Application Server. The Axis2 web application itself is a container for Web Services. Web Services are packed into an own file format with the file extension aar. Due to these archives, Web Services can be installed and configured by a simple user interface at run time. A Web Service is regarded as an independent package which can be installed into the Axis2 runtime environment. Services are configured using the service.xml configuration file.

Axis2 Deployment
Figure 2: Axis2 Deployment

Axis2 offers modules providing additional functionality, for example WS-* standard support, which can also be installed during runtime.

Apache CXF

CXF is also a project of the Apache software foundation. CXF came up from a fusion of XFire and Ionas Celtix project.

CXF was developed with the intention to integrate it into other systems. This is reflected in the CXF API and the use of the Spring framework. Therefore it is simple to integrate CXF into existing systems. For instance CXF respectively its predecessor XFire was integrated into numerous open and closed source projects like ServiceMix or Mule.

A proprietary API as well as the standardized JAX-WS interface are available for the development and use of Web Services.

The JAX-WS Standard

The Java API for XML based Web Services is the successor of the JAX-RPC specification. JAX-WS respectively its predecessor is message based and supports asynchronous communication. The Configuration is managed by annotations therefore Java 5 or higher is required. JAX-WS isn't downwardly compatible to its predecessor JAX-RPC. With JAX-WS it is pretty easy to write and consume Web Services. The default values of numerous parameters are comfortable for the programmer, so that simple Pojos declared with a @WebService annotation can be used as a Service. Listing 1 shows a simple implementation of a Web Service using the @WebService annotation.

01.import javax.jws.WebService;
02.import javax.jws.WebMethod;
03. 
04.@WebService
05.public class HelloWorldService {
06. 
07.public String helloWorld() {
08.return "Hello World!";
09.}
10.}
Listing 1: HelloWorld Web Service using JAX-WS

A WSDL document can also be generated from the class. Annotations can influence the content of the generated WSDL document. For example a different namespace or other element names can be used. If JAXB is already known to the programmer, its annotations can be used to define the serialization in every detail. With the contract first approach a Service Interface, JAXB annotated classes for serialization and a skeleton for the implementation can be generated out of WSDL. According to the WSDL document the generated classes can have numerous annotations. Annotations are also the main point of criticism of JAX-WS. Despite this criticism the JAX-WS specification came out well. It is well attuned and combinable with other Java and Java EE specifications. For example, Listing 2 shows a stateless EJB 3.0 Bean which acts as a Web Service at the same time.

1.@WebService
2.@Stateless
3.public class MyService{
4.public String hello(String name) {
5.return "Hallo"+name;
6.}
7.}
Listing 2: Stateless SessionBean acting as Web Service

JAX-WS Reference Implementation

The JAX-WS Reference Implementation represents the core component of the Web Services protocol stack Metro. The Metro Stack provides support for the following Web Services standards:

  • WS-Addressing
  • WS-Policy
  • Web Services Security aka WS-Security
  • WS-Transaction
  • WS-Reliable Messaging
  • WS-Trust
  • WS-SecureConversation

JAX-WS and Metro are documented in detail. Apart from the JAX-WS, JAXB and JWS specifications there are numerous tutorials und samples. The Netbeans IDE as well as the tutorials of the enterprise pack makes it particularly easy to get started. Of course, Eclipse can also be used for the development with Metro.

Web applications containing Web Services which have been realized with JAX-WS are executable in Glassfish and many other application servers. To make services also executable in Tomcat, two libraries (JAX-WS and JAXB) have to be installed.

JBossWS

JBossWS is the Web Services Framework for the JBoss application server. By providing an integration layer it is possible to choose from three stack options:

  • Native Stack:
  • Apache CXF Stack:
  • Metro Stack:

Performance

Due to the modern streaming StAX parser, the performance of all three SOAP engines is very well. The ping time for a locale roundtrip is less than 1 millisecond (message size about 3KB, Dual Core Notebook). Therefore the time delay by the SOAP communication is negligible in many projects.

WS-* Standards

The support of the WS-Standard family can also be decisive for the selection of a SOAP engine. For example, messages sent to services can be secured with signatures as described in the Web Service Security standard (in short WSS). Table 1 lists the supported WS-* standards for each toolkit.

StandardsAxis2CXFJAX-WS/Metro
WS-Addressing X X X
WS-Coordination X(2) X
WS-MetadataExchange X
WS-Policy X X X
WS-ReliableMessaging X(3) X X
Web Services Security X(1) X(4) X
WS-SecureConversation X(1) X(4) X
WS-SecurityPolicy X X X
WS-Transaction X(2) X
WS-Trust X X X
WS-Federation

Table 2: Support for WS-* Standards ( as of August 2010)

(1) Supported by the additional module Apache Rampart
(2) Supported by the additional module Apache Kandula2
(3) Supported by the additional module Apache Sandesha2
(4) By Apache WSS4J

Conclusion

None of the Web Services frameworks is in general superior to the others. Axis2 is structured modularly, has many features and can be used as an application server for Web Services. A special feature of Axis2 is the support of exchangeable binding frameworks, for example XMLBeans. Axis2 together with the XMLBeans framework is well suited for Web Services which are using very complex schema definitions. The disadvantages of Axis2 are its complexity as well as the insufficient JAX-WS support. Therefore anyone who wants to work with JAX-WS should choose Apache CXF or the reference implementation.

Those who prefer a seamless integration with the Spring framework are well advised with Apache CXF. Furthermore CXF is slim and easy to use. CXF is the tool of choice if a SOAP engine has to be embedded into an existing software.

Who wants to code against the standard is well advised with the JAX-WS implementation. The enterprise pack of the Netbeans development environment supports JAX-WS RI very well. Only a few clicks are needed to build a server or to call a Web Service. The Metro stack that includes JAX-WS RI offers the most comprehensive support for the WS-* standards. A major advantage of Metro 2.0 is its compatibility with Microsofts Windows Communication Foundation.

I hope this article could help you with the decision for a WS toolkit.

댓글을 달아 주세요

  1. Favicon of http://www.moncleroutletespain.com/ BlogIcon moncler españa 2013.01.04 14:02  Addr  Edit/Del  Reply

    You can also know about Visa regulations in specific countries, http://www.moncleroutletespain.com/ moncler. You can know about the ground delays of flights and track the rescheduling, http://www.moncleroutletespain.com/ moncler online. You also do not have to glue yourself before television or news channels to know the status of flight because of bad weathers. You can now easily know about airport closure beforehand. You save time and cost both, http://www.moncleroutletespain.com/ http://www.moncleroutletespain.com/. If you are first time flyer, you can easily know about the boarding process of a particular airport, http://www.moncleroutletespain.com/ moncler españa. If you are going to board at Philadelphia airport or Newark, http://www.moncleroutletespain.com/ moncler chaquetas, you will only get specific knowledge of this airport only. From parking to shops around, http://www.moncleroutletespain.com/ moncler outlet, these airport guides are comprehensive knowledge source for frequent and first time flyers alike. These can save you from the endless hassles which could face you if you are unprepared. Offering the simplest of services such as relevant information on flights from Dallas Fort Worth, on-site and off-site parking slots at Airport, these airport guides work towards to save your day and trip both.Related articles:


    http://2ssoosike.tistory.com/146 http://2ssoosike.tistory.com/146

    http://scor7910.tistory.com/92 http://scor7910.tistory.com/92

  2. Favicon of http://www.moncleroutletespain.com/ BlogIcon moncler outlet 2013.01.04 17:46  Addr  Edit/Del  Reply

    Le chef des opérations de maintien de la paix des Nations unies, http://www.moncleroutletespain.com/ moncler chaquetas, Alain Le Roy, http://www.moncleroutletespain.com/ moncler, a déclaré mercredi à l'AFP qu'il allait demander l'envoi de 1, http://www.moncleroutletespain.com/ moncler outlet.000 à 2, http://www.moncleroutletespain.com/ moncler españa.000 Casques bleus supplémentaires en C?te d'Ivoire, http://www.moncleroutletespain.com/ moncler online, en proie à une grave crise politique, http://www.moncleroutletespain.com/ http://www.moncleroutletespain.com/.Related articles:


    http://exsihell.tistory.com/920 http://exsihell.tistory.com/920

    http://tsukiko.tistory.com/14 http://tsukiko.tistory.com/14

  3. Favicon of http://www.moncleroutletespain.com/ BlogIcon moncler chaquetas 2013.01.05 16:35  Addr  Edit/Del  Reply

    Des contr, http://www.moncleroutletespain.com/ moncler españa?les de contamination à la dioxine vont être effectués, http://www.moncleroutletespain.com/ moncler, selon un porte-parole du ministère de l'Agriculture de l'Etat régional de Basse-Saxe, où sont situés la plus grande partie des élevages, http://www.moncleroutletespain.com/ moncler online.?La nourriture pour ces élevages, aujourd'hui concernés par cette alerte, a, http://www.moncleroutletespain.com/ moncler outlet? été livrée par le fabricant Harles & Jentzsch, installé à Uetersen dans le nord du pays. Selon la Fédération des agriculteurs allemands, http://www.moncleroutletespain.com/ http://www.moncleroutletespain.com/, Harles & Jentzsch a re, http://www.moncleroutletespain.com/ moncler chaquetas?u de l'acide gras contaminé en dioxine d'un commer?ant hollandais qui s'est lui-même fourni auprès d'un fabricant allemand de biodiesel situé à Emden (Nord de l'Allemagne).Les dioxines sont des résidus essentiellement formés lors des combustions, industrielles ou naturelles. Elles ont été classées comme substance cancérigène par l'Organisation Mondiale de la Santé. Santé Un test pour détecter les cellules cancéreuses bient?t sur le marché Actu en continu Inondations/Australie: attention aux serpents et crocodilesRelated articles:


    http://guraguna.tistory.com/category/?page=12+ http://guraguna.tistory.com/category/?page=12+"powered+by+daum"+~endorsement&ct=clnk

    http://hubnbridge.tistory.com/531 http://hubnbridge.tistory.com/531

posted by 동건이 2011. 9. 21. 21:00

Spring과 어울리는 WS framework은?

  • Axis2: More ubiquitous on the marketplace, supports more bindings, supports other languages like C/C++.
  • CXF: Much easier to use, more Spring friendly, faster got support for some WS-* extensions.


     
  • API - CXF pushes "standards based" API's (JAX-WS compliant) whereas Axis2 general goes toward proprietary things. That said, even CXF may require uses of proprietary API's to configure/control various things outside the JAX-WS spec. For REST, CXF also uses standard API's (JAX-RS compliant) instead of proprietary things. (Yes, I'm aware of the JAX-WS runtime in Axis2, but the tooling and docs and everything doesn't target it)

  • Community aspects and supportability - CXF prides itself on responding to issues and making "fixpacks" available to users. CXF did 12 fixpacks for 2.0.x (released two years ago, so about every 2 months), 6 fixpacks to 2.1.x, and now 3 for 2.2.x. Axis2 doesn't really "support" older versions. Unless a "critical" issue is hit, you may need to wait till the next big release (they average about every 9-10 months or so) to get fixes. (although, with either, you can grab the source code and patch/fix yourself. Gotta love open source.)

  • Integration - CXF has much better Spring integration if you use Spring. All the configuration and such is done through Spring. Also, people tend to consider CXF as more "embeddable" (I've never looked at Axis2 from this perspective) into other applications. Not sure if things like that matter to you.

  • Performance - they both perform very well. I think Axis2's proprietary ADB databinding is a bit faster than CXF, but if you use JAXB (standards based API's again), CXF is a bit faster. When using more complex scenarios like WS-Security, the underlying security "engine" (WSS4J) is the same for both so the performance is completely comparable.

  •  

댓글을 달아 주세요

posted by 동건이 2011. 9. 21. 16:49

GPS 두 지점간 정확한 거리 구하는 방법

GPS를 이용한 두지점간 거리계산 방법입니다.

 

안드로이드에서 기본적으로 제공해주는 직선거리 구하는 방법

지구는 타원으로 되어있기에 가까운지역인 경우 오차가 없지만,

거리가 멀어지면 오차가 발생하는걸 알 수 있습니다.

 

방법1.

 

double distance;

 

Location locationA = new Location("point A");

locationA.setLatitude(latA);

locationA.setLongitude(lngA);

Location locationB = new Location("point B");

locationB.setLatitude(latB);

LocationB.setLongitude(lngB);

distance = locationA.distanceTo(locationB);


 

 

방법2.

          float[] results = new float[3];

          Location location = new Location("start");

          location.distanceBetween(

          startLatitude, 

          startLongitude, 

          endLatitude,

          endLongitude,

          results);

          Sring mes = Float.toString(results[0]);

           

          ===============================================================================

          The computed distance is stored in results[0]. 

          

          If results has length 2 or greater, the initial bearing is stored in results[1].

          

          If results has length 3 or greater, the final bearing is stored in results[2].

          

           

          

           

          

          국토지리원에서 공개한 거리계산 함수 사용하기.

          

          지구는 완전한 구라는 가정하에 지구를 GRS80타원체로 봤을경우

          

          두지점간 거리와 방위각 구하는 소스

          

           

          

          //거리 구하는 부분

          

           public double distance(double P1_latitude, double P1_longitude,


             double P2_latitude, double P2_longitude) {


            if ((P1_latitude == P2_latitude) && (P1_longitude == P2_longitude)) {


             return 0;


            }

          

            double e10 = P1_latitude * Math.PI / 180;


            double e11 = P1_longitude * Math.PI / 180;


            double e12 = P2_latitude * Math.PI / 180;


            double e13 = P2_longitude * Math.PI / 180;

          

            /* 타원체 GRS80 */


            double c16 = 6356752.314140910;


            double c15 = 6378137.000000000;


            double c17 = 0.0033528107;

          

            double f15 = c17 + c17 * c17;


            double f16 = f15 / 2;


            double f17 = c17 * c17 / 2;


            double f18 = c17 * c17 / 8;


            double f19 = c17 * c17 / 16;

          

            double c18 = e13 - e11;


            double c20 = (1 - c17) * Math.tan(e10);


            double c21 = Math.atan(c20);


            double c22 = Math.sin(c21);


            double c23 = Math.cos(c21);


            double c24 = (1 - c17) * Math.tan(e12);


            double c25 = Math.atan(c24);


            double c26 = Math.sin(c25);


            double c27 = Math.cos(c25);

          

            double c29 = c18;


            double c31 = (c27 * Math.sin(c29) * c27 * Math.sin(c29))


              + (c23 * c26 - c22 * c27 * Math.cos(c29))


              * (c23 * c26 - c22 * c27 * Math.cos(c29));


            double c33 = (c22 * c26) + (c23 * c27 * Math.cos(c29));


            double c35 = Math.sqrt(c31) / c33;


            double c36 = Math.atan(c35);


            double c38 = 0;


            if (c31 == 0) {


             c38 = 0;


            } else {


             c38 = c23 * c27 * Math.sin(c29) / Math.sqrt(c31);


            }

          

            double c40 = 0;


            if ((Math.cos(Math.asin(c38)) * Math.cos(Math.asin(c38))) == 0) {


             c40 = 0;


            } else {


             c40 = c33 - 2 * c22 * c26


               / (Math.cos(Math.asin(c38)) * Math.cos(Math.asin(c38)));


            }

          

            double c41 = Math.cos(Math.asin(c38)) * Math.cos(Math.asin(c38))


              * (c15 * c15 - c16 * c16) / (c16 * c16);


            double c43 = 1 + c41 / 16384


              * (4096 + c41 * (-768 + c41 * (320 - 175 * c41)));


            double c45 = c41 / 1024 * (256 + c41 * (-128 + c41 * (74 - 47 * c41)));


            double c47 = c45


              * Math.sqrt(c31)


              * (c40 + c45


                / 4


                * (c33 * (-1 + 2 * c40 * c40) - c45 / 6 * c40


                  * (-3 + 4 * c31) * (-3 + 4 * c40 * c40)));


            double c50 = c17


              / 16


              * Math.cos(Math.asin(c38))


              * Math.cos(Math.asin(c38))


              * (4 + c17


                * (4 - 3 * Math.cos(Math.asin(c38))


                  * Math.cos(Math.asin(c38))));


            double c52 = c18


              + (1 - c50)


              * c17


              * c38


              * (Math.acos(c33) + c50 * Math.sin(Math.acos(c33))


                * (c40 + c50 * c33 * (-1 + 2 * c40 * c40)));

          

            double c54 = c16 * c43 * (Math.atan(c35) - c47);

          

            // return distance in meter


            return c54;


           }

          

          //방위각 구하는 부분

          

           public short bearingP1toP2(double P1_latitude, double P1_longitude,


             double P2_latitude, double P2_longitude) {


            // 현재 위치 : 위도나 경도는 지구 중심을 기반으로 하는 각도이기 때문에 

          

            //라디안 각도로 변환한다.


            double Cur_Lat_radian = P1_latitude * (3.141592 / 180);


            double Cur_Lon_radian = P1_longitude * (3.141592 / 180);

          

            // 목표 위치 : 위도나 경도는 지구 중심을 기반으로 하는 각도이기 때문에

          

            // 라디안 각도로 변환한다.


            double Dest_Lat_radian = P2_latitude * (3.141592 / 180);


            double Dest_Lon_radian = P2_longitude * (3.141592 / 180);

          

            // radian distance


            double radian_distance = 0;


            radian_distance = Math.acos(Math.sin(Cur_Lat_radian)


              * Math.sin(Dest_Lat_radian) + Math.cos(Cur_Lat_radian)


              * Math.cos(Dest_Lat_radian)


              * Math.cos(Cur_Lon_radian - Dest_Lon_radian));

          

            // 목적지 이동 방향을 구한다.(현재 좌표에서 다음 좌표로 이동하기 위해서는 

          

            //방향을 설정해야 한다. 라디안값이다.


            double radian_bearing = Math.acos((Math.sin(Dest_Lat_radian) - Math


              .sin(Cur_Lat_radian)


              * Math.cos(radian_distance))


              / (Math.cos(Cur_Lat_radian) * Math.sin(radian_distance)));

          

            // acos의 인수로 주어지는 x는 360분법의 각도가 아닌 radian(호도)값이다.

          

            double true_bearing = 0;


            if (Math.sin(Dest_Lon_radian - Cur_Lon_radian) < 0) {


             true_bearing = radian_bearing * (180 / 3.141592);


             true_bearing = 360 - true_bearing;


            } else {


             true_bearing = radian_bearing * (180 / 3.141592);


            }

          

            return (short) true_bearing;


           }

          

출처 : http://java16.springnote.com

 

 

댓글을 달아 주세요

posted by 동건이 2011. 9. 21. 15:26

SQLite 기본

<목표>  [안드로이드] SQLite데이터베이스 이용하기

   

오늘은 안드로이드 개발에 있어서 없어서는 안될 데이터베이스의 사용법에 대해 알아보겠습니다.

안드로이드는 모바일 환경에 알맞은 SQLite 데이터베이스를 채택하고 있습니다. 기본의 다른 데이터베이스와의 큰 차이는 없습니다.

다른 점이라면, 일반적은 데이터베이스는 테이블 생성시 각 속성에 대한 타입을 지정합니다. 하지만 SQLite는 타입을 지정하는 것이 없습니다. 즉, int, string, text 등의 타입을 지정할 수가 없다는 말이죠. 그러나 메모리와 속도면에서 소규모의 데이터베이스를 운영하는 데 있어서는 이점이 있습니다.

데이터베이스의 사용법은 기존의 데이터베이스를 한번이라도 다뤄보신적 있으신 분은 별 어려움 없이 사용하실 수 있을 것입니다. 처음 접하는 사람들 역시, 기존에 있는 샘플코드를 이용하여 조금만 수정해서 사용하시면, 별 어려움 없이 프로그램에 적용시키실 수 있을 겁니다.

샘플 코드는 인터넷에 널리 퍼져 있는 코드를 정리한 것입니다. 간단한 노트 기능으로 타이틀과 바디를 가지는 테이블이 있고, 이를 이용하여 데이터를 추가, 삭제, 업데이트 등을 수행할 수 있습니다.

   

   

STEP 1  Java Source Code

 

  자바 코드는 크게 두가지로 나뉘어집니다. 데이터베이스를 컨트롤 하는 객체와 이 객체를 사용하여 데이터베이스를 접근하는 엑티비티입니다.

  아래의 예제는 데이터베이스를 컨트롤 하는객체(NotesDbAdapter) 입니다. 이 클래스 내부에 DatabaseHelper객체가 있어 데이터베이스를 관리합니다. 이는 안드로이드에서 제공하는 SQLiteOpenHelper를 상속받아 간단히 만들 수 있습니다. DatabaseHelper 객체에는 크게 세 가지 함수가 존재합니다. 생성자, onCreate, onUpdate 가 있습니다. 말 그대로 onCreate는 데이터베이스를 생성하면서, 데이터베이스 이름과 버전을 설정할 수 있습니다. 이 부분에 쿼리문을 이용하여 데이터베이스의 테이블을 생성합니다. onUpdate는 말 그대로 업데이트가 필요할 시 수행이 됩니다. 현재의 데이터베이스 버전과 업데이트 하려는 데이터베이스의 버전을 비교하여, 낮은 버전일 경우 새롭게 테이블을 구성한다던가, 다른 조작 등을 취할 수 있습니다.

   

[Activity]   데이터베이스 관리 클래스

 

import android.content.ContentValues;

import android.content.Context;

import android.database.Cursor;

import android.database.SQLException;

import android.database.sqlite.SQLiteDatabase;

import android.database.sqlite.SQLiteOpenHelper;

import android.util.Log;

   

   

public class NotesDbAdapter {

   

    public static final String KEY_TITLE = "title";

    public static final String KEY_BODY = "body";

    public static final String KEY_ROWID = "_id";

   

    private static final String TAG = "NotesDbAdapter";

    private DatabaseHelper mDbHelper;

    private SQLiteDatabase mDb;

   

    /**

     * Database creation sql statement

     */

    private static final String DATABASE_CREATE =

"create table notes (_id integer primary key autoincrement, "

            + "title text not null, body text not null);";

   

    private static final String DATABASE_NAME = "data";

    private static final String DATABASE_TABLE = "notes";

    private static final int DATABASE_VERSION = 2;

   

    private final Context mCtx;

   

    private static class DatabaseHelper extends SQLiteOpenHelper {

   

        DatabaseHelper(Context context) {

            super(context, DATABASE_NAMEnullDATABASE_VERSION);

        }

   

        @Override

        public void onCreate(SQLiteDatabase db) {

   

            db.execSQL(DATABASE_CREATE);

        }

   

        @Override

        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {

            Log.w(TAG"Upgrading database from version " + oldVersion + " to "

                    + newVersion + ", which will destroy all old data");

            db.execSQL("DROP TABLE IF EXISTS notes");

            onCreate(db);

        }

    }

   

    public NotesDbAdapter(Context ctx) {

        this.mCtx = ctx;

    }

   

    public NotesDbAdapter open() throws SQLException {

        mDbHelper = new DatabaseHelper(mCtx);

        mDb = mDbHelper.getWritableDatabase();

        return this;

    }

   

    public void close() {

        mDbHelper.close();

    }

   

    public long createNote(String title, String body) {

        ContentValues initialValues = new ContentValues();

        initialValues.put(KEY_TITLE, title);

        initialValues.put(KEY_BODY, body);

   

        return mDb.insert(DATABASE_TABLEnull, initialValues);

    }

   

    public boolean deleteNote(long rowId) {

   

        Log.i("Delete called""value__" + rowId);

        return mDb.delete(DATABASE_TABLEKEY_ROWID + "=" + rowId, null) > 0;

    }

   

    public Cursor fetchAllNotes() {

   

        return mDb.query(DATABASE_TABLEnew String[] { KEY_ROWIDKEY_TITLE,

                KEY_BODY }, nullnullnullnullnull);

    }

   

    public Cursor fetchNote(long rowId) throws SQLException {

   

        Cursor mCursor =

   

        mDb.query(trueDATABASE_TABLEnew String[] { KEY_ROWIDKEY_TITLE,

                KEY_BODY }, KEY_ROWID + "=" + rowId, nullnullnullnull,

                null);

        if (mCursor != null) {

            mCursor.moveToFirst();

        }

        return mCursor;

   

    }

   

    public boolean updateNote(long rowId, String title, String body) {

        ContentValues args = new ContentValues();

        args.put(KEY_TITLE, title);

        args.put(KEY_BODY, body);

   

        return mDb.update(DATABASE_TABLE, args, KEY_ROWID + "=" + rowId, null) > 0;

    }

}

   

  그 밖에는 함수명에서도 볼 수 있듯이 데이터를 추가, 삭제, 업데이트하는 기능입니다. 기존의 데이터베이스와 다른 점은 쿼리문을 이용하지 않고 데이터를 조정이 가능한 것입니다. ContentValues 라는 타입을 이용하여 기존에 있는 테이블의 속성명과 조작하려는 인스턴스를 넣어 한꺼번에 데이터베이스로 요청할 수 있습니다. Insert, update 같이 데이터베이스 객체 내에 있는 함수를 이용하여 쿼리문 없이 데이터베이스 조작이 가능합니다. 이러한 함수는 내부에서 직접 쿼리문을 만들어 데이터베이스로 쿼리문을 날립니다.

자신이 사용하고 싶은 테이블을 구성하신 뒤에, 이 코드를 자신에 맞는 테이블로 바꾸시면 큰 어려움 없이 데이터베이스를 이용하실 수 있으실 겁니다.

 

[Bouns]   Cursor 사용

 

moveToFirst

커서가 쿼리(질의) 결과 레코드들 중에서 가장 처음에 위치한 레코드를 가리키도록 합니다.

moveToNext

다음 레코드로 커서를 이동합니다.

moveToPrevious

이전 레코드로 커서를 이동합니다.

getCount

질의 결과값(레코드)의 갯수를 반환합니다.

getColumnIndexOrThrow

특정 필드의 인덱스값을 반환하며, 필드가 존재하지 않을경우 예외를 발생시킵니다

getColumnName

특정 인덱스값에 해당하는 필드 이름을 반환합니다.

getColumnNames

필드 이름들을 String 배열 형태로 반환합니다.

moveToPosition

커서를 특정 레코드로 이동시킵니다.

getPosition

커서가 현재 가리키고 있는 위치를 반환합니다.

 

  데이터베이스의 특성상 하나의 테이블의 레코드를 읽어 오기 위해서는 커서라는 것이 필요합니다. 조건에 맞는 레코드를 한꺼번에 모두 들고 올 수가 없기 때문에 커서를 이용해서 조작을 합니다. 말 그대로 커서는 현재 레코드를 가리키고 있는 곳을 말합니다. 하나씩 이 커서를 이동하면서 레코드 하나하나씩을 접근해서 가져옵니다. 이 커서 객체를 이용하여 get을 하게 되면 컬럼 번호에 맞게 데이터를 가져올 수 있습니다.

 

[Activity]   데이터베이스 이용 엑티비티

 

import android.app.Activity;

import android.database.Cursor;

import android.os.Bundle;

import android.util.Log;

import android.view.View;

import android.widget.Button;

import android.widget.TextView;

   

public class DatabaseTestActivity extends Activity {

   

    private NotesDbAdapter dbAdapter;

    private static final String TAG = "NotesDbAdapter";

   

        

@Override

    public void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);

    setContentView(R.layout.main);

   

    Log.d(TAG, "DatabaseTest :: onCreate()");

   

    dbAdapter = new NotesDbAdapter(this);

    dbAdapter.open();

   

     Button bt = (Button)findViewById(R.id.inputButton);

     bt.setOnClickListener(new View.OnClickListener() {

   

            public void onClick(View v) {

                dbAdapter.createNote("title""body");

                TextView tv = (TextView)findViewById(R.id.textView1);

                tv.setText("데이터베이스에 넣었습니다.");

                TextView tv1 = (TextView)findViewById(R.id.textView2);

                tv1.setText("Title Body 데이터베이스에 저장하였습니다.");

                 Log.d(TAG, "First Button Click");

            }

        });

   

        Button bt1 = (Button)findViewById(R.id.outputButton);

        bt1.setOnClickListener(new View.OnClickListener() {

   

            public void onClick(View v) {

                Cursor result =    dbAdapter.fetchAllNotes();

                result.moveToFirst();

   

                while(!result.isAfterLast()){

                  String title = result.getString(1);

                  String body = result.getString(2);

   

                  TextView tv = (TextView)findViewById(R.id.textView1);

                  tv.setText(title);

                  TextView tv1 = (TextView)findViewById(R.id.textView2);

                  tv1.setText(body);

                  result.moveToNext();

   

                }

                Log.d(TAG, "Second Button Click");

                result.close();

            }

        });

 }

}

   

  위의 코드는 실제 엑티비티에서 데이터베이스를 이용하는 것을 나타내는 소스코드입니다. 위에서 살펴본 NotesDbAdapter 객체를 생성하여, open()을 한 뒤 사용하면 됩니다. 사용하는 법은 너무나도 직관적이라 생략하겠습니다. While문을 이용하여 커서를 이용하여 테이블에 있는 모든 레코드를 가져와서 화면에 뿌려주는 것을 수행하는 코드입니다.  

   

STEP 2  Xml Code

   

  Xml코드에는 간단히 테스트할 수 있는 TextView객체 두 개만 생성하고 있습니다.  

   

STEP 3  AndroidManifest.xml Code

 

  데이터베이스를 이용하기 위해서 AndroidManifest.xml 코드 수정은 필요하지 않습니다.

   

 

 

 마무리 >  SQLite 데이터베이스 사용하기

 

  데이터베이스를 사용하기 위해서는 안드로이드에서 제공하는 SQLiteOpenHelper를 이용하여 간단히 데이터베이스를 조작할 수 있습니다. 이 것을 상속받아 객체를 만들고 이 객체를 자신의 데이터베이스에 맞게 조작하도록 클래스(NotesDbAdapter)를 만들고, 엑티비티에서는 이 클래스를 생성하여 데이터베이스를 직접 사용할 수 있게 합니다. 간단한 샘플 코드를 이용하여 자신의 데이터베이스 테이블에 맞게 수정하여 사용하면 간단히 데이터를 저장할 수 있는 환경이 됩니다.

   

원문 : http://pulsebeat.tistory.com 

댓글을 달아 주세요

posted by 동건이 2010. 2. 17. 17:37

JAX-WS에 SSL적용


This Tech Tip reprinted with permission by java.sun.com

In Java EE 5, a web service that is based on JAX-WS can be implemented either as an EJB endpoint or servlet endpoint. An example of a JAX-WS-based web service implemented as an EJB endpoint is provided in the Tech Tip Developing Web Services Using EJB 3.0. A JAX-WS-based web service implemented as a servlet endpoint is provided in the Tech Tip Developing Web Services Using JAX-WS.

Irrespective of the way a web service is implemented, most enterprise applications, including those that use web services, need to run in a secure environment. Transport Layer Security (TLS)/Secure Sockets Layer (SSL) is a point-to-point secure transport mechanism that can be used for authentication, message integrity, and confidentiality. TLS/SSL (or in this tip, simply "SSL") meets the security requirements of most enterprise application environments, and is widely adopted.

This Tech Tip shows you how to construct a JAX-WS-based web service that runs with SSL, and how to access the web service from an application client. A sample package accompanies the Tech Tip. It demonstrates a Java client accessing a JAX-WS web service using SSL. Examples are provided for web services implemented as EJB and servlet endpoints. The sample uses an open source reference implementation of Java EE 5 called GlassFish. You can download GlassFish from the GlassFish Community Downloads page.

Write the Class for the Web Service Endpoint

Let's begin by writing a Java class for the web service. SSL has no impact on the Java code for the web service endpoint. The same code works for web services that use SSL or that don't use SSL.

In Java EE 5, you can use annotations to easily construct a JAX-WS web service. Here's an example of a web service implemented as an EJB endpoint:

   package ejbws;

   import javax.annotation.Resource;
   import javax.ejb.Stateless;
   import javax.jws.WebService;
   import javax.xml.ws.WebServiceContext;

   @Stateless
   @WebService
   public class HelloEjb {
       @Resource WebServiceContext wsContext;

       public String hello(String msg) {
           return "Ejb WS: " + wsContext.getUserPrincipal() 
           ": " + msg;
       }
   }

The @Stateless annotation marks the class as a stateless session bean, and the @WebService annotation marks the class as a web service. The @Resource annotation is used to declare resource dependencies that the class has -- in essence, what resources the class needs. These resources are then injected into the endpoint implementation. In this example, the annotation identifies a resource dependency on the WebServiceContext. The class needs the WebServiceContext to get context information about requests, such as related security information.

Here's the same web service implemented as a servlet endpoint:

   package servletws;

   import javax.annotation.Resource;
   import javax.jws.WebService;
   import javax.xml.ws.WebServiceContext;

   @WebService
   public class HelloServlet {
       @Resource WebServiceContext wsContext;

       public String hello(String msg) {
           return "Servlet WS: " + wsContext.getUserPrincipal() 
           ": " + msg;
       }
   }

Specify Security Information in Deployment Descriptors

To use SSL in a web service that is implemented as an EJB endpoint, you need to specify security information in a vendor-specific deployment descriptor (in this tip, sun-ejb-jar.xml). For a web service implemented as a servlet, you need to specify the security information in the web.xml descriptor.

One important aspect of secure communication through SSL is server authentication, that is, confirming the identity of the server to the client. Another aspect is client authentication, where the server confirms the identity of the client. In SSL, you can have either server authentication or the combination of server and client authentication (but not client authentication alone). This tip uses the term "mutual authentication" to mean the combination of server and client authentication. (Note however that other documents might attach a different meaning to mutual authentication. For example, in some documents, the term client authentication is synonymous with mutual authentication.)

To enable SSL server authentication, you need to set the <transport-guarantee> element to CONFIDENTIAL. For a web service implemented as an EJB endpoint, you set the element in the sun-ejb-jar.xml deployment descriptor. For a web service implemented as a servlet, you set the element in the web.xml deployment descriptor. As an example, for the HelloEjb web service, the <transport-guarantee> element in the sun-ejb-jar.xml deployment descriptor should look this:

   <ejb>
     <ejb-name>HelloEjb</ejb-name>
     <webservice-endpoint>
       <port-component-name>HelloEjb</port-component-name>
       <transport-guarantee>CONFIDENTIAL</transport-guarantee>
     </webservice-endpoint>
   </ejb>

For the HelloServletService service, the <transport-guarantee> element web.xml deployment descriptor should look like this:

   <security-constraint>
     <web-resource-collection>
       <web-resource-name>Secure Area</web-resource-name>
       <url-pattern>/HelloServletService/HelloServlet
       </url-pattern>
       <http-method>POST</http-method>
     </web-resource-collection>
     <auth-constraint>
       <role-name>EMPLOYEE</role-name>
     </auth-constraint>
     <user-data-constraint>
       <transport-guarantee>CONFIDENTIAL</transport-guarantee>
     </user-data-constraint>
   </security-constraint>

Notice the <http-method> element value of POST in web.xml. JSR-109, "Implementing Enterprise Web Services", specifies that the service endpoint authorization must be defined using an http-method element value of POST.

In GlassFish, WSDL files are protected by SSL for endpoints with SSL or SSL mutual authentication. For SSL mutual authentication, you need to set the <auth-method> subelement of the <login-config> element to CLIENT-CERT. You also need to set the <transport-guarantee> element to CONFIDENTIAL. For instance, in sun-ejb-jar.xml;

   <ejb>
     <ejb-name>HelloEjb</ejb-name>
     <webservice-endpoint>
       <port-component-name>HelloEjb</port-component-name>
       <login-config>
         <auth-method>CLIENT-CERT</auth-method>
         <realm>certificate</realm>
       </login-config>
       <transport-guarantee>CONFIDENTIAL</transport-guarantee>
     </webservice-endpoint>
  </ejb>

   <security-constraint>
     <web-resource-collection>
       <web-resource-name>Secure Area</web-resource-name>
       <url-pattern>/HelloServletService/HelloServlet
       </url-pattern>
       <http-method>POST</http-method>
     </web-resource-collection>
     <auth-constraint>
       </role-name>EMPLOYEE</role-name>
     </auth-constraint>
     <user-data-constraint>
       <transport-guarantee>CONFIDENTIAL</transport-guarantee>
     </user-data-constraint>
   </security-constraint>
   <login-config>
     <auth-method>CLIENT-CERT</auth-method>
     <realm-name>certificate</realm-name>
   </login-config>

No deployment descriptor is needed for the client program.

Package and Deploy the Web Service Application

Packaging and deploying a web service application that uses SSL is the same as for a web service application that doesn't use SSL. Keep in mind however, that if the web service is implemented as a servlet endpoint in an enterprise archive (that is, a .ear file), you need to include the application.xml file to specify the context-root for the web application.

Write the Client

After deploying the web service, you can access it from a client program. The client program for a web service application that uses SSL is essentially the same as one that doesn't use SSL. The major difference is that instead of using HTTP as the internet protocol, you need to use HTTPS. In the client, you use the @WebServiceRef annotation to declare a reference to a web service. The value of the wsdlLocation parameter in @WebServiceRef is a URL that points to the location of the WSDL file for the service being referenced. So for a web service client that uses SSL, the wsdlLocation parameter in the @WebServiceRef annotation needs to specify an HTTPS URL. For example:

   @WebServiceRef(wsdlLocation=
       "https://serverName:8181/HelloEjbService/HelloEjb?WSDL")
   private static HelloEjbService helloEjbService;

You can then access the port for the web service and invoke the web service:

   HelloEjb helloEjbPort = helloEjbService.getHelloEjbPort();
   helloEjbPort.hello("Hello World");

Client-side artifacts are generated by accessing the WSDL file through HTTPS. To do that, you need to specify the location of a truststore file for the server and its password in the environment variable VMARGS. In SSL, you can use certificates to authenticate the server or for mutual authentication of both the server and client. The truststore file for the server contains the trusted certificates for the server and its keys.

You can specify the location of the server's truststore file and its password in various ways, for example, you can specify them in an ant script as follows:

   <exec executable="wsimport">
     <env key="VMARGS" 
         value="-Djavax.net.ssl.trustStore=${truststore.location} 
         -Djavax.net.ssl.trustStorePassword=${ssl.password}"/>
    <arg line="-keep -d ${client.build} 
    https://serverName:8181/HelloEjbService/HelloEjb?WSDL"/>
   </exec>

Set Up the Client Truststore and Keystore

In addition to a truststore file for the server, you also need a truststore file for the client. The client validates the server certificate against a set of certificates in its truststore. For a secure connection to be made using SSL, the client-side truststore needs to trust the server certificate. For SSL mutual authentication, the server-side truststore also needs to trust the client certificate. If you modify the server-side truststore, you need to restart the server (this allows use of the new certificate). You might not need to do this in a production environment because production certificates are signed by a common Certificate Authority (CA). The GlassFish builds include certificates for several common root CAs.

For SSL mutual authentication, you need to provide your own key in a client keystore (a file that contains the client's keys and certificates). You can use keytool, a key and certificate management utility in JDK 5.0, to generate the keystore.

Run the Client

Before you run the client that access a web service with SSL, you need to set the value of the environment variable, VMARGS. After that, you can run the application as usual. For SSL, set the value of VMARGS to:

   -Djavax.net.ssl.trustStore=${truststore.location} 
   -Djavax.net.ssl.trustStorePassword=${ssl.password}

For SSL mutual authentication, set the value of VMARGS to:

   -Djavax.net.ssl.trustStore=${truststore.location} 
   -Djavax.net.ssl.trustStorePassword=${ssl.password} 
   -Djavax.net.ssl.keyStore =${keystore.location} 
   -Djavax.net.ssl.keyStorePassword=${ssl.password}

Running the Sample Code

To install and run the sample code that accompanies this tip:

  1. If you haven't already done so, download GlassFish from the GlassFish Community Downloads Page, and install it.
  2. Set the following environment variables:
    • GLASSFISH_HOME. This should point to where you installed GlassFish.
    • ANT_HOME. This should point to where ant is installed. Ant is included in the GlassFish bundle that you downloaded. (In Windows, it's in the lib\ant subdirectory.)
    • JAVA_HOME. This should point to the location of JDK 5.0 on your system.

    Add $JAVA_HOME/bin, $ANT_HOME/bin, and $GLASSFISH_HOME/bin to your PATH environment variable.

  3. Download the sample package and extract its contents. You should now see the newly extracted directory as <sample_install_dir>/ttmay2006ws-ssl, where <sample_install_dir> is the directory in which you installed the sample package. The ws-ssl directory below ttmay2006ws-ssl contains the source files and other support files for the sample.
  4. Change to the ws-ssl directory and edit the build.properties file as appropriate. For example, if the admin host is remote, change the value of admin.host from the default localhost to the appropriate remote host. Also, make sure that the following properties are correctly specified:
    • server.cert.cn. The CN name of the server certificate. It should be the host name or the fully-qualified domain name. In the default installation of GlassFish, the server certificate has the alias name s1as. You can display the CN by issuing the following command:
                          keytool -list -v -alias s1as -keystore 
                          $GLASSFISH_HOME/domains/domain1/config/cacerts.jks
      

      In response, you'll be prompted for a keystore password. Respond with the default password, changeit. You can change the password.

    • admin.user. The ID of the administrator who starts and stops the domain.
    • admin.port. The http port number of administrative server.
    • https.port. The https port number of server.
  5. Update the value of AS_ADMIN_PASSWORD in the passwd file to the administrator password.
  6. Set up the client key and certificate, by entering the following command:
                ant setup
    

    This creates a private key in a local keystore, exports the certificate, and imports it to the common truststore. Note that a self-signed certificate is installed in the truststore. This is for testing purposes only and is not recommended for production.

  7. If GlassFish is running, stop it as follows:
                $GLASSFISH_HOME/bin/asadmin stop-domain domain1
    

    Then start it:

           
                $GLASSFISH_HOME/bin/asadmin start-domain domain1
    

    This picks up the new certificate in the truststore.

  8. Build and deploy the sample. First enter the following command:
                ant build
    

    This compiles the EJB and Servlet Web Services classes and creates an ear file.

    Then enter the command:

                ant deploy
    

    This deploys the ear file in GlassFish.

    And finally, the following command:

                ant build-client
    

    This generates artifacts and compiles the client-side code.

  9. Run the client application to access the web service with SSL. Enter the following command:
                ant run
    

    You should see results that look something like this:

                [exec] Retrieving port from the service 
                ejbws.HelloEjbService@4e21db
                [exec] Invoking hello operation on the 
                HelloEjbService port
                [exec] Ejb WS: CN=serverName, OU=SSLClient, O=EJTechTips, 
                L=Santa Clara, ST=California, C=US: Hello World
                [exec] Retrieving port from the service 
                servletws.HelloServletService@ea7549
                [exec] Invoking hello operation on the 
                HelloServletService port
                [exec] Servlet WS: CN=serverName, OU=SSLClient, 
                O=EJTechTips, L=Santa Clara, ST=California, 
                C=US: Hello World
    

    You can see additional information, such as information about the SSL handshake, by adding jvm option -Djavax.net.debug=ssl,handshake. You can do this for the sample by entering the following command:

                 ant run-debug
    

    You can verify that this is an SSL mutual authentication by looking at the CertificateRequest during handshake.

    If you want to see more debugging information, use the jvm option -Djavax.net.debug=all.

  10. You can undeploy the Web Service ear file, by entering the command:
                 ant undeploy
    
  11. After you undeploy the application, remove the generated client certificate from the keystores and restart the server so that the certificate is removed from memory. To do that, enter the commands:
                 ant unsetup
                 $GLASSFISH_HOME/bin/asadmin stop-domain domain1
                 $GLASSFISH_HOME/bin/asadmin start-domain domain1 
    
    

About the Author

Shing Wai Chan is a senior member of the Sun Java Application Server and Java EE SDK development teams. He has been focusing on development projects that relate to security, annotations, CMP, B2B and B2C.

Copyright (c) 2004-2005 Sun Microsystems, Inc.
All Rights Reserved.


'개발 > 외부 참조 글' 카테고리의 다른 글

GPS 두 지점간 정확한 거리 구하는 방법  (0) 2011.09.21
SQLite 기본  (0) 2011.09.21
JAX-WS에 SSL적용  (5) 2010.02.17
웹사이트 분석 방법 및 용량산정 팁  (0) 2010.01.14
사이트별 적절한 H/W 스펙은 어떻게 정하나?  (0) 2010.01.13
ASP.NET 실치  (2) 2009.05.06

댓글을 달아 주세요

  1. Favicon of https://perversion.tistory.com BlogIcon 재미있는사이트 2010.04.06 15:38 신고  Addr  Edit/Del  Reply

    안녕하세요. 초보 블로거 입니다. 아름다운 블로그에 좋은 글 잘 보고 갑니다.

    시간 나실 때 제블로그도 한번 방문해주세요.^^

    무료 웹하드등 알면 유용한 정보를 포스팅 해놓았습니다.

    http://automobili.tistory.com/

  2. Favicon of http://www.logodesignconsultant.com/ BlogIcon Logo Design 2011.07.07 20:46  Addr  Edit/Del  Reply

    its reaaly nice and really cool working . keep doing ....

  3. BlogIcon Lawyer Marketing 2011.08.18 04:10  Addr  Edit/Del  Reply

    해야 이제 당신도 미정 수 :있는과 함께, 선택한 earbuds를 데리러 새로운 최고의 쿠페로 가서 당신의 문의는 Microsoft 준 이러한 사람을 선택하고 다음 음악 플레이어와 하나가 사람에게 바람직 생겼는지 발견 당신은 훨씬 더 보이게 프로그램을 켜십시오. 당신의 당신의 필요를 충족 인식됩니다.

  4. Favicon of http://www.mightystudents.com/ BlogIcon essay example 2011.11.22 15:44  Addr  Edit/Del  Reply

    Thanks for posting this. This is very interesting. I like it.

  5. Favicon of http://www.moncleroutletespain.com/ BlogIcon http://www.moncleroutletespain.com/ 2013.01.05 16:19  Addr  Edit/Del  Reply

    Quand on a la chance d'être marié à Lucy Lawless, à jamais Xéna la guerrière, http://www.moncleroutletespain.com/ moncler outlet, fantasme de toute une génération d'ados, ?a n'empêche pas de se montrer magnanime. Ainsi le producteur Robert Tapert, époux de l'actrice, aurait incité sa délicieuse compagne à se donner corps (beaucoup) et ame (un peu) sur le tournage de Spartacus?: Gods of the Arena.L'actrice révèle à nos confrères d'Access Hollywood?que Robert Tapert l'a clairement encouragée à tourner les scènes de sexe de la série : ??Son avis va parfois contre le mien. C'est du genre, http://www.moncleroutletespain.com/ moncler chaquetas, ‘Lucy, je sais que tu n'es pas à l'aise avec ?a mais c'est comme ?a', http://www.moncleroutletespain.com/ moncler online.??Il aurait simplement relevé qu'il s'agissait d'un ??bon scénario??. Toutefois, http://www.moncleroutletespain.com/ moncler españa, le mari ne va pas jusqu'à assister au tournage des scènes de sexe, http://www.moncleroutletespain.com/ http://www.moncleroutletespain.com/, l'actrice avouant qu'il ne se trouve pas sur le plateau à ces moments là. Sympa mais pas maso quand même, http://www.moncleroutletespain.com/ moncler. News Robert De Niro, une légende à Cannes News Black Swan : Mila Kunis, "J'aimerais être plus sauvage"Related articles:


    http://niki-nowhere.tistory.com/category/?page=5 http://niki-nowhere.tistory.com/category/?page=5

    http://mujige.com/779 http://mujige.com/779

posted by 동건이 2010. 1. 14. 09:29

웹사이트 분석 방법 및 용량산정 팁



342   웹기반시스템하에서의 성능에 관한 이론적 고찰
http://www.javaservice.net/~java/bbs/read.cgi?m=qna&b=consult&c=r_p&n=1008701211

강의를 들으셨음에도 불구하고 뭐부터 시작해야 할 지 모르신다니, 제가 강의를
제대로 못했다는 증거이네요...

먼저, 아파치 access_log 분석을 통해, 사용자에 의한 부하량을 조사하는 것이
우선입니다. access_log 를 이용하시면 다음과 같은 정보를 얻을 수 있습니다.

1) 일중 서로 다른 IP어드레스의 누적치 그래프
   시간당/분당 다녀간 서로 다른 IP어드레스 그래프
   (필요시, Proxy Server 보정치 조정)
2) 일일 동시단말사용자 그래프
3) 동적컨텐츠(Servlet/JSP)에 대한 분당 HIT건수의 일중 그래프

위의 것을 통해, 동시단말사용자에 의한 분당 혹은 초당 요청건수와 그에 따른
한 사용자당 평균 몇 초 간격으로 호출을 하는지를 확인할 수 있습니다.

또한, 과거의 몇 달 동안의 로그가 있다면, 간단히, access_log 의 사이즈
비교만으로도, 사이트의 증가량 및 증가패턴을 이해할 수 있을 것입니다.

4) httpd.conf 파일의 common 로그패턴에 "%T"옵션을 추가하여 해당 요청의
응답시간도 access_log 에 기록토록 하시고 최소한 하루치의 로그를 받으세요.

5) HIT량을 기준으로 한 각 어플리케이션(Servlet/JSP) HIT량 점유 파이 그래프

6) 개별 어플리케이션의 응답시간의 합을 기준으로한 파이그래프

그리고, 이를 통해 가장 응답이 느린 Servlet/JSP와, 또 각 Servlet/JSP별로
그 응답시간의 합을 계산하고 그 비율을 보면, 서버측에서 가장 오랫동안
점유한 서비스의 우선순위를 매길 수 있을 것입니다.

위의 과정을 통해, 어떤 응용어플리케이션이 가장 이 시스템에 어플리케이션적인
부하를 주고 있는지를 리스팅 할 수 있습니다.
경험적으로 볼때, 수백/수천개의 어플리케이션이 있다면 이 중 30-40%만이 사용되며
그 30-40%  중에서도 상위 20%의 어플리케이션이 전체 부하의 80%를 점유하고 있을
것입니다.

7) requestmon 이라는 모듈을 통해, 현재 수행되고 있는 Servlet/JSP 리스트 확인 및
응답이 느린 서비스 추적
관련모듈:
현재실행중인 서비스 모니터링 - requestmon -
http://www.javaservice.net/~java/bbs/read.cgi?m=appserver&b=was&c=r_p&n=982131370
Orion 서버에 requestmon 적용하기
http://www.javaservice.net/~java/bbs/read.cgi?m=appserver&b=orion&c=r_p&n=1009556331
Resin2.0.4 서버에 requestmon 적용하기
http://www.javaservice.net/~java/bbs/read.cgi?m=appserver&b=engine&c=r_p&n=1009768606



8) 위의 과정을 통해 상위 몇몇 개의 서비스를 선택하여 웹스트레스 테스트 툴을 이용,
강의시간에도 말씀드렸듯, 단위시간당 최대 처리건수인 TPS를 구하세요. 그리고, 각종
Tuning작업(DB튜닝, SQL튜닝, 파라메터튜닝, OS 튜닝, N/W 용량확인)을 통해
최대TPS를 끌어올리는 작업을 하세요.

9) 그러나, Tuning을 아무리 하여도 한계는 있겠지요... 그 최대 TPS에 따른 실제
발생한 hit량(access_log)을 비교하고, 동시단말사용자 증가에 따른 필요 전체 TPS를
가늠 해 보세요...


10) 특히 일중 동시단말사용자수 변화에 따른 해당 시점의 서비스 상태를 같이
비교하시면,한 머신에서 최대로 처리할 수 있는 동시단말사용자가 몇명 쯤이겠거니를
판단할 수 있을 것입니다.
이젠 L4/L7나 IBM eND를 통해 여러대의 머신을 클러스트링하여 로드발란싱을 시켜야
할 시점이 되는 것입니다. DB서버의 증설은 당연히 필요할 것으로 보이며,
웹어플리케이션서버(현재는 tomcat으로 운영되고 있군요)의 개수 및 서버용량을
산정해 보세요...

웹기반 시스템하에서의 용량산정은 아직 경험이 없다보니 경험치가 많지 않습니다.
저의 경험치는 다음과 같습니다. 웹어플리케이션서버를 위한 머신의 tpmC 요구량은,

필요서버용량(tpmC) = (동적컨텐츠에의한 분당최대처리건수) x 10tpmC + 여유분50%

입니다. 예를 들어, 초당 100건(100TPS)라면 분당 6,000 TPM 이고, 이는
6,000TPM x 10 tpmC = 60,000 tpmC 이며, 여기에 50%의 Buffer를 첨가하면
90,000 tpmC 가 필요하게 됩니다.

NOTE: 결코 절대적이지 않습니다. 어플리케이션의 특성에 따라 달라지는 것은 당연
하잖습니까. 제가 알기로는, 국내 굴지의 프로젝트에서도 웹서버에 대한 용량산정에
있어서, 만약, 특정한 공식이 있다면, 그 공식은 과거 경험치를 토대로 역산하거나
비즈니스적인 요건에 맞게 미리 서버를 대충 선정하고, 그것에 맞게 그럴싸하게 만든
가라데이타(?, 거짓부렁)입니다. 신뢰하지 마세요 ;-)

작성하신 문구의 어투와, 웹사이트의 구성으로 보건데, 1초당 10건도 처리하지
못하고 있을 듯 합니다. 1초당 10건이라함은(10 TPS), 평균적으로 사용자의
호출패턴이 20초간격으로 한번씩의 호출을 발생시킨다고 가정했을 때,

최대동시단말사용자(x명)/20초 = 10 TPS,

즉, 최대 동시단말사용자는 200 명이 max가 된다는 얘깁니다.

과거 및 현재 부하량을 분석하고, 어플리케이션의 중요도가 높은 것을 선택하여
웹스트레스테스트 시행을 통한 개별 최대TPS를 구하고, 향후 증가 예상을 통해
필요한 용량산정을 수치로 제시하여 고객과 협의하세요.

이러한 패턴으로 작업한 각종 문서들이 본 게시판을 찾아 보시면 다수 있습니다.
참고가 될 겁니다.

PS:  첫화면의 모든 데이타 사이즈가 303KB이네요. 임대받은 IDC센타의 N/W 용량은
어떻게 되는지요? 만약 10 Mbps dedicated 라면, 실전송 속도는 대략 이것은 60%로
가정하고, 10 Mbps x 60% x 1024 / 8 = 768 (KB/sec)가 되네요. 만약, 전송해야할
데이타의 평균량이 300KB라고 가정하면,768(kb/sec) / 300(kb) = 2.56 (건/sec)이
됩니다. 즉, 1초당 2.56 개만 서비스할 수 있다는 얘기가 됩니다. 2.56 TPS라는
얘기는 20초마다 한번씩 클릭하는 사용자 51명(2.56 x 20 = 51.2)이 최대 동시단말
사용자수가 될 것입니다.(예를 든 것 뿐입니다. 이미지는 "return code 304" cache가
되니, 얘기가 다르겠지요)

PS: DB Connection Pool을 사용하고 하지 않고는 해당 어플리케이션의 환경과
부하량 규모에 따라 다릅니다. 얼마나 차이나 나느냐 라는 질문은 우문입니다.
경우에 따라 다른 것이지요. 분명한 것은 성능 차이가 있다는 것입니다.

PS: access_log를 DB에 넣고, 이를 분석하는 아기자기한 저만의 프로그램들을
이 곳에 공개합니다. 시간상, 사용법은 향후 다시 문서화 하겠습니다. 엔지니어라면
소스를 보면 뭘 하자는 것인지 이해 하겠지요...

자바서비스넷(http://www.javaservice.net) --> Etc --> 기타자료실
8   웹로그 분석 프로그램 version 1.0
http://www.javaservice.net/~java/bbs/read.cgi?m=etc&b=etc&c=r_p&n=1015965476


----------------------------------------------------
웹기반 시스템하에서의 용량산정은 아직 경험이 없다보니 경험치가 많지 않습니다.
저의 경험치는 다음과 같습니다. 웹어플리케이션서버를 위한 머신의 tpmC 요구량은,

필요서버용량(tpmC) = (동적컨텐츠에의한 분당최대처리건수) x 10tpmC + 여유분50%

입니다. 예를 들어, 초당 100건(100TPS)라면 분당 6,000 TPM 이고, 이는
6,000TPM x 10 tpmC = 60,000 tpmC 이며, 여기에 50%의 Buffer를 첨가하면
90,000 tpmC 가 필요하게 됩니다.

 

댓글을 달아 주세요

posted by 동건이 2010. 1. 13. 21:17

사이트별 적절한 H/W 스펙은 어떻게 정하나?



1. 용량산정(Capacity Planning)에 대한 기술적 허구

1) 웹서버의 용량은 경험적으로 WAS서버보다 전체적으로 30%이하로 책정하면 되나,
"온라인트레이딩시스템"이 항상 웹서버를 경유하는 형태가 아닌, 예를들어 Applet 혹은
C#기반으로 되어 있어서 웹서버의 부하를 상대적으로 많이 주지 않는 경우라면,  WAS서버
대비 20% 이하로도 가능할 것입니다.

2) "동시사용자수 300명"이라는 너무나 모호한 수치로는 기술적으로 그 무엇도 알아낼 수
없습니다. "동시사용자수"가 "Active User"의 의미라면, ActiveUser는 해당 어플리케이션의
응답시간에 따라 항상 변동될 수 있는 수치이기에 더구나 의미를 가질 수 없습니다.
(그럼에도 불구하여 국내의 많은 분들은 전통적으로 ActiveUser의 크기를 사이징에 대입하곤
했습니다만, 이는 잘못되었다고 주장합니다.)

보다 의미있는 수치는 "일일총접속자수"도 아니고 "시간당최대접속자수"도 아니며, 
peak 시점의 "동시단말사용자수(Concurrent User)"와  각 사용자들이 몇초마다 한번식
클릭하는가 하는  해당 사이트의 고유상수: "Thinktime"에 의해 나타나는 ,

  단위시간당 최대 요청건수(tps) = 동시단말사용자수 / (Thinktime+평균응답시간)
  (tps: transaction per second)

이라는 수치가 보다 사이징에 의미를 갖는 수치입니다. 기존의 보수적인 분들은
"동시사용자수(ActiveUser)"는 "동시단말사용자수"의 "30%이다, 10%이다" 라는 식의
경험치를 주장하곤 했으나, 이는

동시사용자수(ActiveUser) = 동시단말사용자수 x (평균응답시간)/(평균응답시간+Thinktime)

이라는 공식으로 도출되므로, 가장 우측의 우항변수,
"(평균응답시간)/(평균응답시간+Thinktime)" 가 10% 혹은 30%와 같이 고정된 상수가 아님이
확인되며, 이는 사실 동시단말사용자수가 증가함에 따라 임계점(saturation point) 근방까지는
상대적으로 일정하게 낮은 평균응답시간을 갖다가, 임계점을 넘어서는 시점부터 평균응답시간은
무한대를 향하는 수치이기 때문에, 동시사용자수(ActiveUser)는 가변적으로 특정 임계점 근방을
기준으로 동시단말사용자수로 수렴하게 되어 10%나 30%가 아닌 최악의 경우 100%로 나타나게
됩니다.

관련자료: 590   웹퍼포먼스이론: 실사이트 측정결과보고서 및 관련언급
http://www.javaservice.net/~java/bbs/read.cgi?m=qna&b=consult&c=r_p&n=1035524021


3) WAS서버와 TP모니터(예 CICS)를 매개해 주는 CTG(CICS Transaction Gateway)도 WAS서버
대비 30%(이하)가량을 사용하게 됩니다.

4) TP Monitor인 CICS의 경우는 데이타베이스 및 해당 어플리케이션의 특성에 따라 정말
천차만별의 결과를 가져올 수 있습니다. 물론 tpmC라는 수치는 tpc.org에서 제시하는 OLPT환경인
TPC-C시나리오를 기반으로 단위시간당최대처리건수(tpm, transaction per minute)이라는 수치를
제공하므로, 얼추 추정할 수 있지 않겠느냐라고 주장할 수 있으나, 문제는 우리의
어플리케이션은 TPC-C시나리오에 사용된 어플리케션보다 얼마나 무게(weight)가 다른가에 대한
답을 할 수 없다면 무의미하게 됩니다. 물론  "온라인트레이딩시스템"이라는 단서를 달고 있기는
하나, 이 역시 일반화를 하기엔 무리가 따릅니다.
그 어떤 일반적인 수치보다도, 유사한 어플리케이션으로 기 운영되고 있는 기존 환경의 데이타를
참고하는 것이 가장 바람직한 접근일 것이라고 주장합니다.

2. 용량산정(Capacity Planning) 어떻게 접근해야 하는가?

결국, 제시하신 "동시사용자수 300명, 응답시간 3초미만, 온라이트레이딩시스템" 이 3가지
변수로 그 어떤 사이징의 결과도 도출 할 수 없습니다. 제가 권장하는 바는,

1) 충분한 용량의 H/W를 과거 경험치에 비추어 대략 선정하신 후,
2) 실질적인 Capacity Planning은 프로젝트가 진행됨에 따라, 일부 어플리케이션이 개발되고,
3) 단위어플리케이션에 대한 stress test를 거쳐 각 Tier의 용량비율을 구하고,
4) 예상되는 peak시의 동시단말사용자수와 해당 사이트의 고유상수인 Thinktime
   (온라인트레이딩의 경우 인터넷뱅킹과 유사한 25-35초)을 대입하여,
    단위시간당 요청건수(tps, transaction per second)를
    동시단말사용자수/(thinktime + 3초미만)으로 추정해 보고, 이 수치가 앞서 3)에서 구한
    최대 tps보나 낮아서,
5) 향후 오픈을 하더라도 충분한 용량인지를 파악하고,
6) 모자란다면 H/W 증설을 통해서, 혹은 어플리케이션 튜닝을 통해서

원하는 목적을 달성할 수 있을 것입니다.

3. Capacity Estimation

1) 대부분을 동의하실 것입니다. 그럼에도 불구하고, 그렇다면 그 "충분한 용량의 H/W를 과거
경험치에 비추어 대략 선정"을 어떻게 하면 되느냐의 현 시점에서의 질문으로 압축될 것입니다.
그러나, 이 질문에 대한 답변을 가장 잘 알고 있는 분은 바로 기존시스템을 유지보수해 오고
있던 고객 스스로 일 것입니다. 혹은 이미 유사한 아키텍쳐 환경으로 서비스하고 있는
타 업체의 사례를 확인하는 것이 가장 바람직할 것입니다.

2) H/W 적 구성으로 3대의 웹서버와 2대의 (WAS서버+TPMonitor) 구성은 그다지 나쁘지
않습니다. Single Point Failure를 없앴으며, Load-lanance를 통해 향후 확장성이 있는
구성입니다. 웹서버와  WAS서를 분리함으로 역할을 구분하고, 보다 적절한 장애상황에 대응할
수 있습니다.
그러나, WAS서버와 TP Monitor를 또 다시 한단계 더 분리하는 것이 규모가 커 질 수록 여러모로
바람직해 질 것입니다.

3) J2EE 기반의 WAS서버의 필요 H/W 용량은,

(1) 기본적으로 30,000 tpmC 이상의 H/W를 권장하며,(일반화하기엔 무리가 따르지만...)
(2) WAS가 기본으로 thread기반으로 동작하기 때문에 CPU개수가 그다지 중요치는 않으나,
   특정 thread가 어떤 장애상황으로 인해 CPU100%를 모두 다 사용하고하고 있을 경우, 다른
   thread들이 동작하지 않는 상황이 발생할 수 있으므로, 2 CPU 혹은 4CPU이상이 바람직합니다.
   (물론, CPU의 개수보다 H/W의 tpmC 수치가 높을 수록 더욱 높은 성능을 내지만...)
(3)  1btps당(1초에 최대 1건씩 business 어플리케이이션 요청을 처리하는 상황)
   CPU 사용률 70-80%를 가정할 때, 2,000 - 5,000 tpmC 정도가 경험적으로 필요합니다.
   (그 만큼 사이트 마다 천차만별의 다양한 폭이 존재한다는 뜻..)
   예를 들어, peak 시 동시단말(!)사용자수가 1000여명이고, 그들의 thinktime이 30초라면,
   즉 각 사용자는 30초마다 한번씩 클릭한다면, 이들에 의해 발생되는 단위시간당 요청건수는,
   1,000/(30+3초미만) 로써, 30~33 btps 가 필요하게 됩니다. 결국, 필요한 H/W 용량은
   (30~33) btps x (2,000~5,000)tpmC 로써, 이는 60,000 ~ 165,000 tpmC 가 필요하다는 얘기이고,
   이 사이의 gab를 보다 정확하게 하려면, 앞서 설명드렸듯 가오픈단계 이전에
   실어플리케이션을 기반으로 Stress Test가 선행되어야 한다는 것이지요.


PS: 결코, "모르겠습니다"에 대해 합리화를 하려고 한 것이 아니며, 그동안
"웹기반시스템하에서의 성능분석"에 관한 다년 간의 여러가지 고민을 통해 내린 결론이며,
일면 이해하는 면이 없잖아 있겠지만, 여전히 답답함을 그대로 남겨드려 죄송합니다. 아래의
문서들이 도움이 되기를 바랍니다.

[강좌]웹기반시스템하에서의 성능에 대한 이론적 고찰
http://www.javaservice.net/~java/bbs/read.cgi?m=resource&b=consult&c=r_p&n=1008701211


------------------------------------------------------- 
  본 문서는 자유롭게 배포/복사 할 수 있으나 반드시
  이 문서의 저자에 대한 언급을 삭제하시면 안됩니다
================================================
  자바서비스넷 이원영
  E-mail: javaservice@hanmail.net
  PCS:011-898-7904

댓글을 달아 주세요

posted by 동건이 2009. 5. 6. 13:19

ASP.NET 실치


1. ASP.NET 관련 파일들의 복사

.NET Framework 런타임 설치 패키지(dotnetfx.exe) 실행하면 .NET CLR 관련 파일, BCL(Base Class Library) 등과 함께 ASP.NET 관련 파일들을 설치하게 됩니다. 익히 아시다시피 .NET Framework 파일들은 모두 다음 경로에 설치됩니다.

 

C:\WINDOWS\Microsoft.NET\Framework\v[버전번호]

 

모두 RTM(정식버전) 기준으로 .NET 1.0 버전번호는 1.0.3705, 1.1 경우 1.1.4322, 2.0 경우 2.0.50727입니다. 따라서 .NET 2.0 경우 다음 경로에 설치됩니다.

 

C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727

 
중에서 핵심적인 파일들에 대해서 알아보면 다음과 같습니다. ASP.NET 2.0이라고 명시한 파일은 2.0에서만 존재합니다.

n        aspnet_compiler.exe : ASP.NET 2.0 Precompile 도구

n        aspnet_filter.dll : ASP.NET ISAPI 필터 DLL

n        aspnet_isapi.dll : ASP.NET ISAPI Extension

n        aspnet_perf.dll : ASP.NET 성능 카운터

n        aspnet_regiis.exe : ASP.NET IIS 등록 도구

n        aspnet_regsql.exe : ASP.NET 2.0 SQL 서버 연동 기능 설치 도구

n        aspnet_state.exe : ASP.NET Out-of-Process 상태 관리 서버 프로세스

n        aspnet_wp.exe : ASP.NET 작업자 프로세스(Worker Process)

 

파일들은 .NET Framework 버전번호에 따라 연관되는 ASP.NET 버전 역시 달라집니다. 1.1.4322 아래의 파일들은 ASP.NET 1.1 관련된 것이며, 2.0.50727 아래의 파일들은 ASP.NET 2.0 관련된 것입니다.

 

2. ASP.NET 설치, 등록, 응용프로그램 스크립트 매핑

관련 파일들의 설치가 끝나고 나면, 설치 패키지는 다음 명령을 실행합니다.

 

aspnet_regiis.exe -i

 

명령은 ASP.NET 관련 파일들을 실질적으로 설치하고 필요한 등록 작업들을 수행합니다. ASP.NET 성능 카운터를 비롯한 DLL 등록하는 작업들과 ASP.NET 1.x 경우 ASP.NET 클라이언트 스크립트를 ASP.NETClientFiles라는 폴더에 설치하는 것이 포함됩니다.

이것이 끝나면 응용프로그램 스크립트 매핑을 IIS 등록하는 작업을 수행합니다. 스크립트 매핑이 뭐냐고 물어보실 분들을 위해 여기에 대한 설명은 MSDN 되어 있는 것이 있어서 옮겨옵니다.

 

스크립트 맵은 파일 이름 확장명(: .aspx) HTTP 동사(: GET POST) 적절한 ISAPI 확장에 연결합니다. 예를 들어, IIS .aspx 파일에 대한 요청을 받으면 응용 프로그램의 스크립트 맵은 해당 .aspx 파일을 적절한 버전의 ASP.NET ISAPI 확장에 전달하도록 IIS 지시합니다. ASP.NET 응용 프로그램의 스크립트 맵은 일반적으로 IIS(인터넷 정보 서비스) 관리 콘솔에서 설정하며 응용 프로그램에 직접 적용하거나 부모 응용 프로그램에서 상속할 있습니다. 기본적으로 .NET Framework 설치될 ASP.NET 응용 프로그램이 이후 버전이나 호환되지 않는 버전을 사용하는 경우 이외에는 기존의 모든 응용 프로그램의 스크립트 맵이 설치된 ASP.NET ISAPI 확장을 사용하도록 자동으로 업데이트됩니다.

 

스크립트 매핑이 완료된 모습은 다음과 같이 IIS 관리자를 실행 기본 사이트->등록정보-> 디렉터리에서 구성 버튼을 누르면 응용프로그램 매핑을 있습니다.

 

여기에서 우리가 있는 한가지 사항은 만약 .NET Framework 설치하는 시점에 IIS 설치되어 있지 않았거나 도중에 뭔가 문제가 생겨서 정상적으로 설치가 되지 않았을 경우에는 나중에 aspnet_regiis –i 명령을 사용하기만 하면 ASP.NET 설치/등록

댓글을 달아 주세요

  1. 2009.05.08 01:25  Addr  Edit/Del  Reply

    비밀댓글입니다

  2. 2009.06.05 19:21  Addr  Edit/Del  Reply

    비밀댓글입니다

posted by 동건이 2009. 1. 21. 14:06

SQL 서버에서 Server is not configured for RPC 메시지를 보았을 때..


Server is not configured for RPC

나의 경우, 블로그 내부의 다른 mssql 관련 article 에서 와 같이, Linked 서버를 생성한 후, 원격지 mssql 서버의
프로시져를 호출하는 경우 위의 메시지를 보았다.
위의 메시지는 간단한 설정으로 없앨 수 있겠다..

An interesting thing about the linked servers when compared between SQL Server 2000 and SQL Server 2005 is that the default linked server properties differ in options tab. For example RPC and RPC Out are both enabled in SQL Server 2000 but these features are now disabled by default for SQL Server 2005.

You see below a linked server options tag defined in a Microsoft SQL Server 2000
MSSQL 서버 2000에서는 링크서버의 옵션의 속성 창을 열고 다음과 같이 RPC, RPC out 을 enable 해주면 해결된다.

Linked-Server-Properties

And below is a linked server options tab that is defined in MS SQL Server 2005.
아래 그림에서 보는 것과 같이, 링크서버의 옵션을 RPc, RPC out 옵션을 true 로 설정하면 되겠다.

Linked-Server-Properties

댓글을 달아 주세요

  1. Favicon of https://moneyamoneya.tistory.com BlogIcon 머니야 머니야 2009.01.21 16:08 신고  Addr  Edit/Del  Reply

    음..과연it과에 계신분답게 깔끔하세요^^ 잘읽고 갑니다!

posted by 동건이 2009. 1. 20. 17:35

SQL 네이티브 클라이언트 OLE DB 공급자 이용


SQL 네이티브 클라이언트 OLE DB 공급자

업데이트: 2005년 12월 5일

Microsoft SQL 네이티브 클라이언트 OLE DB 공급자는 Microsoft SQL Server 2005 데이터베이스에 OLE DB 인터페이스를 제공합니다. SQL Server 분산 쿼리는 SQL 네이티브 클라이언트 OLE DB 공급자를 사용하면 분산 쿼리가 SQL Server의 원격 인스턴스에서 데이터를 쿼리할 수 있습니다.

SQL Server 데이터베이스를 액세스하기 위해 연결된 서버를 만들려면
  1. sp_addlinkedserver를 실행하여 연결된 서버를 만들고 data_source로 SQL Server의 원격 인스턴스를 실행하는 서버의 네트워크 이름을 지정합니다. SQL Server 연결된 서버에서 공급자 SQLNCLI 지정은 선택 항목입니다.

    예를 들어 네트워크 이름이 NetSQLSrvr인 서버에서 실행되는 SQL Server 인스턴스에 대해 작동하는 LinkSQLSrvr라는 연결된 서버를 만들려면 다음 중 하나를 실행하십시오.

    sp_addlinkedserver N'LinkSQLSrvr', ' ', N'SQLNCLI', N'NetSQLSrvr'
    sp_addlinkedserver N'LinkSQLSrvr', ' ', ' ', N'NetSQLSrvr'

    또는 다음 예에서와 같이 SQL Server 연결된 서버를 해당 네트워크 이름으로 정의할 수 있습니다.

    sp_addlinkedserver N'NetSQLSrvr'
    

SQL Server 2000 인스턴스를 실행하는 서버에 대해 분산 쿼리를 실행할 때는 SQL Server 2000 서비스 팩 4(SP4)를 적용하는 것이 좋습니다. SP4를 적용하지 않은 경우 SP4에 포함된 Instcat.sql 스크립트를 실행하여 카탈로그 저장 프로시저를 업그레이드해야 합니다.

분산 쿼리가 SQL Server 버전 7.0 또는 그 이전 버전을 실행하는 서버에 대해 실행될 때는 분산 쿼리가 제대로 작동하도록 이전 버전의 카탈로그 저장 프로시저를 업그레이드해야 합니다. 예를 들어 서버가 SQL Server 7.0 인스턴스를 실행 중인 경우 SQL Server 2005의 인스턴스에서 실행 중인 서버의 분산 쿼리에서 해당 서버의 카탈로그 저장 프로시저를 참조하려면 먼저 카탈로그 저장 프로시저를 SQL Server 2005로 업그레이드해야 합니다.

원격 SQL Server 테이블이 업데이트되면 로컬 서버나 클라이언트는 이 업데이트에 대해 실행한 트리거로부터 어떤 결과 집합이나 메시지도 받지 못하게 됩니다.

네 부분으로 된 이름을 사용할 때는 항상 스키마 이름을 지정하십시오. 분산 쿼리에 스키마 이름을 지정하지 않으면 OLE DB가 테이블을 찾을 수 없습니다. 로컬 테이블을 참조할 때 소유자 이름을 지정하지 않으면 SQL Server는 기본값을 사용합니다. 다음 SELECT 문은 연결된 서버 로그인이 연결된 서버의 AdventureWorks 데이터베이스에 있는 dbo 사용자에 매핑될 경우에도 7314 오류를 생성합니다.

sp_addlinkedserver @server = N'LinkServer',
    @srvproduct = N' ',
    @provider = N'SQLNCLI', 
    @datasrc = N'ServerNetName', 
    @catalog = N'AdventureWorks'
GO
SELECT *
FROM LinkServer.AdventureWorks.dbo.Vendor

다음 예는 네트워크 이름이 othersite인 같은 컴퓨터를 액세스하는 연결된 서버와 원격 서버를 정의합니다. 이 연결된 서버 정의는 원격 서버의 네트워크 이름과 같은 이름을 사용합니다. 원격 서버 정의는 다른 이름을 사용합니다.

/* Create a linked server definition to othersite. */
EXEC sp_addlinkedserver 'othersite', N'SQL Server'

/* Create a remote server definition using a
   fictitious name. */
EXEC sp_addserver 'RPCothersite'

/* Set the fictitious name to the network name far away. */
EXEC sp_setnetname 'RPCothersite', 'othersite'

이 이름들은 분산 쿼리나 원격 프로시저 호출에서 참조될 수 있습니다.

/* A distributed query referencing othersite. */
SELECT *
FROM othersite.Northwind.dbo.Employees
/* A remote procedure call to the same server. */
EXEC RPCothersite.master.dbo.sp_who
/* Distributed queries can be used to execute
   stored procedures on the other server. */
EXEC othersite.master.dbo.sp_who

연결된 서버를 통해 실행된 저장 프로시저와 원격 서버를 통해 실행된 저장 프로시저의 로그인 매핑 메커니즘에는 몇 가지 차이점이 있습니다. 자세한 내용은 서버 연결을 참조하십시오.

Microsoft SQL 네이티브 클라이언트 OLE DB 공급자는 중첩된 트랜잭션을 지원하지 않습니다. 따라서 여러 Transact-SQL 문이 포함된 트랜잭션 내의 데이터 수정 작업에 대해, 그리고 분산 분할 뷰에 대한 데이터 수정 작업에 대해 XACT_ABORT를 ON으로 설정해야 합니다.

댓글을 달아 주세요

posted by 동건이 2009. 1. 20. 17:33

단순한 트리거, mssql 트리거


트리거란 특정 테이블에 INSERT, DELETE, UPDATE가 발생했을 때 다른 이벤트를 처리하도록 하기 위해서 데이터베이스에서 제공하는 기술이다.

다음은 Insert, Delete, Update에 대한 간략한 예제이다.

1) INSERT
회원 테이블에 회원이 등록되었을 때 회원 정보 중에서  user_id와 phoneno을 주소록 테이블에 기록되는 예이다.
회원 테이블은 Member / 주소록 테이블은  address 라고 가정한다.

// Member라고 하는 테이블에 대해서
// Insert 가 발생한 경우에 실행되는 트리거
Create Trigger ut_Member_Insert on Member
for Insert
AS
     declare @user_id varchar(20)
     declare @phoneno varchar(20)

     Select @user_id = user_id, @phoneno = phoneno From inserted
     insert into address values(@user_id, @phoneno, getDate())

상기 예에서 처럼 입력된 데이터는 Inserted 라고 하는 약속된 테이블(?)에 기록된다.
따라서 그 중에서 필요한 필드 값만 가져온 후 address 테이블에 기록한다.

즉 상기 코드는 회원이 등록된 경우 회원 정보 중에서 아이디와 휴대폰 번호를 주소록이라고 하는 테이블에 입력하기 위한 것이다.

2) DELETE
이번에는 회원 테이블의 특정 레코드를 삭제했을 때 백업용 회원 테이블에 해당 레코드를 입력하는 예이다.
회원 테이블은 Member / 백업용 회원 테이블은 Member_bakcup 이라고 가정한다.

// Member라고 하는 테이블에 대해서
// Delete가 발생한 경우에 실행되는 트리거
Create Trigger ut_Member_Delete on Member
for  Delete
AS
     
   Insert into member_backup
   select * from deleted

상기 예에서 처럼 삭제된 데이터는 Deleted라고 하는 약속된 테이블에 기록된다.
여기에서는 회원 테이블의 모든 데이터를 백업하는 것이므로 특정 필드만을 쿼리하지 않고
전체를 쿼리하여 member_backup 테이블에 기록하도록 하였다.

3) UPDATE
이번에는 회원 테이블에서 휴대폰 번호를 변경한 경우 이를 주소록이라고 하는 테이블에도 변경한다고 가정하자..
회원 테이블은 Member / 주소록 테이블은  Address
휴대폰번호에 해당되는 필드는 phoneno 라고 가정한다.

// Member라고 하는 테이블에 대해서
// Update가 발생한 경우에 실행되는 트리거
Create Trigger ut_Member_Update on Member
for  Update
AS
   declare @user_id varchar(20)
   declare @phoneno varchar(20)

   if update(phoneno)  begin
        select @phoneno = phoneno, @userid = user_id from inserted
        update address set phoneno = @phoneno
        where user_id = @user_id
  end

Update의 경우 Updated 라고 하는 테이블을 사용하는 것이 아니라 Inserted와 Deleted 2개의 테이블을 사용한다.

즉 phoneno 필드 값이 011-1234-5678에서 010-1234-5678로 변경되었다면
원래 들어 있던 011-1234-5678은 Deleted 테이블에 새로 변경된 010-1234-5678은 Inserted 테이블에 놓여지게 된다.
따라서 업데이트 이전의 값과 이후의 값을 Deleted와 Inserted라고 하는 테이블을 통해서 확인할 수 있다.

---------
다른 작업을 하다가 트리거를 사용할 일이 생겨서 처음(?) 써보기는 했는데..
솔직히 트리거의 원래의 용도가 무엇인지 잘 모르겠다.. 아직까지는 정확하게 이해하고 있는 것이 아니라서....
다른 작업을 하다가 트리거를 사용할 일이 생겨서 처음(?) 써보기는 했는데..
솔직히 트리거의 원래의 용도가 무엇인지 잘 모르겠다.. 아직까지는 정확하게 이해하고 있는 것이 아니라서....

이번 경우에는 서버 프로그램에서 특정 테이블의 값을 변경하는데.. 프로그램이 잘못 작성되어 엉뚱한 값으로 변경되는 일이 생겼다. 당장 서버 프로그램을 고칠수 있는 사람이 없어서 임시 방편으로 트리거를 사용하여 해당 테이블의 값이 업데이트 될 때 잘못 업데이트 값을 수정하여 올바른 값이 업데이트 되도록 수정하였다.

댓글을 달아 주세요

posted by 동건이 2009. 1. 20. 13:42

분산트랜잭션, MSDTS 문제 이렇게 해결해 보자.


OLE/DB 공급자 'SQLOLEDB'이(가) 분산 트랜잭션을 시작할 수 없음

아래 내용은 분산환경에서 호출하는 쪽이든, 호출 당하는 쪽이든 모든 서버에 동일하게 설정해야 실행된다.
한쪽에만 실행할 경우, 쿼리에서는 실행되는데 Trigger에서는 실행되지 않는 것을 경험했다..
이에 대한 의견이 있으신 분은 댓글 부탁해요~ ^^

www.wssplex.net
SQL Server 에서 종종 사용되는,. Linked-Server 를 사용하여 다른 SQL Server 에 접근을 하는 경우 종종 다음과 같은 오류 메시지가 나올수 있습니다.. 물론 웹서버에서도 특정 코드에서 SQL 쿼리시 Transaction 요구가 되도록 되어 있다면 이와 비슷한 오류 메시지가 나옵니다. -_-;;

ASP 페이지에서 데이터 트랜잭션을 처리하는 방법
http://support.microsoft.com/kb/299637/ko

OLE/DB 공급자 'SQLOLEDB'이(가) 분산 트랜잭션을 시작할 수 없으므로 작업을 수행할 수 없습니다.
[OLE/DB provider returned message: 지정한 트랜잭션 코디네이터에 새 트랜잭션을 기록할 수 없습니다. ]
OLE DB 오류 추적 [OLE/DB Provider 'SQLOLEDB' ITransactionJoin::JoinTransaction returned 0x8004d00a].


위 오류는,. Linked-Server 로 구성된 A 서버에서 B 서버로 쿼리시,. A 서버에서는 특정 테이블에 Trigger 가 걸려있고 그 Trigger 코드내에 Linked-Server 에 Insert 를 하게 되어 있습니다. 분산쿼리시 JoinTransaction OLE DB 인터페이스를 사용 합니다.

(읽기(Select) 라면,. 상관없겠지만,..... 데이터가 변경되는 Insert, Update, Delete, alter, create, drop 등등 명시적으로 트랜잭션을 호출하지 않더라도 암시적 트랜잭션이 활성화 됩니다.)

이러한 로컬 트랜잭션이 아닌 분산 Transaction 이 가능하게 해주는 것이 바로 MSDTC(Distributed Transaction Coordinator) 입니다. A 서버와 B서버 사이에의 트랜잭션 처리를 MSDTC가 모두 알아서 해주기 때문에 신경쓸 필요가 없는 것이죠. 위의 오류는 이와 같은 MSDTC 를 활성화 또는 엑세스에 문제가 있을때 발생 합니다.




그래서 MSDTC 활성화가 필요한데,.. MSDTC 활성화에 대한 자세한 설명이 있는 아티클이 있으므로  다음 포스트를 참조하는것이 더 이로울듯 싶습니다.^^

MS-DTC Setting on Windows 2003
http://www.simpleisbest.net/archive/2005/07/04/173.aspx

(*DTC 로그온 계정의 경우 다른 계정으로 설정을 했다가 원래 계정으로 복구를 할려면 굳이 msdtc 를 재설치 할필요까지는 없습니다. NT Authority\NetworkService 계정을 넣어주면 됩니다.  여기에서 설정한 계정은 서비스 관리자의 에서 Distributed Transaction Coordinator 의 실행 계정 입니다.)

MSDTC 는,. 다른 호스트의 MSDTC 엑세스를 위해서 RPC 통신을 하게 됩니다.

Linked-Server 에서 라면,. 쿼리 업데이트를 위한 1433 말고도 MSDTC 를 위한 135 포트가 접근이 가능해야 하는데,. 인증을 하게 되어 있는 경우 컴퓨터 인증이므로 Active Directory 환경이 아니고서는 되지 않습니다.

DCEPRC
     Auth type: NTLMSSP (10)
     Auth level: Packet integrity (5)
     NTLMSSP
          NTLMSSP identifier: NTLMSSP
          NTLM Message Type: NTLMSSP_NEGOTIATE (0x00000001)

컴퓨터 인증이기 때문에,. 워크 그룹 환경에서는 인증을 이용할수 없고 다음과 같은 이벤트가 발생하게 되겠지요.

로그온 시도: MICROSOFT_AUTHENTICATION_PACKAGE_V1_0
로그온 계정: WSSPLEX-A2$
워크스테이션: WSSPLEX-A2
오류 코드: 0xC0000064

로그온 실패:
  원인:  알 수 없는 사용자 이름 또는 잘못된 암호
  사용자 이름: WSSPLEX-A2$
  도메인:  WORKGROUP
  로그온 유형: 3
  로그온 프로세스: NtLmSsp
  인증 패키지: NTLM
  워크스테이션 이름: WSSPLEX-A

물론,.  "인증 필요 없음" 이 체크되어 있더라도 Linked-Server 의 옵션에서 RPC 사용이 체크되어 있으면 RPC 로그온을 시도하게 됩니다.



만약,. 한쪽에서만 허용이 되어 있다거나 접속이 가능한 조건이 라면,. 다음과 같은 이벤트가 발생 합니다.

이벤트 형식: 경고
이벤트 원본: MSDTC
MS DTC가 원격 시스템에 있는 MS DTC와 통신할 수 없습니다. 주 시스템에 있는 MS DTC가 보조 시스템에 있는 MS DTC와 RPC 바인딩을 만들었지만 시간을 초과하기 전에 보조 시스템이 주 MS DTC 시스템으로 역방향 RPC 바인딩을 만들지 못했습니다. 두 시스템 간에 네트워크 연결이 되어 있는지 확인하십시오. 오류 설명:d:\nt\com\complus\dtc\dtc\cm\src\iomgrsrv.cpp:1318, Pid: 2680
No Callstack,
CmdLine: C:\WINDOWS\system32\msdtc.exe


MSDTC 구성에 관련해서 위의 참조 링크를 통해서도 해결이 되지 않는다면 다음 링크를 통해서 트러블 슈팅을 해보면 도움이 될것 같습니다.

Troubleshooting Problems with MSDTC
http://msdn.microsoft.com/en-us/library/aa561924.aspx

만약 오류에 의해서 트랜잭션이 실패하거나 중단되는 것은, MSTDC 트랜잭션 통계를 통해서 확인이 가능할텐데요.. 물론 이러한 통계는 msdtc 가 시작된 이후로의 통계 이므로 재시작 되면 없어 집니다.


댓글을 달아 주세요

posted by 동건이 2009. 1. 20. 10:24

MSSQL Server - 연결된 서버(Linked Server) 삭제는 어떻게


MSSQL Server - 연결된 서버(Linked Server) 삭제는 어떻게?

 

SQL Server 2000에서 SP_AddLinkedServer를 이용하여 연결된 서버로 사용하고
연결된 서버를 삭제하고 싶을경우에는 어떻게 하나요?

  구문

sp_dropserver [ @server = ] 'server'
     [ , [ @droplogins = ] { 'droplogins' | NULL} ]

 
출처 : SQL Server 온라인 설명서 - F1

연관된 원격 서버 로그인 및 연결된 서버 로그인 항목이 있는 서버에서 sp_dropserver를 실행하면 원격 서버나 연결된 서버를 제거하기 전에 해당 로그인을 제거해야 한다는 오류 메시지가 반환됩니다. 서버를 제거할 때 서버의 원격 서버 로그인 및 연결된 서버 로그인을 모두 제거하려면 droplogins 인수를 사용합니다.


EXEC sp_dropserver 'server_name', 'droplogins';

server_name 은 설정한 이름으로 변경해주면되고, 뒷에 droplogins 는 그냥 두면 된다.

댓글을 달아 주세요

posted by 동건이 2009. 1. 16. 18:12

MSSQL2000 에서 IPv6 지원하는가? MSSQL과 ipv4, ipv6


Using IP Addresses

The Type 4 JDBC drivers support Internet Protocol (IP) addresses in IPv4 and IPv6 format. IPv6 addresses are only supported when connecting to certain database versions (as shown in Table 2-2). In addition, to connect to IPv6 addresses, the driver machine requires J2SE 5.0 or higher on Windows and J2SE 1.4 on UNIX/Linux.

Table 2-2 IP Address Formats Supported by the Type 4 JDBC Drivers 
Driver
IPv4
IPv6
Microsoft SQL Server
All supported versions
Microsoft SQL Server 2005 and higher

If your network supports named servers, the server name specified in the connection URL or data source can resolve to an IPv4 or IPv6 address. Alternatively, you can specify addresses using IPv4 or IPv6 format in the server name portion of the connection URL. You also can specify addresses in either format using the ServerName data source property.

Note: When specifying IPV6 addresses in a connection URL or data source property, the address must be enclosed by brackets.

In addition to the normal IPv6 format, the Type 4 JDBC drivers support IPv6 alternative formats for compressed and IPv4/IPv6 combination addresses.

For complete information about IPv6, go to the following URL:

댓글을 달아 주세요

posted by 동건이 2009. 1. 16. 17:50

MSSQL SSL 적용3


SSL 암호화에 대한 클라이언트 구성

Microsoft SQL Server JDBC 드라이버 또는 클라이언트는 서버가 올바른 서버이며 서버 인증서가 클라이언트에서 신뢰하는 인증 기관에서 발행되었는지 검사해야 합니다. 서버 인증서의 유효성을 검사하기 위해서는 연결 시 트러스트 자료를 제공해야 합니다. 또한 서버 인증서의 발급자가 클라이언트에서 신뢰하는 인증 기관이어야 합니다.

이 항목에서는 먼저 클라이언트 컴퓨터에 트러스트 자료를 제공하는 방법에 대해 설명합니다. 그런 다음 SQL Server 인스턴스의 SSL(Secure Sockets Layer) 인증서가 개인 인증 기관에서 발행된 경우 서버 인증서를 클라이언트 컴퓨터의 트러스트 저장소로 가져오는 방법에 대해 설명합니다.

서버 인증서의 유효성을 검사하는 방법은 SSL 지원 이해의 서버 SSL 인증서 유효성 검사 섹션을 참조하십시오.

클라이언트 트러스트 저장소 구성

서버 인증서의 유효성을 검사하려면 명시적으로 trustStoretrustStorePassword 연결 속성을 사용하거나 암시적으로 기본 JVM(Java Virtual Machine)의 기본 트러스트 저장소를 사용하여 연결 시에 트러스트 자료를 제공해야 합니다. 연결 문자열에 trustStoretrustStorePassword 속성을 설정하는 방법은 SSL 암호화를 사용한 연결을 참조하십시오.

trustStore 속성이 지정되지 않았거나 null로 설정된 경우 Microsoft SQL Server 2005 JDBC 드라이버는 기본 JVM의 보안 공급자인 SunJSSE( Java Secure Socket Extension)를 사용합니다. SunJSSE 공급자는 기본 TrustManager를 제공하는데 이 속성은 트러스트 저장소에 제공된 트러스트 자료에 대해 SQL Server에서 반환한 X.509 인증서의 유효성을 검사하는 데 사용됩니다.

TrustManager는 다음 검색 순서에 따라 기본 trustStore를 찾으려고 합니다.

  • 시스템 속성 "javax.net.ssl.trustStore"가 정의된 경우 TrustManager는 해당 시스템 속성에 지정된 파일 이름을 사용하여 기본 trustStore 파일을 찾으려고 합니다.

  • "javax.net.ssl.trustStore" 시스템 속성이 정의되지 않은 경우와 "<java-home>/lib/security/jssecacerts" 파일이 있는 경우 해당 파일이 사용됩니다.

  • "<java-home>/lib/security/cacerts" 파일이 있는 경우 해당 파일이 사용됩니다.

자세한 내용은 Sun Microsystems 웹 사이트에서 SUNX509 TrustManager 인터페이스 설명서를 참조하십시오.

Java Runtime Environment를 사용하면 trustStore 및 trustStorePassword 시스템 속성을 다음과 같이 설정할 수 있습니다.

java -Djavax.net.ssl.trustStore=C:\MyCertificates\storeName
java -Djavax.net.ssl.trustStorePassword=storePassword

이 경우 이 JVM에서 실행 중인 모든 응용 프로그램이 이러한 설정을 기본값으로 사용합니다. 응용 프로그램에서 기본 설정을 재정의하려면 연결 문자열 또는 SQLServerDataSource 클래스의 해당 setter 메서드에서 trustStoretrustStorePassword 연결 속성을 설정해야 합니다.

또한 "<java-home>/lib/security/jssecacerts" 및 "<java-home>/lib/security/cacerts"와 같은 기본 트러스트 저장소 파일을 구성하고 관리할 수도 있습니다. 이를 위해서는 JRE(Java Runtime Environment)와 함께 설치되는 JAVA "keytool" 유틸리티를 사용하십시오. "keytool" 유틸리티에 대한 자세한 내용은 Sun Microsystems 웹 사이트에서 keytool 설명서를 참조하십시오.

트러스트 저장소로 서버 인증서 가져오기

SSL 핸드셰이크 중 서버에서는 공개 키 인증서를 클라이언트로 보내는데 공개 키 인증서의 발급자를 CA(인증 기관)라고 합니다. 클라이언트에서는 인증 기관이 신뢰할 수 있는 기관인지 확인해야 합니다. 신뢰할 수 있는 CA의 공개 키를 알고 있으면 이를 확인할 수 있습니다. 일반적으로 JVM은 미리 정의된 신뢰할 수 있는 인증 기관 집합과 함께 제공됩니다.

SQL Server 인스턴스의 SSL 인증서가 개인 인증 기관에서 발행된 경우 클라이언트 컴퓨터의 트러스트 저장소에 있는 신뢰할 수 있는 인증서 목록에 해당 인증 기관의 인증서를 추가해야 합니다.

이를 위해서는 JRE(Java Runtime Environment)와 함께 설치되는 JAVA "keytool" 유틸리티를 사용하십시오. 다음 명령 프롬프트는 "keytool" 유틸리티를 사용하여 파일에서 인증서를 가져오는 방법을 보여 줍니다.

keytool -import -v -trustcacerts -alias myServer -file caCert.cer -keystore truststore.ks

이 예에서는 "caCert.cer" 파일을 인증서 파일로 사용합니다. 이 인증서 파일은 서버에서 가져와야 합니다. 다음은 서버 인증서를 파일로 내보내는 방법을 설명하는 단계입니다.

  1. 시작, 실행을 차례로 클릭하고 MMC를 입력합니다. MMC는 Microsoft Management Console의 머리 글자어입니다.

  2. MMC에서 인증서를 엽니다.

  3. 개인, 인증서를 차례로 확장합니다.

  4. 서버 인증서를 마우스 오른쪽 단추로 클릭한 다음 모든 작업/내보내기를 선택합니다.

  5. 다음을 클릭하여 인증서 내보내기 마법사의 시작 대화 상자에서 이동합니다.

  6. "아니요, 개인 키를 내보내지 않습니다."가 선택되어 있는지 확인하고 다음을 클릭합니다.

  7. DER 인코딩 이진 X.509(.CER) 또는 Base-64 인코딩 X.509(.CER)가 선택되어 있는지 확인하고 다음을 클릭합니다.

  8. 내보낼 파일 이름을 입력합니다.

  9. 다음을 클릭한 다음 마침을 클릭하여 인증서를 내보냅니다.

'개발 > 외부 참조 글' 카테고리의 다른 글

MSSQL Server - 연결된 서버(Linked Server) 삭제는 어떻게  (0) 2009.01.20
MSSQL2000 에서 IPv6 지원하는가? MSSQL과 ipv4, ipv6  (0) 2009.01.16
MSSQL SSL 적용3  (0) 2009.01.16
JDBC SSL 적용2  (0) 2009.01.16
JDBC SSL 적용  (0) 2009.01.16
MSQL 서버 IPv6 JDBC  (0) 2009.01.16

댓글을 달아 주세요

posted by 동건이 2009. 1. 16. 17:49

JDBC SSL 적용2

SSL 암호화를 사용한 연결

Microsoft SQL Server 2005 JDBC 드라이버 버전 1.2는 응용 프로그램에서 SSL(Secure Sockets Layer) 암호화를 사용할 수 있도록 새로운 연결 속성과 새로운 getter/setter 메서드를 제공합니다.

이 항목의 예에서는 Java 응용 프로그램에서 새 연결 문자열 속성을 사용하는 방법에 대해 설명합니다. encrypt, trustServerCertificate, trustStore, trustStorePassword, hostNameInCertificate 등의 새 연결 문자열 속성에 대한 자세한 내용은 연결 속성 설정을 참조하십시오.

encrypt 속성과 trustServerCertificate 속성이 true로 설정되어 있는 경우 Microsoft SQL Server 2005 JDBC 드라이버는 SQL Server SSL 인증서의 유효성을 검사하지 않습니다. 이 설정은 일반적으로 SQL Server 인스턴스에 자체 서명된 인증서만 있는 경우와 같이 테스트 환경에서 연결을 허용하는 데 필요합니다.

다음 코드 예제는 연결 문자열에 trustServerCertificate 속성을 설정하는 방법을 보여 줍니다.

String connectionUrl = 
    "jdbc:sqlserver://localhost:1433;" +
     "databaseName=AdventureWorks;integratedSecurity=true;" +
     "encrypt=true;trustServerCertificate=true";

encrypt 속성은 true로 설정되어 있고 trustServerCertificate 속성은 false로 설정되어 있는 경우 Microsoft SQL Server 2005 JDBC 드라이버는 SQL Server SSL 인증서의 유효성을 검사합니다. 서버 인증서의 유효성 검사는 SSL 핸드셰이크의 일부로 서버가 연결할 올바른 서버인지 확인합니다. 서버 인증서의 유효성을 검사하려면 명시적으로 trustStoretrustStorePassword 연결 속성을 사용하거나 암시적으로 기본 JVM(Java Virtual Machine)의 기본 트러스트 저장소를 사용하여 연결 시에 트러스트 자료를 제공해야 합니다.

trustStore 속성은 클라이언트에서 신뢰하는 인증서 목록이 포함되어 있는 인증서 trustStore 파일에 대한 경로(파일 이름 포함)를 지정합니다. trustStorePassword 속성은 trustStore 데이터의 무결성을 검사하는 데 사용되는 암호를 지정합니다. JVM의 기본 트러스트 저장소를 사용하는 방법은 SSL 암호화에 대한 클라이언트 구성을 참조하십시오.

다음 코드 예제는 연결 문자열에 trustStoretrustStorePassword 속성을 설정하는 방법을 보여 줍니다.

String connectionUrl = 
    "jdbc:sqlserver://localhost:1433;" +
     "databaseName=AdventureWorks;integratedSecurity=true;" +
     "encrypt=true; trustServerCertificate=false;" +
     "trustStore=storeName;trustStorePassword=storePassword";

JDBC 드라이버는 hostNameInCertificate라는 속성을 추가로 제공하는데 이 속성은 서버의 호스트 이름을 지정합니다. 이 속성의 값은 인증서의 주체 속성과 일치해야 합니다.

다음 코드 예제는 연결 문자열에서 hostNameInCertificate 속성을 사용하는 방법을 보여 줍니다.

String connectionUrl = 
    "jdbc:sqlserver://localhost:1433;" +
     "databaseName=AdventureWorks;integratedSecurity=true;" +
     "encrypt=true; trustServerCertificate=false;" +
     "trustStore=storeName;trustStorePassword=storePassword" +
     "hostNameInCertificate=hostName";
Note참고:

또는 SQLServerDataSource 클래스에서 제공하는 적절한 setter 메서드를 사용하여 연결 속성의 값을 설정할 수 있습니다.


'개발 > 외부 참조 글' 카테고리의 다른 글

MSSQL2000 에서 IPv6 지원하는가? MSSQL과 ipv4, ipv6  (0) 2009.01.16
MSSQL SSL 적용3  (0) 2009.01.16
JDBC SSL 적용2  (0) 2009.01.16
JDBC SSL 적용  (0) 2009.01.16
MSQL 서버 IPv6 JDBC  (0) 2009.01.16
Load-balancing Tomcat with apache, 톰캣 로드밸런싱  (0) 2009.01.16

댓글을 달아 주세요

posted by 동건이 2009. 1. 16. 17:48

JDBC SSL 적용


SSL 암호화 사용

SSL(Secure Sockets Layer) 암호화는 Microsoft SQL Server 2005 JDBC 드라이버 버전 1.2의 새로운 기능으로, 네트워크를 통해 SQL Server의 인스턴스와 클라이언트 응용 프로그램 간에 암호화된 데이터를 전송할 수 있습니다.

SSL(Secure Sockets Layer)은 네트워크를 통한 중요한 정보 가로채기와 다른 인터넷 통신을 방지하기 위한 보안 통신 채널을 설정하는 프로토콜입니다. SSL을 통해 클라이언트와 서버가 서로의 ID를 인증할 수 있습니다. 참가자가 인증된 후 SSL은 안전한 메시지 전송을 위해 참가자 간에 암호화된 연결을 제공합니다.

Microsoft SQL Server 2005 JDBC 드라이버는 사용자가 지정한 연결 속성과 서버/클라이언트 속성에 따라 특정 연결에 대한 암호화를 설정하고 해제하는 인프라를 제공합니다. 사용자는 인증서 저장소 위치와 암호, 인증서 유효성 검사에 사용할 호스트 이름 및 통신 채널 암호화 시간을 지정할 수 있습니다.

Note참고:

SSL 암호화를 사용하면 네트워크를 통해 SQL Server 인스턴스와 응용 프로그램 간에 전송되는 데이터에 대한 보안이 강화됩니다. 그러나 암호화를 사용하면 성능이 저하됩니다.

이 섹션의 항목에서는 Microsoft SQL Server 2005 JDBC 드라이버 버전 1.2에서 새 연결 속성을 포함하여 SSL 암호화를 지원하는 방식과 클라이언트측에서 트러스트 저장소를 구성하는 방법에 대해 설명합니다.

섹션 내용

항목 설명

SSL 지원 이해

Microsoft SQL Server 2005 JDBC 드라이버 버전 1.2에서 SSL 암호화를 지원하는 방식에 대해 설명합니다.

SSL 암호화를 사용한 연결

새 SSL 특정 연결 속성을 사용하여 SQL Server 데이터베이스에 연결하는 방법에 대해 설명합니다.

SSL 암호화에 대한 클라이언트 구성

클라이언트측에서 기본 트러스트 저장소를 구성하는 방법과 개인 인증서를 클라이언트 컴퓨터의 트러스트 저장소로 가져오는 방법에 대해 설명합니다.



MSSQL 2000 이상 부터 Encryption Methods 가 지원되는 구나...

Table 2-6 Data Encryption Methods Supported by the Type 4 JDBC Drivers
Driver
Database-Specific
SSL
Microsoft SQL Server
 
X1

1Supported for Microsoft SQL Server 2000 and higher.



'개발 > 외부 참조 글' 카테고리의 다른 글

MSSQL SSL 적용3  (0) 2009.01.16
JDBC SSL 적용2  (0) 2009.01.16
JDBC SSL 적용  (0) 2009.01.16
MSQL 서버 IPv6 JDBC  (0) 2009.01.16
Load-balancing Tomcat with apache, 톰캣 로드밸런싱  (0) 2009.01.16
아파치2.2 와 톰캣 5.5 연동  (0) 2009.01.16

댓글을 달아 주세요

posted by 동건이 2009. 1. 16. 17:34

MSQL 서버 IPv6 JDBC


연결 URL 작성

연결 URL의 일반적인 형식은 다음과 같습니다.

jdbc:sqlserver://[serverName[\instanceName][:portNumber]][;property=value[;property=value]]

여기서

  • jdbc:sqlserver://(필수)는 하위 프로토콜이라고 하며 일정한 형태를 나타냅니다.

  • serverName(옵션)은 연결할 서버의 주소입니다. 이는 DNS나 IP 주소일 수도 있고 로컬 컴퓨터인 경우 localhost나 127.0.0.1일 수도 있습니다. 연결 URL에 지정하지 않은 경우 속성 컬렉션에 서버 이름을 지정해야 합니다.

  • instanceName(옵션)은 serverName에서 연결할 인스턴스입니다. instanceName을 지정하지 않으면 기본 인스턴스에 연결됩니다.

  • portNumber(옵션)는 serverName에서 연결할 포트이며 기본값은 1433입니다. 기본값을 사용하는 경우 URL에 포트나 앞에 붙는 ':'을 지정할 필요가 없습니다.

    Note참고:

    연결 성능을 최적화하려면 명명된 인스턴스에 연결할 때 portNumber를 설정해야 합니다. 그러면 포트 번호를 확인하기 위해 서버까지 왕복 이동할 필요가 없습니다. portNumber 및 instanceName을 모두 사용하는 경우 portNumber가 우선 순위를 갖고 instanceName은 무시됩니다.

  • property(옵션)는 하나 이상의 옵션 연결 속성입니다. 자세한 내용은 연결 속성 설정을 참조하십시오. 목록에 있는 속성은 모두 지정할 수 있습니다. 속성은 세미콜론(';')으로만 구분할 수 있고 중복될 수 없습니다.

Caution note주의:

보안을 위해 사용자 입력을 토대로 연결 URL을 작성하지 않는 것이 좋습니다. URL에는 서버 이름과 드라이버만 지정해야 합니다. 사용자 이름 및 암호 값에는 연결 속성 컬렉션을 사용합니다. JDBC 응용 프로그램의 보안에 대한 자세한 내용은 JDBC 드라이버 응용 프로그램 보안을 참조하십시오.

연결 예

사용자 이름 및 암호를 사용하여 로컬 컴퓨터에서 기본 데이터베이스에 연결합니다.

jdbc:sqlserver://localhost;user=MyUserName;password=*****;

Note참고:

이전 예제에서는 연결 문자열에 사용자 이름과 암호를 사용했지만 Windows 운영 체제에서 응용 프로그램을 실행하는 경우 보다 안전한 통합 보안을 사용해야 합니다. 자세한 내용은 이 항목 후반에 있는 통합 인증으로 연결 섹션을 참조하십시오.

통합 인증을 사용하여 로컬 컴퓨터의 기본 데이터베이스에 연결하는 경우:

jdbc:sqlserver://localhost;integratedSecurity=true;

원격 서버의 명명된 데이터베이스에 연결하는 경우:

jdbc:sqlserver://localhost;databaseName=AdventureWorks;integratedSecurity=true;

기본 포트에서 원격 서버에 연결하는 경우:

jdbc:sqlserver://localhost:1433;databaseName=AdventureWorks;integratedSecurity=true;

사용자 지정 응용 프로그램 이름을 지정하여 연결하는 경우:

jdbc:sqlserver://localhost;databaseName=AdventureWorks;integratedSecurity=true;applicationName=MyApp;

명명된 다중 SQL Server 인스턴스

SQL Server 2000 및 SQL Server 2005에서는 한 서버에 다중 데이터베이스 인스턴스를 설치할 수 있습니다. 각 인스턴스는 특정 이름으로 식별합니다. SQL Server의 명명된 인스턴스에 연결하려면 명명된 인스턴스의 포트 번호를 지정하거나(기본 설정) 인스턴스 이름을 JDBC URL 속성 또는 datasource 속성으로 지정합니다. 인스턴스 이름이나 포트 번호 속성을 지정하지 않으면 기본 인스턴스에 대한 연결이 설정됩니다. 다음 예를 참조하십시오.

포트 번호를 사용하려면 다음을 수행합니다.

jdbc:sqlserver://localhost:1433;integratedSecurity=true;<more properties as required>;

JDBC URL 속성을 사용하려면 다음을 수행합니다.

jdbc:sqlserver://localhost;instanceName=instance1;integratedSecurity=true;<more properties as required>;

연결 URL에서 값 이스케이프 처리

공백, 세미콜론, 인용 부호와 같은 특수 문자가 삽입되어 있으므로 연결 URL 값의 일부를 이스케이프 처리해야 하는 경우가 있을 수 있습니다. JDBC 드라이버는 이런 문자가 중괄호로 묶인 경우 이스케이프 처리를 지원합니다. 예를 들어 {;}는 세미콜론을 이스케이프 처리합니다.

이스케이프 처리되는 값에 특수 문자(특히 '=', ';', '[]' 및 공백)는 포함될 수 있지만 중괄호는 포함될 수 없습니다. 이스케이프 처리해야 하는 값에 중괄호가 포함된 경우 해당 값을 속성 컬렉션에 추가해야 합니다.

Note참고:

중괄호 안의 공백은 리터럴이며 잘리지 않습니다.

통합 인증으로 연결

JDBC 드라이버는 integratedSecurity 연결 문자열 속성을 통해 Windows 운영 체제에서 형식 2 통합 인증을 사용할 수 있습니다. 통합 인증을 사용하려면 sqljdbc_auth.dll 파일을 JDBC 드라이버가 설치된 컴퓨터의 Windows 시스템 경로에 있는 디렉터리에 복사합니다.

sqljdbc_auth.dll 파일은 다음 위치에 설치되어 있습니다.

<installation directory>\sqljdbc_<version>\<language>\auth\

Note참고:

32비트 JVM(Java Virtual Machine)을 실행할 경우 운영 체제가 x64 버전이라도 x86 폴더에 있는 sqljdbc_auth.dll 파일을 사용하십시오. x64 프로세서에서 64비트 JVM을 실행할 경우 x64 폴더의 sqljdbc_auth.dll 파일을 사용하십시오. IA-64 프로세서에서 64비트 JVM을 실행할 경우 IA64 폴더의 sqljdbc_auth.dll 파일을 사용하십시오.

또는 java.libary.path 시스템 속성을 설정하여 sqljdbc_auth.dll의 디렉터리를 지정할 수도 있습니다. 예를 들어 JDBC 드라이버가 기본 디렉터리에 설치된 경우 Java 응용 프로그램이 시작될 때 다음과 같은 가상 컴퓨터(VM) 인수를 사용하여 DLL의 위치를 지정할 수 있습니다.

-Djava.library.path=C:\Microsoft SQL Server 2005 JDBC Driver\sqljdbc_<version>\enu\auth\x86

IPv6 주소로 연결

JDBC 드라이버는 연결 속성 컬렉션 및 serverName 연결 문자열 속성에 IPv6 주소를 사용하도록 지원합니다. jdbc:sqlserver://serverName과 같은 serverName 초기값은 연결 문자열의 IPv6 주소에는 지원되지 않습니다. 원시 IPv6 주소 대신 serverName의 이름을 사용하면 모든 경우의 연결에 원활하게 작동합니다. 자세한 내용은 다음 예를 참조하십시오.

serverName 속성을 사용하려면

jdbc:sqlserver://;serverName=3ffe:8311:eeee:f70f:0:5eae:10.203.31.9\\instance1;integratedSecurity=true;

속성 컬렉션을 사용하려면

Properties pro = new Properties();

pro.setProperty("serverName", "serverName=3ffe:8311:eeee:f70f:0:5eae:10.203.31.9\\instance1");

Connection con = DriverManager.getConnection("jdbc:sqlserver://;integratedSecurity=true;", pro);

참고 항목

댓글을 달아 주세요

posted by 동건이 2009. 1. 16. 11:33

Load-balancing Tomcat with apache, 톰캣 로드밸런싱


원문 : http://www.theserverside.com/tt/knowledgecenter/knowledgecenter.tss?l=LoadBalancingTomcatApache

Introduction

Tomcat은 웹어플리케이션을 호스팅할 때 가장 인기있는 어플리케이션 서버입니다. 

Apache는 https encryption과 decryption, URL rewriting, 기타등등과 같은 서비스를 제공하는데 인기있는 웹서버입니다.

Apache는 load balancer를 이용 여러개의 Tomcat 어플리케이션 서버간에 로드 벨런스도 할 수 있습니다.


이글은 어플리케이션 서버를 로드밸런싱 하는 몇가지 방법들에 대해 간단히 말하고자 합니다. Apache 'mod_proxy'를 이용해 럳, 벨런싱 설정하는 자세한 방법에 대해 설명할것이고 apache의 'server affinity'와 노드의 안전한 제거와 같은 부분들에 대한점 역시 살펴 볼것입니다.


Apache로 로드밸런싱 테스트할 수 있는 웹 어플리케이션을 다운받으세요. Jmeter스크립트 역시 Apache 로그 테스트 기능을 제공합니다.


Apache와 로드밸런싱 설정은 자바 개발자가 작은 팀에서 일하거나 테스트환경을 구축하는 상황이 아닌한 시스템관리자의 역할입니다. 하지만 로드밸런싱의 뒷면에 숨어 있는 원리를 이해하는것은 좋습니다. 이 지식은 실환경에서 발생하는 이슈사항을 해결하는데 도움이 될것입니다.


이 글은 웹어플리케이션 컨텍스트 로드 밸런싱에 대해 설명합니다. 어플리케이션은 https를 통해 접근하고 사용자의 로그인이 필요하며 몇몇 사용자 특정 정보는 세션에 저장됩니다.


Background knowledge

이글을 읽는 여러분이 다음과 같은 기술과 개념에 대해 알고 있다는 전제합니다.

  • Apache (Version 2.2)
  • Tomcat (Version 5.5.23)
  • Jmeter for load testing web applications

Some important terms

Load balancing - 사용자 요청은 하나 이상의 서버에 의해 처리되고 모든 서버는 '동등하게(equally)' 로드합니다.

                         (user requests are processed by more than one server with all servers sharing the load ‘equally’)
Server affinity(sticky session) - 서버 친근감(server affinity)때문에 사용자의 여러 요청은 똑같은 서버에 의해 처리됩니다. 이는 사용자 세션 데이터는 오직 하나의 서버에만 저장되고 사용자로부터의 모든 요청은 사용자에 대한 세션데이터를 저장하고 있는 서버로만 가야하는 비 클러스터링 서버에서 필요합니다.

Transparent failover - 사용자는 서버충돌을 알지 못합니다. Transparent failover는 요청레벨이 될수도 있고 세션레벨이 될수도 있습니다. Transparent failover는 어플리케이션 서버를 클러스터링 함으로써 극복할 수 있습니다. 클러스터링함으로써 모든 서버는 동일해지고 서버의 문제로 인해 서비스에 방해받지 않습니다. 로드밸런싱만 하면 서버 문제시 사용자는 다시 로그인해야 합니다.

Server Cluster - 사용자에게 하나의 서버처럼 보이는 서버군입니다. 서버의 문제가 사용자에겐 투명합니다.(사용자는 서버에 문제가 발생했는지 알지 못합니다.) 사용자 데이터는 클러스터 그룹의 모든 서버에서 유지하게 됩니다. 따라서 어떤 서버든 어떤 사용자 요청이던 어떤 서버가 문제가 생기더라도 문제없이 서비스를 처리할 수 있습니다. 서버문제가 생긴후 사용자는 다시 로그인할 필요가 없습니다. 사용자 세션 데이터가 네트워크를 통해 하나 이상의 서버에 복사되기 때문에 성능상 오버헤드는 있습니다. 따라서 클러스터링은 transparent failover가 요구될때에만 적용해야 합니다.

Scalability - 응답시간 감소 없이 시스템이 로드 증가를 감당하는 능력을 측정한 것입니다.

Response time - 사용자 요청을 처리하는데 걸린 시간입니다.

Real workers - Apache에서 로그밸런스 시스템의 구성을 이루는 서버들을 언급할때 사용되는 용어입니다. real workers는 실제 일을 하고 일반적으로 remote host입니다.

Virtual worker - Apache에서 real worksers에게 프로세스를 위임(delegate)하는 로드밸런서를 말합니다.


Load balancing algorithms

  • Round robin - 요청은 버전 충돌없이 처리 됩니다.
  • Weighted round robin - 서버의 각기 다른 capacity에 맞게 요청이 배분됩니다.(as a defined by a load factor)
            Apache 는 이에 관해 2가지 버전이 있습니다.
    • Request counting algorithm - 요청은 요청의 본질(? nature of the request)애 상관없이 라운드로빈 방식으로 위임 됩니다.
    • Weighted traffic counting alrogithm - Apache가 요청 바이트를 기초로 real worker에게 위임합니다.
Compare Load balancing with Clustering

로드밸런싱과 클러스터링 모두 하나 이상의 서버에 부하를 분산함으로 scalability를 향상시키는데 목표를 둡니다. 둘다 수평적 scalability 증가에 목표를 둡니다.

 Load balancing
Clustering
 서버 문제 발생 후 사용자는 로그인해야 함
서버 문제 후에 사용자가 다시 로그인할 필요 없음
따라서 failover가 사용자에게 투명함
 로드밸런싱은 웹서버나 DNS, 로드밸런서 장비, 톰캣 밸런서 웹 어플리케이션을 통해 이루어짐
클러스터링 기능은 어플리케이션 서버에 의해 제공.
클러스터링은 로드밸런싱 역시 필요로 함
 어플리케이션 서버(예:톰캣) 간에 서로 통신을 하지 않음
어플리케이션 서버(예:톰캣)간에 서로 통신을 함
 하나의 서버에서 여러 서버로 로드밸런싱을 적용 했을때 응답시간에 최소한의 영향만 끼침
 하나의 서버에서 클러스터링 시스템으로 전환하게 되면 세션 데이터가 네트워크를 통해 복사되기 때문에 응답시간은 감소하게 된다.

싱글 서버에 비해 세션데이터가 많을 수록 성능 저하가 커짐

응답시간 역시 클러스터의 노드 수에 달려 있습니다. 노드수가 많을수록 TCP를 이용 모든 노드에 데이터 복제하는데 성능저하가 발생합니다. 이는 UDP를 이용 세션데이터를 복사함으로 성능저하를 감소할 수 있습니다. UDP를 사용하면 세션 데이터 복사중 손실이 발생할 수 있습니다. 따라서 사용자는 서버 문제발생 후 다시 로그인 해야할 수 도 있습니다.
 로드밸런싱은 클러스터링에 독립적으로 사용 가능함
 클러스터링은 로드밸런싱도 필요하지만 'server affinity'를 과하게 합니다. 'transparent failover'를 제공하는 대신 더 복잡한 환경설정과 응답시간 감소 비용을 필요로 합니다.
일반적으로 싱글 서버에서 로드밸런싱할때 어플레키이션에 변경할게 없음
 어플리케이션은 반드시 클러스터된 환경 표준 에 맞아야 한다. 세션에 저장되는 사용자 데이터는 반드시 'serialiable'해야 하고 좋은 응답시간을 위해서 세션에 데이터를 조금만 저장해야한다.


Choices for implementing Load balancing

Hardware based load balancing
  • Pros
    • Fast
  • Cons
    • Expensive
    • Proprietary
    • Less flexible
Software based load balancing (e.g.Apache or Tomcat balancer)
  • Pros
    • Open source and free to implement width Apache and Tomcat balancer application
    • Easy to configure
    • More flexible
  • Cons
    • Lower performance compared to hardware based solution
Alternatives for software based load balancing
  • Apache 'mod_proxy' module or 'mod_jk' module. However 'mod_proxy' is easier to configure and newer than 'mod-jk' module.
  • Using Tomcat balancer application
  • Linux virtual server
  • Using DNS for load balancing
이 글의 나머지 부분에서는 Apache 'mod_proxy' 모듈을 이용 로드 밸런싱 하는 방법에 대해 설명합니다.


Load balancing with server affinity
간단한 로드 밸런스 설정은 stateful 웹 어플리케이션에 적합하지 않은 'server affinity'를 제공하지 않습니다. stateful 웹 어플리케이션에서는 사용자 상태(세션 데이터)가 하나의 서버에 유지됩니다. 앞선 모든 사용자 요청은 반드시 동일한 서버에 의해 처리되야 합니다. Server affinity(sticky session)에 따라서 stateful 웹 어플리케이션을 위해 클러스터링을 사용하지 않을 필요가 있습니다. 최소의 로드밸런스 설정은 2개의 어플리케이션 서버 그리고 하나의 웹서버(로드 밸런서)로 설정됩니다. 만약 https decryption이 필요하면 Apache 서버도 https descryption을 사용해야 합니다. server affinity 로드 밸런스 시스템에서는 모든 사용자1 요청이 Tomcat instance 1로 갑니다.
이는 다음과 같습니다.


Apache는 톰켓에서 브라우저로 보내지는 'jsessionid'를 다시 작성함으로 server affinity를 구현합니다. tomcat worker 이름을 'jsessionid'가 브라우저로 보내지기 전에 'jsessionid'끝에 추가합니다. 동일한 사용자로 부터의 다음 요청에선 'jsessionid'로부터 Tomcat worker 이름을 읽고, 그 요청을 이름에 해당하는 Tomcat worker에게 위임합니다.  브라우저에 쿠키로 저장된 톰켓 워커 이름을 갖는 'jsessionid'는 다음과 같습니다.

2개의 어플리케이션 서버에 대한 Apache 로드 밸런서 설정을 위한 Apahce 환경파일(httpd.conf)는 다음과 같습니다.
ProxyPass /apache-load-balancing-1.0 balancer://mycluster stickysession=JSESSIONID
<Proxy balancer://mycluster>
    BalancerMember ajp://tomcat1:8009/apache-load-balancing-1.0 route=tomcat1 loadfactor=50
    BalancerMember ajp://tomcat2:8009/apache-load-balancing-1.0 route=tomcat2 loadfactor=50
</Proxy>

위 설정이 로드되려면 'mod_proxy'모듈이 필요합니다. 첫줄은 '/apache-load-balancing-1.0'요청에 대한 프록시를 예약하고 'mycluster'라는 이름의 로드 밸런서(virtual worker)에게 모든 요청을 위임하도록 설정합니다. Sticky sessions와 쿠키로 구현된 'JSESSIONID'사용이 가능합니다. 'Proxy' 부분은 로드밸런서가 사용가능한 모든 서버(real worker) 리스트를 기술합니다.
로드 밸런싱의 각 관계자(participant)에 대해 우리는 url(http, ftp, ajp프로토콜을 이용)을 정의하고 톰캣 'server.xml'파일에 정의되어 있는 톰켓엔진에 메치될 이름을 줍니다.  'loadfactor'는 1~100사이의 수가 가능합니다. 50으로 설정했기 때문에 추후 동적으로 증가나 감소할 수 있습니다. 'TOMCAT_FOLDER/conf'폴더에 있는 'server.xml'파일에는 다음과 같은 설정이 반드시 있어야 합니다.

...
<Engine name="Catalina" defaultHost="localhost" jvmRoute="tomcat2">
...

2개의 브라우저 세션과 톰캣서버 콘솔, 그리고 서버 응답이 동일한 사용자의 모든 요청이 동일한 서버에 의해 처리됨을 보여줍니다.


Load balancing manager and safe removal of server node
Apache load balancing manager Apache는 로드 밸런싱을 위해 사용되는 서버들의 상태와 노드들의 안전한 제거를 준비하기 위한 'balancer manager'를 제공합니다. balancer manager를 사용하려면 'httpd.conf'파일에 다음 부분을 추가해야 합니다.
<Location /balancer-manager>
    SetGandler balancer-manager
</Location>

Balancer manager requires ‘mod_proxy’ and ‘mod_proxy_balancer’ modules to be loaded.

Balancer manager will now be accessible at the url ‘/balancer-manager’.

Screenshot of this is shown below:


Safe removal of a server node 어플리케이션 서버(real worker) 유지보수를 위해 오프라인할 필요가 있을때, 오프라인된 기간동안 해당 서버의 로드 팩터를 매우 낮게 설정합니다. 소수의 새로운 사용자들만이 그 서버를 통해 서비스를 제공받을 겁니다. All existing users ‘sticking’ to this real worker will continue to be processed by this real worker. 이는 real worker가 오프라인 됐을때 일정시간이 흐른 후 다시 로그인해야하는 사용자 수를 줄이는데 도움이 됩니다. 서버의 온라인될 준비가 완료되면 balancer manager를 통해 제어가 가능해집니다.

Tests
About the attached web application and JMeter script  첨부된 웹 어플리케이션은 하나의 서블릿과 3개의 JSP페이지로 되어 있습니다. 서블릿은 사용자 인증과 세션에 사용자 이름을 저장하기 위한 10명의 사용자 이름과 비밀번호가 하드코딩되어 있습니다. 서블릿은 서버의 이름과 사용자 이름역시 출력합니다. 로그인 JSP(index.jsp)는 로그인하기 위해 사용되고 두번째 JSP(greeting.jsp)는 로그인후 환영인사를 출력하기 위해 사용됩니다. 이 JSP 역시 서버 이름과 사용자 이름을 출력합니다. 세번째 JSP(user_details.jsp)는 사용자 상세 정보와 서버 이름, 요청을 처리하기 위한 서버의 아이피 주소를 출력합니다. 이 JSP역시 사용자 이름과 서버 이름을 출력합니다. 서버의 이름은 web.xml의 context 파라미터 설정을 통해 이루어집니다. 2개의 어플리케이션을 구별하기 위해 디플로이 전에 이름을 바꿔 주세요.
<context-param>
    <param-name>serverName
    <param-value>Tomcat instance 1
</context-param>

첨부한 JMeter 스크립트는 10개의 쓰레드가 로그인과 user detail을 요청하도록 설정되 있습니다.  2개의 브라우저를 이용한 수동 테스트는 server affinity를 보여줍니다. 2개의 브라우저를 실행하고 각각 다른 이름으로 로그인을 합니다. 톰캣의 서버 콘솔로 한 사용자의 요청은 항상 동일한 톰켓 인스턴스가 처리하는것을 확인할 수 있을겁니다.

Load testing with JMeterThe attached JMeter script is used to simulate a load of 10 users. The attached JMeter script has been setup to record the response. Comparing the response from the server and the server console, we can see that the load of 10 users is shared equally between 2 servers and all requests from one user are processed by the same server.

Sudden loss of one server and then restoring the serverThis can be simulated with either shutting down tomcat to simulate a server crash. This is best simulated using JMeter as a client to simulate a load of 10 users continuously requesting pages from the servers.Run the attached JMeter script and once the load test is running, take one server down. Any subsequent requests to the offline server will be redirected to the second server. When one server goes down, the user session data is lost and so all the users who have ‘affinity’ to that server will have to login again.

Reducing single point of failure

Load balancer can become the single point of failure. This can be reduced by using round robin DNS to delegate user requests to more than one load balancer. The load balancer delegates requests to more than one application server. In this scenario, if the load balancer and/or the application server goes down, the other load balancer and application servers can still provide some level of service. This is illustrated in the diagram below

:

Conclusion

Apache can be used to load balance Tomcat servers. This setup provides other useful features such as ‘Server affinity’ and safe removal of nodes for scheduled maintenance. Load balancing is recommended if transparent failover is not required. It is easy to setup load balancing and ‘server affinity’ with Apache.JMeter can be used to load test the configuration and to test the behaviour in case of a server crash.The load balancer can become the single point of failure. This can be reduced by using 2 load balancer and using round robin DNS to delegate request to more than one server.

Source Files

web application.zip
apache load balance load test script.jmx

Biography

Avneet Mangat 6 years experience in Java/J2EE. Currently working as Lead developer at Active Health Partners ( www.ahp.co.uk ). Bachelors degree in Software Engineering, Sun Certified Web developer and Java programmer, Adobe certified Flash Designer and Prince2 certified (foundation). Lead developer of open source tool DBBrowser, please see http://databasebrowser.sourceforge.net/ Outside interests include photography and travelling. Please contact me at avneet.mangat@ahp.co.uk or avneet.mangat@gmail.com for more information.

댓글을 달아 주세요