Stephen Ball 블로그 글 중에 REST API를 클라이언트 개발에 큰 도움이 될만한 글이라 생각되어 번역해보았습니다.

REST API 클라이언트 구현 중 마스터-디테일 관계 구현에 도움이 될것입니다.

이 글은 ‘REST 서버와 클라이언트 개발하기’의 세번째 편이다. 여기에서는TRESTResponseDataSetAdapter를 주로 사용한다.

 

앞선 두편의 글에서, REST서버를 만들고 YAML을 이용하여 API 전체 도움말을 제공해보았다. 당시  우리는 데이터 집합 3개를 제공했었다. 그리고 나서, 코드를 직접 쓰지 않고도 마스터-디테일 관계를 가진 데이터 집합(들)을 REST 상에 오픈했다. 앞선 글과 비디오를 보지 못했다면, 1편부터 시작하기를 권장한다.- 이 세번째 편에서는 델파이로 멀티 플랫폼 클라이언트를 만들어서 앞에서 만든 API를 사용해보기로 하자.

 

클라이언트를 만드는 순서

이 글과 비디오는 아래 순서로 진행된다.

  1, REST API에 연결할 컴포넌트(들) 설정 (RAD 방식으로 빠르게 구현)

  2, JSON을 읽어서 마스터-디테일 데이터셋(들)로 변환 (JSON 데이터의 계층 구조를 기준으로)

  3, 생성된 데이터셋을 라이브바인딩(LiveBindings)을 이용하여 코드 작성없이 화면에 표현

  4, API 호출을 줄이는 팁

 

클라이언트에서 REST 리소스에 연결하기

델파이/C++빌더에서 REST 리소스에 빠르게 연결하도록 하는 컴포넌트 셋트는 윈도우용 VCL 애플리케이션과 멀티-플랫폼용 FMX에서 모두 사용할 수 있다. 해당 유닛(들)은 모두 REST 네임스페이스 안에 있으며, 윈도우, 맥OS, 안드로이드, iOS 각각에 알맞은 네이티브 코드를 만들어낸다. 

 

이미 ‘TRESTClient를 사용하여 MailChimp와 Azure Translation Services에 연결하기’ 편에서 이 컴포넌트 세트에 대한 기초를 다루었으므로, 지금은 바로 REST Debugger를 활용하여 바로 시작해보자. REST Debugger는 매우 유용하며, 다양한 목적으로 사용할 수 있는 도구이다. 

 

REST Debugger는 (RADStudio /bin 디렉토리에 들어있는) 애플리케이션이다. REST 엔드 포인트에 빠르게 연결할 때 사용된다. 사용자 보안 정보, 엔드 포인트, 리소스, 파라미터 등을 화면에서 손쉽게 지정하고 나서 “copy components” 버튼을 클릭하고나서, 개발 화면에서 붙여넣기를 하면, REST 데이터를 가져오는데 필요한 모든 컴포넌트(들)이 앞서 설정한 모든 정보가 반영된  상태로 추가된다. (REST Debugger를 개발 환경 도구 메뉴에 추가하는 방법 보기

 

아래와 같이 REST Debugger를 실행하고, 필요한 설정을 한 후, 원하는 엔드 포인트에 잘 연결되는지를 확인하고나서 해당 컴포넌트(들)을 애플리케이션으로 가져오면 된다.

RestDebugger.gif

 

 

비디오 보기 - Rest Debugger 사용하기

 

클라이언트에서 JSON을 TDataSet으로 변환

TRESTResponse 컴포넌트에 있는 JSON 배열 데이터를 TDataSet으로 변환할 때에는TRESTResponseDataSetAdapter가 유용하다.
TRestResponseDataSetAdapater.png

 

 

 

TRESTResponseDataSetAdapter는 TRESTRequest 통해 가져온 JSON 내용을 FieldDefs에 맞게 변환하여 TDataSet에 넣어준다. 

 

RAD 스튜디오 개발 환경에서 TRESTRequest를 (마우스 오른쪽을 클릭하여) Execute를 실행하면, 반환되는 데이터 내용을 바탕으로 TDataSet에 자동으로 FieldDefs(들)이 완성된다. 255자가 넘는 문자열이 필요하다면 StringFieldSize 프로퍼티를 수정하면 된다. (또는 원하는 문자열에 해당되는 FieldDefs를 수정하면 된다.)

 

RESTResponseDataSetAdapter를 사용해 JSON 데이터 배열의 상세 데이터 다루기

TRESTRequest는 하나를 TRESTResponseDataSetAdapters 여러개에서 사용할 수 있는데 상당히 편리하다. 지금 처럼 JSON 배열 안에 또 다른 배열 데이터가 들어있는 경우에도 API 호출을 한번만에 전달할 수 있다.

JSON-data-with-embedded-Array.png

 

샘플 REST 서버에 있는 예시(http://localhost:8080/exams/1/questionsfull/)

 

REST 서버의 /exams/{exam_id}/questionsfull/ 리소스는 QUESTIONS 배열을 제공하는데, 각 QUESTIONS 배열에는 해당 QUESTIONS에서 제시될 문항들이 ANSWERS 배열로 들어있다. 

 

위의 예를 반복하면 QUESTIONS을 데이터 집합으로 익스포트할 수 있다. (하지만, 다루기 쉬운 형태로 결과가 나오지는 않는다. 따라서). 

 

TRESTResponseDataSetAdapter를 하나 더 사용하여 RootElement에 특정 JSON 배열 필드를 지정하자. (예를 들어 특정 QUESTIONS에 해당하는 ANSWERS 배열들만 디테일 TDataSet에 넣도록 하자).

MasterDetail_TRESTRequestDataSetAdapter1.gif

예> RootElement 가져오기

 

RESTDebugger는 필요한 컴포넌트를 구성 (또는 RootElement 관련 구문을 확인) 할 때에도 역시 도움이 된다. TRESTResponseDataSetAdapter과 TDataSet를 수동으로 새로 추가할 수도 있다. 아니면 위와 같이 복사하여 붙여넣고 나서 중복해서 생긴 TRESTClient and TRESTRequest만 삭제하면 된다. JSON의 RootElement는 JSON 내용의 인덱스와 해당 프로퍼티의 이름을 기반으로 한다. 예를들어 [0].ANSWERS는 (우리가 지금 가져오려는 값인) JSON 배열의 첫번째 요소에 있는 ANSWERS 필드를 가져와서 TDataSet으로 변환한다.

 

런타임 시, TRESTRequestDataSetAdapter의 RootElement 사용하기

해당 TDataSet(들)은 지정된 TRESTResponse와 RootElement에 의해 자동으로 채워진다. 하지만, 지정된 RootElement가 Questions 데이터셋의 현재 레코드에 맞춰주어야 한다.  TDataSet의 AfterScroll 이벤트에서 쉽게 처리할 수 있다. (지금은 데이터 로드는 신경쓰지 말자. 관련 메소드를 만들고 사용하는 것은 잠시 후에 보기로 하자).

procedure TdataExams.table_QUESTIONSAfterScroll(DataSet: TDataSet);
begin
  if (DataSet.FieldByName('QUESTION_ID').AsString 
    = '') or Loading then Exit;

  rdsaANSWERS.RootElement :=
    '['+Pred(DataSet.RecNo).ToString+'].ANSWERS';
end;

이제 스크롤 될 때, 마스터 디테일 데이터가 데이터셋에 로드된다. 하지만, 질문이 해당 시험과 확실히 잘 연결되도록 해야한다. 

 

Exams 데이터셋에서 역시 같은 이벤트를 사용하면, Questions API에 전달할 파라미터를 (해당되는 EXAM에 맞게) 업데이트하고  TRESTRequest.Execute 메소드를 상용하여 데이터를 가져올 수 있다.

procedure TdataExams.tblEXAMSAfterScroll(DataSet: TDataSet);
begin
  if  Loading or  (DataSet.FieldByName('EXAM_ID').AsString = '') then
    Exit;

  RESTRequestQUESTIONSFULL.Params.
  ParameterByName('EXAM_ID').Value := 
    DataSet.FieldByName('EXAM_ID').AsString;
  BeginLoad;
  try
    // reset the RootElement before execute
    rdsaANSWERS.RootElement := '[0].ANSWERS';
    RESTRequestQUESTIONSFULL.Execute;
  finally
    EndLoad(rdsaQUESTIONS.Dataset);
  end;
end;

Loading, BeginLoad, EndLoad

해당 데이터용 코드 전체가 해당 데이터모듈 안에 들어 있도록 하기 위해 LoadExams 메소드를 추가한다. 여기에는 다음과 같은 메소드(들)이 포함된다. FLoad : Integer는 이 데이터모듈의 변수(variable)로써 데이터가 로드되는 시점을 추적한다. 일단 로드가 되는 중에는 데이터셋이 스크롤 되는 동안 API 호출이 중복하여 발생되지 않도록 체크한다.

procedure TdataExams.BeginLoad;
begin
  Inc(FLoad);
end;

procedure TdataExams.EndLoad(DataSet: TDataSet);
begin
  Dec(FLoad);
  // Now loading is done, update the data
  if Assigned(DataSet) and
     Assigned(DataSet.AfterScroll) then
    DataSet.AfterScroll(DataSet);
end;

function TdataExams.Loading: Boolean;
begin
  Result := FLoad > 0;
end;

procedure TdataExams.LoadExams;
begin
  BeginLoad;
  try
    RESTRequestEXAMS.Execute;
  finally
    EndLoad(rdsaEXAMS.Dataset);
  end;
end;

 

화면에 데이터 표현하기

화면에 데이터를 어떻게 표현하는지 확실히 알지 못한다면, 위에 언급한 비디오를 보거나 이전에 작성한 라이브바인딩(LiveBindings) 글 시리즈를 살펴보기 바란다. 예를 들어 시험, 질문, 답변이라는 그리드 3개로 시작해보는 것도 좋다. 

요컨대, uses에 해당 데이터 모듈을 추가(File > Use Unit.. > 목록에서 해당 데이터 모듈 선택)했는 지 확인하고 나서, 폼에서 마우스 오른쪽 클릭 > Bind Visually > 해당 데이터셋을 원하는 그리드 콘트롤에 연결하면 된다. 이제 클라이언트 애플리케이션에서는 해당 데이터모듈에 있는 LoadExams 메소드만 호출하면 된다. 다음 시간까지… 해피 코딩(happy coding)!

 

이 글의 본문. 즉, Developing client applications using RESTful master-detail data with TRESTResponseDataSetAdapter은 Stephen Ball's Technical Blog에 먼저 게시되었다..

 

번호 제목 글쓴이 날짜 조회 수
공지 [DelphiCon 요약] 코드사이트 로깅 실전 활용 기법 (Real-world CodeSite Logging Techniques) 관리자 2021.01.19 22115
공지 [UX Summit 요약] 오른쪽 클릭은 옳다 (Right Click is Right) 관리자 2020.11.16 20659
공지 [10.4 시드니] What's NEW! 신기능 자세히 보기 관리자 2020.05.27 22701
공지 RAD스튜디오(델파이,C++빌더) - 고객 사례 목록 관리자 2018.10.23 28461
공지 [데브기어 컨설팅] 모바일 앱 & 업그레이드 마이그레이션 [1] 관리자 2017.02.06 29722
공지 [전체 목록] 이 달의 기술자료 & 기술레터 관리자 2017.02.06 25071
공지 RAD스튜디오(델파이, C++빌더) - 시작하기 [1] 관리자 2015.06.30 46008
공지 RAD스튜디오(델파이,C++빌더) - 모바일 앱 개발 사례 (2020년 11월 업데이트 됨) 험프리 2014.01.16 181771
1183 [고객사례-사물인터넷, 앱, 델파이] 로봇청소기 제어 앱 '니토 툴리오' 관리자 2020.03.24 465
1182 RAD Studio 10.3.3 안드로이드 앱에서 센서 컴포넌트 사용시 링크 오류 해결방법 김원경 2020.03.18 373
1181 [델파이 안드로이드 64비트 오류 수정] TInAppPurchase 컴포넌트 수정 file 김원경 2020.03.18 377
1180 [기술백서] 다양한 팀 '협업' 방법론과 개발 방식 관리자 2020.03.18 679
1179 RAD Studio IDE에 툴 추가하기 file 김원경 2020.03.17 376
1178 RAD 서버 : 웹 속성을 폴더에 매핑하기 file 김원경 2020.03.17 1582
1177 델파이 개발자 관점에서 본 윈도우 개발 file 김원경 2020.03.13 760
1176 C++ 언어와 C++빌더의 23년! 관리자 2020.03.13 626
1175 MS 비주얼 스튜디오 C++을 C++빌더와 함께 활용하기 관리자 2020.03.12 656
1174 Swagger / YAML 및 RESTful API의 자체 문서화 김원경 2020.03.11 1798
1173 [고객사례-유틸리티, 델파이] Navuu 관리자 2020.03.09 396
1172 [고객사례-유틸리티, 델파이] SupRemo - 개인방송, 화상회의 솔루션 관리자 2020.03.09 916
1171 RAD 서버에 Swagger UI 임베이딩 김원경 2020.03.09 595
1170 검사(Audits)와 측정(Metrics) 기능을 이용 소스코드 표준과 규약 준수를 측정하고 개선할 수 있습니다. 험프리 2020.03.06 309
1169 TEMSDataSetResource 컴포넌트를 사용하여 RAD 서버의 마스터-디테일 데이터 구현하기 file 김원경 2020.03.06 459
» RESTful 마스터-디테일 데이터를 사용하는 클라이언트 애플리케이션을 TRESTResponseDataSetAdapter를 사용하여 개발하기 file 험프리 2020.03.03 644
1167 [10.4 프리뷰] 베타 서비스 시작 & 새 기능 미리 보기 관리자 2020.03.03 1666
1166 델파이 25주년 기념 무료 크로스 플랫폼 샘플 앱 25개 선정(델파이/C++ 샘플 150여종) 험프리 2020.03.02 690
1165 윈도우 10에서의 High DPI 김원경 2020.03.02 1397
1164 이 달의 기술자료 - 2020년 03월 file 험프리 2020.02.28 317