'PP'에 해당되는 글 98건

  1. 2012.01.13 C#에서 AxSHDocVw.Dll 활성화 시키기 [출처] C#에서 AxSHDocVw.Dll 활성화 시키기|작성자 신우아빠
  2. 2012.01.13 MSN 메신저 스타일의 Task Bar 점멸 기능 구현
  3. 2012.01.13 포커스를 빼앗지 않는 폼 구현
  4. 2012.01.13 iBatis 장점
  5. 2012.01.13 일반 구성 설정(ASP.NET)
  6. 2012.01.12 Spring .Net 활용 가이드
  7. 2012.01.10 Framework-based Development - 오픈 소스 적용 사례
  8. 2012.01.10 Framework-based Development - 종류
  9. 2012.01.10 Framework-based Development - 적용
  10. 2012.01.10 Framework-based Development - 개념
  11. 2012.01.10 닷넷 관련 개발 프레임워크
  12. 2012.01.10 DI
  13. 2012.01.10 서론.
  14. 2012.01.09 JSON 의 eval() 함수 사용의 문제
  15. 2012.01.09 JSON Text를 JSON Object로 변환하기
  16. 2012.01.08 jQuery 이벤트 정리
  17. 2012.01.08 [jQuery] Core , Selectors , Attributes , Manipulation, Events
  18. 2012.01.08 다른 라이브러리와 같이 쓰기
  19. 2012.01.08 jQuery Core
  20. 2012.01.08 [Jquery,CoffeeScript] 모질라 파이어폭스 Ajax. 한글 키 이벤트 처리.
  21. 2012.01.08 jQuery UI 테스트 2
  22. 2012.01.08 jQuery 이벤트 테스트 2
  23. 2012.01.08 jQuery 이벤트 테스트 1
  24. 2012.01.08 jQuery UI 테스트 2 1
  25. 2012.01.08 DataTable 수동으로 만들고 값넣기.
  26. 2012.01.08 C# <-> VB.net 코드 변환 사이트
  27. 2012.01.08 [ASP.NET] Repeater(리피터) 3
  28. 2012.01.08 [ASP.NET] Repeater(리피터) 2
  29. 2012.01.08 [ASP.NET] Repeater(리피터) 1
  30. 2012.01.08 [캐싱] 도넛 캐싱 구현 - ASP.NET 2.0 Output Cache Substitution
posted by 방랑군 2012. 1. 13. 20:30

윈도우 7 기준

C:\Program Files (x86)\Microsoft SDKs\Windows\v7.0A\Bin 폴더로 이동

AxImp.exe 명령을 이용해 shdocvw.dll 을 등록하면, SHDocVW 와 AxSHDocVW 를 함께 등록한다.

AxImp %Windir%\System32\shdocvw.dll

이렇게 하면 AxSHDocVw.DLL이 생성되는 것을 확인할 수 있다.

posted by 방랑군 2012. 1. 13. 20:01

Blinking in task bar like a MSN messenger

 

이번 강좌의 주제는 “MSN 메신저 스타일의 Task Bar 점멸 기능 넣기입니다.

MSN이나 네이트온 메신저는 새로운 친구가 접속 하거나 새로운 메시지가 도착하면  가지 방법으로 사용자에게 알려주는데  중에 좌측의 시스템 트레이에서 조그만 창이 스르르 올라 오는 기능을 구현 하는 것은 많이 알려져 있습니다만 Task Bar 해당 프로그램의  이름이 점멸하는 기능을 구현 하는 것은 상대적으로  알려져 있지 않은  같아 간단한 강좌를 작성 했습니다.

간단한 기능이므로 필요한 기능만 언급할 것입니다덕분에 강좌의 길이도 작습니다.

 필요한 기능인데 구현 방법을 알지 못해  고생 하는 개발자에게 도움이 되길 바랍니다.

 

[알아두세요]

1.        강좌에서 만들어진 예제는 Windows XP Professional SP2에서 테스트되었습니다.

2.        강좌는 .NET Framework 2.0 Visual Studio 2005 기준으로 제작되었습니다.

3.        강좌에서 사용된 개발 도구와 언어는  Visual Studio 2005 C#입니다.

 

1.       어떤 기능을 구현  것인가?

많은 메신저들이 새로운 메시지가 도착하거나 친구가 접속 했을  사용자에게 알려주기 위해 Task Bar 점멸 기능을 사용합니다 강좌는 메신저를 만들기 위한 강좌는 아니므로 단지 필요한 기능만을 습득하기 위해 샘플 어플리케이션이  활성화되고 일정 시간(5) 경과해도 활성화 되지 않으면 강제로 Task Bar에서 해당 어플리케이션 부분이 점멸하는 기능을 구현  것입니다(그림 1).

 

[그림 1]

 

2.       핵심 API

Task Bar 점멸 기능을 구현하기 위해서는 API 이용하는 방법이 가장 쉽습니다물론  번의 삽질로도 C# 코드만으로 구현이 가능하겠지만 이미 있는 기능 사용하는 것이 수명 연장에도 도움이 되겠죠해당 API 선언부를 알아보겠습니다. MSDN 있는 내용 그대로입니다.

 

FlashWindowEx

Flashes the specified window. It does not change the active state of the window.

BOOL FlashWindowEx)

   PELASHWINFO pfwi

);

Parameters

pfwi

   [in] A pointer to a FLASHWINFO structure.

Return Values

The return value specifies the window’s state before the call to the FlashWindowEx function. If the window caption was drawn as active before the call, the return value is nonzero. Otherwise, the return value is zero.

 

C#에서 사용하기 위한 선언도 알아보죠필요한 상수도 함께 알아보겠습니다.

[StructLayout(LayoutKind.Sequential)]

public struct FLASHWINFO

{

    public UInt16 cbSize;

    public IntPtr hwnd;

    public UInt32 dwFlags;

    public UInt16 uCount;

    public UInt32 dwTimeout;

}

 

private const UInt32 FLASHW_STOP = 0;

private const UInt32 FLASHW_TRAY = 2;

 

[DllImport("user32.dll")]

static extern Int16 FlashWindowEx(ref FLASHWINFO pwfi);

 

3.       간단한 샘플을 만들어보자.

API 모양새를 둘러 보았으니 간단하게 맛보기 샘플을 만들어 보겠습니다. API 어떤 방식으로 동작하는지를 알아보기 위한 것이니 단순하게 API 호출하고 어플리케이션이 어떻게 반응하는지 살펴보겠습니다.

 

Step 1. 윈도우 어플리케이션 프로젝트를 하나 만듭니다.

 

Step 2. 메인  클래스에 위의 API 선언부를 전부 복사  넣습니다.

 

Step 3.  위에 버튼 컨트롤을 하나 배치합니다.

 

Step 4. 버튼의 클릭 이벤트 핸들러에 API 호출하는 코드를 삽입합니다(소스 1).

private void button1_Click(object sender, EventArgs e)

{

    FLASHWINFO fInfo = new FLASHWINFO();

 

    fInfo.cbSize = (ushort)Marshal.SizeOf(fInfo);

    fInfo.hwnd = this.Handle;

    fInfo.dwFlags = FLASHW_TRAY;

    fInfo.uCount = UInt16.MaxValue;

    fInfo.dwTimeout = 0;

 

    FlashWindowEx(ref fInfo);

}

[소스 1]

 

Step 5. 빌드 하고 실행한  버튼을 누르면 Task Bar 해당 어플리케이션 이름 부분이 점멸합니다.

 

4.       어플리케이션 비활성화 알림 기능을 구현  보자.

테스트로 간단한 어플리케이션을 만들어 보았으니 이제 조금  복잡한 기능을 가진 어플리케이션을 만들어 보겠습니다.

제작할 어플리케이션이 가지게  기능은 폼이 비활성화되고 5초가 지나도 활성화 되지 않으면 Task Bar에서 점멸하여 사용자에게 알려주는 기능입니다.

 

Step 1. 윈도우 어플리케이션 프로젝트를 하나 만듭니다.

 

Step 2. 메인  클래스에 위의 API 선언부를 전부 복사  넣습니다.

 

Step 3. Timer 하나 추가하고 Interval 5000으로 설정합니다.

 

Step 4. 폼의 Deactivate 이벤트 핸들러에 타이머를 시작하는 코드를 삽입합니다(소스 2).

private void Form1_Deactivate(object sender, EventArgs e)

{

    this.timer1.Start();

}

[소스 2]

 

Step 5. 타이머의 Tick이벤트 핸들러에 점멸 기능을 활성화 시키는 API 호출 코드를 삽입합니다(소스 3).

private void timer1_Tick(object sender, EventArgs e)

{

    FLASHWINFO fInfo = new FLASHWINFO();

 

    fInfo.cbSize = (ushort)Marshal.SizeOf(fInfo);

    fInfo.hwnd = this.Handle;

    fInfo.dwFlags = FLASHW_TRAY;

    fInfo.uCount = UInt16.MaxValue;

    fInfo.dwTimeout = 0;

 

    FlashWindowEx(ref fInfo);

}

 

Step 6. 폼의 Activate 이벤트 핸들러에 타이머를 정지하고 점멸 기능을 비활성화 시키는 API 호출 코드를 삽입합니다(소스 4).

private void Form1_Activated(object sender, EventArgs e)

{

    this.timer1.Stop();

    FLASHWINFO fInfo = new FLASHWINFO();

 

    fInfo.cbSize = (ushort)Marshal.SizeOf(fInfo);

    fInfo.hwnd = this.Handle;

    fInfo.dwFlags = FLASHW_STOP;

    fInfo.uCount = UInt16.MaxValue;

    fInfo.dwTimeout = 0;

 

    FlashWindowEx(ref fInfo);

}

 

Step 7. 빌드하고 실행합니다테스트  보면 Minimize 버튼을 클릭하거나 다른 어플리케이션을 활성화해서 폼이 비활성화되면 5  Task Bar에서 점멸 기능이 동작 하고 폼을 활성화시키면 점멸 기능이 멈추는 것을   있습니다(그림 2).

 

[그림 2]

 

5.       마무리

FlashWindowEx 동일한 기능을 가진 API로는 FlashWindow 있습니다사용법이 훨씬 간단하므로 단순한 기능을 원한다면 사용에 무리는 없습니다하지만 점멸 간격 등의 정교한 제어를 원한다면 FlashWindowEx API 사용하는 것이 좋습니다파라메터에 해당하는 FLASHWIFO 구조체의 값을 적절히 바꾸어보면서 기능을 살펴보면 정확한 사용법을   있을 것입니다.

 

 

 

 

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

서용혁 (hyuki, mvp, c#)

crazy for .NET

Visual Studio 2005, .NET Framework, C#, MSDN Magazine

 

http://www.clrlab.org

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

posted by 방랑군 2012. 1. 13. 19:55

참조 :   http://www.devpia.com/MAEUL/Contents/Detail.aspx?BoardID=18&MAEULNo=8&no=1774&ref=1774 

1. WinAPI를 사용한다.

2. ShowWithoutActivation 프로퍼티를 상속받아서 Child Form Class를 구현한다.

 

 

그럼 차례대로 소개하도록 하겠습니다. 그리 어렵지 않습니다.

 

 

 

1. WinAPI - ShowWindow함수 사용

 

[System.Runtime.InteropServices.DllImport("user32.dll")]

public static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);

 

//RecvMemoWnd가 Form입니다. (쪽지창)

RecvMemoWnd memo = new RecvMemoWnd (strTitle, strContent, strTime, strSender);

ShowWindow(memo .Handle, WM_SHOWNOACTIVATE); //WM_SHOWNOACTIVATE = 4

 

 

 

2. 닷넷 - ShowWithoutActivation를 오버라이드하는 Child Form Class

 

public class Test : Form

{

   bool showWithoutActivation = false;

   protected override bool ShowWithoutActivation

   {

      get

      {

         return showWithoutActivation;

      }
   }

 

   public void Show(bool activate)

   {

      showWithoutActivation = !activate;

      Show();
   }
}

 

--------------------------------------------------------------------

 

Test test = new Test();

test.Show(false); 
posted by 방랑군 2012. 1. 13. 02:19

 iBatis는 여러 솔루션들로부터 최고의 아이디어들을 표출하여 그 시너지를 이끌어낸다.

표는 각각의 접근 방법 중에서 iBatis가 차용한 몇몇 아이디어들을 정리한 것이다.

 방법

 비슷한 이점

해결된 문제점 

 저장 프로시저

 iBatis는 SQL을 캡슐화 하고 외부로 분리하여 애플리케이션 외부에 SQL을 둔다. iBatis는 저장 프로시저와 비슷하지만 객체지향적인 API를 제공한다. iBatis는 또한 저장 프로시저를 직접 호출하는 방법도 지원한다.

 비즈니스 로직이 데이터베이스 밖에 있도록 한다. 배포하기 쉽다. 테스트하기 쉽다. 이식성이 좋다.

 인라인 SQL

 iBatis는 SQL을 원형 그대로 작성할 수 있다. 문자열 연결이나 파라미터 값 설정, 결과값 가져오기 등이 불필요하다.

 iBatis는 애플리케이션 코드내에 삽입되지 않는다. 전처리기가 불필요하다. SQL의 일부가 아닌 모든 기능을 사용할 수 있다.

 동적 SQL

 iBatis는 파라미터를 기반으로 하여 동적으로 쿼리를 구성하는 기능을 제공한다. 쿼리 구성 API는 필요 없다.

 iBatis는 애플리케이션 코드에 섞인 연결된 블록으로 SQL을 작성할 필요가 없다.

 객체/관계 매핑

 iBatis는 ORM도구의 적재 지연, 조인해서 값 가져오기, 실시간 코드 생성, 상속 등과 같은 많은 기능들을 동일하게 제공한다.

 iBatis는 어떤한 데이터 모델과 객체모델의 조합도 사용할 수 있다. 이들을 어떻게 설계 할지에 대한 제약이나 규칙 같은 것은 거의 없다.

 

 

-SQL의 외부 저장과 캡슐화

  이 두 개념이 합쳐져서 iBatis가 이룩한 많은 가치와 고급기능들을 제공해준다.

 

외부로 뺀 SQL

  사용자 인터페이스 설계, 애플리케이션 프로그래밍 그리고 데이터베이스 관리 같은 서로 다른 프로그래밍 역할에 따라 다뤄지는 사항들은 서로 분리하는 것이 좋다. 이렇게 분리하면 시스템의 특정 부분에 집중할 수 있는 잘 계층화된 설계를 얻을 수 있다. 만약 SQL을 자바 소스 코드에 집어넣으면 데이터베이스 관리자나 혹은 .NET개발자들이 동일한 데이터베이스에서 작업할 경우 불편하게 된다. 외부로 뺀 SQL을 애플리케이션 소스 코드로부터 분리하여 둘 모두를 명확하게 유지할 수 있게 한다. 그렇게 함으로써 SQL은 상대적으로 특정 언어나 플랫폼에 독립적인 상태가 된다.

 

SELECT

   PRODUCTID,

   NAME,

   DESCRIPTION,

   CATEGORY

FROM PRODUCT

WHERECATEGORY = #categoryId#

 

기존 SQL과 가장 다른 점은 파라미터 #categoryId#의 형태가 특정 언어에 종속적인 세부사항에 따라 달라지는 점이다. iBatis는 이를 더 이식성 좋고 읽기 쉽게 해준다.

 

캡슐화된 SQL

  오래된 개념 중 하나로 모듈화가 있다. 캡슐화는 코드를 응집성 있는 모듈로 조직하는 것뿐만 아니라 또한 세부적인 구현을 숨기고 호출하는 코드에게 인터페이스만을 노출시키는 모듈화의 한 형태이다.

  이러한 개념은 퍼시스턴스 계층으로도 확대 적용할 수 있다. SQL의 입력과 출력을 정의하고 애플리케이션의 다른 부분으로부터 SQL 코드를 숨겨서 SQL을 캡슐화할 수 있다. 객체지향 소프트웨어 개발자라면 인터페이스를 구현으로부터 분리하는 것과 같은 방식이라고 보면 된다. SQL 개발자라면 저장 프로시저 안에 SQL을 숨기는 것이 캡슐화라고 생각하면 된다.

  iBatis는 SQL을 캡슐화하기 위해 XML을 사용한다. XML을 선택한 까닭은 일반적으로 모든 플랫폼에 이식가능하고, 산업 전반에 걸쳐 채용되었기 때문이다.

  iBatis는 XML을 사용해서 SQL 구문의 입력과 출력을 정의한다. iBatis는 파라미터와 실행 결과를 객체의 프로퍼티로 매핑하게 한다.

 

<select id="categoryById"

   parameterClass="string" resultClass="category">

          SELEC PRODUCTID, NAME, DESCRIPTION, CATEGORY

          FROM PRODUCT

          WHERE CATEGORY = #categoryId#

</select>

 

  SQL이 XML 요소로 둘러싸여 있다. 이것이 SQL을 캡슐화한 것으로 단순한 <select>요소가 SQL 구문의 이름과 파라미터 입력 타입과 결과 출력 타입을 정의하고 있다. SQL을 외부로 빼고 캡슐화함으로써 간결함과 일관성을 모두 이루어냈다.

posted by 방랑군 2012. 1. 13. 01:07


참조 : http://msdn.microsoft.com/ko-kr/library/ms228112.aspx

'PP > SPRING.NET' 카테고리의 다른 글

Spring .Net 활용 가이드  (0) 2012.01.12
DI  (0) 2012.01.10
서론.  (0) 2012.01.10
posted by 방랑군 2012. 1. 12. 20:06



Spring .Net 프레임워크 활용 가이드입니다

  • 애플리케이션 프레임워크
  • Spring.NET 프레임워크
  • IoC 컨테이너와 DI
  • AOP (Aspect-Oriented Programming)

좋은 자료들을 틈나는대로 업데이트 할 예정입니다

많은 관심 부탁드립니다^^

'PP > SPRING.NET' 카테고리의 다른 글

일반 구성 설정(ASP.NET)  (0) 2012.01.13
DI  (0) 2012.01.10
서론.  (0) 2012.01.10
posted by 방랑군 2012. 1. 10. 03:15

안녕하세요. 코난 김대우 입니다.

이 개발 프레임워크 관련 내용은 http://kingcrap.com 블로그 장현춘님의 허락을 받고 가져온 글이며, 모든 저작권은 장현춘님께 있습니다. 
원본 출처 : http://kingcrap.com/entry/Framework-based-Development-오픈-소스-적용-사례

 

 

 

지난 시간에는 프레임웍 기반 개발이란 어떤 의미가 있으며 이때 사용할 수 있는 범용 개발 프레임웍은 어떤 것들이 시장에 나와 있는지에 대해 살펴보았다.

 

Framework-based Development – 개념 
Framework-based Development – 적용 
Framework-based Development – 종류 
Framework-based Development - 오픈 소스 적용 사례

 

이번 시간에는 주제를 좁혀서 범용 개발 프레임웍 중에서 닷넷 개발자 생태계 내에서 성장하고 발전해가는 오픈 소스 프레임웍의 적용 사례를 살펴보고자 한다. 오픈 소스 프레임웍들을 실제 적용하여 비지니스를 하고 있는 사례들을 살펴봄으로해서 닷넷 개발자 생태계의 건강성을 확인하고 닷넷 오픈 소스 프레임웍의 현재와 미래를 가늠해보는 시간이 되었으면 한다.

 

대부분의 SI 업체들은 SI 프로젝트에서 공통적으로 사용할 표준 개발 프레임웍이라는 것을 가지고 있는데, 대부분 오픈 소스 기반의 범용 프레임웍들을 조합하여 기본적인 기능을 제공하고 이를 기반으로 자사가 가지고 있는 도메인 특화된 노하우를 올리거나 일반 범용 프로임웍이 제공하지 못하는 모니터링이나 툴 최적화 기능 등을 묶어 제공하는 경우가 일반적이다. 아래 그림에서 보듯이 범용 프레임웍들의 조합을 통해 시장에서 입증된 QoS (품질요소)를 제공하고 그 기반위에 고객에게 전달할 가치를 부가적으로 제공하게 된다. 고객에게 전달할 가치가 범용 프레임웍만으로 끝난다면, 이것만 가지고 고객에게 어필(별도의 비용 청구 등)할 수 없을 것이다. 혹은 특정 회사가 개발하여 제공하는 프레임웍이라는 것이 시장의 범용 프레임웍들의 조합만으로도 제공할 수 있는 가치를 전달한다면 고객에게 외면 받을 것은 자명하다.

 

clip_image001_c2817416-14d2-4e0f-94bc-53c5ddef6b13.png

 

국내외를 막론하고 기업이 오픈 소스 기반의 프레임웍을 사용한 경우 일반적으로 그 사실을 외부에 알리는 것을 꺼려하는 경우가 있다. 이런 이유로 Spring.NET의 해외 적용 사례를 보더라도 유럽의 굴지의 온라인 여행사라든가, 어떤 도메인의 유명한 기업 정도만 밝히는 경우가 허다하다. 국내에도 마찬가지여서 외부로 드러나는 적용사례는 극히 드물다. 오늘 소개할 사례를 이전 DevDays 2008과 Open & Interop Day에서 적용 사례 발표를 했던 기업들이다.

 

아래는 이랜드 시스템의 표준 개발 프레임웍에 적용되어 있는 오픈 소스 프레임웍에 대한 내용이며, 황용호 팀장께서 발표하신 슬라이드에서 가져왔다. 이랜드 시스템의 Formular#은 Spring.NET + NHibernate의 조합을 통해 기본 기능을 제공하고 비지니스 특성상 북경 개발 센터와의 원활한 협업을 위해 사용되는 툴들에 대한 add-on 모듈이라든지, 테스팅 자동화와 같은 기능을 제공하고 있다.

 

clip_image002_e70f020d-4f20-4d06-aef8-756326b48961.png

 

예스24에서는 iBATIS.net을 현재 운영 중인 쇼핑몰에 적용한 사례를 최만석 팀장께서 발표하였으며 아래는 그 일부이다.

 

clip_image003_b1d95859-6b74-4086-958a-db9cf23d6b44.png

 

SK C&C에서는 개발 프레임웍인 NEXCORE.NET에 적용된 오픈 소스 프레임웍에 대해 설명을 하셨으며 아래는 이진우 대리께서 발표한 자료에서 발췌했다. NEXCORE.NET은 ASP.NET MVC + Spring.NET + iBATIS.NET 혹은 Entity Framework 등으로 구성되어 있으며 Visual Studio에 통합된 자동화가 인상 깊은 프레임웍이다.

 

clip_image004_bac7af48-1151-41ed-a3ad-9a1cdb315909.png

위에서 언급된 세가지 사례는 발표 자료와 함께 동영상 자료가 DevDays 2008에 게시되어 있으므로 좀 더 상세한 내용을 원하시는 분은 DevDays 2008 싸이트를 참고하시길...

 

그 밖에도 국내 또 다른 SI 업체의 개발 프레임웍에 ASP.NET MVC가 사용되고 있으며, 닷넷 솔루션 파트너사의 일부 솔루션에도 NHibernate가 사용되고 있음을 확인할 수 있었다.

 

마지막으로, 오픈 소스 프레임웍들을 적용하여 사업을 할 경우에 이들에 강제하고 있는 라이선스 정책에 대해서도 관심을 가질 필요가 있다. 오픈 소스는 곧 무료이기에 내 맘대로 가져다 고쳐 쓰면 되지..라는 잘못된 생각에 빠져 마냥 가져다 쓰다가 저작권 위반으로 소송으로 가는 경우가 심심찮게 보고되고 있다. 위에서 언급된 것들 중 가장 많이 사용되는 프레임웍의 라이선스 정책을 보면, Spring.NET과 iBATIS.NET이 Apache License 2.0을 채택하고 있으며, NHibernate가 LGPL을 채택하고 있다. 즉, 이것들 모두 상용 제품 만드는데 사용할 수 있으나 NHibernate가 채택한 LGPL의 경우에는 좀 더 엄격하여, 가져다가 소스를 수정했으면 NHibernate 관련 부분의 소스를 공개하여야 하는 제약이 있다. 물론 이 보다 더 엄격하여 GPL의 경우, 오픈 소스 소프트웨어를 가져다 쓰면, 이와 링크 형태로 엮일 지라도 메모리 상의 영역을 함께 쓰는 모든 소프트웨어의 소스 코드 전부를 공개해야하며 상용 소프트웨어와의 결합을 금지하고 있다. 다만, 이 경우에도 배포만 하지 않고 웹 싸이트에서 서비스 형태로 제공된다면 설령 GPL일 지라도 공개할 의무는 없다.

각종 오픈 소스 소프트웨어의 라이선스 정책에 대한 간단한 설명과 비교자료를 원하시는 분은 예전 정통부와 컴퓨터프로그램보호위원회가 함께 펴 낸 오픈 소스 SW 라이선스 가이드를 참고하시길...

 

아울러 알려지지 않았지만, 시장에서 오픈 소스 프레임웍을 적용하여 프로젝트가 진행되었거나 진행되고 있는 곳이 있다면 가능한 선에서 그 정보를 댓글이나 메일을 통해 공유하여, 오픈 소스를 적용하고자하나 용기가 없어 주저하고 계신 분들께 힘을 실어주시길....

 

[참고링크]

Framework-based Development - 개념

Framework-based Development - 적용

Framework-based Development - 종류

Framework-based Development - 오픈 소스 적용 사례

'PP > Framework' 카테고리의 다른 글

Framework-based Development - 종류  (0) 2012.01.10
Framework-based Development - 적용  (0) 2012.01.10
Framework-based Development - 개념  (0) 2012.01.10
닷넷 관련 개발 프레임워크  (0) 2012.01.10
자료들..  (0) 2012.01.04
posted by 방랑군 2012. 1. 10. 03:14

지난 포스팅에서는 프레임웍 기반 개발이란 무엇인가 살펴보고, 닷넷 개발 생태계 측면에서 오픈 소스 기반의 프레임웍이 제공하는 가치에 대해 알아 보았다. 또한 이후 포스팅에서는 프레임웍 기반 개발의 장점과 적용시 유의사항에 대해 살펴보았다.

Framework-based Development – 개념
Framework-based Development – 적용
Framework-based Development – 종류
Framework-based Development - 오픈 소스 적용 사례

이번 시간에는 프레임웍 기반 개발시 적용할 수 있는 오픈 및 오픈 소스 프레임웍들에는 어떠한 것들이 있는지 살펴보기로 한다.

통상적인 웹 기반 애플리케이션을 개발할 경우 Presentation-Business-Data Tier라는, 일반적으로 얘기하는 3 Tier 아키텍처를 갖게 되는데, 각 Tier에서 사용할 수 있는 범용 개발 프레임웍으로는 아래와 같은 것들이 있다. (필자는 logical은 layer, physical은 tier라는 구분을 좋아하지 않는다. 인접하는 컴포넌트 사이에 수평적으로 서비스를 제공하고 주고 받는 사이를 tier, 한 tier내에서 수직적인 구조를 layer라고 구분하는 것을 좋아한다.)

전통적으로 프리젠테이션 티어 구현 기술로는 ASP.NET이 있었고 이는 널리 알려진 바대로 Page Controller를 구현한 일종의 MVC 프레임웍이다. 프리젠테이션 티어의 가장 큰 관심사는 사용자의 요구를 어떻게 효과적으로 처리할 것인가에 관한 것으로 MVC가 그 핵심이다. 엔터프라이즈 솔루션 아키텍처 디자인 패턴이라는 p&p가 제공하는 가이드에 Page Controller의 최상위 클래스가 복잡한 분기문으로 가득차게 되면 Front Controller를 고민하라고 했듯이, 일반적으로 Front Controller는 Page Controller 보다 좀더 복잡한 애플리케이션 구축에 활용하는 패턴이다. Front Controller 패턴으로 구현한 ASP.NET 기반의 MVC 프레임웍이 바로 ASP.NET MVC 프레임웍이며 현재 베타상태이다. ASP.NET MVC 이전에 시장에는 Castle Project에서 오픈 소스 기반으로 MonoRail을 만들어 배포하고 있었으며, 자바에서 포팅된 Maverick.NET이라는 것도 있었다. 그외 MVC의 View 부분을 치환할 수 있는 다양한 엔진들이 등장하였는데, 그 중에는 자바 template engine인 Velocity의 닷넷 버전인 NVelocity, MonoRail을 위한 View Engine인 Brail, Rails의 view engine으로 널리 쓰이는 Haml의 닷넷 버전인 NHaml 등이 있다. 향후 프리젠테이션 티어의 구현 기술로 가장 주목을 받을 것은 ASP.NET MVC임에는 이론의 여지가 없어 보인다.

비지니스 티어의 가장 큰 관심사는 객체 라이프싸이클 관리이다. 사용자의 요구에 대해서 비지니스 도메인을 구현한 객체들을 얼마나 효과적으로 생성하고 관리하며, 프레임웍과 도메인 구현 엔티티 사이의 의존성을 줄여 향후 유지보수 측면에서 IT 부서의 부담을 줄여 줄 수 있는지가 관심사이며 여기에 핵심 키워드는 Dependency Injection, AOP 라 볼 수 있다. 전통적으로 일반 닷넷 객체 (PONO – Plain Old NET Object)로 원하는 비지니스 기능을 구현했으며 이때는 닷넷 프레임웍이 제공하는 기본적인 객체 생성 및 GC 매커니즘에 의존하고 개발자의 스킬에 의해 메모리 관리 등을 처리하였다. 하지만, 근래에 DI 기능을 기본으로 탑재한 컨테이너들이 수도 없이 출현하였고 가장 대표적인 것들이 위 그림에 나와 있다. Unity는 마이크로소프트 P&P 팀이 제공하는 것으로 Enterprise Library의 객체 라이프싸이클 관리 기능을 제공하는 ObjectBuilder의 Wrapper 클래스들로 구현되어 있으며 현재 Silverlight 지원하는 버전까지 제공되고 있다. 그 밖에 자바 진영의 대표적인 DI 컨테이너인 Spring이 포팅된 Spring.NET이 많은 개발자의 관심을 끌고 있으며 실제로 국내외 닷넷 프로젝트에 적극 활용되고 있다. DI 기본 기능에 프리젠테이션 티어와 데이타 티어의 각종 프레임웍에 대한 편리한 Wrapper 기능을 제공하는 것으로 정평이 나 있다. StructureMap은 Jeremy D. Miller가  만들어 유지보수하고 있으며 닷넷 진영의 가장 오래된 DI 컨테이너이다. Windsor 컨테이너는 Castle Project의 산물이며, NInject는 빠른 DI 기능 제공을 내세우며 근래에 등장한 컨테이너로서 실버라이트 및 .NET Compact Framework 지원 버전까지 제공한다. 많은 비지니스 티어 관련 프레임웍 중에서 전 세계적으로 가장 많이 사용되고 있는 것은 StructureMap으로 알려져 있으나 향후에는 Unity 아니면 Spring.NET이 대세가 되지 않을까하고 조심스럽게 점쳐 본다. 이유는 Enterprise Library의 DI 기능은 위에서 언급된 DI 컨테이너들 거의 모두를 사용하여 제공될 수 있으나 기본적으로는 Unity가 포함되어 있다. 따라서 이전부터 Enterprise Library를 써 오면서 ObjectBuilder에 익숙한 사람들은 많은 고민없이 Unity를 선택할 것으로 판단된다. Unity (Objectbuilder)는 시장에서 어느 정도 검증되었고 피드백도 좋다. Spring.NET은 자바 진영의 de-facto standard DI 컨테이너이며 이의 명성을 바탕으로 닷넷 진영에서도 빠르게 세를 넓히고 있다.

데이터 티어는 기본적으로 ORM (Object-Relational Mapping)을 제공하며 이 티어에는 Object와 RDB 사이의 Impedence Mismatch를 해결하는 다양한 기술들이 제공되고 있다. 전통적으로는 ADO.NET API를 사용하여 DAO 패턴을 적용하여 ORM을 처리하였고 지금도 가장 많이 쓰이고 있는 방식이 아닐까 생각된다. .NET Framework 3.5부터 등장한 LINQ (to SQL, Entity, Object, XML)는 개발자들로 하여금 SQL에 대한 두려움을 어느 정도 상쇄시켜 줄 수 있는 획기적인 DSL 방식의 해결책이다. Entity Framework은 마이크로소프트가 내놓은 진정한 의미의 ORM이라고 할 수 있으며 객체와 데이터베이스 테이블 사이의 다대다 매핑을 지원하며 둘 사이에 의존성을 갖지 않고 독자적으로 변경을 가할 수 있도록 고안된 추상화 레벨을 한 단계 끌어올린 ORM이다. NHibernate와 iBATIS.net은 자바 진영의 ORM 시장을 양분하고 있는 오픈 소스 기반의 대표적인 ORM 툴이며 이것들의 닷넷 버전이다. NHibernate와 iBATIS.net은 현재 국내외 프로젝트에서 주목을 받으며 적용된 사례가 있으며, 각각 고유한 장점이 있기에 적용하고자 하는 필요에 가장 잘 부합하는 것을 선택하는 것이 필요하다. SubSonic은 Rob Coney가 만든 오픈 소스 ORM으로 Rails의 scaffolding 기능까지 제공하고 있다. 또한 SubSonic은 .NET Framework 3.5 SP1에서 제공되는 ASP.NET Dynamic Data에 Scaffolding 기능을 제공하며 .NET Framework에 포함되었다. 하지만 여전히 SubSonic은 오픈 소스로 제공되고 있다. ActiveRecord는 역시 Castle Project의 ORM 관련 산물이다. ORM  툴들은 여기 예시된 것 이외에 상용을 포함하여 훨씬 많은 것들이 시장에 나와 있으며, 이 많은 프레임웍 중에서 LINQ, NHibernate, iBATIS.NET이 가장 주목을 많이 받을 것으로 기대된다. LINQ to NHibernate도 이미 시장에 나와 있듯이 핵심 기능은 NHibernate나 iBATIS.net을 쓰되 개발자 인터페이스 부분은 LINQ가 담당할 가능성도 있다.

참고로, Castle Project를 진행했던 Hamilton Verissimo와 SubSonic을 만든 Rob Conery 모두 마이크로소프트 직원이 되었지만, 현재 이들은 여전히 오픈 소스 프레임웍 개발에 전념하고 있다.

정리하면 다음과 같은 조합이 가장 현실적인 대안이 되지 않을까 한다. 
ASP.NET MVC + { Unity, Spring.NET } + { LINQ, NHibernate, iBATIS.net }

이들 프레임웍들은 서로의 존재를 모르고 시장에 나온 경우가 많다. 따라서 이들 프레임웍들을 효과적으로 연동하기 위한 약간의 수고 필요한데, 대부분의 경우 특히 유명한 프레임웍들은 서로에 대해 연동하는 Wrapper를 자체적으로 제공하거나 MVCContrib과 같이 별도의 프로젝트에서 인접 티어의 프레임웍 연동 기능을 제공하고 있다. 예를 들면, MVCContrib은 ASP.NET MVC와 인접한 다양한 DI 컨테이너들 즉, Unity, Spring.NET, Windsor 등에 대한 연동 모듈을 제공하고 있으며, Spring.NET 자체적으로는 NHibernate에 대한 Wrapper를 제공하고 있다.

시장에서 가장 많이 사용하는 범용 프레임웍들을 조합하여 하나의 예로서 Billy McCafferty가 제시하는 것으로 Sharp Architecture가 있다.

그림에서 보듯이 Billy는 다양한 시도를 진행했다. 처음에 ASP.NET MVC + Spring.NET + NHibernate의 조합을 제시했다가 DI 기능만을 위해 Spring.NET을 쓰는 것이 비효율적이라 생각되어 Spring.NET을 빼고 DI 기능을 손수 PONO 형태로 구현했었다. 이후 NInject라는 가벼운 DI 컨테이너를 다시 도입한 빌드를 선보였고, 근래에는 NInject 대신에 Windsor 컨테이너를 조합한 빌드를 제시하고 있다. 따라서 Sharp Architecture 싸이트에 가보면 다양한 조합의 빌드를 다운받아 테스트해 볼 수 있다.

여기에서 언급된 다양한 프레임웍 및 관련 자료에 대한 링크는 다음과 같다.

마이크로소프트 제공

Patterns & Practices

http://www.microsoft.com/practices

CodePlex

http://www.codeplex.com

ASP.NET MVC

http://www.asp.net/mvc

ASP.NET MVC Contrib

http://www.codeplex.com/MVCContrib

Scott Guthrie Blog

http://weblogs.asp.net/scottgu/

Unity Application Block

http://www.codeplex.com/unity

Enterprise Library

http://www.codeplex.com/entlib

 오픈 소스 프레임워크

Sharp Architecture

http://code.google.com/p/sharp-architecture/

Castle Project (MonoRail, Windsor, ActiveRecord)

http://www.castleproject.org/

Ninject (DI)

http://ninject.org

Spring.NET (DI)

http://springframework.net

StructureMap (DI)

http://structuremap.sourceforge.net/Default.htm

S2Container.NET (DI)

http://s2container.net.seasar.org/en/index.html

autofac (DI)

http://code.google.com/p/autofac/

compactcontainer (DI for compact framework)

http://code.google.com/p/compactcontainer/

LinFu (DI)

http://code.google.com/p/linfu/

NHibernate (ORM)

http://www.hibernate.org/343.html

iBATIS.NET (ORM)

http://ibatis.apache.org/

SubSonic (ORM)

http://subsonicproject.com

'PP > Framework' 카테고리의 다른 글

Framework-based Development - 오픈 소스 적용 사례  (0) 2012.01.10
Framework-based Development - 적용  (0) 2012.01.10
Framework-based Development - 개념  (0) 2012.01.10
닷넷 관련 개발 프레임워크  (0) 2012.01.10
자료들..  (0) 2012.01.04
posted by 방랑군 2012. 1. 10. 03:13

안녕하세요. 코난 김대우 입니다.

이 개발 프레임워크 관련 내용은 http://kingcrap.com 블로그 장현춘님의 허락을 받고 가져온 글이며, 모든 저작권은 장현춘님께 있습니다. 
원본 출처 : http://kingcrap.com/entry/Framework-based-Development-적용


    
지난 포스팅에서는 프레임웍 기반 개발이라는 것이 개발자 영역에서의 자연스런 진화의 산물이며, 시장에 널려 있는 수많은 프레임웍 가운데 자사의 현실에 적합한 프레임웍들의 조합을 통해 프로젝트 전체를 관통하는 뼈대를 만들어 좀 더 나은 애플리케이션을 만드는 기법임을 알 수 있었다. 또한 이때 조합의 대상이 될 즉, candidate 프레임웍들로는 가급적 닷넷 개발 생태계의 산물인 오픈 프레임웍을 선정함이 바람직함을 얘기한 바 있다.

 

Framework-based Development – 개념 
Framework-based Development – 적용 
Framework-based Development – 종류 
Framework-based Development - 오픈 소스 적용 사례

 

이번 시간에는 프레임웍 기반 개발이라는 것이 일반적으로 어떠한 장점이 있는지, 그러한 것을 적용할 때 어떤 방법을 쓰는 것이 좋은지 살펴보도록 하자.

 

개발 프레임웍을 프로젝트에 도입하는 순간 기본적으로 프로젝트의 복잡성은 증가한다. 낯선 프레임웍에 대한 두려움과 새롭게 배워야하는 부담이 개발자들을 짓누르기도 한다. 라이브러리성 프레임웍의 경우 단순히 사용 방식을 익혀야 하는 수고가 더 든다는 정도에 그칠 수 있지만, 개발 프레임웍 즉, 애플리케이션의 컨트롤을 좌우하는 소위 Dependency Injection 등을 제공하는 컨테이너 형태의 프레임웍을 도입하게 되면 문제는 훨씬 복잡한 양상을 띈다. 늘 익숙한 방식의 직접 호출이 아닌 중간에 프레임웍이 위치하여 간접 호출이 일어난다는 것은 기본이고, 라이브러리를 사용할 경우 내가 주체가 되어 예측가능한 시간에 객체를 생성하고 예측가능한 방식으로 객체의 라이프싸이클을 관리할 수 있는 것과는 달리, DI 기능의 프레임웍을 도입할 경우 주객이 전도된다. 이것을 Inversion of Control이라고 부른다. 즉, 일단 DI 컨테이너로 넘어간 컨트롤은 내가 짠 코드와 무관하게 잘 짜여진 프레임웍의 규칙에 의거하여 진행하며 내가 짠 코드는 프레임웍이 정한 룰에 의해 필요시 불리어 객체가 생성되고 관리되며 소멸된다. 흔히 말하는 라이브러리성 프레임웍이 아닌 개발 프레임웍들을 도입하게 되면 일정정도 Inversion of Control이 일어나게 된다. 이 또한 처음 프레임웍을 접할 때 익숙치 않은 경험이 되며 직관적이지 않고 수많은 설정과 장치들을 파악하는 수고들이 번거롭게 느껴지기도 한다. 이렇듯 언뜻 보기에 프로젝트의 복잡성을 증가시키고 참여 인력들에게 낯선 것에 대한 두려움과 학습의 번거로움을 선사하는 프레임웍을 도입하면 어떠한 장점이 있을까 ?

 

clip_image001_98a7a532-42e5-4a33-8d9e-498de0cf28d8.png

오픈 프레임웍의 경우 시장에서 수많은 프로젝트라는 담금질을 거치면서 scalability, managebility, maintainability, performance 등등의 비기능적 요구사항들은 일정수준 이상의 수준에 도달하게 되고, 프레임웍이 제공하는 정형화된 호출 패턴을 준수하게 되어 코드가 일관성 있게 작성 유지되는 장점이 있다. 또한 프로젝트 규모가 커질수록 참여하는 조직이 다양해지고 참여 인력의 기술 수준 또한 다양할 수 밖에 없는데, 이처럼 다양한 수준의 개발자들에게 각종 품질 요소와 관련된 것들을 맡기는 것이 아니라 대부분을 프레임웍에게 맡겨 처리하게 함으로써 일정 수준 이상의 품질을 보장할 수 있게 된다. 반제품화된 프레임웍의 특성상 개발 기간 및 비용을 절감할 수 있으며, 참여 인력의 만족도 또한 증가하게 된다. 언뜻 이해되지 않는 대목일 수도 있으나 처음 프레임웍을 접하고 낯설었지만 개발에 적용하면서 익숙해져 결국 프로젝트가 끝날 무렵에는 이 큰 프로젝트에 시장에서 de-facto standard로 받아들여지는 프레임웍을 적용하여 개발했다는 자신감을 갖게되며, 또한 개인 이력서에도 멋지게 한 줄 올릴 수 있다. 닷넷에서는 아직 낯선 풍경이겠으나 자바 진영의 구인란을 보면 예를 들어, Struts+Spring+Hibernate 경험자 우대 등의 구체적인 프레임웍 경험을 중시하는 구인 광고를 흔히 볼 수 있다.

 

잠시 쉬어가는 코너로 오픈 프레임웍에 대해 거부감이 있는 독자를 위해 예전에 겪었던 경험을 잠시 써 보면... 
대략 4년 전쯤, 대법원이 국내 굴지의 SI 업체가 개발중이었던 시스템에 대해 Architecture Assessment를 한국 썬에 요청한 적이 있었다. 썬은 호주의 아키텍트 두 명과 국내 컨설턴트 두명(그중 하나 필자)을 파견하여 SI 업체가 개발 중인 시스템을 분석하고 참여자들과의 인터뷰를 통해 보고서를 제출하였다. 많은 지적 사항 가운데 프레임웍 관련된 부분만을 언급하면... 
SI 업체가 만들어 유지 보수하며 다년간 많은 프로젝트에서 사용하고 있는 자체 개발 프레임웍을 쓰지 말고 가급적 오픈 소스 기반의 프레임웍을 쓸 것을 추천하였다. 아이러니한 것은 그 당시 썬은 자사 상용 프레임웍인 Sun One Application Framework (“JATO”)를 팔고 있을 때였는데, 썬 직원이 아무런 주저없이 자사 솔루션이 아닌 오픈 소스 프레임웍을 추천하고 돌아간 것이다.....

 

시장에서 널리 쓰이는 프레임웍들을 조합하여 프로젝트의 전체 뼈대를 만들고자 할 경우 어떤 접근 방식을 취하는 것이 좋을까 ? 프로젝트가 시작되면 기본적으로 통합팀을 중심으로 각종 가이드가 만들어지고 참여 인력에 대한 각종 교육이 진행된다. 가령 단순하게는 naming convetion에서 방법론이라든지 신기술이라든지 적용할 프레임웍에 이르기까지... 
낯설지만 시장에서 각광받는 프레임웍들을 조합하여 진행할 때, 참여 인력 모두가 프레임웍에 대해 전문가가 될 필요는 없다. 아니 그럴 수도 없다. 많은 경우 함께 공부해가면서 책에 나와 있는 예제 중심으로 코드를 만드는데, 시일도 오래 걸리거니와 자칫 사소한(?) 것에 발목잡혀 낭패를 볼 수도 있다. 추천하는 것은 가급적 프로젝트 진행하는 팀 내에는 해당 프레임웍에 대한 전문가가 최소 한명이 있어야 한다. 이유는 프레임웍이라는 것이 개발 생태계에서 진화를 하면서 소위 “By Design”이라는 형태의 제약이나 의도된 설계가 있기 마련이다. 참여 인력 모두가 이런 것까지 학습할 시간적 여유가 없으며 누군가는 이러한 것들을 고려하여 개발자들이 사용할 가이드를 만들어 배포하여야 한다. 개발자에게 배포되는 가이드는 많은 것들을 고려하여 작성되었겠지만 실제 개발자에게 전달할 메시지는 아주 단순한 형태이어야 한다. 가령 개발 3단계, 첫째 맡고 있는 Use Case에서 추출한 명사로부터 대문자로 시작하는 클래스를 만들되 통합팀에서 배포한 BaseXXX를 상속받아 작성하고 둘째 반드시 XXX() 메소드를 오버라이드한다. 셋째 컴파일 한 후 특정 위치에 복사한 후 주어진 설정 파일에 등록하면 된다. 사용할 수 있는 소스 코드 탬플릿 양식과 샘플은 형상 관리 도구의 특정 branch에 있으니 참고하라는 식의... 물론 개발자들이 개발 과정에서의 갖게 되는 의문을 풀어주고 이해를 돕기위해 아키텍처 문서나 프레임웍 동작 원리 등을 제공하여 프로젝트를 거치면서 개발자들의 자연스런 성장을 돕는 것도 필요하다.

 

잠시 또 사례를 들면, 프레임웍에 대한 전문 인력이 없이 개발자들이 학습과 개발을 병행하며 프로젝트를 진행할때 발생했던 사례로써 역시 굴지의 국내 또 다른 SI 업체의 자바 솔루션 개발 경우이다.    
그룹사 전체에 특정 LOB 애플리케이션을 공급하는 SI 업체는 새 버전에 이전과 달리 Struts이라는 자바 진영의 그 당시 de-facto standard로 통했던, 현재에도 가장 많이 쓰이는 MVC 프레임웍이기도 한 프레임웍을 도입하기로 하고 참여 인력 내에서 책을 구입하여 개발과 학습을 병행하였는데, 아키텍처 자문을 해주는 과정에서 한가지 단순하지만 중요한 실수를 발견할 수 있었다. Struts이 관리(?)되고 있는 Apache 재단의 홈페이지에도 나와 있는 아주 단순한 원칙, “Action” 클래스는 같은 URI 요청에 대해 singleton으로 동작한다는 사실을 모르고 클래스를 작성하였던 것이다. 하여 개인이 테스트 할때는 별 탈이 없었지만 동시에 요청이 들어오면 thread-safe하지 않은 행동을 보이고 있었던 것.... Struts의 히스토리를 보면 원래는 singleton이 아니었는데 중간에 왜 singleton으로 바꾸게 되었는지 설명해 놓은 대목이 있다. 이런 것을 모든 개발자가 알 필요는 없지만 최소한 한 사람 누군가는 알고 이를 고려한 가이드나 설계가 제시되고 이를 통해 쓸데없이 시간과 정력이 낭비되는 것을 막아야 한다.

 

이런 유사한 사례는 신기술 혹은 새로운 프레임웍을 적용할 경우 흔히 볼 수 있다. 
다음 시간에는 현재 닷넷 개발 생태계내에서 만들어지고 발전되어 가고 있는 오픈 프레임웍들을 살펴보고 어떠한 것들이 시장에서 각광을 받고 있는지 함께 알아보는 시간이 되었으면 한다.

 

clip_image002_f4c091c4-816c-4caf-bda4-f38c530cb7b1.png

또한 참고로 예전 포스팅에서 정리했던 닷넷 개발 프레임웍 리스트를 보는 것도 도움이 될 것으로 생각한다.

 

[참고링크]

Framework-based Development - 개념

Framework-based Development - 적용

Framework-based Development - 종류

Framework-based Development - 오픈 소스 적용 사례

 


'PP > Framework' 카테고리의 다른 글

Framework-based Development - 오픈 소스 적용 사례  (0) 2012.01.10
Framework-based Development - 종류  (0) 2012.01.10
Framework-based Development - 개념  (0) 2012.01.10
닷넷 관련 개발 프레임워크  (0) 2012.01.10
자료들..  (0) 2012.01.04
posted by 방랑군 2012. 1. 10. 03:09

출처 :   http://www.sqler.com/bDevelopmentFramework/375059 

안녕하세요. 코난 김대우 입니다.

이 개발 프레임워크 관련 내용은 http://kingcrap.com 블로그 장현춘님의 허락을 받고 가져온 글이며, 모든 저작권은 장현춘님께 있습니다. 
원본 출처 : http://kingcrap.com/entry/Framework-based-Development 

 

 

프레임웍 기반 개발이라는 것은 말 그대로 엔터프라이즈 애플리케이션을 개발함에 있어서 기존에 만들어진 프레임웍의 조합을 통해 좀 더 빼르고 견고하게 원하는 결과물을 만들어 내는 것을 말하며, 이는 어느 특정 벤더의 개발 방법론도 아니고 개발 영역에서 자연스럽게 발전하여 체득된 개발 방식이다. SI 경험이 많은 대부분의 기업에게는 기업용 애플리케이션 개발에 있어서 경험으로 부터 다듬어져 프레임웍의 형태를 띄는 것들을 가지고 있다. 추상화 혹은 모듈화 정도의 차이가 있을 뿐, 혹은 대외적으로 홍보하는 이름이 있고 없을 뿐 대부분의 개발이 프레임웍 기반으로 진행되고 있다고 봐도 무방하다.

 

향후 몇 번에 걸쳐 프레임웍 기반 개발에 대해 살펴보기로 하자

Framework-based Development – 개념 
Framework-based Development – 적용 
Framework-based Development – 종류 
Framework-based Development - 오픈 소스 적용 사례

 

clip_image001_473d7c64-904a-4ce9-85ee-1d6a9b41885b.png

이처럼 많은 개발사 혹은 개발자들이 경험으로부터 선호하게 되는 프레임웍이라 것은 선조 프로그래머들의 지혜를 재활용하는 많은 방법 중에서 가장 개발자에게 직관적이고 현실적인 재사용 수단이다. 즉, 남들이 만들어 시장에서 다양한 곳에 적용되어 능력을 검증 받은 코드셋을 가져다 내 환경에, 나의 프로젝트에 맞게 약간의 변형을 가하고 설정을 변경하여 재사용할 수 있는 잘 만들어진 클래스 집합인 것이다. 프레임웍을 분류하는 방식은 프레임웍의 정의만큼이나 다양하나 일반적으로 블랙 박스 vs 화이트 박스 혹은 라이브러리성 vs 개발 프레임웍(컨트롤) 혹은 아주 간단하고 자주 쓰이는 오픈 (오픈 소스) vs 상용 프레임웍 등이 있다.

 

프레임웍 기반 개발이라는 것은 상용이든 오픈이든 용도에 맞는 가장 적절한 프레임웍들의 조합을 통해 전체 프로젝트를 관통하여 사용될 뼈대를 완성하고 개발자들로 하여금 비지니스 로직을 구현하여 이 뼈대가 제시하는 Contract에 맞게끔 개발하도록 만드는 정형화된 개발 방식이다. 이렇게 시장에서 검증된 프레임웍들의 조합을 통해 자연스럽게 흔히 얘기하는 비기능적 요구사항 (소위 QoS 요소)들을 달성하고 개발자들은 주어진 도메인에 집중하여 고객에게 전달할 가치 (기능적 요구 사항 포함)를 창출하도록 만드는 것이다. 이를 통해 개발자들의 창의성과 생산성을 기반 프레임웍 개발에 쓰여 낭비하지 않도록 하며 좀 더 나은 고객 가치를 전달하는데 사용케하자는 것이다.

 

여기서 생각해 볼 문제는 과연 어떤 프레임웍들을 조합의 대상으로 삼을 것인가 하는 점이다. 이 점에서 많은 부분 동의하지 못하는 분들도 있을 것 같은데, 필자는 가급적 오픈 (혹은 오픈 소스) 기반의 범용 개발 프레임웍들을 조합하길 권장하는 바이다. 흔히 말하는 범용 개발 프레임웍은 말 그대로 도메인에 특화된 로직을 품고 있지 않아서 대부분의 프로젝트에 쓰일 수 있는 기본 기능을 담고 있는 것들이다.

가령 로깅, 에러 처리등의 라이브러리들을 포함하여 객체 라이프 싸이클 관리, 모니터링 혹은 다른 레이어와의 인터페이스 모듈 등등 모든 프로젝트에서 항상 고민하는 것들이 포함된다. 세상에는 이미 나 혹은 내가 속한 팀, 더 나아가 우리 회사가 만들어 자랑스럽게 내세우는 프레임웍 보다 더 훨씬 더 잘 만들어 공개되어 우리 회사가 10년 아니 우리 회사가 망할때 까지 수행해도 다 못할 만큼의 전세계 수많은 프로젝트에서 다양한 환경에서 검증되어 발전해가는 즉, 닷넷의 개발 생태계 내에서 태어나 성장하는 뛰어난 범용 개발 프레임웍들이 널려 있다. 이제는 이러한 것들을 함께 공유하고 이러한 개발 생태계내에 우리도 일원으로 참여하여 생태계를 키우고 그로 인한 열매를 함께 향유하는 것이 필요하다.

 

오해하지 말 것은 필자가 범용 개발 프레임웍이라고 칭하는 부분이다. 도메인에 특화된 비지니스 프레임웍들을 여전히 상용으로 판매되고 있다. 가령 금융 패키지 혹은 코어 뱅킹, 제조 패키지 등등 도메인에 특화되어 있기에 닷넷에 대한 개발 노하우가 있다고 누구나 만들 수 있는 것도 아니며 도메인 지식이 풍부해야 진입할 수 있는 영역이기에 개발 생태계가 관장하기에는 아직 닷넷 개발 생태계가 성장하기 못한 면이 있다. 하지만 마음만 먹으면 누구나 만들 수 있는 범용 개발 프레임웍은 사정이 다르다. 전세계가 유사한 기능을 하는 비슷비슷한 프레임웍이 나타나는 이유는 간단하다. “난 쟤들 거 이런 이런 점이 맘에 안들어...” 이거다. 이렇게 만들어진 것이 대중의 사랑을 받게 되면 개발 프레임웍에 있어 de-facto standard로 자리잡아 칭송을 받게 되는 것이다.

 

고객이 입장에서 보면 오픈을 써야하는 이유는 더 극명하다. 벤더 종속적인 프레임웍을 도입하였을 경우 기반이 되는 .NET의 발전에 맞추어 유지보수해야 하는 문제며, 소스 코드를 포함한 소유권 문제 등도 있고, 프레임웍 개발사가 증명할 수 있는 각종 QoS 수준과 전세계 닷넷 개발 생태계가 증명할 수 있는 수준과의 신뢰성 등 고객은 이미 오픈 혹은 오픈 소스에 대해 많은 것을 알고 있다. 개발자들의 자유로운 접근과 사용, 그리고 그 과정에서 주고 받는 Q&A 및 피드백을 통해 오픈 프레임웍은 자연스럽게 생태계속에 편입되어 발전하게 되는 것이다.

 

다음 시간에는 현재 우리가 사용할 수 있는 프레임웍들에는 어떤 것이 있고 어떤 점을 고려하여 선정하여야 하는지 더 나아가 적용할 때 고민해야 할 부분등에 대해 함께 알아보도록 하자.

 

clip_image002_4b15f2f2-fd45-40a1-b9f7-146ed7230ce0.png

 

 

[참고링크] 

Framework-based Development - 개념

Framework-based Development - 적용

Framework-based Development - 종류

Framework-based Development - 오픈 소스 적용 사례

  

'PP > Framework' 카테고리의 다른 글

Framework-based Development - 종류  (0) 2012.01.10
Framework-based Development - 적용  (0) 2012.01.10
닷넷 관련 개발 프레임워크  (0) 2012.01.10
자료들..  (0) 2012.01.04
프레임워크를 이해하기 위한 패턴 언어  (0) 2012.01.04
posted by 방랑군 2012. 1. 10. 03:09

출처 :  http://www.sqler.com/bDevelopmentFramework/375007 

안녕하세요. 코난 김대우 입니다.

이 개발 프레임워크 관련 내용은 http://kingcrap.com 블로그 장현춘님의 허락을 받고 가져온 글이며, 모든 저작권은 장현춘님께 있습니다.
원본 출처 : http://kingcrap.com/entry/닷넷-관련-개발-프레임웍-Beta

일부 내용에 변경이 있는 부분은 명시 후 수정합니다.

 

 

 

닷넷 프로젝트에서 사용할 수 있는 프레임웍을 한눈에 볼 수 있도록 정리해보자 
프레임웍을 구분하는 방법은 여러가지이나 간단하게 티어별로 구분하도록 한다. 

프리젠테이션 티어 (웹) 
1. ASP.NET MVC - ASP.NET 기반의 MVC 프레임웍. 마이크로소프트 제공 
2. MonoRail - 오픈 소스 Castle 프로젝트에서 만든 Rail와 유사한 MVC 웹 프로임웍 
3. Maverick.NET - 자바 Maverick의 닷넷 버전으로 오픈 소스 MVC 웹 프레임웍, 업데이트 안됨 
4. DotNetNuke - 포털 프레임웍에 가까움. 오픈 소스 

비지니스 티어 (DI Container) 
1. Spring.NET - 오픈 소스. 자바 Spring의 닷넷 버전. 대표적인 DI Container. 
2. ObjectBuilder - Enterprise Library(EntLib)에 들어 있으며, EntLib, Composite UI Application Block 등에 사용된 DI Container 
3. Unity - Enterprise Library 4.0 버전에 사용될 DI Container로 ObjectBuilder 후속작. EL과 별개로 사용될 수 있도록 별도 프로젝트로 진행중이며 Codeplex에 현재 2008년 2월 CTP 공개. 
4. Windsor Container - 오픈 소스 Castle 프로젝트 일환 
5. StructureMap - 닷넷에서 가장 오래된 DI Container. Jeremy D. Miller가 만들고 유지보수하고 있는 오픈 소스 프레임웍
6. NInject - "Lightning-fast dependency injection for .net"을 표방한 오픈 소스 DI Container. 닷넷 프레임웍 3.5 및 Compact Framework 3.5 지원, Silverlight 지원 등이 특징

데이터 티어 
1. ADO.NET 
2. LINQ to SQL - .NET Framework 3.5 이상의 기본 기능(2011년 5월 현재 4.0). 엔티티와 테이블의 1:1 매핑. VS2008 이상 툴 지원 
3. ADO.NET Entity Framework (LINQ to Entity) 
4. NHibernate - 자바 Hibernate의 닷넷 버전. 오픈 소스 
5. iBatis.NET - 자바 iBatis의 닷넷 버전. 오픈 소스 
6. Active Record - 오픈 소스 Castle 프로젝트의 일환. Active Record 패턴을 구현. NHibernate 기반이나 Configuration을 XML이 아닌 Attribute을 이용 
7. LLBLGen Pro - 상용. 
8. WilsonORMapper - 상용. 
9. LightSpeed - 상용. 
10. Codus - 상용. 
11. Sooda - 폴란드에서 만든 오픈 소스 ORM 으로 폴란드에서는 구직시 도움되는 기술. 
12. SubSonic - 오픈 소스 ORM. ASP.NET 3.5 Extension에 포함된 ASP.NET Dynamic Data 기능 구현에 사용됨.
13. NConstruct - 상용 / 무료, NHibernate 용 코드 자동 생성(HBM, Entity 등), VS용 project 파일 생성 등

All-in-one
1. DotNetNuke - 복잡한 웹 싸이트 구축, CMS에 까깝다고 할 수 있음
2. Oxite - ASP.NET MVC를 사용, 블로그 엔진, Mix Online 싸이트 운영

기타 범용 프레임웍 (혹은 라이브러리) 
1. Enterprise Library - MS patterns and practices(PnP) 팀이 Codeplex를 통해 제공. 캐싱, 로깅, 암호화 등등 
2. NVelocity - 템플릿 엔진. 진전이 없어 Castle 프로젝트에서 별도 진행 
3. NUnit - 단위 테스트 
4. NAnt - 빌드 
5. log4net - 로깅 

6. CruiseControl.NET - 통합 빌드, ThoughtWorks에서 개발한 오픈 소스 

'PP > Framework' 카테고리의 다른 글

Framework-based Development - 적용  (0) 2012.01.10
Framework-based Development - 개념  (0) 2012.01.10
자료들..  (0) 2012.01.04
프레임워크를 이해하기 위한 패턴 언어  (0) 2012.01.04
프레임워크 리팩토링 정리  (0) 2012.01.04

DI

posted by 방랑군 2012. 1. 10. 00:06

spring.NET

스프링 닷넷은 자바 진영에서 매우 다양한 곳에서 쓰이고 있는 유명한 프레임워크 스프링의 닷넷 버전이다. 아래의 그림을 보면 알 수 있듯이 단순한 컨버젼이 아니라 스프링이 가지고 있는 개념을 닷넷에 가장 어울리도록 최적화한 것이라고 볼 수 있다.

springnet.png

여기서는 이런 다양한 스프링 닷넷 프레임워크 중 DI에 대해서 간략하게 알아보겠다.(이 부분은 코어에 소속된 부분이다. 즉 스프링의 다양한 개념 중에서도 매우 중요하며 기초적인 부분이다.)

DI

먼저 DI라는 개념을 먼저 파악해야 한다. DI는 Dependency Injection의 약자로서 번역하면 의존성 주입 정도가 된다. 간략하게 설명하자면 하나의 클래스에서 다른 클래스의 객체를 사용할 경우에 직접 객체를 생성해서 사용하지 않고 사전에 설정해 둔 바에 따라서 객체를 가져와 사용할 수 있게 한다는 개념이다.

이렇게 할 경우의 가장 큰 장점은 가져오는 객체의 구조나 생성방식이 바뀌더라도 설정파일을 바꾸는 것만으로 그에 무관하게 사용할 수 있다는 점이다.

아래의 간단한 예를 보면 쉽게 이해가 되리라 생각한다.


스프링 닷넷에서 DI의 사용

먼저 사전작업으로 Spring.Net 프레임워크를 다운받아 설치해두는 작업이 필요하다.(이는 스프링닷넷 프레임워크 사이트에서 다운받아 설치만 하면 되므로 생략)

그리고 Spring.Core 어셈블리 파일을 참조추가해둔다. 이로서 사전 작업은 끝

Program.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Spring.Context;
using Spring.Context.Support;

namespace SpringNET
{
class Program
{
static void Main(string[] args)
{
IApplicationContext ctx = ContextRegistry.GetContext();
Hello hello = (Hello)ctx.GetObject("MyHello");
string name = "lee";
string result = hello.SayHello(name);
Console.WriteLine(result);
Console.Read();
}
}
class Hello
{
public string SayHello(string name)
{
return "Hello!, " + name;
}
}
}


위와 같이 소스코드를 하나 작성한다. 다른 부분은 간단하므로 설명하지 않고 DI가 실제로 일어나는 붉은 색부분만 설명하면 첫번째 줄은 현재 어셈블리의 설정파일로 부터(아래에 작성해 볼 것이다.) 어플리케이션 컨텍스트를 가져온다. 둘째줄은 가져온 컨텍스트에서 MyHello라는 이름의 Object를 가져오도록 하는 것이다.

App.config

<?xml version="1.0" encoding="utf-8" ?>
<configuration>

<configSections>
<sectionGroup name="spring">
<section name="context" type="Spring.Context.Support.ContextHandler, Spring.Core" />
<section name="objects" type="Spring.Context.Support.DefaultSectionHandler, Spring.Core" />
</sectionGroup>
</configSections>

<spring>
<context>
<resource uri="config://spring/objects" />
</context>

<objects xmlns="http://www.springframework.net">

<object name="MyHello" type="SpringNET.Hello, SpringNET">
</object>
</objects>
</spring>
</configuration>


위의 파일은 해당 어셈블리의 설정파일과 같은 것이다. 여기에 스프링에 관한 설정도 넣을 수 있다.

다른 부분은 무시하고 핵심적인 부분만 설명하면 붉은 색의 코드 한 줄이 의존성 주입이 가능하도록 해주는 부분이다. 객체의 이름은 MyHello, 클래스형은 SpringNET.Hello이며 해당 객체가 들어있는 어셈블리의 이름은 SpringNET라는 이야기이다.

간단히 스프링 닷넷의 DI를 살펴보았다. 좀더 자세한 것은 스프링 닷넷의 다른 기능을 봐가며 살펴보도록 하겠다.


참고자료: spring-net-reference.pdf Spring.NET_guide_ensoa_v.0.2.pdf

'PP > SPRING.NET' 카테고리의 다른 글

일반 구성 설정(ASP.NET)  (0) 2012.01.13
Spring .Net 활용 가이드  (0) 2012.01.12
서론.  (0) 2012.01.10
posted by 방랑군 2012. 1. 10. 00:00
출처 :   http://dncblog.tistory.com/53 

Spring은 이미 오래전부터 자바진영에서 각광받고 있는 프레임웤으로서, 닷넷버전으로도 공개가 되었습니다. 
그것이 바로, Spring.NET인데요,   
Spring.NET은 닷넷기반의 엔터프라이즈 어플리케이션을 구축하기 위한 어플리케이션 프레임웤  이라고 정의할 수 있습니다. 



Spring.NET의 각 모듈의 구성을 보시면, 하단 우측의 AOP 기반으로, ASP.NET,  Web Serivce, ORMapping, DataAccess, NUnit, Remoting, COM+ 등의 다양한 코어 모듈 기반의 프레임웤입니다. 

AOP(Aspected Oriented Programming) 란  관점 지향 프로그래밍이라고 해석되는데요, 
이는, 프로젝트를 진행할때,  개발자가 고민해야하는 비지니스 로직을 핵심관심사라 보고, 그외의 인증/권한/예외처리/로깅/트랜젝션관리 등에 대한 것을 횡단관심사로 보아, 관심의 분리를 일컷습니다. 
이는, 개발자는 핵심관심사에 치중하며, 횡단관심사는 프레임웤의 각 컨테이너가 제공을 해주게 됩니다. 
그리고 각 컨테이너는 IOC(Inversion Of Control) 형태로 구성되어있는데요,  
기존에 개발방법론에서는 작성되어있는 프레임웤은 Library로서의 기능이 강했습니다. 
개발자는  비지니스 로직에 집중하면서,  횡단 관심사에 대한 호출이 필요한 경우에는 작성되어있는 프레잌웤 라이브러리를 호출해서 사용하였었지요. 
그러나, IOC 형태로 구성된 컨테이너 들은  프레잌웤 코드가 전체 어플리케이션의 처리흐름을 제어하며, 특정한 이벤트가 발생할 시마다 다형성을 통해, 어플리케이션이 확장한 메소드를 호출함으로서, 결과적으로는 제어가 프레임웤에서 어플리케이션으로 거꾸로 흐르게 되는 방법을 말합니다. 
그리고 객체가 참조하고 있는 다른 객체를 스스로가 new로 create하지 않고, 인터페이스를 통해서 Assing받아 사용하는 방식을 따르고 있습니다.

[예제1]  
App.config 
    <objects xmlns="http://www.springframework.net" >
       <object id="MyHello" type="DI.Hello, DI"></object>
    </objects>

Interface 
    interface IHello
    {
        string sayHello(string str); 
    }

Class 
    class Hello : IHello
    {
        public string sayHello(string str)
        {
            return str; 
        }
    }

MainApp
        static void Main(string[] args)
        {
            IApplicationContext ctx = ContextRegistry.GetContext();  //app.config에 설정된 object를 가져옵니다. 
            IHello hello = (IHello) ctx.GetObject("MyHello"); //  MyHello object를 노출된 interface 를 통한 Assign 
            string str = "안녕";
            string result = hello.sayHello(str);  
            Console.WriteLine(result);
        }

MainApp에서 Hello 클래스의 객체를 직접 create하지 않고, IHello 인터페이스를 도입함으로서, MainApp와 Hello와의 종속성이 제거되었습니다.  여기서 Hello가 컴퍼넌트 역할을 하게됩니다.
configuration에 사용하고자 하는 컴퍼넌트를 명시하고,  MainApp에서는  해당 컴퍼넌트를 사용할수 있도록 interface를  제공한 것입니다. 
위와 같은 프로그래밍 모델을  IOC, DI 라고 부릅니다. 


Spring.NET에서는 AutoProxy기능이 지원되는데요,  이는 특정 메소드가 호출될때, configuration에 define된 룰에 따라, 메소드호출을 intercept하여, 흐름의 제어를 할수 있게 되는것입니다. 

[예제2]
 
 
Configuration
<!--AutoProxy 설정-->
      <object id="MyServiceCommand" type="Spring.Aop.Framework.AutoProxy.ObjectNameAutoProxyCreator, Spring.Aop">
        <property name="ObjectNames">
          <list>
            <value>K*</value>
          </list>
        </property>
        <property name="InterceptorNames">
          <list>
            <value>Interceptor</value>
          </list>
        </property>
      </object>
  <!-- Intercept시 호출된 클래스정보-->
  <object id="Interceptor" type="ConsoleApplication2.Interceptor, ConsoleApplication2"/>
  
 <!--Object-->
      <object id="English" type="ConsoleApplication2.HelloWorldSpeaker, ConsoleApplication2">
        <property name="Language" value="English"/>
      </object>
     <object id="Korean" type="ConsoleApplication2.HelloWorldSpeaker, ConsoleApplication2">
        <property name="Language" value="Korean"/>
      </object>
  
interface
    public interface IHelloWorldSpeaker
    {
        void SayHello();
    }

Class 
   public class HelloWorldSpeaker : IHelloWorldSpeaker
    {
       public void SayHello()
        {
            switch (language)
            {
                case Language.English:
                    Console.WriteLine("영어");
                    break;
                case Language.Korean:
                    Console.WriteLine("한국어");
                    break;
            }
        }
    }

Interceptor 
 public class Interceptor : IMethodInterceptor
    {
        public object Invoke(IMethodInvocation invocation)
        {
            Console.WriteLine("실행전");
            object rval = invocation.Proceed();
            Console.WriteLine("실행후");
            return rval;
        }
    }

또한 before/After/Around 등의 Advice를  configuration에 세팅하게되면, 메소드의 실행전후에 특정 흐름을 끼워넣을수도 있게 됩니다. 

Spring.NET에서는 Quart.NET을 이용한  스케줄러 구현을 지원합니다.일반적으로, 기존에 우리 스케줄러를 작성하기 위해서는 쓰레드개념을 생각 안할 수가 없는데요, 
이때, Threadpool을 관리함에 있어서 여러가지 고민해야될것들이 많았습니다 
Pool의 count , 객체 소멸시점, 특정 시간에만 동작하기 위한 Timer .. 외에도 여러가지 존재할것 같습니다. 
그렇다면, Spring.NET에서는 이 모든것들에 대해서 어떻게 구현하게 될까요.. 
이제부터 직접 스케줄러를 구현해 보도록 하겠습니다. 

1. configuration  
2. scheduler
3. trigger 
4. jobDetail 

configration을 작성해야 하는데요, 이는 app.config에 작성할 수도 있고, 따로 xml파일로 뺼수도 있습니다. 
configuration에는 스케줄에 해당하는 object와, 스케줄에 대한 반복적인 주기를 뜻하는 트리거, 그리고 마지막으로 각 트리거가 수행하는 Job에 대해서 명시해야합니다. 

[예제3]
 
Scheduler
<object id="quartzSchedulerFactory"  type="Spring.Scheduling.Quartz.SchedulerFactoryObject, Spring.Scheduling.Quartz">
    <property name="SchedulerName" value="quartz1"/>
    <property name="triggers">
      <list>
        <ref object="CronTrigger" />
        <ref object="SimpleTrigger" />
       </list>
    </property>
  </object>

Trigger  
<object id="SimpleTrigger"  type="Spring.Scheduling.Quartz.SimpleTriggerObject, Spring.Scheduling.Quartz">
    <!-- see the example of method invoking job above -->
    <property name="JobDetail" ref="SchedulerJob" />
    <!-- 10 seconds -->
    <property name="StartDelay" value="10s" />
    <!-- repeat every 10 seconds -->
    <property name="RepeatInterval" value="10s" />
  </object>
  <object id="CronTrigger" type="Spring.Scheduling.Quartz.CronTriggerObject, Spring.Scheduling.Quartz">
    <property name="JobDetail" ref="SchedulerJob" />
    <!-- 5초마다의 interval Fire -->
    <property name="CronExpressionString" value="0/5 * * * * ?" />
  </object>

Job
<object name="SchedulerJob" type="Spring.Scheduling.Quartz.JobDetailObject, Spring.Scheduling.Quartz">
    <property name="JobType" value="Publisher.SchedulerJob, Publisher" />
    <property name="JobDataAsMap">
      <dictionary>
        <entry key="Timeout" value="5" />
       </dictionary>
    </property>
  </object>

모든 object는 Id(Name)와 Type을 지정해주어야합니다. 
그리고, 각 오브젝트마다 가지는 프로퍼티가 조금씩 다른데요, 
스케줄에서는 해당 스케줄에 대한 반복적인 주기를 뜻하는 트리거를 지정하게됩니다. 
저는 simpleTrigger와 cronTrigger라는 두개의 트리거를 지정했는데요,  몇분에 한번씩. 처럼 간단한 작업주기인경우에는 simpleTrigger를, 일중일 중에서 토/일을 제외한 매일 아침 10시부터 12시까지 20분간격으로. 라는 조금은 복잡해보이는 반복주기인경우에는 crontrigger를 사용하면 됩니다. 
그리고 각 트리거에서는 수행할  Job에 대해서 명시를 해야하는데요, 
JobType이라는 프로퍼티를 통해, 수행할 Task의 Type을 지정하게됩니다 Type은 어셈블리명, 네이스페이스명으로 지정하시면 됩니다.
위의 configration는 Publisher.SchedulerJob을 하나는 10초마다, 하나는 5초마다 반복 수행하는 스케줄러임을 알수 있게됩니다. 
config세팅이 끝나면, 이제 Publisher.SchedulerJob을 작성해 보겠습니다. 

[예제4]
 class SchedulerJob : QuartzJobObject
    {
        protected override void ExecuteInternal(JobExecutionContext context)
        {
                 Console.WriteLine("Excute..."); 
         }
    }


SchedulerJob은 QuartzJobObject를  상속받아, 예약되어있는 ExecuteInternal메소드를 오버라이딩 하면 됩니다 
파라메터인 JobExecutionContext타입의 context에는 configration에서 작성한 해당 Job의 정보를 모두 알 수 있습니다. 
위와 같이 QuartzJobObject를 상속하여, Job을 수행하는 방식 외에, 직접 TargetMethod를 지정할 수도 있습니다.

스케줄 트리Listener를 등록해 놓으면, 트리거가 Fire될때, 혹은 misFire되거나 실행이 완료되었을때의 이벤트를 Listen할 수가 있습니다.

[예제5]
   
 public class TriggerListener : ITriggerListener
    {
        
public void TriggerFired(Trigger trigger, JobExecutionContext context)
        {
            Console.WriteLine("TriggerFired");
        }

         public void TriggerMisfired(Trigger trigger)
        {
            Console.WriteLine("TriggerMisfired");
        }

        public void TriggerComplete(Trigger trigger, JobExecutionContext context,
                                    SchedulerInstruction triggerInstructionCode)
        {
            Console.WriteLine("TriggerComplete");
        }
    }

작성된 스케줄러를 실행시켜보겠습니다. 
[실행결과]

5초마다 Crontrigger가, 10초마다 simpleTrigger가 수행되고 있으며, 각 이벤트가 Fire될때마다 Trigger를 Listen하고 있습니다.

지금까지 간략하게나마, Spring.NET을 이용하여 스케줄러를 만들어 보았는데요,, 
잘 동작하네요 :)  

읽어주셔서 감사합니다.   

'PP > SPRING.NET' 카테고리의 다른 글

일반 구성 설정(ASP.NET)  (0) 2012.01.13
Spring .Net 활용 가이드  (0) 2012.01.12
DI  (0) 2012.01.10
posted by 방랑군 2012. 1. 9. 03:00

상품등록 화면을 ajax로 처리하다 보니
데이터의 자료구조를 잘 만들어야 할 필요가 있다.

그래서 json 의 사용..

배열과 크게 다를건 없지만 걍 객체지향 냄새가 좀더 난다는거..
그리고 배열 요소(인덱스) 처리하느라 골머리 썩지 않는 점은 참 좋다. 직관적이기도 하고..

그런데 json 데이터를 객체화 하기 위해 자바스크립트의 eval! 메소드를 사용해야 하는데..

이게 악성코드를 실행시킬 위험이 있단다.

그래서

json.org/json2.js 배포파일이 필요하게 됬다.

더 상세한건
http://blog.outsider.ne.kr/257 요분의 포스팅이 참 도움이 된다.
땡큐베리 감사...

어찌됬든
eval!(o.responseText) 가 아닌 JSON.parse(o.responseText)로 객체화 하자

'PP > JSON' 카테고리의 다른 글

JSON Text를 JSON Object로 변환하기  (0) 2012.01.09
Json / JQuery (Ajax)/ Asp.net 3가지를 연동하여 데이터 가져오기  (0) 2012.01.07
JSON 개요 및 예제  (0) 2012.01.04
DATASET - > JSON  (1) 2012.01.04
JSON.NET  (0) 2012.01.04
posted by 방랑군 2012. 1. 9. 02:59
JSON 은 써보면 써볼수록 유용한 것 같다. 간결하고 편하고 직관적이다. 어쨌든 JSON Text를 Object로 변환해야 할 때가 있다. 여기서 JSON Text라는 것은 형태는 JSON의 형태이지만 자바스크립트에서 이걸 Object가 아닌 그냥 텍스트로만 인식하고 있다는 것이다. 이걸 Object로 바꾸어야만 그안의 값을 불러다가 사용할 수 있다.

가장 흔한 예가 Ajax를 사용할 경우이다. Ajax로 호출을 하고 결과값으로 받은 req.responseText로 JSON을 받았을 경우에는 그냥 Text이기 때문에 Object로 변환해 주어야 한다.

{ id:'Outsider', sex:'male' }

Ajax에서 리턴받을 JSON의 형태가 위와 같이 되어 있을 경우에는 

?
1
2
var obj = eval("("+returnValue.responseText+")");
alert(obj.id);  // Outsider

위의 코드처럼 eval을 해주면 JSON 오브젝트로 변환할 수 있다.

[ { id:'Outsider', sex:'male' },
  { id:'Zziuni', sex:'male' } ]

JSON이 위의 형태처럼 배열로 되어 있을 경우에는

?
1
2
var obj = eval(returnValue.responseText);
// -> { id:"Outsider", sex:"male" }

그냥 eval을 해주면 JSON 오브젝트로 변환할 수 있다.

다만 이렇게 변환할 경우 eval()은 빠르기는 하지만 단순히 그안의 스트링을 그대로 실행시켜 주는 것이기 때문에 리턴값으로 자바스크립트 명령문이 온다면 그대로 실행시켜버리기 때문에 보안이슈가 발생할 수 있다.  

이렇게 리턴받은 소스를 신뢰하기 어려울 때는 JSON.org 에서 제공하는 JSON parser을 사용해야 한다. JSON parser는 오직 JSON text만 받아들이고 다른 스크립트는 거부하고 eval()만큼이나 빠르다.

?
1
2
var obj = JSON.parse(returnValue.responseText);
// -> { id:"Outsider", sex:"male" }

JSON.parse()의 목적대로 JSON 텍스트 외에는 거부해야하기 때문에 JSON문법을 정확히 지켜주지 않으면 SyntaxError 예외가 던져진다. 그렇기 때문에 키와 값을 모두 쌍따옴표(")로 묶어주는 문법을 정확하게 지켜주어야 한다.(물론 이 경우는 값들이 스트링이기 때문에 쌍따옴표로 묶어주는 것입니다.) 아래처럼....

{ "id":"outsider", "sex":"male" }

여기서 JSON.parse()를 사용하기 위해서는 Douglas Crockford 가 만든 json2.js 가 필요하다. json2.js는 더글라스 크록포드가 JSON의 편리한 사용을 위해 만든 JSON API의 새버전이다.(그래서 2가 붙어있다.) 이 API에는 2개의 메서드가 들어있는데 JSON.stringify()와 JSON.parse()이다. JSON.stringify()는 JSON.parse()와는 완전히 반대로 JSON 객체를 주면 JSON 텍스트로 만들어서 준다. 필요할때 갖다 쓰면 된다. (John Resig 이 이전버전보다 새버전의 API가 훨씬 좋다고 꼭 이걸 쓰란다.)

'PP > JSON' 카테고리의 다른 글

JSON 의 eval() 함수 사용의 문제  (0) 2012.01.09
Json / JQuery (Ajax)/ Asp.net 3가지를 연동하여 데이터 가져오기  (0) 2012.01.07
JSON 개요 및 예제  (0) 2012.01.04
DATASET - > JSON  (1) 2012.01.04
JSON.NET  (0) 2012.01.04
posted by 방랑군 2012. 1. 8. 21:36

출처 : http://snowple.tistory.com/355

+ 이벤트 등록(live)
.live() 은 .bind()를 기초로 엘리먼트에 이벤트 핸들러 함수를 연결할 때 몇가지 기능을 추가한 함수.
보통 Ajax등으로 동적으로 생성된 엘리먼트에 대해서는 .bind()함수를 통해 이벤트를 추가해 주지 못한다. 따라서 live() 함수는 동적으로 생성된 엘리먼트에 대해서도 이벤트를 추가해 주는 기능을 가지고 있다.

$('#id').live('click', function(e) {

/* TODO */

});


등록할 수 있는 이벤트 타입
- click
- dblclick
- keydown
- keypress
- keyup
- mousedown
- mousemove
- mouseout
- mouseover
- mouseup


+ 이벤트 등록(bind)

$('#id').bind('click', function(e) {

/* TODO */

});




jQuery 셀렉터 정리


+ 선택

$('div') /* 문서 안의 모든 div를 선택 */
$('#myid') /* id="myid" 인 유일한 엘리먼트를 선택 */
$('.myclass') /* 클래스가 class="myclass" 인 엘리먼트를 선택 */
$('p#myid') /* id가 myid 이면서 p 태그인 유일한 엘리먼트를 선택 */
$('a img') /* <a> 엘리먼트의 하위 엘리먼트들 중에서 <img> 를 가진 엘리먼트를 선택 */
$('#main p') /* id가 main인 하위 엘리먼트들 중에서 <p> 태그를 가진 엘리먼트를 선택 */
$('li > ul') /* <li> 엘리먼트의 하위 엘리먼트들 중에서 <ul>인 엘리먼트들을 선택 */
$('[name=myname]') /* name의 속성값이 myname인 엘리먼트를 선택 */
$('a[href=address]') /* <a>를 가진 엘리먼트에서 속성 href가 address인 것을 선택 */



+ 폼 셀렉터

$(':input') /* 모든 폼 엘리먼트(<input>, <select>, <textarea>, <button>)을 선택 */
$(':text') /* 모든 텍스트 필드(<input type="text">) 를 선택한다. */
$(':radio') /* 모든 라디오버튼 필드(<input type="radio">) 를 선택한다. */
$(':checkbox') /* 모든 체크박스 필드(<input type="checkbox">) 를 선택한다. */
$(':checked') /* 체크된 체크박스 또는 라디오버튼 엘리먼트를 선택 */



+ 사용자 정의 셀렉터

$('li').filter(':even').css('background-color', 'red') /* <li> 태그 중에서 짝수번째 라인은 빨간색 배경 지정 */
$('li:eq(2)') /* 3번째 <li>를 선택 */
$('.myclass:eq(1)') /* 클래스명이 myclass인 엘리먼트 가운데 2번째 엘리먼트를 선택 */
$('li').eq(2).css('background-color', 'red') /* <li> 태그중에서 2번째 태그에 배경을 빨간색을 지정 */



+ 찾기

$('#conditions').find('li') /* id가 conditions인 하위 모든 엘리먼트들 중에서 <li> 태그를 가진 것 선택 */
$('li').prev() / $('li').prevAll()
$('li').next() / $('li').nextAll()



+ 체크박스의 값을 콤마(,)로 만들기

$(':checkbox').map(function() {

return this.id;

}).get().join(',');
>> 4,5,8




DOM 처리


+ 기본속성 설정

$('#check_input').attr('checked', false) /* 체크해제 */
$('#check_input').attr('title', 'mytitle') /* id가 check_input인 엘리먼트의 title 속성을 "mytitle"로 변경 */
$('#check_input').attr({

alt: 'test',
title: 'test'

});
if ($('#save').prop('checked') == true) {

/* id가 save인 엘리먼트가 체크된 상태 */

}
.width() /* 길이 설정 */



+ 객체 생성

var odv = $(document.createElement('div'));
odv.attr('id', 'test');
odv.addClass('ui-state-condition');



+ 입력과 선택

.html()
.text()
.val()

$('input:text.item').val(function() {

return this.value;

});
.index() /* 몇번째 엘리먼트인지 숫자로 반환 */




AJAX


+ ajax

$.ajax({

type: "POST",

url: "histogram.php",
data: {key : value, key1: value1},
dataType: "html",
beforeSend: function() { },
success: function(res, textStatus) {

$('#id').html(res);

}

});



+ load

$('#id').load('condition.php', {key: value, key1: value1}, function() {

/* 로딩 성공했을 때 */

}); 
posted by 방랑군 2012. 1. 8. 21:28
1. jQuery 개요
라이브러리다운로드 - www.JQuery.com
특징 : DOM 엘리먼트 셀렉터
       DOM : HTML, XML을 제어
       Ajax지원
       Plugin 지원
       단순화된 이벤트처리
       브라우저별 호환성


사용법
헤드태그안에 삽입
<script type="text/javascript" src="<%=cp%>/data/js/jquery-1.6.2.min.js"></script>
//src=라이브러리를 추가한 곳
<script type="text/javascript">
//작성

</script>






2. Core

태그접근 : $("a"), $("div")
클래스접근 : $(".클래스명), $("태그.클래스명")
ID접근 : $("#id")   ---> document.getElementById("id")  와 같음
중첩구조 : $("#id").find("li") => $("#id li")으로 가능



3. Selectors(선택자)

기본선택자
* 모든 요소와 매칭
E 모든 E요소와 매칭
E F E의 자손이고 F인 요소와 매칭
E>F E의 자식이고 F인 요소와 매칭
E+F E의 바로 다음형제인 F요소와 매칭
E~F E가 바로 이전형제인 F요소와 매칭
E:has(F) F를 최소 하나의 자손으로 가지고 있는 E요소와 매칭
E.c c라는 클래스를 가진 E요소와 매칭 (*.c나 .c와 같음)
E#i i라는 아이디를 가진 E요소와 매칭 (*#i나 #i와 같음)
E[@a]
a라는 속성을 가진 E요소와 매칭
E[@a=v] a속성값이 v인 E요소와 매칭
E[@a^=v]  a속성값이 v로 시작하는 E요소와 매칭
E[@a$=v] a속성값이 v로 끝나는 E요소와 매칭
E[@a*=v] a속성값이 v를 포함하는 E요소와 매칭

위치형선택자 : 기본선택자뒤에 쓰인다.
B:first 첫번째 B요소와 매칭
B:last 마지막 B요소와 매칭
B:first-child 첫번째 B요소와 매칭
B:last-child 마지막 B요소와 매칭
B:only-child B요소가 하나일 경우 B요소와 매칭
B:nth-child(n) n번째 B요소와 매칭(n:one-based)
B:nth-child(odd|even) 홀/짝수 B요소와 매칭
B:nth-child(Xn+Y) X배수 + Y인 B요소와 매칭(n:zero-based)
B:even 짝수 B요소와 매칭
B:odd 홀수 B요소와 매칭
B:eq(n) n+1번째 B요소와 매칭(n:zeno-based)
B:gt(n) n+1번째 초과 B요소와 매칭
B:lt(n) n이하 B요소와 매칭


사용자정의형 선택자
B:animated jQuery 애니메이션 메서드로 애니메이션이 활성화된 B요소와 매칭
B:button 버튼 형태(button, input[@type=submit], input[@type=reset], input[@type=button])의 B요소와 매칭
B:checkbox input[@type=checkbox]인 B요소와 매칭
B:enabled 활성화 상태인 B요소와 매칭
B:file input[@type=file]인 B요소와 매칭
B:header h1~h6인 B요소와 매칭
B:hidden 비가시 상태 또는 input[@type=hidden]인 B요소와 매칭
B:image input[@type=image]인 B요소와 매칭
B:input 입력 요소(input, select, textarea)인 B요소와 매칭
B:not(f) :(콜론)으로 시작하는 f를 제외한 B요소와 매칭
B:parent 자식요소가 있는 B요소와 매칭
B:password input[@type=password]인 B요소와 매칭
B:radio input[@type=radio]인 B요소와 매칭
B:reset input[@type=reset]인 B요소와 매칭
B:selected option요소 중 현재 선택된 B인요소와 매칭
B:submit input[@type=submit]인 B요소와 매칭
B:text input[@type=text]인 B요소와 매칭
B:visible 가시 상태인 B요소와 매칭


 ###$( html ) 
    태그를 바디안에 삽입하기
       $("<div><i>안녕하세요</i></div>").appendTo("body");

 ###eq(pos)
    선택된  pos번째 태그 선택.
    $("tr:eq(6)").css("color", "silver"); // 6번째 tr태그 색깔변경 

 ###gt(pos)
    선택된 pos이후의 모든 태그선택
    $("tr:gt(3)").css("color", "red");  // 인덱스가 3이후인것들 모두 색깔변경

 ###lt(pos)
    선택된 JQuery 오브젝트중  pos보다 앞에있는 오브젝트들을 선택.
    $("tr:lt(3)").css("color", "red");  // 인덱스가 3이전인것들 모두 색깔변경 


 ###index(subject)
    subject의 위치.
    var index = $("div").index($("div:contains('jquery')"));  //div안에서 jquery라는 element 찾기


 ###each(callback)
    
    매치되는 모든 요소에 대하여 callback 메소드 실행(루프)
    $("div").each(function(args){           <!-- div에 해당되면 -->
if(this.style.color!='blue')
this.style.color='blue';
else
this.style.color='';
    });


 ###length
    선택된 요소의 갯수.
    var n = $("div").length;  //div태그의 개수리턴

 ###size()
    선택된 요소의 갯수.
    alert( 'Size: ' + $('li').size() ); // <li>의 개수를 리턴한다.

 ###$.fn.extend( prop ) 
  플러그인만들기.
  //check, uncheck함수를 이용한 플러그인
$.fn.extend({   
check:function(){
return this.each(function(){  //each
this.checked=true;
});
},
uncheck:function(){
return this.each(function(){
this.checked=false;
});
}
});


 $("li:first").css("background", "#CCCCCC");

 $("li:first-child").css("background", "#CCCCCC");





4. Attributes(속성)
.attr() 
속성값 가져오기 : .attr(attributeName)
속성값 병경하기 : .attr(attributeName, value)
$("img").attr("src", "img/ii.jpg"); //img 요소의 src속성을 img/ii.jpg으로 변경


.removeAttr()
속성값제거
$("#name").removeAttr("disabled");


.val() 선택된 요소값 가져오기
var name = $(“#txtName”).val(); //입력된 값 가져오기
$(“#txtName”).val(“새로운 값 입력”); //값 입력하기






5. Manipulation(조작)

내용변경관련
html()        일치된 요소의 html 내용을 가져옴
html(val)      일치된 요소의 html 본문을 val 값으로 설정
text()        일치된 모든 요소의 텍스트를 가져옴.
text(val)      모든 일치된 요소의 텍스트를 val 값으로 설정
예)var text = $("div").text();
   var html = $("div").html();   

추가관련(내부) 
append(content)         일치된 요소의 내부에 content를 추가
appendTo(selector) 일치된 요소를 selector에 의해 일치된 모든 요소들 내부에 추가 
prepend(content) append(content)와 동일하며, 다만, 내부 앞쪽에 추가
prependTo(selector) appendTo(selector)와 동일하며, 다만, 내부 앞쪽에 추가

예)$("b.link").append("(클릭)");

추가관련(외부)
after(content) 일치된 요소 뒤에 content를 삽입
efore(content) 일치된 요소 앞에 content를 삽입
insertAfter(selector) 일치된 요소를 selector에 의해 일치된 모든 요소들 뒤쪽에 삽입
insertBefore(selector) insertBefore(selector)와 같으나, 요소 앞쪽에 삽입

예)$("a").after("<font>(클릭)</font>");
-><a href="http://naver.com">네이버</a><font>(클릭)</font>






6. Events

bind : 이벤트 추가
unbind : 이벤트 제거
click : 마우스 클릭시...
change : <input />, <textarea />, <select /> 요소의 값 변경시 발생하는 이벤트
dbclick : 마우스를 더블클릭 했을 경우 발생하는 이벤트
focus : 요소에 포커스 되었을 때 발생하는 이벤트
keydown : 키 입력 시 발생되는 이벤트이며, 모든 키에 대해 적용
keyup : 키 입력 후 발생되는 이벤트 입니다.
keypress : keydown 이벤트와 동일하게 키 입력 시 발생이 되지만 enter, tab등의 특수키에는 이벤트가 발생되지 않음
mousedown : 마우스 클릭 시 발생하는 이벤트
mouseenter :  선택한 요소의 영역에 마우스가 위치했을 때 발생되는 이벤트
mouseleave : 선택한 요소의 영역에서 마우스가 벗어 났을 때 발생되는 이벤트
mousemouse : 선택한 요소에 마우스를 클릭하면 발생하는 이벤트
mouseout : 선택한 요소의 영역에서 마우스가 벗어 났을 때 발생되는 이벤트
mouseover : 마우스를 올려놓으면 발생
mouseup : 마우스 클릭 후 발생되는 이벤트
scroll : HTML 문서가 스크롤 되었을 때 발생하는 이벤트ㅋ
select : 선택한 개체를 마우스를 통해 선택 하였을 때 발생하는 이벤트
submit : Submit이 일어날 때 발생하는 이벤트
hover() : 마우스가 요소 위에 위치했을 때 발생하는 이벤트
blur() : 요소에서 포커스를 잃을 경우에 발생하는 이벤트

'PP > Jquery' 카테고리의 다른 글

jQuery 이벤트 정리  (0) 2012.01.08
다른 라이브러리와 같이 쓰기  (0) 2012.01.08
jQuery Core  (0) 2012.01.08
[Jquery,CoffeeScript] 모질라 파이어폭스 Ajax. 한글 키 이벤트 처리.  (0) 2012.01.08
jQuery UI 테스트 2  (0) 2012.01.08
posted by 방랑군 2012. 1. 8. 21:27

출처 :  http://findfun.tistory.com/entry/jQuery-%EC%89%BD%EA%B2%8C%ED%95%98%EA%B8%B0-%EB%8B%A4%EB%A5%B8-%EB%9D%BC%EC%9D%B4%EB%B8%8C%EB%9F%AC%EB%A6%AC%EC%99%80-%EA%B0%99%EC%9D%B4-%EC%93%B0%EA%B8%B0 

Javascript Library 들이 출현하면서 자바스크립트의 중요성은 비약적으로 높아졌습니다. Rich UI 를 구현함에 있어서 이 라이브러리들의 기여도는 결정적이였습니다. 풍부해진 사용자 경험(UX)을 바탕으로 웹 어플리케이션이란 용어도 등장하기 시작했습니다. 아마 앞으로는 웬만한 어플리케이션은 웹 기반이 되지 않을까 합니다.

많아진 Javascript Library 들을 같이 사용해야 하는 경우가 있습니다. 이에 jQuery는 다음과 같은 권고 사항을 제시하고 있습니다.

원문을 보시려면 여기를 클릭하세요.

GENERAL : 개요

jQuery 라이브러리와 Plugin 들은 jQuery 네임스페이스안에 종속되어 있습니다. 만약 여러분이 jQuery 외의 Prototype, MooTools, YUI 등과 같은 다른 라이브러리와 같이 사용하길 원하면 jQuery의 "전역(global)" 객체들은 jQuery 네임스페이스 안에서 사용해야 합니다.

jQuery 에서는 다음과 같이 경고(권고) 합니다. jQuery의 '$' 를 'jQuery' 로 바꿔 사용하십시요.

완전 직역이네요. ^^;; 쉽게 설명드리자면 jQuery하고 Prototype을 같이 쓰실 경우가 생기시면 jQuery의 $ 를 jQuery 라고 바꿔 쓰라는 얘기입니다. Prototype에도 $ 가 있으니까요. 아래 구체적인 예시들이 있습니다.

 

OVERRIDING THE $-FUNCTION : $ 함수를 재정의 하세요.

jQuery.noConflict() 함수를 사용한 후 그 이후부터는 $ 대신 jQuery 사용할 수 있습니다. 아래는 예제코드입니다.

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<html>
<head>
  <script src="prototype.js"></script>
  <script src="jquery.js"></script>
  <script>
    jQuery.noConflict();
     
    // Use jQuery via jQuery(...)
    jQuery(document).ready(function(){
      jQuery("div").hide();
    });
     
    // Use Prototype with $(...), etc.
    $('someid').hide();
  </script>
</head>
<body></body>
</html>

6라인 이후에는 $ 대신에 jQuery 라고 사용하신 것을 보실 수 있습니다. 14라인의 $ 는 Prototype의 $ 가 됩니다. $를 Prototype에게 양보한다는 거네요. 참 착한 jQuery입니다. ^^

그런데 $ 라고 쓰다가 jQuery 라고 쓰려니 타자의 압박이 있습니다. 그래서 jQuery 는 아래와 같이 대체어(alternate names)를 사용할 수 있게 했습니다.

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<html>
<head>
  <script src="prototype.js"></script>
  <script src="jquery.js"></script>
  <script>
    var $j = jQuery.noConflict();
     
    // Use jQuery via $j(...)
    $j(document).ready(function(){
      $j("div").hide();
    });
     
    // Use Prototype with $(...), etc.
    $('someid').hide();
  </script>
</head>
<body></body>
</html>

6라인을 보시면 $j 라고 변수선언을 했습니다. 그 아래 부터 jQuery 가 아닌 $j 로 사용하실 수 있습니다. $j 말고도 사용하고 싶은 대체어를 만드시면 됩니다. $findfun 이나 $jq 와 같이 말이죠.

그럼에도 불구하고 "아~ 나는 무조건 $를 써야겠다" 라고 하시는 분들을 위해서 jQuery는 또 하나의 방법을 제시합니다.(이 방법은 별로인거 같습니다.)

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<html>
<head>
  <script src="prototype.js"></script>
  <script src="jquery.js"></script>
  <script>
    jQuery.noConflict();
     
    // Put all your code in your document ready area
    jQuery(document).ready(function($){
      // Do jQuery stuff using $
      $("div").hide();
    });
     
    // Use Prototype with $(...), etc.
    $('someid').hide();
  </script>
</head>
<body></body>
</html>

9라인과 같이 jQuery 네임스페이스 안에 속한 내용들은 이전 처럼 $ 를 사용하실 수 있습니다. 11라인을 보세요. 그대로 $ 를 사용했습니다. 하지만 썩 좋은 코드는 아닌 것 같습니다.

jQuery.noConflict() 함수가 기억이 나지 않거나 실수로 기술하지 않았을 경우에는 에러를 찾기 힘들 수 있습니다. 아래 내용을 보시면 해결 방법이 있습니다.

 

INCLUDING JQUERY BEFORE OTHER LIBRARIES : jQuery 라이브러리 인클루드를 다른 라이브러리 보다 위쪽에 하세요.

jQuery 라이브러리 인클루드를 항상 제일 위쪽에 하시면 jQuery.noConflict() 함수를 기억하지 않으셔도 됩니다.

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<html>
<head>
  <script src="jquery.js"></script>
  <script src="prototype.js"></script>
  <script>
    // Use jQuery via jQuery(...)
    jQuery(document).ready(function(){
      jQuery("div").hide();
    });
     
    // Use Prototype with $(...), etc.
    $('someid').hide();
  </script>
</head>
<body></body>
</html>

3,4 라인을 보시면 jquery.js 가 위쪽입니다. 그리고 코드 상에 jQuery.noConflict() 가 없는 것을 보실 수 있습니다.

 

결론적으로 jQuery 라이브러리와 다른 라이브러리들 같이 사용하시려면 아래와 같이 사용하시는 것을 적극 권장합니다.

  •  jQuery 라이브러리 인클루드를 다른 라이브러리 보다 위쪽에다 할 것.
  •  
  •  var $j = jQuery; 와 같이 대체어를 사용할 것.

 

두 가지 이상의 라이브러리를 동시에 같은 프로젝트에 사용할 일은 거의 없어 보입니다. 하지만 그런 일이 없으란 법은 없겠죠. 그런 경우를 대비해서 한번 읽고 넘어가는 것도 좋겠네요. jQuery 의 세심한 배려에 박수를 보냅니다.

자 이번 포스팅은 여기 까지입니다. 그럼 모두들 즐프하세요~. 
posted by 방랑군 2012. 1. 8. 21:23

출처 :  http://findfun.tistory.com/67 

API(Application Program Interface, 응용프로그램 인터페이스)란 어떤 응용프로그램에서 제공한 메소드들의 모음입니다. 사전적으로 해석을 해보자면 "응용 프로그램과 대화하기" 가 되겠습니다. 사람사이의 대화방법은 몸짓, 말, 글을 사용합니다. 이것들을 인터페이스라고 할 수 있습니다. 단, 서로 의미가 통해야 합니다. 즉, 사전에 정의된 해석방법으로만 대화가 가능하죠. 고개 숙여 인사를 하는 박찬호를 보고 이상하게 생각했다는 미국인들과 같이 해석의 방법이 미리 정의되지 않은 대화방법으로는 오해 또는 소통이 불가하게 됩니다.

프로그램에서도 어떤 응용프로그램에 접근하기 위해 사전에 정의된 함수들의 모음이 존재하고, 이 모음을 외부에 노출하기 위해 정리한 것이 API 라고 할 수 있습니다. 즉, API 는"내가 만든 프로그램을 사용하고 싶으면 이런저런 약속을 지켜서 사용하고, 어떤 행동을 일으키고 싶을때 사용하는 함수들을 알려줄테니 그걸로 써라"라는 문서가 됩니다.

jQuery 와 같이 잘 정리된 라이브러리는 개발자들에게 천국입니다. API 가 어렵지 않으며 관련 자료도 많은 jQuery는 문제가 발생했을 때 빠른 시간안에 해결을 할 수 있게 됩니다. 일전에 잘 사용하지 않은 산업용 PDA 에 Windows-CE 기반 프로그램을 하다가 아주 고생했던 기억이 납니다. 다시 겪고 싶지 않은 경험입니다. ^^;.

사설이 길었네요. 자~ 이제 드디어 API 를 할 수 있게 되었네요. API 에 대해 모두 쓸 예정이지만 때에 따라서는 생략도 하게 될 것 같습니다. 그나저나 얼마나 길어지게 될지.. 좀 두렵기도 한데요 ^^;;. 자 시작합니다.

Core

jQuery 의 핵심입니다. 우리가 $() 로 사용하고 있는 것에 대한 설명입니다. 실제로는 jQuery() 라고 사용해야 하지만 축약어로 $() 로 사용하고 있는 jQuery 코어에 대한 설명입니다.

원문 링크  http://api.jquery.com/category/core/

함수 목록

  • 일치하는 요소들(elements)를 사용하기 위해 CSS 선택자(selector)와 같은 문자열을 사용합니다.
  • jQuery 의 $ 변수 사용을 포기합니다.

jQuery()

함수들

 jQuery( selector, [ context ] )
  • jQuery( selector, [ context ] )
  • jQuery( element )
  • jQuery( elementArray )
  • jQuery( jQuery object )
  • jQuery()
 jQuery( html, [ ownerDocument ] )
  • jQuery( html, [ ownerDocument ] )
  • jQuery( html, props )
 jQuery( callback )
  • jQuery( callback )

jQuery( selector, [ context ] )Returns : jQuery

개요 : CSS 선택자(selector)와 일치하는 요소들(elements)을 사용하기 위한 문자열을 사용합니다.

  • jQuery( selector, [ context ] )
  • selector 선택자(selector)를 문자열로 표현
  • context DOM 요소, 문서(Document) 또는 문맥상에서 사용되는 jQuery
  • jQuery( element )
  • element jQuery 객체에 속한 DOM 요소
  • jQuery( elementArray )
  • elementArray jQuery 객체에 속한 DOM 요소들의 배열
  • jQuery( jQuery object )
  • jQeury object 복사를 위한 jQuery 객체
  • jQuery()

jQuery() - $() 로 사용하고 있는 - 는 제공된 선택자(selector)를 검색하고 그 요소(elements)를 jQuery 객체화 합니다. 직역이 어렵네요. 즉, 우리가 제시한 선택자를 문서상에서 찾아서 jQuery() 객체로 만들어 줍니다. 그래야 jQuery 의 함수와 속성들을 사용할 수 있으니까요. 아래와 같이 선택자(selector)를 문자열로 적어주면 해당 문서에서 이 문자열과 일치하는 요소들(elements)을 찾아 jQuery 객체로 만들어 준다는 얘기입니다.

$('div.foo');

 Selector Context : 선택자 사용방법

기본적으로 선택자를 찾기 위해서 문서의 처음부터 검색을 합니다. 하지만 때에 따라서는 원하는 부분만 찾을 필요도 있습니다. 성능이 최우선이기 때문이죠. 이런 경우를 위해서 $() 함수의 2번째 인자를 이용할 수가 있습니다. 아래 예제는 div.foo 가 클릭되었고 그 요소의 태그가 span 일 경우 bar 라는 클래스를 span 에 추가하는 구문입니다.

$('div.foo').click(function() {
  $('span', this).addClass('bar');
});

원하는 부분만 선택해서 검색할 수 있는 기능이 있다는 얘기입니다. 위 예제 중 $('span', this) 는 $(this).find('span') 과 같은 의미입니다. 즉, find() 함수를 사용하여 원하는 요소를 찾아서 어떤 일을 진행할 수 있습니다. 실제로 전체 문서를 다 찾아서 처리하는 방식은 지양해야 하는 방식입니다. 하지만 꼭 써야 할 경우도 생길수도 있지만 가급적이면 다른 방법을 강구해야 할 것 같습니다.

 Using DOM elements : DOM 요소 사용하기

이미 찾은 DOM 요소(element) 또는 요소들(elements)을 이용하여 jQuery 객체를 만드는 방법은 2~3가지 방법을 사용할 수 있습니다. 시스템 이벤트에 의해 호출되는 함수(callback function)를 통해 전달된 그 요소(an element)를 이용하여 jQuery 함수들을 쉽게 사용하려면 "this" 키워드를 사용하면 됩니다. 아~ 영어 무지 딸립니다. 죽겠습니다. ㅜ,.ㅡ;; 유추해 보자면, 기본적으로 DOM 요소가 가진 특정 콜백함수들이 호출되면 그 이벤트를 전달한 요소(element)를 알아낼 수 있는데요. 그 요소(element)로 jQuery 함수를 사용하고 싶다면 "this" 키워드를 사용하면 된다라는 얘기인 것 같습니다. 그럴 듯 한가요? ㅎㅎ;;; 아래 예제를 보시죠.

$('div.foo').click(function() {
  $(this).slideUp();
});

위 예제는 'div.foo' 요소 클릭이라는 시스템 콜백함수가 호출되면 그 요소를 slideUp() 이라는 jQuery 함수를 사용해서 표현하라 라는 의미입니다. slideUp() 이 뭐하는 함수인지는 일단 제껴두고, 이 클릭 이벤트가 발생된 요소를 그 slideUp() 을 하기 위해서 $(this) 를 사용했다는 점을 봐달라는 겁니다. 여기에서 this 가 바로 $('div.foo') 로 찾아낸 DOM 요소의 jQuery 객체가 된다는 얘기입니다. 와~ 말 무지 어렵습니다. 에혀~. 원문에서는 아래의 부가 설명이 있습니다.

이 예제는 어떤 요소가 클릭(clicked) 되었을 때 슬라이딩 에니메이션(sliding animation)을 발생시킨다는 의미가 내포되어 있습니다. 이 조정자(handler receives : 클릭된 요소를 의미)는 순수한 DOM 요소(element)이며 이 요소를 $(this)를 이용하여 jQuery 객체화를 하게 됩니다. 이 요소(위에서 조정자)가 jQuery 의 함수를 사용하기 위해서는 jQuery 객체화가 되어야 합니다. 즉, 순수 DOM 요소는 jQuery 함수를 사용할 수 없기 때문이죠.

또한, XML 데이터를 Ajax 를 통해서 전달 받은 뒤, $() 함수를 이용해서 쉽게 jQuery 객체화가 가능합니다. jQuery 객체화가 이루진 후에는 이 XML 구조(structure)에서 우리는 찾고자 하는 요소를 jQuery 의 .find() 함수나 DOM 의 검색 함수들을 이용해서 쉽게 찾아 낼 수 있습니다.

예 제
p 태그를 하위 요소로 가지고 있는 div 를 찾아서 테두리에 선을 그린다.

<!DOCTYPE html>
<html>
<head>
  <script src="http://code.jquery.com/jquery-1.4.4.js"></script>
</head>
<body>
  <p>one</p> <div><p>two</p></div> <p>three</p>
<script>$("div > p").css("border", "1px solid gray");</script>

</body>
</html>

미리보기

jQuery( html, [ ownerDocument ] )Returns : jQuery

개요 : 순수한 HTML(raw HTML) 문자열을 이용하여 동적인(on the fly) DOM 요소를 만듭니다.

  • jQuery( html, [ ownerDocument ] )
  • html 동적인 HTML 문자열입니다. XML 이 아닌 HTML 만 분석합니다.
  • ownerDocument 만들어진 새 요소(new elements)가 위치한 문서
  • jQuery( html, props )
  • html 단독, 독립적인 HTML 요소로 정의할 수 있는 HTML 태그 문자열 (예 : <div/> 또는 <div></div>)
  • props 만들어진 새 요소의 속성, 이벤트, 함수들

HTML 문자열을 가지고 DOM 요소를 만들어 낼 수 있습니다.

 Creating New Elements : 새 요소 만들기

만약 당신이 $() 함수에 문자열을 전달했다면, jQuery 는 그 문자열에 태그의 요소(<tag...> 와 같은)가 있는지 확인해 봅니다. 없다면 위의 예처럼 선택자 표현(selector expression)이라 판단하고 처리를 하게 됩니다. 하지만 문자열에 HTML 태그가 있다면 jQuery 는 그 태그에 해당하는 DOM 요소를 만들어 문서에 추가하게 됩니다. 추가된 요소(elements)는 jQuery 객체 형태를 유지하기 때문에 jQuery 의 많은 함수들을 쉽게 사용할 수 있게 됩니다. 아래 예제와 같은 구문도 jQuery 객체로 인식하여 jQuery 함수들을 사용할 수 있게 됩니다.

$('<p id="test">My <em>new</em> text</p>').appendTo('body');

위 예제와 같이 속성이 없는 하나의 태그가 아닌 복잡한 수준이라면 마치 innerHTML 을 사용하는 것과 같이 동적으로 요소를 추가하게 됩니다. 더 들여다 보자면, jQuery 는 전달된 HTML 태그들을 <div>를 만들어서 그 안에 innerHTML 을 이용하여 위치(sets) 시키게 됩니다. 즉, div 태그를 임의로 만들고 그 안에 전달된 태그 문자열을 DOM 요소로 추가한다는 얘기입니다. 만일 단순한 하나의 태그로 구성된 문자열 - $('<img />> 또는 $(<a></a>) 와 같은 - 이라면 jQuery 는 JavaScript의 createElement() 함수를 이용하여 새 요소를 만들어 내게 됩니다.

복잡한 수준의 HTML 태그를 추가해야 할 일이 생기기도 하지만 HTML 소스가 정확하게 복사되지 않는 브라우져들도 있습니다. 예를 들어 인터넷 익스플로러 8 이전의 버젼들은 모든 절대 경로(absolute URLs)를 href 속성으로 만들어 버리고 IE 9 이전 버젼들은 HTML5 의 신규 요소들을 정확하게 처리하지 못합니다.

따라서 안전하게 크로스 브라우징이 되려면 웹 표준(well-formed)을 지켜야만 합니다. 태그들은 반드시 닫는 태그와 함께 사용해야 합니다.

$('<a href="http://jquery.com"></a>');

반드시 위와 같이 사용하거나 아래와 같이 사용해야 합니다.

$('<a/>');

jQuery 1.4 이후부터는 두번째 인자를 통해서 속성들을 부여할 수 있습니다. 이 인자에는 .attr() 함수에서 전달할 수 있는 인자를 포함한 속성 집합을 모두 사용할 수 있습니다. 게다가 사용자 이벤트 외에도 val, css, html, text, data, width, height, offset 과 같은 jQuery 의 함수도 추가할 수 있습니다. 참고로 인터넷 익스플로러에 input 태그를 추가한 후에 그 타입을 속성으로 변경 처리할 수는 없습니다. 즉, 체크박스를 추가하고 싶다면 반드시 '<input type="checkbox" />'와 같이 사용해야 합니다.(라고 되있지만 제가 테스트해 결과 모두 다 정상적으로 되더군요. 이 부분 해석을 발로 해서 뭔가 잘못된 것 같습니다. 혹시 관련해서 알려주실 분 있으시면 대 환영입니다. lol )

예 제
div 태그와 그 안의 모든 내용들이 동적으로 만들어 지고, body 요소에 추가됩니다. 내부적으로 이런 요소가 만들어지고 그 안에 innerHTML 속성을 사용해 마크업이 됩니다. 그러니까 이것은 꽤 유연하지만 한계도 같이 지니고 있습니다.(무슨 소리인지 모르겠습니다. ^^;;)

$("<DIV>
<P>Hello</P></DIV>").appendTo("body")

예 제
2번째 인자인 속성 맵을 이용하여 DOM 요소 만들기

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
$("<div/>", {
  "class": "test",
  text: "Click me!",
  click: function(){
    $(this).toggleClass("test");
  }
}).appendTo("body");
 
$("<input>", {
  type: "text",
  val: "Test",
  focusin: function() {
    $(this).addClass("active");
  },
  focusout: function() {
    $(this).removeClass("active");
  }
}).appendTo("form");

미리보기

위 소스를 보시면 1라인에 <div/> 라고 되어 있는 걸 보실 수 있습니다. 이렇게 하던가 <div></div> 이렇게 사용해야 한다는 겁니다. 그리고 속성들과 메소드들을 얼마든지 추가할 수 있습니다. 위 "Click me" 는 jQuery 의 toggleClass 함수를 사용하여 글자색을 클릭 시마다 변경하는 함수를 집어 넣었습니다. 아래 input 은 포커스가 들어오면 active 클래스를 토글하게 됩니다. 참 유용한 내용입니다.

jQuery( callback )Returns : jQuery

개요 : 문서가 모두 읽혀지면(finished loading) 호출될 함수를 지정합니다.

  • jQuery( callback )
  • callback 이 함수는 DOM 이 준비가 되면 실행됩니다.

이 함수는 $(document).ready() 와 같은 동작을 합니다. 혹시 $() 함수가 잘 동작되지 않을 때를 대비하여 사용하면 좋습니다. 즉, $(document).ready() 함수가 동작하지 않았을 때를 대비하여 jQuery( function($) {}); 와 같이 사용하시면 됩니다.

jQuery.noConflict()

이 함수는 jQuery() 의 별칭인 $() 의 사용을 더 이상 하지 않을 때 사용하게 됩니다. 이 내용은 이전 포스팅으로 대체하겠습니다.

http://findfun.tistory.com/entry/jQuery-쉽게하기-다른-라이브러리와-같이-쓰기  [새창으로] [바로이동]

 

우와 이번 포스팅 진짜 깁니다. 게다가 이 글을 쓰는 동안 베타버젼의 메소드가 하나 더 추가되었더 군요. ㅡ,.ㅡ;; jQuery.addClass() 라는 녀석입니다. 아직 베타여서 기술하지 않았습니다. 힘들어서 안한거 아닙니다. 절대로. 너무 길어서 나누어 할까 하다가 같은 페이지에서 볼 수 있어야 겠다고 생각이 들었습니다. 너무 길어져 버려서 스크롤 내리는 데만도 한참이네요. ㅡㅡ;;

어찌됬든 jQuery 의 핵심(core)를 들여다 봤습니다. 실제 사용하는데 있어서 이 내용을 몰라도 관계 없습니다. 그래도 관심있게 본 거랑은 다르겠죠. 휴우~ 다음번 부터는 내용이 좀 짧았으면 하네요.

그럼 즐프하세요. 
posted by 방랑군 2012. 1. 8. 20:56

출처 :   http://www.dorajistyle.pe.kr/2011/12/jquerycoffeescript-ajax.html?utm_source=feedburner&utm_medium=feed&utm_campaign=Feed%3A+DelightOnTheSimpleLife+%28%EC%9B%94%ED%92%8D%EB%8F%84%EC%9B%90%28%E6%9C%88%E9%A2%A8%E9%81%93%E9%99%A2%29+-+Delight+on+the+Simple+Life.%29 

[Jquery,CoffeeScript] 모질라 파이어폭스 Ajax. 한글 키 이벤트 처리.

모질라 파이어폭스에서 Ajax 한글 키 이벤트를 처리하는 Jquery,커피스크립트 코드입니다.

모질라 파이어폭스 Ajax. 한글 키 이벤트 처리.(Jquery Mozilla Force Keyup CoffeeScript module)

저는 주 브라우저로 모질라 파이어폭스를 사용합니다.
Ajax 모듈을 만드는데, 한글을 입력하면 못 알아듣더군요.
http://javascript.info/tutorial/keyboard-events에서 키 이벤트 체크를 해 봤습니다.
한글 키가 눌리면 Keydown(Keycode=229) 이벤트가 한 번만 발생하고,
Keyup 이벤트는 발생하지 않습니다.
중국어,일본어를 테스트 해보니 이 역시 같은 현상이군요.
한글과 다름없이 229키 코드가 딱 한번 발생합니다.
아마도 다른 블록형 문자 또한 같은 이벤트를 발생 시킬 거라 예상됩니다.
모질라에서 한글 키 이벤트를 부드럽게 처리하는 커피 스크립트 모듈을 만들었어요.
모질라 파이어폭스 이용자도 한글을 편하게 쓸 권리가 있으니까요.
필요하신 분은 마음껏 가져다 쓰세요.

커피스크립트 버전(Jquery Mozilla Force Keyup module  - Coffeescript version)



  
# Mozilla Force Keyup CoffeeScript module
# by 月風(http:://dorajistyle.pe.kr)
# How to use
# mozillaForceKeyup(”inputid”)
# in HTML.
# <input id=”input
id”>
mozillaForceKeyup = (targetId) ->
  if jQuery.browser.mozilla
    isIntervalRunning = null
    target = '#'+targetId
    $(target).bind 'keydown',(e) ->
      if e.which == 229
        forceKeyup = () ->
          $(target).trigger('keyup')
        if not isIntervalRunning
          isIntervalRunning = setInterval forceKeyup, 100

    $(target).bind 'blur',(e) ->
      if isIntervalRunning
        clearInterval isIntervalRunning
        isIntervalRunning = null



자바스크립트 버전(Jquery Mozilla Force Keyup module - Javascript version)



// Mozilla Force Keyup Javascript module
// by 月風(http:://dorajistyle.pe.kr)
// How to use
// mozillaForceKeyup(”inputid”)
// in HTML.
// <input id=”input
id”>

mozillaForceKeyup = function(targetId) {
var isIntervalRunning, target;
if (jQuery.browser.mozilla) {
isIntervalRunning = null;
target = '#' + targetId;
$(target).bind('keydown', function(e) {
var forceKeyup;
if (e.which === 229) {
forceKeyup = function() {
return $(target).trigger('keyup');
};
if (!isIntervalRunning) {
return isIntervalRunning = setInterval(forceKeyup, 100);
}
}
});
return $(target).bind('blur', function(e) {
if (isIntervalRunning) {
clearInterval(isIntervalRunning);
return isIntervalRunning = null;
}
});
}
};

 

'PP > Jquery' 카테고리의 다른 글

다른 라이브러리와 같이 쓰기  (0) 2012.01.08
jQuery Core  (0) 2012.01.08
jQuery UI 테스트 2  (0) 2012.01.08
jQuery 이벤트 테스트 2  (0) 2012.01.08
jQuery 이벤트 테스트 1  (0) 2012.01.08
posted by 방랑군 2012. 1. 8. 20:54

1. test8.jsp

01 <%@ page contentType="text/html; charset=UTF-8"%>
02 <%
03 String cp = request.getContextPath();
04 %>
05 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
06 <html>
07 <head>
08 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
09 <title>Insert title here</title>
10
11 <link href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.8/themes/base/jquery-ui.css" rel="stylesheet" type="text/css"/>
12 <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.5/jquery.min.js"></script>
13 <script src="http://ajax.googleapis.com/ajax/libs/jqueryui/1.8/jquery-ui.min.js"></script>
14
15 <script>
16 $(document).ready(function() {
17 $("#accordion").accordion();
18 });
19 </script>
20
21 </head>
22 <body style="font-size:62.5%;">
23 <h1>jQuery 테스트</h1>
24
25 <div id="accordion">
26 <h3><a href="#">Section 1</a></h3>
27 <div>
28 <p>
29 Mauris mauris ante, blandit et, ultrices a, suscipit eget, quam. Integer
30 ut neque. Vivamus nisi metus, molestie vel, gravida in, condimentum sit
31 amet, nunc. Nam a nibh. Donec suscipit eros. Nam mi. Proin viverra leo ut
32 odio. Curabitur malesuada. Vestibulum a velit eu ante scelerisque vulputate.
33 </p>
34 </div>
35 <h3><a href="#">Section 2</a></h3>
36 <div>
37 <p>
38 Sed non urna. Donec et ante. Phasellus eu ligula. Vestibulum sit amet
39 purus. Vivamus hendrerit, dolor at aliquet laoreet, mauris turpis porttitor
40 velit, faucibus interdum tellus libero ac justo. Vivamus non quam. In
41 suscipit faucibus urna.
42 </p>
43 </div>
44 <h3><a href="#">Section 3</a></h3>
45 <div>
46 <p>
47 Nam enim risus, molestie et, porta ac, aliquam ac, risus. Quisque lobortis.
48 Phasellus pellentesque purus in massa. Aenean in pede. Phasellus ac libero
49 ac tellus pellentesque semper. Sed ac felis. Sed commodo, magna quis
50 lacinia ornare, quam ante aliquam nisi, eu iaculis leo purus venenatis dui.
51 </p>
52 <ul>
53 <li>List item one</li>
54 <li>List item two</li>
55 <li>List item three</li>
56 </ul>
57 </div>
58 <h3><a href="#">Section 4</a></h3>
59 <div>
60 <p>
61 Cras dictum. Pellentesque habitant morbi tristique senectus et netus
62 et malesuada fames ac turpis egestas. Vestibulum ante ipsum primis in
63 faucibus orci luctus et ultrices posuere cubilia Curae; Aenean lacinia
64 mauris vel est.
65 </p>
66 <p>
67 Suspendisse eu nisl. Nullam ut libero. Integer dignissim consequat lectus.
68 Class aptent taciti sociosqu ad litora torquent per conubia nostra, per
69 inceptos himenaeos.
70 </p>
71 </div>
72 </div>
73 </body>
74 </html>

실행 결과

[출처] jQuery UI 테스트 1|작성자 엄보

'PP > Jquery' 카테고리의 다른 글

jQuery Core  (0) 2012.01.08
[Jquery,CoffeeScript] 모질라 파이어폭스 Ajax. 한글 키 이벤트 처리.  (0) 2012.01.08
jQuery 이벤트 테스트 2  (0) 2012.01.08
jQuery 이벤트 테스트 1  (0) 2012.01.08
jQuery UI 테스트 2  (1) 2012.01.08
posted by 방랑군 2012. 1. 8. 20:49

1. test2.jsp

01 <%@ page contentType="text/html; charset=UTF-8"%>
02 <%
03 String cp = request.getContextPath();
04 %>
05 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
06 <html>
07 <head>
08 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
09 <title>Insert title here</title>
10
11 <!-- jQuery 사용시 jquery-1.X.X.min.js 파일 연결 필수 -->
12 <script type="text/javascript" src="<%=cp%>/js/jquery-1.6.1.min.js" ></script>
13
14 <script type="text/javascript">
15 //jQuery는 $(선택자) 또는 jQuery(선택자)로 시작한다.
16 //$() 또는 $(document).ready()는
17 //문서가 사용 가능한 시점에 자동으로 인식해서 실행됨.
18 //$(function() { })와
19 //$(document).ready(function() { })는 같은 표현
20 $(document).ready(function() {
21 alert("Hello, JavaScript");
22 });
23 $(document).ready(function() {
24 alert("Hello, jQuery");
25 });
26 </script>
27
28 </head>
29 <body>
30 <h1>jQuery 테스트</h1>
31 jQuery에서 동일한 이벤트 등록시 둘 다 실행됨.
32 </body>
33 </html>

실행 결과



posted by 방랑군 2012. 1. 8. 20:48
01 <%@ page contentType="text/html; charset=UTF-8"%>
02 <%
03 String cp = request.getContextPath();
04 %>
05 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
06 <html>
07 <head>
08 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
09 <title>Insert title here</title>
10
11 <!-- jQuery 사용시 jquery-1.X.X.min.js 파일 연결 필수 -->
12 <script type="text/javascript" src="<%=cp%>/js/jquery-1.6.1.min.js" ></script>
13
14 <script type="text/javascript">
15 //익명 함수
16 //동일한 이벤트가 동시에 있는 경우 나중에 작성한 부분만 실행됨.
17 window.onload=function() {
18 alert("Hello, JavaScript");
19 };
20 window.onload=function() {
21 alert("Hello, jQuery");
22 };
23 </script>
24
25 </head>
26 <body>
27 <h1>jQuery 테스트</h1>
28 자바스크립트에서 동일한 이벤트 등록시 나중에 작성한 부분만 실행됨.
29 </body>
30 </html>

실행 결과

posted by 방랑군 2012. 1. 8. 20:46
01 <%@ page contentType="text/html; charset=UTF-8"%>
02 <%
03 String cp = request.getContextPath();
04 %>
05 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
06 <html>
07 <head>
08 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
09 <title>Insert title here</title>
10
11 <link href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.8/themes/base/jquery-ui.css" rel="stylesheet" type="text/css"/>
12 <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.5/jquery.min.js"></script>
13 <script src="http://ajax.googleapis.com/ajax/libs/jqueryui/1.8/jquery-ui.min.js"></script>
14
15 <script>
16 $(document).ready(function() {
17 $("#dialog").dialog();
18 });
19 </script>
20
21 </head>
22 <body style="font-size:62.5%;">
23 <h1>jQuery 테스트</h1>
24
25 <div id="dialog" title="Dialog Title">A dialog is a floating window that contains a title bar and a content area.
26 The dialog window can be moved, resized and closed with the 'x' icon by default.
27 If the content length exceeds the maximum height, a scrollbar will automatically appear.
28 A bottom button bar and semi-transparent modal overlay layer are common options that can be added.
29 A call to $(foo).dialog() will initialize a dialog instance and will auto-open the dialog by default.
30 If you want to reuse a dialog, the easiest way is to disable the "auto-open" option with: $(foo).dialog({ autoOpen: false }) and open it with $(foo).
31 dialog('open'). To close it, use $(foo).dialog('close'). A more in-depth explanation with a full demo is available on the Nemikor blog.
32 </div>
33
34 </body>
35 </html>

실행 결과

[출처] jQuery UI 테스트 2|작성자 엄보

posted by 방랑군 2012. 1. 8. 01:36

 급하게 테스트시 dataset 을 만들기 위해 xml 이나 db 로딩 말고 수동으로 만들때가 있다..

private DataTable GetDT()
        {
            DataTable dtdataTable = new DataTable();

            DataColumn col = new DataColumn("SEQ", typeof(Int32));

            col.AutoIncrementSeed = 1;
            col.AutoIncrement = true;
            col.AutoIncrementStep = 1;
            col.Caption = "Value ID";
            dtdataTable.Columns.Add(col);

            DataColumn[] Keys = new DataColumn[2];
            Keys[0] = col;
            dtdataTable.PrimaryKey = Keys;

            col = new DataColumn("TITLE", typeof(string));
            dtdataTable.Columns.Add(col);

            col = new DataColumn("CONTENTS", typeof(string));
            dtdataTable.Columns.Add(col);

            //col = new DataColumn("Value", typeof(string));
            //col.MaxLength = 50;
            //dtdataTable.Columns.Add(col);

            //col = new DataColumn("DateTime", typeof(Int32));
            //dtdataTable.Columns.Add(col);

            ArrayList ar = new ArrayList();
            ar.Add(1);
            ar.Add("a");
            ar.Add("b");

            dtdataTable.LoadDataRow(ar.ToArray(), true);

            ar.Clear();
            ar.Add(2);
            ar.Add("c");
            ar.Add("d");

            dtdataTable.LoadDataRow(ar.ToArray(), true);

            return dtdataTable;
            
        } 
posted by 방랑군 2012. 1. 8. 01:16


VB.NET 코드를 C# 코드로 변환해주는 사이트

사이트 #1 http://www.developerfusion.co.uk/utilities/convertvbtocsharp.aspx

사이트 #2 http://converter.telerik.com/Default.aspx

+단, 에러가 있으면 변환불가.

'PP > 번외' 카테고리의 다른 글

코딩에 도움이 되는 사이트들  (0) 2012.01.07
C# VS JAVA ~!~!~!  (0) 2012.01.04
posted by 방랑군 2012. 1. 8. 00:50

  Repeater.aspx 코딩부분....  ==> 두번째 이야기 에 코딩 덧붙인 것입니다..;;;

 <button id="btnTest_button" name="btnTest_button"

       onclick="return fn_Test(); runat="server">Toggle Button</button>
 <input type="button" id="btnTest" name="btnTest"

                     onclick="return fn_Test();" value="Toggle Button_2" />
 <input type="hidden" id="hdnAllValue" name="hdnAllValue" />
 <asp:HiddenField ID="hdnServerValue" runat="server" />

 Repeater.aspx - 자바스크립트 코딩 부분

 <script type="text/javascript">
  function fn_Test() {

   // 테이블 id ==> tblObj
   var tmpObj = document.getElementById("tblObj");
   // 토클효과를 주기 위한

   var objVisible = tmpObj.style.display;

   // 초기화         
    document.getElementById("hdnAllValue").value = "";            
    var tblRowCnt = tmpObj.rows.length;
            
    for (var i = 1; i < tblRowCnt; i++) {
            document.getElementById("hdnAllValue").value +=

            document.getElementById("txtValue_" + i.toString()).value + "^";

    // 값 축적 ==> 
            }

   document.getElementById("hdnServerValue").value =

                                 document.getElementById("hdnAllValue").value;

    //

   if ("none" == objVisible) {
        tmpObj.style.display = "block";}
   else {  tmpObj.style.display = "none";}

   return false;
  }
</script>

 Repeater.aspx .cs

 protected void Page_Load(object sender, EventArgs e)
{
    if (!IsPostBack)
    {
        DataBindings();
    }

    // 값이 같게 나와야되요..!! 전 저장을 제때못해서..;; 같게나와야정상임.
    string tmp = Request["hdnAllValue"];

    //==> 
    string tmp_1 = hdnServerValue.Value;

    //==> 
}

 

posted by 방랑군 2012. 1. 8. 00:50

Repeater 바인딩 예제
 ==> 이 그림의 예제는 리피터 콘트롤 바인딩 예제로 준비 한 것입니다.^^

 RptTest_1.aspx : 코딩

 <%@ Page Language="C#" AutoEventWireup="true"

                         CodeFile="RptTest_1.aspx.cs" Inherits="RptTest_1" %>

  ........

 <html xmlns="http://www.w3.org/1999/xhtml">
 <head id="Head1" runat="server">
 </head>
 <body>
  <form id="form1" runat="server">
   <div>
    <asp:Repeater ID="Rpt_1" runat="server">
    <HeaderTemplate>
     <table id="tblObj" border="1px">
      <tr>
       <th>번호</th>
       <th>제목</th>
       <th>내용</th>
       <th>비고</th>
      </tr>
    </HeaderTemplate>
    <ItemTemplate>
     <tr> 
     <td style="text-align:center;"><%# PlusNum(Eval("SEQ"))%></td>
     <td><%# Eval("TITLE")%></td>
     <td><%# Eval("CONTENTS")%></td>
     <td> <input type="text" id="txtValue_<%# Eval("SEQ")%>"

                             name="txtValue_<%# Eval("SEQ")%>" size="30" />
     </td>
     </tr>
    </ItemTemplate>
    <FooterTemplate>
  </table>
    </FooterTemplate>
 </asp:Repeater>
 </div>
 </form>
 </body>
 </html>

 RptTest_1.aspx.cs : 코딩

 public partial class RptTest_1 : PageBase
 {
   protected void Page_Load(object sender, EventArgs e)
   {
     if (!IsPostBack)
     {
      DataBindings();
     }
   }

 private void DataBindings()
 {

   SqlConnection con = new SqlConnection(constr);
   con.Open();

   SqlCommand com = new SqlCommand();
   com.Connection = con;
   com.CommandType = CommandType.StoredProcedure;
   com.CommandText = "USP_TEST_BOARD";
   SqlDataAdapter ad = new SqlDataAdapter(com);
   DataSet ds = new DataSet("NOVITEST");
   ad.Fill(ds, "TEST_BOARD");

   DataTable dt = ds.Tables["TEST_BOARD"];
   int rowCnt = dt.Rows.Count;
   for (int i = 0; i < rowCnt; i++)
   {
    dt.Rows[i]["TITLE"] = TestMethod(dt.Rows[i]["TITLE"].ToString());
   }

    this.Rpt_1.DataSource = dt;
    this.Rpt_1.DataBind();

    con.Close();
  }

  private string TestMethod(object strObj)
  {
    return strObj.ToString() + " - New Add Test String";
  }

  public string PlusNum(object objTmp)
  {
    return (Convert.ToInt32(objTmp) + 100).ToString();
  }
}

예제 설명

 1] <%# PlusNum(Eval("SEQ"))%> ==> 함수를 만들어서 바인딩한 예제

 2] id="txtValue_<%# Eval("SEQ")%>" 이런식으로 각 고유 아이디 가능 하다

 3] private string TestMethod(object strObj) ==> 코드 안딴에서 함수 처리

 ※ 참고

 DataSource에 배열을 바인딩 할 경우
  ==> <%# Container.DataItem %>

posted by 방랑군 2012. 1. 8. 00:49

리피터 컨트롤

 1] 데이터를 반복해서 보여주는 컨트롤

 2] 템플릿을 통해 행에 보여줄 형식을 지정

 템플릿 종류

 ItemTemplate

  - 데이터 항목을 보여줄 템플릿

  - 반드시 정의^^

 AlternatingItemtemplate

  - 열을 변경하면서 열의 색깔을 다르케 나오케 한다던가....

  - 반드시 지정 - X

 HeaderTemplate

  - 말그대로 머리 / 제목 부분

 FooterTemlate

  - 데이터 항목 리스트를 다 보여준 후에 보여질 것들 표시

  - 바닥영역

 SeparatorTemplate

  - 데이터 항목과 항목 사이에 보여줄 분리 템플릿

 기본 리피터 정의 형식

 <asp:Repeater ID="Rpt_1" runat="server">
  <HeaderTemplate>
   <table id="tblObj" border="1px" style="display:none;">
    <tr>
     <th>번호</th>
     <th>제목</th>
     <th>내용</th>
     <th>비고</th>
     </tr>
  </HeaderTemplate>
  <ItemTemplate>

   <%# Eval("CONTENTS")%>

  </ItemTemplate>

 sqlDataSource를 이용한 간단한 예제

 <asp:Repeater ID="rpt1" runat="server" DataSourceID="sql1">
 <HeaderTemplate>
 <table border="1px">
 <tr>
    <th>제목</th>
    <th>내용</th>
    <th>글쓴이</th>
    <th>기타</th>
    <th>글번호</th>
    <th>수정날</th>
 </tr>
 </HeaderTemplate>
 <ItemTemplate>
  <tr>
    <td><%# Eval("TITLE")%></td>
    <td><%# Eval("CONTENTS")%></td>
    <td><%# Eval("WRITE_DT")%></td>
    <td><%# Eval("ETC")%></td>
    <td><%# Eval("SEQ")%></td>
    <td><%# Eval("MODI_DT")%></td>
  </tr>
 </ItemTemplate>
 </asp:Repeater>
 <asp:SqlDataSource ID="sql" runat="server" 
    ConnectionString="<%$ ConnectionStrings:TIS %>" 
    SelectCommand="SELECT [SEQ], [TITLE], [CONTENTS],

                    [WRITE_DT], [MODI_DT], [ETC] FROM [TEST_BOARD]">
 </asp:SqlDataSource>

posted by 방랑군 2012. 1. 8. 00:46

출처 :  http://blog.naver.com/guruby?Redirect=Log&logNo=140031649144 

 이 글은 ASP.NET 개발을 책임지고 있는 Scott Guthrie의 블로그에서 가져온 글입니다.

원문은 http://weblogs.asp.net/scottgu/archive/2006/11/28/tip-trick-implement-donut-caching-with-the-asp-net-2-0-output-cache-substitution-feature.aspx에서 보실 수 있습니다.

 

이번 글은 좀 길어서 제대로 번역했는 지 의심스럽기도 합니다..
"번역은 반역이다"라는 말을 실감하고 있습니다..

 

-------------------------------------------------------------------------------


도넛 캐싱 구현 - ASP.NET 2.0 Output Cache Substitution

 

약간의 배경지식:
ASP.NET에서 매우 강력하지만 아직은 덜 사용되고 있는 것 중의 하나로 캐싱이 있다.
ASP.NET 캐싱 기능은 반복적인 사용자 요청에 대해 반복적으로 수행되는 것을 피할 수 있게 한다.
일단 한번 html 내용이나 data를 만들고 나서는 작업 결과를 저장해 놓았다가 재사용한다.
이것은 애플리케이션의 성능을 드라마틱하게 향상시킬 수 있다.
그리고 데이터베이스같은 중요한 자원의 부담을 줄일 수 있다.

 

Steve Smith는 ASP.NET 1.1에서의 캐싱에 대해 몇년 전 MSDN에 좋은 기사를 썼다.
그 기사는 ASP.NET 1.1 캐싱 기능의 몇가지 기본 사항과 사용방법에 대한 글이다.
만일 ASP.NET 캐싱 기능을 전에 사용해본 적이 없다면, 한번 시도해 볼 것을 권한다.
ASP.NET 2.0은 캐싱에 두가지 매우 중요한 기능을 추가했다.

 

1) SQL 캐쉬 무효화 지원 (SQL Cache Invalidation Support)
이것은 데이터베이스의 테이블이나 로우가 수정되면 자동적으로 캐쉬가 무효화되게 한다.
예를 들어 전자상거래 사이트의 제품 목록 페이지가 캐쉬되고 있는 상태에서
언제라도 가격을 바꾸면 바로 반영된다. (옛날 가격을 보여주지 않는다)

 

2) 출력 캐쉬 대체 (Output Cache Substitution)
내가 "도넛 캐싱"이라고 부르는 이 재치있는 기능은 출력 캐쉬된 페이지에서 일부분만 변하게 할 수 있다.
이것은 전체 페이지 출력 캐싱을 좀더 적극적으로 사용할 수 있게 한다.
부분 캐싱을 위해서 페이지를 여러개의 .ascx 사용자 컨트롤로 나눌 필요가 없다.
아래 팁은 이 기능을 만들게 된 동기와 구현 방법에 대해 설명한다.

 


실제 세계에서의 시나리오:

정해진 제품 카테고리로부터 제품 목록을 보여주는 페이지를 만들고자 한다.
제품목록 페이지인 Products.aspx 에는 <asp:datalist> 컨트롤이 있는데

middle-tier의 product data에 바인딩되어 있다.
이 페이지를 출력 캐쉬하면 매번 같은 요청에 대해 데이터베이스를 사용하지 않을 수 있다.
구현은 쉽다. 그저 페이지 맨위에 <%@ OutputCache %> 지시를 추가하면 된다.

 

아래 페이지에서 출력 캐쉬가 어떻게 설정되어 있는 지 보라.
100,000초 동안 캐쉬되고 있다가 northwind의 제품테이블이 수정되면 다음 요청부터 페이지가 즉시 갱신된다.
출력캐쉬 지시에 "VaryByParam" 속성이 있다. 이것은 ASP.NET이 categoryID별로 페이지를 따로 캐쉬하게 한다.
(예를 들어 Products.aspx?categoryId=1과 Products.aspx=2는 따로 저장된다.)

 

Products.aspx:

 

<%@ Page Language="VB" MasterPageFile="~/Site.master" AutoEventWireup="false" CodeFile="Products.aspx.vb" Inherits="Products" %>
<%@ OutputCache Duration="100000" VaryByParam="CategoryID" SqlDependency="northwind:products" %>

 

<asp:Content ID="Content1" ContentPlaceHolderID="ContentPlaceHolder1" Runat="Server">
<div class="catalogue">
    <asp:DataList ID="DataList1" RepeatColumns="2" runat="server">
        <ItemTemplate>
            <div class="productimage">
                <img src="images/productimage.gif" />
            </div>
            <div class="productdetails">
            
                <div class="ProductListHead">
                    <%#Eval("ProductName")%>
                </div>
                
                <span class="ProductListItem">
                    <strong>Price:</strong>
                    <%# Eval("UnitPrice", "{0:c}") %>
                </span>
            </div>
        </ItemTemplate>
    </asp:DataList>
    <h3>Generated @ <%=Now.ToLongTimeString()%></h3>
</div>
</asp:Content>

 


Products.aspx.vb:

 

Partial Class Products
    Inherits System.Web.UI.Page

    Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load

        Dim products As New NorthwindTableAdapters.ProductsTableAdapter

        DataList1.DataSource = products.GetProductsByCategoryID(Request.QueryString("categoryId"))
        DataList1.DataBind()

    End Sub

End Class


브라우저에서 접근하면 아래와 같이 보인다.


 


 


 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

아래쪽의 timestamp를 주의깊게 봐라.
이 timestamp는 100,000초가 지나거나 product 테이블의 데이터가 수정되면 바뀐다.
이 페이지는 모든 HTTP 요청에 대해 캐쉬된 것을 보여준다.
이 방법은 서버가 초당 1000여번의 요청 처리를 가능하게 하고 데이터베이스는 사용하지 않게 한다.
(그래서 무지하게 빠르다)

 

 

문제점:

위 예제의 한가지 문제점은 환영 메시지와 사용자 이름에서 발생한다. (위쪽 빨간 동그라미 참조)
이것은 ASP.NET 2.0 <asp:loginname> 컨트롤을 사용해서 Site.Master 페이지에서 생성되는 메시지이다.

 

<div class="header">
    <h1>Caching Samples</h1>
            
    <div class="loginstatus">
        <asp:LoginName FormatString="Welcome {0}!" runat="server" />
    </div>        
</div>

 

문제는 전체 페이지를 캐쉬하기 때문에 발생한다.
이 페이지에 접근하는 첫번째 사용자의 이름이 캐쉬되어서 다른 사용자에게 잘못된 환영 메세지를 보여주게 된다.
(이건 더 안좋은 상황이다..)

 


해결책:


이 방법을 해결하는데 두가지 방법이 있다.

 

첫번째 방법은 페이지를 전면 개편해서 사용자 컨트롤로 도배하는 것이다.
캐쉬될 필요가 있는 내용을 사용자 컨트롤 안에 넣고

각 .ascx 사용자 컨트롤의 맨 위에 <%@ OutputCache %>을 추가한다.
이 방법 역시 매번 데이터베이스에 접근하는 것을 피하고 사용자 이름도 정확하게 나오도록 한다.
이것은 ASP.NET 1.1에서 사용하는 방법인데 당연히 ASP.NET 2.0에서도 된다.


출력 캐쉬 대체 블럭 - <asp:substitution> 컨트롤 사용:
출력 캐쉬 대체 블럭은 전체가 캐쉬된 페이지에서 변경될 수 있는 부분을 표시할 수 있게 한다.
(예를 들면 위의 예제에서 사용자 이름이 그렇다)
나는 때때로 이것을 "도넛 캐싱 기능"이라고 부른다.
왜냐하면 페이지의 바깥 부분은 캐쉬되고 안쪽의 몇몇 구멍이 동적으로 변하기 때문이다.

이것은 사용자 컨트롤을 사용한 페이지 부분 캐쉬와 정확히 반대되는 개념이다.
페이지 부분 캐쉬는 페이지 전체가 동적으로 변하고 일부분이 캐쉬된다.

출력 캐쉬 대체는 (정확히 위의 Products.aspx 예에서 처럼) 페이지 전체를 출력 캐쉬해서 구현할 수 있다.
페이지 중에서 동적으로 변경되는 부분만 <asp:substitution> 컨트롤로 표시하면 된다.

 

<div class="header">
    <h1>Caching Samples</h1>
    
    <div class="loginstatus">
        <asp:Substitution ID="Substitution1" runat="server" MethodName="LoginText" />
    </div>
</div>

 

예를 들어 위 시나리오에서 환영 메세지를 동적으로 만들고 싶다면,
아래 메서드를  Site.Master 코드 비하인드 파일에 넣고 부르면 된다.

 

Partial Class Site
    Inherits System.Web.UI.MasterPage

    Shared Function LoginText(ByVal Context As HttpContext) As String
        Return "Hello " & Context.User.Identity.Name
    End Function

End Class

 

이제 전체 페이지 중에서 <asp:substitution> 컨트롤 부분만 빼고 출력 캐쉬되었다.

만일 쇼핑 카트같은 추가적인 개인 정보를 넣고 싶다면 당연히 그럴 수 있다.
좋은 점은 페이지의 다른 부분은 모두 캐쉬되었서 페이지를 생성하기 위해서
더이상 데이터베이스에 접근하지 않아도 된다는 것이다.
(이것이 의미하는 것은 한대의 서버로도 초당  수천번의 페이지 요청을 처리할 수 있다는 것이다)

사실은 요청을 처리하는 동안 어떠한 컨트롤도 생성되지 않는다. 단지 위의 static 메서드만 불린다.
그래서 모든 것이 무지 빠르다..

 


출력 캐쉬 대체 블럭 - Response.WriteSubstitution 메서드를 사용:

<asp:substitution>로 바뀌는 부분을 표시하는 방법 외에도 Response.WriteSubstitution를 사용하는 방법도 있다.

이 메서드는 HttpResponseSubstitutionCallback 위임 개체를 전달인자로 가진다.
그래서 애플리케이션 어디에서나 구현 가능하다.

(code-behind 클래스의 static 메서드에서 가능한 것이 아니다)

<asp:substitution> 도 내부적으로는 이 메서드를 사용해서 code-behind 클래스의 delegate와 연결한다.
같은 방법으로 당신의 사용자 컨트롤이나 페이지에서 사용할 수 있다.


결론:

아직도 캐쉬기능을 사용하지 않는 ASP.NET 애플리케이션을 발견하고 있다.
ASP.NET은 전체 페이지 출력 캐쉬, 페이지 부분 출력 캐쉬, 그리고 이제는 "도넛 캐싱"을 지원한다.
이것은 파라미터나 로직에 따라 캐쉬된 내용이 바뀔 수 있고 데이터베이스가 바뀌면 자동으로 내용을 갱신하게 한다.
일정 수준 이상의 애플리케이션이라면 캐쉬를 사용하지 않는 애플리케이션을 찾기 힘들 것이다.

 

나는 강력히 모든 ASP.NET의 캐쉬 기능을 알아 볼 것을 권한다.
다른 캐쉬 사용 예를 보기 원한다면 내 Tips/Tricks talk from the recent ASP.NET Connections event을

다운로드하길 바란다.
이 발표에서 나는 어떻게 전체 페이지 캐싱, 페이지 부분 캐싱, 대체 블럭 캐싱, SQL 캐쉬 무효화를 하는지 보여준다.
그리고 추가적인 ASP.NET 팁들 보려면 내 ASP.NET Tips, Tricks and Resources page를 보기 바란다.

 

이 글이 도움이 되기를
Scott

'PP > ASP.NET' 카테고리의 다른 글

[ASP.NET] Repeater(리피터) 2  (0) 2012.01.08
[ASP.NET] Repeater(리피터) 1  (0) 2012.01.08
[캐싱] Caching Process  (0) 2012.01.08
[캐싱] ASP.NET 캐싱 기능을 살펴보자.  (0) 2012.01.08
[캐싱] 웹사이트 캐싱전략  (0) 2012.01.08