개요 및 이 글에서 다루는 범위
SAP Extended Warehouse Management(EWM)에서 창고 태스크(Warehouse Task)는 작업자의 실제 물리적 이동·작업을 지시하는 최소 실행 단위입니다. I_WarehouseTask는 이 태스크 데이터를 ABAP CDS 뷰 계층에서 표준화된 형태로 노출하는 인터페이스 뷰이며, RAP/Fiori/Analytics에서 EWM 태스크 정보를 조회할 때 가장 먼저 접근하게 되는 진입점입니다. 이 글에서는 다음을 단계별로 살펴봅니다.
- I_WarehouseTask의 위치(VDM 계층)와 키 필드 구조 이해
- 창고 번호·태스크 유형·이동 데이터 필드의 의미와 조인 전략
- 기본 조회 → 실무 시나리오(피킹/입고) → 프로덕션 패턴까지 3단계 코드 작성
- EWM 권한 객체와 클라이언트/시간 의존성에서의 흔한 함정 회피
이 글은 S/4HANA 2022 이상의 Embedded EWM 환경을 기준으로 작성되었으며, Decentralized EWM 1909 이상에서도 일부 필드를 제외하면 동일하게 적용됩니다.
먼저 알고 있어야 할 것들
이 글은 ABAP CDS의 기본 문법(define view, association, annotation)과 SELECT/OpenSQL 사용 경험을 가정합니다. 또한 EWM의 핵심 마스터/트랜잭션 객체(창고 번호, Storage Bin, Handling Unit, Warehouse Order, Warehouse Task)의 개념을 알고 있으면 필드 매핑이 훨씬 쉽습니다. RAP 또는 Service Binding 작성 경험이 있다면 3단계 프로덕션 예제 이해가 빨라집니다.
환경 및 준비 사항
본 예제는 다음 환경에서 검증을 권장합니다.
- SAP S/4HANA 2022 FPS02 또는 2023(Embedded EWM 활성화)
- ABAP Development Tools(ADT) for Eclipse 2024-03 이상
- 권한 객체:
/SCWM/MON,/SCWM/WHN(창고 번호 권한),S_RFC - 최소 1건 이상의 Warehouse Order/Task 트랜잭션 데이터(테스트 창고 번호 권장)
- 분석 시나리오라면 SAP Analytics Cloud 또는 Fiori Elements List Report 프리뷰 사용
ADT에서 I_WarehouseTask를 Open Repository Object로 열어 Source/Annotation을 먼저 살펴본 뒤 실습을 진행하면 필드 의미를 빠르게 파악할 수 있습니다.
핵심 개념: 창고 태스크와 I_WarehouseTask의 위치
EWM의 실행 모델은 "Document → Order → Task" 3계층으로 단순화할 수 있습니다. Outbound Delivery Order가 들어오면 시스템은 Warehouse Request를 만들고, 이를 기반으로 Warehouse Order(작업 단위 묶음)와 Warehouse Task(실제 이동/적치/피킹 1건)를 생성합니다. 태스크 1건은 본질적으로 "어떤 자재(Product)를, 얼마나(Quantity), 어디서(Source Bin/HU) 어디로(Destination Bin/HU) 옮긴다"는 명령서이며, 데이터베이스 레벨에서는 /SCWM/ORDIM_C(확정), /SCWM/ORDIM_O(미확정), /SCWM/ORDIM_H(이력) 테이블에 분산 저장됩니다.
I_WarehouseTask는 이 분산된 테이블을 비즈니스적으로 의미 있는 단일 뷰로 묶어주는 Virtual Data Model(VDM)의 Interface View(I_ 접두어)입니다. 비유하자면 물류 센터의 "작업 지시서 캐비넷"을 표준 양식으로 정리해 외부에 노출한 창구입니다. 내부 구조가 어떻게 바뀌더라도 I_ 뷰의 시그니처는 안정적으로 유지되므로, 컨슈머는 테이블을 직접 참조하지 않고 이 뷰만 바라보면 됩니다.
VDM 계층 구조에서 흐름은 다음과 같습니다.
- Basic View: 원천 테이블 1:1 매핑(예:
/SCWM/ORDIM_C래퍼) - Composite/Interface View:
I_WarehouseTask— 비즈니스 시맨틱 부여, association 정의 - Consumption View:
C_WarehouseTaskTP류 — Fiori 앱·OData 노출용
주요 키·식별 필드는 다음과 같이 이해하면 됩니다.
EWMWarehouse: 창고 번호(이전LGNUM)WarehouseTask: 태스크 번호(10자리,TANUM에 해당)WarehouseOrder: 상위 묶음 단위WarehouseProcessType,ActivityArea,StorageProcess: 프로세스 분류SourceStorageBin/DestinationStorageBin,SourceHandlingUnit/DestinationHandlingUnit: 이동 출발/도착Product,ProductQuantity,ProductQuantityUnit: 자재와 수량WarehouseTaskStatus(미확정/확정/취소),ConfirmationDateTime
실전 코드 1단계: 기본 조회 뷰 작성
가장 먼저 I_WarehouseTask를 단순 래핑하여 특정 창고의 오늘 생성된 피킹 태스크를 조회하는 커스텀 뷰를 만들어 봅니다. Z 네임스페이스로 인터페이스 뷰를 작성합니다.
@AccessControl.authorizationCheck: #CHECK
@EndUserText.label: 'Picking Task Overview'
@Metadata.ignorePropagatedAnnotations: true
define view entity ZI_PickingTaskOverview
as select from I_WarehouseTask as Task
{
key Task.EWMWarehouse as Warehouse,
key Task.WarehouseTask as TaskNumber,
Task.WarehouseOrder as OrderNumber,
Task.WarehouseProcessType as ProcessType,
Task.Product as Material,
Task.ProductQuantity as PickQuantity,
Task.ProductQuantityUnit as PickUnit,
Task.SourceStorageBin as FromBin,
Task.DestinationStorageBin as ToBin,
Task.WarehouseTaskStatus as TaskStatus,
Task.CreationDateTime as CreatedAt,
Task.ConfirmationDateTime as ConfirmedAt
}
where
Task.WarehouseProcessType like '20%' -- Picking 프로세스 그룹
and Task.CreationDateTime >= $session.system_date
위 뷰는 I_WarehouseTask의 raw field를 비즈니스에 친숙한 alias로 노출합니다. $session.system_date 활용으로 하드코딩된 날짜를 피했고, like '20%' 패턴으로 피킹 프로세스 유형 그룹을 필터링했습니다. ADT의 Data Preview로 즉시 결과를 확인할 수 있습니다.
실전 코드 2단계: 입고-피킹 통합 시나리오와 에러 처리
실무에서는 단순 조회를 넘어 Inbound(GR) 태스크와 Outbound(Picking) 태스크를 함께 모니터링하면서, 미확정 태스크의 지연 시간을 계산해야 합니다. Association을 활용해 자재 마스터·창고 조직 정보를 결합하고, ABAP 클래스에서 호출 시 예외 처리를 포함시킵니다.
@AccessControl.authorizationCheck: #CHECK
@EndUserText.label: 'WHT Monitor with Delay'
define view entity ZI_WhseTaskMonitor
as select from I_WarehouseTask as Task
association [0..1] to I_Product as _Product on _Product.Product = Task.Product
association [0..1] to I_EWMWarehouse as _Wh on _Wh.EWMWarehouse = Task.EWMWarehouse
{
key Task.EWMWarehouse as Warehouse,
key Task.WarehouseTask as TaskNumber,
Task.WarehouseProcessType as ProcessType,
case
when Task.WarehouseProcessType like '10%' then 'GR'
when Task.WarehouseProcessType like '20%' then 'PICK'
when Task.WarehouseProcessType like '40%' then 'PUTAWAY'
else 'OTHER'
end as TaskCategory,
Task.Product as Material,
Task.ProductQuantity as Quantity,
Task.ProductQuantityUnit as Unit,
Task.WarehouseTaskStatus as Status,
Task.CreationDateTime as CreatedAt,
Task.ConfirmationDateTime as ConfirmedAt,
cast( tstmp_seconds_between(
Task.CreationDateTime,
tstmp_current_utctimestamp(),
'FAIL' ) as abap.dec(15,0) ) as OpenSeconds,
_Product.ProductType as MaterialType,
_Wh.WarehouseDescription as WarehouseName,
_Product,
_Wh
}
where Task.WarehouseTaskStatus = ' ' -- 미확정만
ABAP 컨슈머 측에서는 try-catch와 로깅을 포함합니다.
METHOD get_open_tasks.
DATA(lo_log) = cl_bali_log_factory=>create_log( ).
TRY.
SELECT FROM zi_whsetaskmonitor
FIELDS warehouse, tasknumber, taskcategory, material,
quantity, unit, openseconds, warehousename
WHERE warehouse = @iv_warehouse
AND taskcategory IN ( 'PICK', 'PUTAWAY' )
AND openseconds > @iv_threshold_sec
ORDER BY openseconds DESCENDING
INTO TABLE @rt_tasks.
IF sy-subrc <> 0.
lo_log->add_message(
cl_bali_message_helper=>create_message(
severity = if_bali_constants=>c_severity_info
text = |No open tasks for { iv_warehouse }| ) ).
ENDIF.
CATCH cx_sy_open_sql_db INTO DATA(lx_sql).
lo_log->add_exception( lx_sql ).
RAISE EXCEPTION TYPE zcx_wht_read
EXPORTING previous = lx_sql.
ENDTRY.
cl_bali_log_db=>get_instance( )->save_log( log = lo_log ).
ENDMETHOD.
핵심은 ① CDS에서 비즈니스 카테고리화(case)와 시간 계산(tstmp_seconds_between)을 미리 수행한다는 점, ② 컨슈머는 단순 필터만 담당해 가독성과 재사용성을 높였다는 점입니다.
실전 코드 3단계: RAP Projection과 권한·성능 고려
프로덕션에서는 Fiori Elements 또는 SAC에서 곧바로 소비할 수 있도록 Projection View와 Service Binding을 구성합니다. 동시에 EWM 권한 객체 /SCWM/LGN 기반 DCL(Data Control Language)을 적용해 창고별 데이터 격리를 보장합니다.
@AccessControl.authorizationCheck: #CHECK
@Search.searchable: true
@OData.publish: false
@UI.headerInfo: { typeName: 'Warehouse Task',
typeNamePlural: 'Warehouse Tasks' }
define root view entity ZC_WarehouseTaskTP
provider contract transactional_query
as projection on ZI_WhseTaskMonitor
{
@UI.lineItem: [{ position: 10, label: 'Warehouse' }]
@UI.selectionField: [{ position: 10 }]
key Warehouse,
@UI.lineItem: [{ position: 20 }]
@UI.identification: [{ position: 20 }]
key TaskNumber,
@UI.lineItem: [{ position: 30 }]
TaskCategory,
@UI.lineItem: [{ position: 40 }]
@Semantics.quantity.unitOfMeasure: 'Unit'
Quantity,
Unit,
@UI.lineItem: [{ position: 50, criticality: 'Criticality' }]
OpenSeconds,
case
when OpenSeconds > 3600 then 1
when OpenSeconds > 1800 then 2
else 3
end as Criticality,
Material,
MaterialType,
WarehouseName
}
@EndUserText.label: 'DCL for Warehouse Task'
@MappingRole: true
define role ZC_WAREHOUSE_TASK_ROLE {
grant select on ZC_WarehouseTaskTP
where ( Warehouse ) = aspect pfcg_auth( /SCWM/LGN, LGNUM, ACTVT = '03' );
}
성능 측면 권장 사항은 다음과 같습니다.
- 대량 태스크가 누적되는 창고는
CreationDateTime기준 파티션 키 활용을 고려하고, 조회 시 항상 시간 범위 필터를 강제합니다. - Association은 필요한 시점에만 실제 select에 포함되도록 path 사용을 자제하고, 분석 뷰는 별도 Aggregation View(
@Analytics.dataCategory: #CUBE)로 분리합니다. - 오래된 확정 태스크는
I_WarehouseTaskHistory류의 이력 뷰로 분기 조회해 hot 영역의 부하를 줄입니다.
자주 마주치는 실수와 해결법
Q1. I_WarehouseTask에서 데이터가 한 건도 안 보입니다. 가장 흔한 원인은 권한 객체 /SCWM/LGN 미부여입니다. EWM 데이터는 단순 클라이언트 격리뿐 아니라 창고 번호별 권한이 강제되므로 SU53으로 권한 트레이스를 먼저 확인하세요. 또한 Embedded EWM의 경우 비즈니스 시스템 그룹(BSG) 설정이 잘못되면 같은 시스템에서도 뷰가 비어 보일 수 있습니다.
Q2. 확정 후 사라진 태스크는 어디서 보나요? 미확정/확정/취소는 각각 다른 물리 테이블에 저장됩니다. I_WarehouseTask는 주로 활성(미확정+확정 일부) 데이터를 노출하며, 이력은 별도의 Historical CDS 뷰 또는 /SCWM/ORDIM_H 기반 커스텀 뷰로 접근해야 합니다. 컨슈머가 "방금 확정한 태스크가 사라졌다"고 보고하면 status 필터를 점검하세요.
Q3. 시간 필드가 UTC라서 한국 시간과 다르게 보입니다. CreationDateTime·ConfirmationDateTime은 일반적으로 UTC TimeStamp입니다. UI 표시용으로는 @Semantics.systemDateTime: true를 활용하거나, 컨슈머 측에서 CONVERT TIME STAMP로 사용자 타임존에 맞춰 변환하는 것을 권장합니다. 보고서에서 "하루치 데이터"를 다룰 때 UTC 경계와 로컬 경계 차이로 누락이 생기지 않도록 주의하세요.
그 외 자주 발생하는 함정으로는, WarehouseProcessType 코드 체계가 고객별 커스터마이징되어 있다는 점(표준값 가정 금지), HU 관리 창고와 비-HU 창고에서 SourceHandlingUnit이 공백일 수 있다는 점, association을 무분별하게 select에 노출하면 HANA 옵티마이저가 불필요한 조인을 평탄화하지 못해 성능이 저하될 수 있다는 점을 들 수 있습니다.
이후에 학습하면 좋은 주제
I_WarehouseTask를 이해했다면 이어서 다음 주제로 확장하기를 권장합니다. 첫째, I_WarehouseOrder·I_WarehouseRequest·I_InboundDelivery와 association을 연결해 End-to-End 물류 흐름을 단일 뷰로 묶는 분석 모델을 설계해 보세요. 둘째, RAP의 Behavior Definition을 활용해 태스크 확정·취소 액션을 OData 서비스로 노출하는 Managed/Unmanaged 시나리오를 실습할 수 있습니다. 셋째, SAP Analytics Cloud Live Connection으로 OpenSeconds 기반 KPI 대시보드를 구성하면 운영 모니터링에 즉시 적용할 수 있습니다. 마지막으로, Event-Driven 아키텍처가 필요하다면 ABAP Channels나 Application Log + Event Mesh 연계를 검토하세요.
관련 문서 및 추가 학습 링크
- SAP S/4HANA On-Premise Documentation Hub (help.sap.com)
- SAP Extended Warehouse Management 공식 문서 (help.sap.com)
- ABAP CDS Development User Guide (help.sap.com)
- ABAP RESTful Application Programming Model 가이드
- SAP Community: EWM 토픽 (community.sap.com)
- SAP Blogs: Embedded EWM Tag
- SAP API Business Hub: S/4HANA Cloud Warehouse APIs
댓글 0
아직 댓글이 없습니다.