ABAP for BW - Start Routine, End Routine, Expert Routine, Field Routine, Transformations, CMOD, BADI, User Exit, Customer Exit, Variable Exits
Monday, November 12, 2007
How to Remove Leading Zeros in Transformations
2) You can also tick the "Convesrion" option in Trasnfer Rules. This will perform same as ALPHA Converstion.
3) Some times you need to write an ABAP routine to remove leading zeros in Transfer Rules or Update Rules.
Here is the sample code to remove leading zeros for 0ALLOC_NMBR field
DATA: V_OUTPUT TYPE TRANSFER_STRUCTURE-ALLOC_NMBR.
CALL FUNCTION 'CONVERSION_EXIT_ALPHA_OUTPUT'
EXPORTING
INPUT = TRAN_STRUCTURE-ALLOC_NMBR
IMPORTING
OUTPUT = V_OUTPUT
RESULT = V_OUTPUT.
4) Another example ABAP Routine.
IF TRAN_STRUCTURE-ALLOC_NMBR+0(4) = '0000'.
RESULT = TRAN_STRUCTURE-ALLOC_NMBR+4(6).
ELSE.
RESULT = TRAN_STRUCTURE-ALLOC_NMBR.
ENDIF.
Monday, November 5, 2007
How To get the Master Data Attribute Value in UR's
Some times it is not possible to select Master Data attributes directly using the "Master Data Attribute Value of" option. If this is your requirement, you can get the master data attribute values by writing a simple ABAP Routine in your UR's.
There is a standard Function Module(FM) :RSAU_READ_MASTER_DATA to read master data attributes directly.
Click here to see the example code.
Apart from using the above FM you can directly read master data table using SELECT statement. See the below example.
Example: I am trying to load data from an ODS to Cube & I have 0COSTCENTER as an attribute of ZCUSTOMER. In my ODS I have only ZCUSTOMER Number, But in cube I have ZCUSTOMER as well as 0COSTCENTER. To update 0COSTCENTER in Cube, I have to write a ABAP Routine in UR's for ZCUSTOMER lookup.
*---------- Code to be written in Start Routine of UR's--------
DATA: t_/bic/pzcustomer TYPE STANDARD TABLE OF /bic/pzcustomer WITH HEADER LINE.
DATA: v_cost_center LIKE /bic/pzcustomer-costcenter.
*$*$ begin of routine - insert your code only below this line *-*
* fill the internal tables "MONITOR" and/or "MONITOR_RECNO",
* to make monitor entries
CLEAR: t_/bic/pzcustomer.
REFRESH: t_/bic/pzcustomer.
SELECT * FROM /bic/pzcustomer APPENDING TABLE t_/bic/pzcustomer
WHERE objvers = 'A'.
SORT t_/bic/pzcustomer BY /bic/zcustomer.
* if abort is not equal zero, the update process will be canceled
ABORT = 0.
*--- End of Start Routine in UR's-----------------------------
Now write below in your Update Routine
READ TABLE t_/BIC/PZCUSTOMER WITH KEY /BIC/ZCUSTOMER =
COMM_STRUCTURE-/BIC/ZCUSTOMER BINARY SEARCH.
V_COST_CENTER = t_/BIC/PZCUSTOMER-COSTCENTER.
* result value of the routine
RESULT = V_COST_CENTER.
Tuesday, October 23, 2007
How To Calculate End Date of a Month
Based on Posting Date(0PSTNG_DATE) field we need to find the last date of the month. Posting Date can be any day of the month. But when loading into the cube it should be transformed into the last date of the month.
Here is the sample code used in the update rules.
data: ls_sdate like comm_structure-PSTNG_DATE,
ls_edate like sy-datum.
CALL FUNCTION 'SLS_MISC_GET_LAST_DAY_OF_MONTH'
EXPORTING
DAY_IN = LS_SDATE
IMPORTING
LAST_DAY_OF_MONTH = LS_EDATE
* EXCEPTIONS
* DAY_IN_NOT_VALID = 1
* OTHERS = 2
.
IF SY-SUBRC <> 0.
RESULT = LS_EDATE.
Note:
- You can use the above sample code to find last date of the month from any date filed.
- You can use this code in transfer rules by replacing comm_structure with tran_structure.
- For BI 7 users replace comm_structure with SOURCE_FIELDS.
Sunday, October 21, 2007
Update Routines for PA_C02
Info Source : HR_PA_0
Info Objects: Age Range, Gender, Nationality, Language, Age in years, Country Key, Country Code, Region, Postal Code, Capacity Utilization level, Seniority
* global Data Declarations for all the routines.
DATA: employee_md LIKE /bi0/memployee,
employee_wa LIKE /bi0/memployee,
person_md LIKE /bi0/mperson,
person_wa LIKE /bi0/mperson.
DATA: g_record_no LIKE sy-tabix.
INCLUDE rs_bct_hr_update_rules_general.
INCLUDE rs_bct_hr_papa_update_rules.
*$*$ begin of routine - insert your code only below this line *-*
* ---------------------------------------
* Start of Age Range Routine
DATA: ULTIMO LIKE SY-DATUM,
AGE TYPE I.
IF G_RECORD_NO <> RECORD_NO.
G_RECORD_NO = RECORD_NO.
CLEAR: EMPLOYEE_MD, PERSON_MD.
CLEAR: EMPLOYEE_WA, PERSON_WA.
ENDIF.
PERFORM CALCULATE_ULTIMO
using COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING ULTIMO
RETURNCODE.
PERFORM READ_MD_PERSON
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING EMPLOYEE_WA
PERSON_WA
RETURNCODE.
EMPLOYEE_MD = EMPLOYEE_WA.
PERSON_MD = PERSON_WA.
IF NOT PERSON_MD-DATEBIRTH IS INITIAL.
AGE = ULTIMO+0(4) - PERSON_MD-DATEBIRTH+0(4).
IF ULTIMO+4(4) LT PERSON_MD-DATEBIRTH+4(4).
AGE = AGE - 1.
ENDIF.
* IF AGE LT 20.
* RESULT = 1.
* ELSEIF AGE LT 30.
* RESULT = 2.
* ELSEIF AGE LT 40.
* RESULT = 3.
* ELSEIF AGE LT 50.
* RESULT = 4.
* ELSEIF AGE LT 60.
* RESULT = 5.
* ELSEIF AGE LT 70.
* RESULT = 6.
* ELSE.
* RESULT = 7.
* ENDIF.
IF AGE LT 25. "under 25
RESULT = 1.
ELSEIF AGE LE 34. "between 25 - 34
RESULT = 2.
ELSEIF AGE LE 44. "between 35 - 44
RESULT = 3.
ELSEIF AGE LE 54. "between 45 - 54
RESULT = 4.
ELSEIF AGE LE 64. "between 55 - 64
RESULT = 5.
ELSE.
RESULT = 6. "Over 65
ENDIF.
ELSE.
CLEAR RESULT.
ENDIF.
RETURNCODE = 0.
* End of Age Range routine
*------------------------------------------
* Routine for Gender
IF G_RECORD_NO <> RECORD_NO.
G_RECORD_NO = RECORD_NO.
CLEAR: EMPLOYEE_MD, PERSON_MD.
CLEAR: EMPLOYEE_WA, PERSON_WA.
ENDIF.
PERFORM READ_MD_PERSON
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING EMPLOYEE_WA
PERSON_WA
RETURNCODE.
EMPLOYEE_MD = EMPLOYEE_WA.
PERSON_MD = PERSON_WA.
RESULT = PERSON_MD-GENDER.
RETURNCODE = 0.
* End of Gender Routine
*---------------------------------------------
* Routine for Nationality
IF G_RECORD_NO <> RECORD_NO.
G_RECORD_NO = RECORD_NO.
CLEAR: EMPLOYEE_MD, PERSON_MD.
CLEAR: EMPLOYEE_WA, PERSON_WA.
ENDIF.
PERFORM READ_MD_PERSON
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING EMPLOYEE_WA
PERSON_WA
RETURNCODE.
EMPLOYEE_MD = EMPLOYEE_WA.
PERSON_MD = PERSON_WA.
RESULT = PERSON_MD-NATION.
RETURNCODE = 0.
* End of Nationality Routine
*------------------------------------------
* Routine for Language
IF G_RECORD_NO <> RECORD_NO.
G_RECORD_NO = RECORD_NO.
CLEAR: EMPLOYEE_MD, PERSON_MD.
CLEAR: EMPLOYEE_WA, PERSON_WA.
ENDIF.
PERFORM READ_MD_PERSON
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING EMPLOYEE_WA
PERSON_WA
RETURNCODE.
EMPLOYEE_MD = EMPLOYEE_WA.
PERSON_MD = PERSON_WA.
RESULT = PERSON_MD-PERSLANGU.
RETURNCODE = 0.
* End of Language Routine
*-----------------------------------------
*Routine for Age in Years
DATA: ULTIMO LIKE SY-DATUM.
IF G_RECORD_NO <> RECORD_NO.
G_RECORD_NO = RECORD_NO.
CLEAR: EMPLOYEE_MD, PERSON_MD.
CLEAR: EMPLOYEE_WA, PERSON_WA.
ENDIF.
PERFORM CALCULATE_ULTIMO
using COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING ULTIMO
RETURNCODE.
PERFORM READ_MD_PERSON
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
CHANGING EMPLOYEE_WA
PERSON_WA
RETURNCODE.
EMPLOYEE_MD = EMPLOYEE_WA.
PERSON_MD = PERSON_WA.
IF NOT PERSON_MD-DATEBIRTH IS INITIAL.
RESULT = ULTIMO+0(4) - PERSON_MD-DATEBIRTH+0(4).
IF ULTIMO+4(4) LT PERSON_MD-DATEBIRTH+4(4).
RESULT = RESULT - 1.
ENDIF.
ENDIF.
RETURNCODE = 0.
* End of Age in Years Routine
*----------------------------------------------
* Routine for Country Key
if g_RECORD_NO <> RECORD_NO.
g_RECORD_NO = RECORD_NO.
clear: employee_md, person_md.
clear: employee_wa, person_wa.
endif.
perform read_md_person
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing employee_wa
person_wa
RETURNCODE.
employee_md = employee_wa.
person_md = person_wa.
RESULT = PERSON_MD-COUNTRY.
RETURNCODE = 0.
* End of Country key Routine
*---------------------------------------------
* Routine for Contry Code
if g_RECORD_NO <> RECORD_NO.
g_RECORD_NO = RECORD_NO.
clear: employee_md, person_md.
clear: employee_wa, person_wa.
endif.
perform read_md_person
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing employee_wa
person_wa
RETURNCODE.
employee_md = employee_wa.
person_md = person_wa.
RESULT = PERSON_MD-COUNTY_CDE.
RETURNCODE = 0.
* End of Country Code Routine
*------------------------------------------
* Routine for Region
if g_RECORD_NO <> RECORD_NO.
g_RECORD_NO = RECORD_NO.
clear: employee_md, person_md.
clear: employee_wa, person_wa.
endif.
perform read_md_person
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing employee_wa
person_wa
RETURNCODE.
employee_md = employee_wa.
person_md = person_wa.
RESULT = PERSON_MD-REGION.
RETURNCODE = 0.
* End of Region Routine
* --------------------------------------------
* Routine for Postal Code
if g_RECORD_NO <> RECORD_NO.
g_RECORD_NO = RECORD_NO.
clear: employee_md, person_md.
clear: employee_wa, person_wa.
endif.
perform read_md_person
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing employee_wa
person_wa
RETURNCODE.
employee_md = employee_wa.
person_md = person_wa.
RESULT = PERSON_MD-POSTAL_CD.
RETURNCODE = 0.
*End of Postal Code Routine
*------------------------------------------
* Routine for Capacity Utilization Lvl
DATA: TMP_PAYPCT TYPE I.
if g_RECORD_NO <> RECORD_NO.
g_RECORD_NO = RECORD_NO.
clear: employee_md, person_md.
clear: employee_wa, person_wa.
endif.
perform read_md_employee
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing employee_wa
RETURNCODE.
employee_md = employee_wa.
* fill the internal table "MONITOR", to make monitor entries
* result value of the routine
* rounded
TMP_PAYPCT = EMPLOYEE_MD-PAYPCT.
RESULT = TMP_PAYPCT.
* End of Routine Capacity Utilization Lvl
*------------------------------------------------
* Routine for Length of Service
data: ultimo like sy-datum.
if g_RECORD_NO <> RECORD_NO.
g_RECORD_NO = RECORD_NO.
clear: employee_md, person_md.
clear: employee_wa, person_wa.
endif.
perform read_md_employee
using COMM_STRUCTURE-employee
COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing employee_wa
RETURNCODE.
employee_md = employee_wa.
perform calculate_ultimo
using COMM_STRUCTURE-calmonth
RECORD_NO
RECORD_ALL
SOURCE_SYSTEM
changing ultimo
RETURNCODE.
IF NOT EMPLOYEE_WA-ENTRYDATE IS INITIAL.
RESULT = ULTIMO+0(4) - EMPLOYEE_WA-ENTRYDATE+0(4).
IF ULTIMO+4(4) LT EMPLOYEE_WA-ENTRYDATE+4(4).
RESULT = RESULT - 1.
endif.
ENDIF.
IF RESULT LT 1.
RESULT = 1.
ELSEIF RESULT LT 2.
RESULT = 2.
ELSEIF RESULT LT 5.
RESULT = 3.
ELSEIF RESULT LT 10.
RESULT = 4.
ELSE.
RESULT = 5.
ENDIF.
* End of Length of service routine
*-----------------------------------------
Update Routines for HR Structural Authorizations
Info Source - 0HR_PA_3
Info Object - TCTIOBJNM
* fill the internal table "MONITOR", to make monitor entries
RETURNCODE = 0.
* result value of the routine
case COMM_STRUCTURE-HR_OBJTYPE.
when 'O'. RESULT = '0ORGUNIT'.
when 'C'. RESULT = '0JOB'.
when 'S'. RESULT = '0HRPOSITION'.
when 'P'. RESULT = '0EMPLOYEE'.
when 'Q'. RESULT = '0QUALIFICTN'.
when 'QK'. RESULT = '0QUALIGROUP'.
when 'BA'. RESULT = '0APPRAISAL'.
when 'A'. RESULT = '0HRWORKCNTR'.
when 'BK'. RESULT = '0AP_CRIT'.
when 'BS'. RESULT = '0AP_SCHEME'.
when 'E'. RESULT = '0EVENT'.
when 'D'. RESULT = '0EVENTTYPE'.
when 'L'. RESULT = '0EVENTGROUP'.
when 'F'. RESULT = '0EVLOCATION'.
when 'G'. RESULT = '0RESOU'.
when 'R'. RESULT = '0RESTYPE'.
when 'H'. RESULT = '0EXTPERS'.
when 'U'. RESULT = '0EXTORG'.
when others.RETURNCODE = 4.
endcase.
* if the returncode is not equal zero, the result will not be updated
* if abort is not equal zero, the update process will be canceled
ABORT = 0.
How To Write a Start Routine in Update Rules
Here I am giving some sample ABAP code used in Update rules to filter unwanted records.
NE - Not Equal
EQ - Equal(=)
LT - Less Than (<)
GT - Greater Than (>)
BT - Between
1 :
-----------------------------------------------
DELETE DATA_PACKAGE WHERE ORGUNIT IS INITIAL.
-----------------------------------------------
2:
-----------------------------------------------
DELETE DATA_PACKAGE WHERE REPTT NE '00000009'.
* DELETE DATA_PACKAGE WHERE REPTT EQ '00000009'.
* DELETE DATA_PACKAGE WHERE REPTT = '00000009'.
-----------------------------------------------
3:
-----------------------------------------------
DELETE DATA_PACKAGE WHERE REPTT EQ '00000001'
OR REPTT EQ '00000002'
OR REPTT EQ '00000003'
OR REPTT EQ '00000004'
OR REPTT EQ '00000005'
OR REPTT EQ '00000006'.
-----------------------------------------------
4:
-----------------------------------------------
DELETE DATA_PACKAGE WHERE WRHRS EQ '0'
AND DUR_ACTUAL EQ '0'
AND DUR_VALUE EQ '0'
AND PLHRS EQ '0'
AND ALP_AMOUNT EQ '0'.
-----------------------------------------------
5:
-----------------------------------------------
LOOP AT DATA_PACKAGE.
IF DATA_PACKAGE-COMP_CODE NE '1000'.
DELETE DATA_PACKAGE.
ENDLOOP.
-----------------------------------------------
If you have any more examples, please feel free to post in the comments.