본문 바로가기

CDS View(Core Data Service)/Core Data Service 기초

Authorization Concept

ABAP 기반의 권한 부여 프레임워크는 아래 그에 나와 있는 것처럼 여러 구성요소들인 권한 객체, 프로파일, 그리고 사용자 역할을 활용하여 애플리케이션 내에서 권한과 관련된 체크를 구현합니다. 이러한 체크들은 사용자가 프로그램, 트랜잭션, 또는 애플리케이션에 접근할 때 ABAP 런타임 환경에서 암묵적으로 수행됩니다.

또 다른 방법으로, 애플리케이션 코드 내에서 명시적으로 권한을 체크하려면 AUTHORITY-CHECK 문을 사용하여 런타임에서 접근을 평가할 수도 있습니다. 그러나 이 접근 방식의 단점은 애플리케이션 데이터와 애플리케이션에서 사용되는 권한 객체 사이에는 보이지 않는 연결이 존재한다는 것입니다. 또한 디버깅 권한이 있는 사용자는 이러한 체크를 우회할 수 있으며, 이는 보안 위험을 야기할 수 있습니다.

이러한 접근 방식은 또한 애플리케이션이 레코드 또는 데이터베이스 수준에서 권한 체크가 필요한 경우에도 권장되지 않습니다. 클래식한 접근 방식에서는 데이터베이스 수준에서 이러한 체크를 무시하여 더 큰 데이터셋의 읽기를 용이하게 합니다. 그런 다음 ABAP 코드에서 관련 권한 체크를 수행하여 사용자 마스터 레코드에서 접근을 확인함으로써 데이터셋을 필터링합니다. 이러한 전통적인 데이터-코드 접근 방식은 SAP HANA에서 애플리케이션을 개발하는 동안 권장되지 않습니다.


Data Control Language Overview


AS ABAP 7.40 SP10 버전부터, CDS (Core Data Services) 뷰 정의에 대한 접근 제어를 모델링되고 선언적인 방식으로 정의하기 위해 새로운 종류의 Repository Object인 DCL 소스(DCL Source)가 도입되었습니다.

그림1과 그림2에서 보여지는 것처럼, DCL 소스는 DEFINE ROLE 키워드를 사용하여 하나 이상의 CDS 엔티티를 대상으로 CDS 역할을 정의합니다. GRANT SELECT ON 문을 사용하여 WHERE 절에 접근 조건을 지정하여 뷰에 대한 사용자 권한을 검증합니다. CDS 엔티티가 Open SQL 문을 사용하여 애플리케이션 프로그램에서 접근되면, 그림 2에서 보여지는 것처럼 데이터베이스 인터페이스는 자동으로 DCL 소스에 지정된 접근 조건에 따라 결과 집합을 필터링합니다.

이러한 접근 제어는 오직 CDS 뷰가 Open SQL 문을 사용하여 애플리케이션 프로그램에서 직접 접근되거나, 데이터 모델을 사용할 수 있게 해주는 Service Adaptation Description Language (SADL)을 통해 접근되는 경우에만 유효합니다. 그렇지 않은 경우에는 다른 뷰를 통해 간접적으로 접근되는 경우에는 접근 제어가 무시될 수 있습니다.

그림1
그림 2


Data Control Language Syntax and Access Conditions


접근을 관리하기 위해, DCL 소스를 정의할 수 있습니다. DEFINE ROLE 문을 사용하여 하나 이상의 CDS 엔티티에 대해 GRANT SELECT ON 키워드를 이용하여 접근 권한을 지정하고 WHERE 절에 접근 조건을 지정합니다.

DCL 소스를 만들기 위해서는 아래와 같은 단계를 따라야 합니다.

1. DEFINE ROLE 문을 사용하여 DCL 소스를 정의합니다. 정의된 역할의 이름은 <DCL_SOURCE_NAME>으로 지정합니다.
2. GRANT SELECT ON 문을 사용하여 하나 이상의 CDS 엔티티에 대해 DCL 소스를 정의할 수 있습니다. 각 CDS 엔티티의 이름은 중괄호 { } 내부에 <CDS_ENTITY1>, <CDS_ENTITY2>와 같이 지정합니다.
3. 각 CDS 엔티티에 대해 접근 조건을 지정할 수 있으며, 각 GRANT 문에 최소한 하나의 조건을 지정해야 합니다.
4. 여러 개의 CDS 엔티티가 있는 경우에는 세미콜론 (;)을 구분자로 사용하여 이들을 분리해야 합니다.

DCL 소스에서는 접근 조건이 사용자의 권한을 필드 값에 대해 확인하고 WHERE 절을 사용하여 정의될 수 있습니다. 아래 소스 코드에 나와있는 것처럼, 접근 조건은 다음과 같은 방법으로 지정할 수 있습니다.


■ 리터럴 조건 또는 현재 사용자
■트랜잭션 PFCG(Policy-Based Access Control)에 대한 접근 조건

--Access Conditions using Literals
@EndUserText.label: 'Demo access control using literal'
@MappingRole: true
define role Zdcl_Example_01 
{
grant select on cds_entity
where entity_element_1 = ‘literal_value’
   or entity_element_2 = aspect user; 
}



--Access Conditions using PFCG
@EndUserText.label: 'Demo access control using PFCG'
@MappingRole: true
define role Zdcl_Demo 
{
grant select on cds_entity
where ( entity_element_1,
   or entity_element_2 ) = aspect pfcg_auth(authorization_object,
                                            authorization_field_1,
                                            authorization_field_2,
                                            filter_field1 = ‘filter_value_1’);
}

리터럴 조건을 사용하면 CDS 뷰의 필드를 리터럴 값과 비교하여 액세스를 제한할 수 있습니다. 예시는 아래와 같습니다.

Where entity_element_1} = {literal_value}
or ${entity_element_2} = aspect user;

아래에서 보여지는 Zdcl_Example_01 역할은 CDS 엔티티 ZCDS_Example_01을 대상으로 정의되었습니다. 이 역할은 엔티티 필드 CARRID를 기반으로 리터럴 조건을 사용하여 엔티티의 접근을 제한합니다. 아래 그림에서 보여지는 것처럼, 엔티티의 역할을 정의하기 이전에는 CDS 뷰의 결과 집합이 모든 레코드를 표시합니다.

@EndUserText.label: 'DCL source with Simple literal Condition'
@MappingRole: true

define role Zdcl_Example_01 {
grant select on ZCDS_Example_01
                where carrid = 'AZ';
}

CDS 뷰에 대한 엔티티 역할이 정의되면, 역할 정의에서 정의된 리터럴 조건에 따라 결과 집합이 제한됩니다. 아래 그에서 보여지는 것처럼 결과 집합은 엔티티 역할에 설정된 접근 조건에 따라 제한됩니다.

PFCG (Policy-Based Access Control) 조건을 사용하면 CDS 엔티티의 하나 이상의 필드를 사용하여 현재 사용자의 사용자 마스터 레코드에서 권한을 평가할 수 있습니다. 이 권한 평가는 사용자 역할에 할당된 권한 객체를 기반으로 합니다. 각 PFCG 조건은 항상 하나의 권한 객체와 관련됩니다. 뷰의 필드들은 아래 코에서 보여지는 구문을 사용하여 권한 객체의 필드들과 연결됩니다.

where
(entity_element_1, entity_element_2) =
aspect pfcg_auth(authorization_object,
                 authorization_field_1,
                 authorization_field_2,
                 filter_field_1 = 'filter_value_1');

 

다음 예제에서는 역할 Zdcl_Example_02가 두 개의 권한 객체인 S_CARRID와 ZSFLIGHT를 사용하여 CDS 엔티티 ZCDS_example_02에 대한 액세스를 부여하도록 정의되었습니다. 이때 권한 객체들과 그 필드들은 역할 정의의 WHERE 절에서 pfcg_auth 함수의 인수로 전달됩니다.

첫 번째 조건은 권한 필드 CARRID 및 Transaction PFCG에서 권한 객체 S_CARRID에 대해 정의된 권한 프로파일의 필드 값을 기반으로 레코드를 제한합니다. 아래 그에서 보여지는 것처럼, ABAP에서는 다음과 같은 예제에서 키워드 AUTHORITY-CHECK를 사용하여 동등한 권한 체크를 애플리케이션 프로그램에서 수행합니다.

AUTHORITY-CHECK OBJECT 'S_CARRID'
ID 'CARRID' FIELD ‘AA’
ID 'ACTVT' FIELD '01'.

두 번째 조건은 권한 필드 CONNID 및 Transaction PFCG에서 권한 객체 ZSFLIGHT에 대해 정의된 권한 프로파일의 필드 값을 기반으로 레코드를 제한합니다. 아래 그림에서 보여지는 것처럼, ABAP에서는 다음과 같은 예제에서 키워드 AUTHORITY-CHECK를 사용하여 동등한 권한 체크를 애플리케이션 프로그램에서 수행합니다.

AUTHORITY-CHECK OBJECT 'ZSFLIGHT'
ID 'CONNID' FIELD ‘0017’
ID 'ACTVT' FIELD '01'.

CDS 뷰를 역할 정의와 함께 사용하기 전에, 해당하는 권한 객체가 Transaction PFCG에서 프로파일에 할당되어 있으며, 관련 사용자에게 할당되어 있는지 확인해야 합니다(그림 1). 이렇게 하면 암시적 권한 체크가 수행될 수 있습니다 (그림 2).

그림 1
그림 2

PFCG 접근 조건을 관리하기 위해서는 아래 단계를 따르면 됩니다.

1. 아래는 SFLIGHT 데이터 소스로부터 모든 열을 가져오는 ZCDS_example_02 CDS 뷰의 정의입니다.

@AbapCatalog.sqlViewName: 'ZCDS_EX_SQL_02'
@AbapCatalog.compiler.compareFilter: true
@AbapCatalog.preserveKey: true
@AccessControl.authorizationCheck:#CHECK
@EndUserText.label: 'CDS to select all fields'
define view ZCDS_example_02
as select
*
from sflight

 

2. 아래 코드는 CDS 뷰 ZCDS_example_02에 대한 액세스 조건을 정의하기 위한 ZDCL_Example_02 역할의 정의입니다.

@EndUserText.label: 'DCL source with PFCG Aspect'
@MappingRole: true
define role Zdcl_Example_02 {
grant
  select on ZCDS_example_02
  where
  (carrid) = aspect pfcg_auth(s_carrid,
                              carrid,
                              actvt = '03')
  and
  (connid) = aspect pfcg_auth(zsflight,
                              connid,
                              actvt = '03');

3. 위 코드에서 WHERE 절의 왼쪽 부분은 하나 이상의 쉼표로 구분된 뷰 필드들을 괄호 안에 포함해야 합니다.
4. WHERE 절의 오른쪽 부분에는 코에서 보여지는 것처럼 권한 객체를 지정하기 위해 ASPECT 키워드와 pfcg_auth 함수가 포함되어야 합니다.
5. pfcg_auth 함수의 인수는 권한 객체와 해당하는 필드들을 하나씩 기대합니다. 이는 위 코에서 보여진 것과 같습니다.


CDS 뷰 ZCDS_example_02의 결과 집합은 그림 1에서 보여지는 것처럼 엔티티의 역할이 정의되기 이전에는 모든 레코드를 표시합니다. 그러나 CDS 뷰에 엔티티 역할이 정의된 후에는 결과 집합이 엔티티의 역할 정의에서 정의된 권한 조건을 기반으로 제한됩니다. 이는 PFCG 조건을 사용하여 권한을 제어하는 방식으로 그림 2에서 보여집니다.

그림 1
그림 2


Data Control Language Source Definition


접근 제어를 정의하기 위해 ADT(ABAP Development Tools)에서 Repository Object의 새로운 종류인 DCL 소스(Data Control Language source)가 도입되었습니다. CDS 뷰와 유사하게 DCL 소스는 ADT를 통해서만 정의하고 분석할 수 있습니다.

DCL 소스 코드 에디터에서 제공되는 접근 제어를 정의하기 위한 사용 가능한 템플릿은 아래 STEP 7에서 나중에 보여질 것과 같습니다. 아래는 이 템플릿들의 목록을 나타냅니다.

■ Define role with simple conditions(접근 조건을 갖는 간단한 역할을 정의)
리터럴 조건 또는 현재 사용자 이름을 사용하여 CDS 엔티티에 인스턴스별 액세스를 부여하는 간단한 역할을 정의합니다.


■ Define role with PFCG aspect(PFCG Aspect를 사용하여 역할을 정의)
PFCG 역할에 할당된 클래식 권한 개념(권한 객체 사용)과 PFCG 역할에서 파생된 권한을 기반으로 CDS 엔티티에 인스턴스별 액세스를 부여하는 역할을 정의합니다.

■ Define role with inherited conditions(상속 조건을 사용하여 역할을 정의)
상속을 사용하여 보호된 엔티티를 데이터 원본으로 사용하는 CDS 엔티티에 대한 CDS 접근 제어를 생성합니다. 이렇게 하면 조건을 복사하지 않고도 CDS 엔티티에 대한 액세스 제어를 만들 수 있습니다.

■ Define role with generic aspect(일반적인 Aspect를 사용하여 역할을 정의)
e generic Aspect 정의에서 정의된 e generic Aspect의 값에 기반하여 CDS 엔티티에 인스턴스별 액세스를 부여하는 역할을 정의합니다.

■ Define role generic aspect(e generic Aspect를 정의)
generic Aspect가 현재 사용자에 대해 허용된 값을 제공하는 방법을 정의합니다.

■Define role with unrestricted access(제한 없는 액세스를 부여하는 역할을 정의)
CDS 엔티티에 무제한 액세스를 부여하는 역할을 정의합니다.

■ Define role with privileged access(특권 채널을 사용하여 특권 액세스를 부여하는 역할을 정의)
특권 채널을 사용하지 않으면 CDS 엔티티에 대한 액세스를 거부하는 역할을 정의합니다. 다른 CDS 접근 제어를 통해 액세스가 부여된 경우에는 여전히 액세스가 가능합니다.

DCL 소스를 만들기 위해서는 다음과 같은 순서를 따라야합니다.

Step 1. SAP HANA Studio나 Eclipse를 실행합니다.
Step 2. Window - Perspective - Open Perspective - Other - ABAP의 순서로 ADT 안에 있는 ABAP perspective를 실행합니다.
Step 3. File - New - Other ABAP Repository obejct - DCL을 클릭하고 Next를 클릭합니다.
Step 4. 아래 그림에서 보여지는 대로, 접근 제어를 생성할 프로젝트와 패키지를 지정합니다. "이름(Name)"과 "설명(Description)" 필드에 각각 접근 제어의 이름과 설명을 제공합니다. 그리고 다음 단계로 진행하기 위해 "다음(Next)"을 클릭합니다.

Step 5. 다음 화면에서 CTS를 입력합니다.
Step 6. 접근 제어를 정의할 DCL 소스 템플릿을 선택합니다.

Step 7. 아래에서 보여지는 대로, DCL 소스를 사용하여 제한을 적용하려는 CDS 엔티티 이름인 "ZCDS_Example_01"을 지정합니다.



Step 8. carrid에 대한 액세스 조건으로 리터럴 "AA"를 지정하여 접근 제어를 저장하고 활성화합니다.

DCL 소스가 활성화된 후, Listing 8.32에서 보여지는 것과 같이 해당 DCL 소스와 연관된 CDS 뷰는 정의된 접근 조건에 따라 결과 집합을 필터링합니다.

그림 1에서 보여지는 예시에서, CDS 뷰 ZCDS_Example_01은 어떠한 접근 제어도 생성되기 이전에는 모든 레코드를 표시합니다. 즉, 접근 제어가 존재하지 않는 상태입니다. 이는 결과 집합이 제한되지 않고 모든 데이터가 표시되는 것을 의미합니다.

그러나 그림 2에서 보여지는 것처럼, 접근 제어가 DCL 소스 Zdcl_Example_01을 사용하여 정의된 후, 해당 DCL 소스에 정의된 접근 조건에 따라 결과 집합이 필터링됩니다. DCL 소스 Zdcl_Example_01은 리터럴을 사용하여 접근 조건을 정의하고, 이 조건을 만족하는 레코드만 결과 집합에 표시됩니다. 

@EndUserText.label: 'DCL source with Simple literal Condition'
@MappingRole: true
define role Zdcl_Example_01 {
grant select on ZCDS_Example_01
where carrid = 'AA'; }

그림 1
그림 2

아래 소스는 DCL 소스 Zdcl_Example_01이 사용된 예시를 보여줍니다. 이 예시에서는 단순한 리터럴 조건을 사용하여 정의된 접근 제어를 기반으로 결과 집합이 제한되는 것을 보여줍니다.

@AbapCatalog.sqlViewName: 'ZCDS_EX_SQL01'
@AbapCatalog.compiler.compareFilter: true
@AbapCatalog.preserveKey: true
@AccessControl.authorizationCheck: #CHECK
@EndUserText.label: 'CDS using one data source'
define view ZCDS_Example_01
as select from sflight
{
@EndUserText.label: 'Carrier No'
key carrid,
key connid,
key fldate
@<EndUserText.label: 'Connection Flight No'

Data Control Language Source Annotations


DCL 역할 정의에서는 역할 매핑 및 역할 이름에 대한 짧은 텍스트를 정의하기 위해 몇 가지 관련 권한 관련 주석(annotations)이 사용 가능합니다. 이러한 주석들은 DCL 소스의 DEFINE ROLE 문 앞에 정의되므로 CDS 역할에 특화된 범위를 갖습니다.

아래 표는 DCL 권란 정의를 도와주는 Annotation 입니다

DCL Role Annotation Value Purpose
@EndUserText.Label   역할에 대한 번역 가능한 짧은 텍스트
@Mapping Role true 클라이언트와 관계없이 모든 사용자에게 암시적인 역할 할당이 있는
false currently not supported

DCL 역할을 정의할 때, 해당 역할은 ABAP 주석인 @MappingRole을 값으로 true를 포함해야 합니다. 이 주석은 모든 사용자에게 자동 및 암시적인 역할 할당을 허용하며, 클라이언트와 관계없이 적용됩니다. 다른 값(false)은 현재 지원되지 않으며 사용해서는 안 됩니다.

그러나 역할 정의에서 이러한 주석들을 정의하는 것만으로는 CDS 엔티티에 대한 액세스 관련 체크를 수행하는 데는 부족합니다. 또한 액세스 관련 주석은 DDL 소스에 적절한 값과 함께 정의되어야 합니다. 이렇게 함으로써 암시적 권한 체크가 수행됩니다.

DDL 소스 정의에서 주석인 @AccessControl.authorizationCheck은 역할 정의에 정의된 액세스 조건을 기반으로 런타임에서 자동으로 권한 체크를 수행할 수 있도록 허용합니다. 또한 해당 주석에 적절한 값을 제공함으로써 동작을 더욱 세밀하게 제어할 수 있습니다.

@AccessControl.authorizationCheck 주석은 다음과 같은 값을 지원하며, 이 값들은 아래 표에도 요약되어 있습니다. ADT(ABAP Development Tools)의 Problems 뷰에서 경고를 확인할 수 있습니다.

■ #CHECK
이 값은 주석의 기본값입니다. CDS 엔티티에 대한 역할 정의가 있으면 권한 체크가 수행됩니다. 그러나 역할이 정의되지 않은 경우 구문 검사에서 경고가 발생합니다. 

■ #NOT_REQUIRED
이 동작은 #CHECK와 유사하며, CDS 엔티티에 대한 역할 정의가 있으면 권한 체크가 수행됩니다. 그러나 CDS 엔티티에 대해 역할이 정의되지 않은 경우 경고가 발생하지 않습니다. 이 값은 매핑 역할을 의도하거나 정의했지만 아직 매핑이 존재하지 않을 때 권장됩니다.

■ #NOT_ALLOWED
CDS 엔티티에 대해 역할이 정의되었지만 권한 체크가 허용되지 않기 때문에 권한 체크가 수행되지 않으며, 경고가 발생합니다. 

DDL Source View Annotation Value Description
@AccessControl. authorizationCheck #CHECK: 권한 체크를 수행하고, 역할이 할당되지 않은 경우 구문 경고를 표시
#NOT_REQUIRED: #CHECK와 유사한 동작을 수행하지만 구문 경고를 표시
#NOT_ALLOWED: 권한 체크를 수행하지 않고, 역할이 할당된 경우 구문 경고가 표시

 

반응형

'CDS View(Core Data Service) > Core Data Service 기초' 카테고리의 다른 글

Enhancement  (0) 2023.07.16
Consuming CDS View  (0) 2023.07.16
CDS View Association  (0) 2023.07.10
CDS View Annotations  (0) 2023.07.09
CDS View 내장 함수 & 표현식 5. Date and Time Function  (0) 2023.07.06