ABAP BAPI 複製標準專案模板實現專案立項

2022-07-13 18:00:16

一、複製標準專案模板實現專案立項

因為CJ20N錄屏存在困難,所以想通過BDC實現複製專案模板建立專案立項行不通,因此需要通過BAPI解決。

因為專案立項包含:專案定義、WBS、網路、作業,因此需要分別呼叫四個BAPI實現該功能

二、CJ01 專案定義與WBS

輸入專案定義編號和引數檔案

 傳入必輸欄位,點選WBS元素總覽

 

 輸入WBS層級,點選儲存即可

建立專案BAPI

"-----------------------------@斌將軍-----------------------------
DATA:gs_proj_bus2001_new TYPE bapi_bus2001_new,
     gt_bapiret2         TYPE TABLE OF bapiret2,
     gs_bapiret2         TYPE bapiret2.

gs_proj_bus2001_new-project_definition = 'NPD-2022037'."is_proj-pspid.       "專案編號
gs_proj_bus2001_new-description        = '測試'."is_proj-post1.       "PS: 短描述 (第一行文字)
gs_proj_bus2001_new-responsible_no     = '80000667'."lv_vernr.            "專案經理編號
gs_proj_bus2001_new-applicant_no     = '81000003'."lv_vernr.            "申請部門編號
gs_proj_bus2001_new-start              = '20220225'."is_proj-plfaz.       "開始日期
gs_proj_bus2001_new-finish             = '20220428'."is_proj-plsez.       "完成日期
gs_proj_bus2001_new-company_code       = '2000'."is_proj-vbukr.       "專案的公司程式碼
gs_proj_bus2001_new-profit_ctr         = ''."is_proj-prctr.       "利潤中心
gs_proj_bus2001_new-project_profile    = 'APS0001'."is_proj-profl.       "專案引數檔案
gs_proj_bus2001_new-plant              = '2000'."is_proj-werks.       "工廠
*IF is_proj-func_area IS NOT INITIAL.
*  gs_proj_bus2001_new-func_area        = is_proj-func_area.   "功能控制範圍
*ENDIF.

CALL FUNCTION 'BAPI_PS_INITIALIZATION'.

CALL FUNCTION 'BAPI_BUS2001_CREATE'
  EXPORTING
    i_project_definition = gs_proj_bus2001_new
  TABLES
    et_return            = gt_bapiret2.


LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
ENDLOOP.

IF sy-subrc EQ 0.
  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.
  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ENDIF.
CHECK sy-subrc NE 0.
CALL FUNCTION 'BAPI_PS_PRECOMMIT'
  TABLES
    et_return = gt_bapiret2.

LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
ENDLOOP.

IF sy-subrc EQ 0.
  CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'
    IMPORTING
      return = gs_bapiret2.

  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.

  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ELSE.
  CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
    EXPORTING
      wait   = 'X'
    IMPORTING
      return = gs_bapiret2.
*   專案定義建立成功
ENDIF.
"-----------------------------@斌將軍-----------------------------

建立WBS的BAPI

"-----------------------------@斌將軍-----------------------------
DATA:lv_pspid           TYPE bapi_bus2001_new-project_definition,
     gt_wbs_bus2054_new TYPE TABLE OF bapi_bus2054_new,
     gs_wbs_bus2054_new TYPE bapi_bus2054_new,
     gt_bapiret2        TYPE TABLE OF bapiret2,
     gs_bapiret2        TYPE bapiret2.

CLEAR:gs_wbs_bus2054_new.
gs_wbs_bus2054_new-wbs_element                    = 'NPD-2022038'."gs_wbs-posid.     "工作分解結構元素 (WBS 元素)
gs_wbs_bus2054_new-description                    = '第一層'."gs_wbs-post1.     "PS: 短描述 (第一行文字)
gs_wbs_bus2054_new-responsible_no                 = '80000667'."lv_vernr.         "專案經理編號
*gs_wbs_bus2054_new-profit_ctr                     = ''."gs_wbs-prctr.     "利潤中心
gs_wbs_bus2054_new-proj_type                      = '11'."gs_wbs-prart.     "專案型別
gs_wbs_bus2054_new-wbs_account_assignment_element = 'X'."gs_wbs-belkz.     "標誌:科目分配元素
*gs_wbs_bus2054_new-wbs_billing_element            = ''."gs_wbs-fakkz.     "識別符號: 開票元素
gs_wbs_bus2054_new-wbs_left                       = ''."gs_wbs-left_posid."左側WBS
gs_wbs_bus2054_new-wbs_up                         = ''."gs_wbs-up_posid.  "上級WBS
*gs_wbs_bus2054_new-user_field_char20_1            = ''."gs_wbs-usr00.     "業務類別
*gs_wbs_bus2054_new-user_field_char20_2            = ''."gs_wbs-usr01.     "CRM 商機編碼
*gs_wbs_bus2054_new-user_field_char10_1            = ''."'X'.              "產品
*gs_wbs_bus2054_new-statistical                    = ''."gs_wbs-xstat.     "統計
*gs_wbs_bus2054_new-wbs_cctr_posted_actual         = ''."gs_wbs-kostl.     "CCtr 過賬
APPEND gs_wbs_bus2054_new TO gt_wbs_bus2054_new.

CLEAR:gs_wbs_bus2054_new.
gs_wbs_bus2054_new-wbs_element                    = 'NPD-2022038.001'."gs_wbs-posid.     "工作分解結構元素 (WBS 元素)
gs_wbs_bus2054_new-description                    = '第二層'."gs_wbs-post1.     "PS: 短描述 (第一行文字)
gs_wbs_bus2054_new-responsible_no                 = '80000667'."lv_vernr.         "專案經理編號
*gs_wbs_bus2054_new-profit_ctr                     = ''."gs_wbs-prctr.     "利潤中心
gs_wbs_bus2054_new-proj_type                      = '11'."gs_wbs-prart.     "專案型別
gs_wbs_bus2054_new-wbs_account_assignment_element = 'X'."gs_wbs-belkz.     "標誌:科目分配元素
*gs_wbs_bus2054_new-wbs_billing_element            = ''."gs_wbs-fakkz.     "識別符號: 開票元素
gs_wbs_bus2054_new-wbs_left                       = ''."gs_wbs-left_posid."左側WBS
gs_wbs_bus2054_new-wbs_up                         = 'NPD-2022038'."gs_wbs-up_posid.  "上級WBS
*gs_wbs_bus2054_new-user_field_char20_1            = ''."gs_wbs-usr00.     "業務類別
*gs_wbs_bus2054_new-user_field_char20_2            = ''."gs_wbs-usr01.     "CRM 商機編碼
*gs_wbs_bus2054_new-user_field_char10_1            = ''."'X'.              "產品
*gs_wbs_bus2054_new-statistical                    = ''."gs_wbs-xstat.     "統計
*gs_wbs_bus2054_new-wbs_cctr_posted_actual         = ''."gs_wbs-kostl.     "CCtr 過賬
APPEND gs_wbs_bus2054_new TO gt_wbs_bus2054_new.

CLEAR:gs_wbs_bus2054_new.
gs_wbs_bus2054_new-wbs_element                    = 'NPD-2022038.002'."gs_wbs-posid.     "工作分解結構元素 (WBS 元素)
gs_wbs_bus2054_new-description                    = '第三層'."gs_wbs-post1.     "PS: 短描述 (第一行文字)
gs_wbs_bus2054_new-responsible_no                 = '80000667'."lv_vernr.         "專案經理編號
*gs_wbs_bus2054_new-profit_ctr                     = ''."gs_wbs-prctr.     "利潤中心
gs_wbs_bus2054_new-proj_type                      = '11'."gs_wbs-prart.     "專案型別
gs_wbs_bus2054_new-wbs_account_assignment_element = 'X'."gs_wbs-belkz.     "標誌:科目分配元素
*gs_wbs_bus2054_new-wbs_billing_element            = ''."gs_wbs-fakkz.     "識別符號: 開票元素
*gs_wbs_bus2054_new-wbs_left                       = 'NPD-2022037.001'."gs_wbs-left_posid."左側WBS
gs_wbs_bus2054_new-wbs_up                         = 'NPD-2022038'."gs_wbs-up_posid.  "上級WBS
*gs_wbs_bus2054_new-user_field_char20_1            = ''."gs_wbs-usr00.     "業務類別
*gs_wbs_bus2054_new-user_field_char20_2            = ''."gs_wbs-usr01.     "CRM 商機編碼
*gs_wbs_bus2054_new-user_field_char10_1            = ''."'X'.              "產品
*gs_wbs_bus2054_new-statistical                    = ''."gs_wbs-xstat.     "統計
*gs_wbs_bus2054_new-wbs_cctr_posted_actual         = ''."gs_wbs-kostl.     "CCtr 過賬
APPEND gs_wbs_bus2054_new TO gt_wbs_bus2054_new.

lv_pspid = 'NPD-2022038'.

CALL FUNCTION 'BAPI_PS_INITIALIZATION'.

CALL FUNCTION 'BAPI_BUS2054_CREATE_MULTI'
  EXPORTING
    i_project_definition = lv_pspid
  TABLES
    it_wbs_element       = gt_wbs_bus2054_new
    et_return            = gt_bapiret2.

LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AE'.
ENDLOOP.

IF sy-subrc EQ 0.

  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.

  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.

ENDIF.
CHECK sy-subrc NE 0.
CALL FUNCTION 'BAPI_PS_PRECOMMIT'
  TABLES
    et_return = gt_bapiret2.

LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AE'.
ENDLOOP.

IF sy-subrc EQ 0.
  CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'
    IMPORTING
      return = gs_bapiret2.

  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.

  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ELSE.
  CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
    EXPORTING
      wait   = 'X'
    IMPORTING
      return = gs_bapiret2.
ENDIF.
"-----------------------------@斌將軍-----------------------------

 三、CN21建立網路和作業

分配給WBS,點選作業

 

建立作業,分配給WBS,點選儲存即可

建立網路BAPI

"-----------------------------@斌將軍-----------------------------
DATA:gs_net_bus2002_new TYPE bapi_bus2002_new,
     gt_bapiret2        TYPE TABLE OF bapiret2,
     gs_bapiret2        TYPE bapiret2.

CLEAR : gs_net_bus2002_new.
gs_net_bus2002_new-project_definition = 'NPD-2022037'."is_network-pspid.       "專案定義
gs_net_bus2002_new-wbs_element        = 'NPD-2022037'."is_network-posid.       "工作分解結構元素 (WBS 元素)
gs_net_bus2002_new-short_text         = '網路測試'."is_network-ktext.       "描述
*  gs_net_bus2002_new-plant              = ''."is_network-werks.       "工廠
*  gs_net_bus2002_new-mrp_controller     = ''."is_network-dispo.       "MRP控制者
CALL FUNCTION 'BAPI_PS_INITIALIZATION'.
CALL FUNCTION 'BAPI_BUS2002_CREATE'
  EXPORTING
    i_network = gs_net_bus2002_new
  TABLES
    et_return = gt_bapiret2.
LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.

ENDLOOP.
IF sy-subrc EQ 0.
  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.
  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ENDIF.
CHECK sy-subrc NE 0.
CALL FUNCTION 'BAPI_PS_PRECOMMIT'
  TABLES
    et_return = gt_bapiret2.
LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.

ENDLOOP.
IF sy-subrc EQ 0.
  CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'
    IMPORTING
      return = gs_bapiret2.
  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.
  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ELSE.
  CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
    EXPORTING
      wait   = 'X'
    IMPORTING
      return = gs_bapiret2.
  READ TABLE gt_bapiret2 INTO gs_bapiret2 WITH KEY id = 'CNIF_PI'
                                                   number = '003'.
  IF sy-subrc EQ 0.
*    ev_aufnr = gs_bapiret2-message_v2.
  ENDIF.
ENDIF.
"-----------------------------@斌將軍-----------------------------

建立作業BAPI

"-----------------------------@斌將軍-----------------------------

DATA:lv_aufnr TYPE bapi_network_list-network.
DATA:gt_act_bus2002_new TYPE TABLE OF bapi_bus2002_act_new,
     gs_act_bus2002_new TYPE bapi_bus2002_act_new,
     gt_bapiret2        TYPE TABLE OF bapiret2,
     gs_bapiret2        TYPE bapiret2.

CLEAR:gs_act_bus2002_new.
gs_act_bus2002_new-activity           = '0010'."gs_activity-vornr.       "在網路和庫網路中的作業編號
gs_act_bus2002_new-description        = '封裝測試'."gs_activity-ltxa1.       "工序短文字
gs_act_bus2002_new-control_key        = ''."gs_activity-steus.       "控制碼-內協(ZPS1)和成本(ZPS3)
gs_act_bus2002_new-wbs_element        = 'NPD-2022037.001'."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-duration_normal        = 2."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-work_cntr          = ''."gs_activity-arbpl.       "工作中心
gs_act_bus2002_new-work_activity      = ''."gs_activity-arbei.       "工作(時間單位H)
*-------------MOD ON 20200423--------Begin-----------------------------------
**    gs_act_bus2002_new-calculation_key    = gs_activity-indet.       "用於計算的碼
*IF gs_activity-steus = 'ZPS1' AND gs_activity-arbei IS INITIAL.
*  gs_act_bus2002_new-calculation_key    = 0.       "用於計算的碼
*ELSE.
*  gs_act_bus2002_new-calculation_key    = gs_activity-indet.       "用於計算的碼
*ENDIF.
*-------------MOD ON 20200423--------End-------------------------------------
*gs_act_bus2002_new-acttype            = gs_activity-larnt.       "活動型別
*gs_act_bus2002_new-cost_elem          = gs_activity-sakto.       "成本要素編碼
*gs_act_bus2002_new-profit_ctr         = gs_activity-prctr.       "利潤中心
*IF gs_activity-steus EQ 'ZPS3'.
*  gs_act_bus2002_new-activity_costs   = gs_activity-prkst.       "作業中的成本
**    ELSE.
**      gs_act_bus2002_new-user_field_curr1 = gs_activity-prkst.       "使用者欄位 - 值3
*ENDIF.

APPEND gs_act_bus2002_new TO gt_act_bus2002_new.

CLEAR:gs_act_bus2002_new.
gs_act_bus2002_new-activity           = '0020'."gs_activity-vornr.       "在網路和庫網路中的作業編號
gs_act_bus2002_new-description        = '專案產品設計'."gs_activity-ltxa1.       "工序短文字
gs_act_bus2002_new-control_key        = ''."gs_activity-steus.       "控制碼-內協(ZPS1)和成本(ZPS3)
gs_act_bus2002_new-wbs_element        = 'NPD-2022037.001'."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-duration_normal        = 2."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-work_cntr          = ''."gs_activity-arbpl.       "工作中心
gs_act_bus2002_new-work_activity      = ''."gs_activity-arbei.       "工作(時間單位H)
APPEND gs_act_bus2002_new TO gt_act_bus2002_new.

CLEAR:gs_act_bus2002_new.
gs_act_bus2002_new-activity           = '0030'."gs_activity-vornr.       "在網路和庫網路中的作業編號
gs_act_bus2002_new-description        = '專案立項'."gs_activity-ltxa1.       "工序短文字
gs_act_bus2002_new-control_key        = ''."gs_activity-steus.       "控制碼-內協(ZPS1)和成本(ZPS3)
gs_act_bus2002_new-wbs_element        = 'NPD-2022037.002'."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-duration_normal        = 2."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-work_cntr          = ''."gs_activity-arbpl.       "工作中心
gs_act_bus2002_new-work_activity      = ''."gs_activity-arbei.       "工作(時間單位H)
APPEND gs_act_bus2002_new TO gt_act_bus2002_new.

CLEAR:gs_act_bus2002_new.
gs_act_bus2002_new-activity           = '0040'."gs_activity-vornr.       "在網路和庫網路中的作業編號
gs_act_bus2002_new-description        = '專案評估'."gs_activity-ltxa1.       "工序短文字
gs_act_bus2002_new-control_key        = ''."gs_activity-steus.       "控制碼-內協(ZPS1)和成本(ZPS3)
gs_act_bus2002_new-wbs_element        = 'NPD-2022037.002'."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-duration_normal        = 2."gs_activity-posid.       "工作分解結構元素 (WBS 元素)
gs_act_bus2002_new-work_cntr          = ''."gs_activity-arbpl.       "工作中心
gs_act_bus2002_new-work_activity      = ''."gs_activity-arbei.       "工作(時間單位H)
APPEND gs_act_bus2002_new TO gt_act_bus2002_new.

CALL FUNCTION 'BAPI_PS_INITIALIZATION'.
lv_aufnr = '4000088'.
CALL FUNCTION 'CONVERSION_EXIT_ALPHA_INPUT'
  EXPORTING
    input  = lv_aufnr
  IMPORTING
    output = lv_aufnr.

CALL FUNCTION 'BAPI_BUS2002_ACT_CREATE_MULTI'
  EXPORTING
    i_number    = lv_aufnr
  TABLES
    it_activity = gt_act_bus2002_new
    et_return   = gt_bapiret2.

LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AE'.
ENDLOOP.

IF sy-subrc EQ 0.
  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.
  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ENDIF.

CHECK sy-subrc NE 0.
CALL FUNCTION 'BAPI_PS_PRECOMMIT'
  TABLES
    et_return = gt_bapiret2.
LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AE'.
ENDLOOP.

IF sy-subrc EQ 0.
  CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'
    IMPORTING
      return = gs_bapiret2.

  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.
  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.
ELSE.
  CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
    IMPORTING
      return = gs_bapiret2.
ENDIF.
"-----------------------------@斌將軍-----------------------------

 四、程式碼整合

通過整合四個BAPI,實現複製標準模板完成專案立項過程

"-----------------------------@斌將軍-----------------------------
FUNCTION zps01_project_create.
*"----------------------------------------------------------------------
*"*"本地介面:
*"  IMPORTING
*"     VALUE(I_INPUT) TYPE  ZSPS_CJXM
*"  EXPORTING
*"     VALUE(E_RETURN) TYPE  BAPIRETURN
*"----------------------------------------------------------------------

  DATA:gs_proj_bus2001_new TYPE bapi_bus2001_new,
       gt_wbs_bus2054_new  TYPE TABLE OF bapi_bus2054_new,
       gs_wbs_bus2054_new  TYPE bapi_bus2054_new,
       gs_net_bus2002_new  TYPE bapi_bus2002_new,
       gt_act_bus2002_new  TYPE TABLE OF bapi_bus2002_act_new,
       gs_act_bus2002_new  TYPE bapi_bus2002_act_new,
       gt_bapiret2         TYPE TABLE OF bapiret2,
       gs_bapiret2         TYPE bapiret2.

  DATA:lv_new_pspid TYPE proj-pspid,
       lv_bz_pspid  TYPE projs-pspid,
       lv_ctumode   TYPE ctu_params-dismode,
       lv_update    TYPE ctu_params-updmode,
       lv_aufnr     TYPE bapi_network_list-network,
       lv_bzxm      TYPE proj-pspid,
       lv_prart     TYPE char10,
       lv_wtges     TYPE char17,
       lv_bzwbs     TYPE ps_posid,
*       lv_profl     TYPE proj-profl,
       lv_number    TYPE numc3,
       lv_check     TYPE char1,
       ls_return    TYPE bapireturn,
       lv_message   TYPE char200,
       lv_msg       TYPE char200.

  IF i_input-pspid IS INITIAL.
    e_return-type = 'E'.
    e_return-message = '標準專案編碼為空'.
    RETURN.
  ENDIF.

  IF i_input-vbukr IS INITIAL.
    e_return-type = 'E'.
    e_return-message = '公司程式碼為空'.
    RETURN.
  ENDIF.

  "獲取專案型別相關設定資訊
  SELECT SINGLE
    *
  FROM zpst_prart
  INTO @DATA(ls_prart)
  WHERE bukrs = @i_input-vbukr
    AND zprart = @i_input-prart.

  "獲取專案經理與OA賬號關聯表資料
  SELECT SINGLE
    vernr,
    verna
  FROM tcj04
  INTO @DATA(ls_cj04)
  WHERE verna = @i_input-usr00.

  IF ls_cj04 IS INITIAL.
    e_return-type = 'E'.
    e_return-message = '專案經理' && i_input-usr01 && '不存在'.
    RETURN.
  ENDIF.

  CLEAR:lv_bz_pspid.
  lv_bz_pspid = i_input-pspid."標準模板專案定義編號
  CALL FUNCTION 'CONVERSION_EXIT_ABPSN_INPUT'
    EXPORTING
      input  = lv_bz_pspid
    IMPORTING
      output = lv_bz_pspid.

  "獲取相同專案型別,最大的專案編號
  CLEAR:lv_prart.
  lv_prart = i_input-prart && sy-datum+0(4) && '%'.
  CLEAR:lv_new_pspid.
  SELECT
  MAX( pspid )
  FROM proj
  INTO lv_new_pspid
  WHERE pspid LIKE lv_prart.

  IF lv_new_pspid IS INITIAL.
    lv_number = 1.
  ELSE.
    lv_number = lv_new_pspid+7(3).
    lv_number = lv_number + 1.
  ENDIF.

  lv_new_pspid = i_input-prart && '-' && sy-datum+0(4) && lv_number."要建立的專案定義編號

*  CLEAR:lv_profl.
*  lv_profl = ."專案引數檔案
*  CASE i_input-prart.
*    WHEN 'NPD' OR 'NPI' OR 'RDT' OR 'AUT' OR 'TRY'.
*      lv_profl = '0001'.
*    WHEN 'TEH' OR 'EXP' OR 'ITA'.
*      lv_profl = '0002'.
*    WHEN 'COS'.
*      lv_profl = '0003'.
*    WHEN 'FAC'.
*      lv_profl = '0004'.
*    WHEN OTHERS.
*  ENDCASE.
*  IF i_input-vbukr = '1000'.
*    lv_profl = 'LRC' && lv_profl.
*  ELSEIF i_input-vbukr = '2000'.
*    lv_profl = 'APS' && lv_profl."專案引數檔案
*  ENDIF.

  SELECT SINGLE
    *
  FROM projs
  INTO @DATA(ls_projs)
  WHERE pspid = @lv_bz_pspid.

  IF sy-subrc EQ 0.
    "--------------------------------建立專案--------------------------------------
    CLEAR:gs_proj_bus2001_new.
    gs_proj_bus2001_new-project_definition = lv_new_pspid.       "專案編號
    gs_proj_bus2001_new-description        = i_input-post1.       "PS: 短描述 (第一行文字)
    gs_proj_bus2001_new-responsible_no     = ls_cj04-vernr.            "專案經理編號
    gs_proj_bus2001_new-applicant_no     = ls_projs-astnr."lv_vernr.            "申請部門編號
    gs_proj_bus2001_new-start              = i_input-plfaz.       "開始日期
    gs_proj_bus2001_new-finish             = i_input-plsez.       "完成日期
*      gs_proj_bus2001_new-company_code       = '2000'."is_proj-vbukr.       "專案的公司程式碼
    gs_proj_bus2001_new-profit_ctr         = ''."is_proj-prctr.       "利潤中心
    gs_proj_bus2001_new-project_profile    = ls_prart-profl."is_proj-profl.       "專案引數檔案
*      gs_proj_bus2001_new-plant              = '2000'."is_proj-werks.       "工廠

    "初始化
    CALL FUNCTION 'BAPI_PS_INITIALIZATION'.

    "建立專案
    REFRESH:gt_bapiret2.
    CALL FUNCTION 'BAPI_BUS2001_CREATE'
      EXPORTING
        i_project_definition = gs_proj_bus2001_new
      TABLES
        et_return            = gt_bapiret2.

    CLEAR:lv_check,lv_message.
    LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
      lv_check = 'E'.
      lv_message = lv_message && gs_bapiret2-message.
      CLEAR:gs_bapiret2.
    ENDLOOP.

    IF lv_check = 'E'.
      "錯誤後初始化
      CALL FUNCTION 'ZPS01_PS_FLAG'.

      e_return-type = 'E'.
      e_return-message = lv_message.
      RETURN.
    ELSE.
      CLEAR:ls_return.
      "成功時提交
      CALL FUNCTION 'ZPS01_PS_PRECOMMIT'
        IMPORTING
          e_return = ls_return.
      IF ls_return-type = 'E'.
        e_return-type = 'E'.
        e_return-message = ls_return-message.
        RETURN.
      ENDIF.

      "--------------------------------建立WBS--------------------------------------
      SELECT
        pspnr,"標準 WBS: 內部專案號 (具有退出(根據 ID ))
        posid,"標準專案中的 WBS 元素
        post1,"PS: 短描述 (第一行文字)
        psphi,"當前的內部專案號 - 標準 WBS
        stufe"專案層次的等級
      FROM prpss
      INTO TABLE @DATA(lt_prpss)
      WHERE psphi = @ls_projs-pspnr.

      SORT lt_prpss BY pspnr.

      IF lt_prpss IS NOT INITIAL.
        LOOP AT lt_prpss INTO DATA(ls_prpss).
          CLEAR:gs_wbs_bus2054_new.
          IF sy-tabix = 1.
            gs_wbs_bus2054_new-wbs_element = lv_new_pspid.
            gs_wbs_bus2054_new-user_field_char20_1 = i_input-usr00.
            gs_wbs_bus2054_new-description                    = i_input-post1."ls_prpss-post1."PS: 短描述 (第一行文字)
          ELSE.
            gs_wbs_bus2054_new-wbs_element = lv_new_pspid && '.' && ls_prpss-posid+10(3)."'NPD-2022037' '.' '001'"工作分解結構元素 (WBS 元素)
            gs_wbs_bus2054_new-wbs_up                         = lv_new_pspid."gs_wbs-up_posid.  "上級WBS
            gs_wbs_bus2054_new-description                    = ls_prpss-post1."PS: 短描述 (第一行文字)
          ENDIF.

          gs_wbs_bus2054_new-responsible_no                 = ls_cj04-vernr."專案經理編號
          "gs_wbs_bus2054_new-profit_ctr                     = ''."gs_wbs-prctr.     "利潤中心
          gs_wbs_bus2054_new-proj_type                      = ls_prart-prart.     "專案型別
          gs_wbs_bus2054_new-wbs_account_assignment_element = 'X'."gs_wbs-belkz.     "標誌:科目分配元素
          "gs_wbs_bus2054_new-wbs_billing_element            = ''."gs_wbs-fakkz.     "識別符號: 開票元素
          gs_wbs_bus2054_new-wbs_left                       = ''."gs_wbs-left_posid."左側WBS
          "gs_wbs_bus2054_new-user_field_char20_1            = ''."gs_wbs-usr00.     "業務類別
          "gs_wbs_bus2054_new-user_field_char20_2            = ''."gs_wbs-usr01.     "CRM 商機編碼
          "gs_wbs_bus2054_new-user_field_char10_1            = ''."'X'.              "產品
          "gs_wbs_bus2054_new-statistical                    = ''."gs_wbs-xstat.     "統計
          "gs_wbs_bus2054_new-wbs_cctr_posted_actual         = ''."gs_wbs-kostl.     "CCtr 過賬
          APPEND gs_wbs_bus2054_new TO gt_wbs_bus2054_new.
          CLEAR:ls_prpss.
        ENDLOOP.

        CALL FUNCTION 'BAPI_PS_INITIALIZATION'.
        "建立WBS
        REFRESH:gt_bapiret2.
        CALL FUNCTION 'BAPI_BUS2054_CREATE_MULTI'
          EXPORTING
            i_project_definition = lv_new_pspid
          TABLES
            it_wbs_element       = gt_wbs_bus2054_new
            et_return            = gt_bapiret2.

        CLEAR:lv_check,lv_message.
        LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
          lv_check = 'E'.
          lv_message = lv_message && gs_bapiret2-message.
          CLEAR:gs_bapiret2.
        ENDLOOP.

        IF lv_check = 'E'.
          "錯誤後初始化
          CALL FUNCTION 'ZPS01_PS_FLAG'.

          e_return-type = 'E'.
          e_return-message = lv_message.
          RETURN.
        ELSE.
          CLEAR:ls_return.
          "成功時提交
          CALL FUNCTION 'ZPS01_PS_PRECOMMIT'
            IMPORTING
              e_return = ls_return.
          IF ls_return-type = 'E'.
            e_return-type = 'E'.
            e_return-message = ls_return-message.
            RETURN.
          ENDIF.

          "--------------------------------建立網路--------------------------------------
          CLEAR : gs_net_bus2002_new.
          gs_net_bus2002_new-project_definition = lv_new_pspid."is_network-pspid.       "專案定義
          gs_net_bus2002_new-wbs_element        = lv_new_pspid."is_network-posid.       "工作分解結構元素 (WBS 元素)
          gs_net_bus2002_new-profile         = ls_prart-profid."is_network-ktext.       "網路引數檔案
          CLEAR:ls_prpss.
*          READ TABLE lt_prpss INTO ls_prpss WITH KEY stufe = 1."獲取最上層WBS的描述
*          IF sy-subrc EQ 0.
*            gs_net_bus2002_new-short_text         = ls_prpss-post1."is_network-ktext.       "描述
*          ENDIF.
          gs_net_bus2002_new-short_text         = i_input-post1."ls_prpss-post1."is_network-ktext.       "描述
          CALL FUNCTION 'BAPI_PS_INITIALIZATION'.
          "建立網路
          REFRESH:gt_bapiret2.
          CALL FUNCTION 'BAPI_BUS2002_CREATE'
            EXPORTING
              i_network = gs_net_bus2002_new
            TABLES
              et_return = gt_bapiret2.

          CLEAR:lv_check,lv_message.
          LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
            lv_check = 'E'.
            lv_message = lv_message && gs_bapiret2-message.
            CLEAR:gs_bapiret2.
          ENDLOOP.

          IF lv_check = 'E'.
            "錯誤後初始化
            CALL FUNCTION 'ZPS01_PS_FLAG'.

            e_return-type = 'E'.
            e_return-message = lv_message.
            RETURN.
          ELSE.
            "成功時提交
            REFRESH:gt_bapiret2.
            CALL FUNCTION 'BAPI_PS_PRECOMMIT'
              TABLES
                et_return = gt_bapiret2.

            CLEAR:lv_check,lv_message.
            LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
              lv_check = 'E'.
              lv_message = lv_message && gs_bapiret2-message.
              CLEAR:gs_bapiret2.
            ENDLOOP.
            IF lv_check EQ 'E'.
              CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.

              CALL FUNCTION 'ZPS01_PS_FLAG'.
            ELSE.

              CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
                EXPORTING
                  wait = 'X'.

              READ TABLE gt_bapiret2 INTO gs_bapiret2 WITH KEY id = 'CNIF_PI'
                                                   number = '003'.
              IF sy-subrc EQ 0.
                lv_aufnr = gs_bapiret2-message_v2.
              ENDIF.
            ENDIF.
            IF ls_return-type = 'E'.
              e_return-type = 'E'.
              e_return-message = ls_return-message.
              RETURN.
            ENDIF.

            "--------------------------------建立作業--------------------------------------
            READ TABLE lt_prpss INTO ls_prpss WITH KEY stufe = 1."獲取最上層WBS的描述

            SELECT
              plko~plnty,"
              plko~plnnr,"
              plko~plnal,"
              plko~zaehl,"
              plko~pspnr,"

              plpo~plnkn,"
              plpo~vornr,"
              plpo~ltxa1,"
              plpo~dauno,"
              plpo~daune,"
              plpo~pspnr AS zbzwbs"
            FROM plko
            INNER JOIN plpo ON plko~plnnr = plpo~plnnr
            INTO TABLE @DATA(lt_plko)
            WHERE plko~pspnr = @ls_prpss-pspnr
              AND plko~plnty = '0'
              AND plpo~plnty = '0'.
            IF lt_plko IS NOT INITIAL.
              LOOP AT lt_plko INTO DATA(ls_plko).
                CLEAR:gs_act_bus2002_new.
                gs_act_bus2002_new-activity           = ls_plko-vornr.       "在網路和庫網路中的作業編號
                gs_act_bus2002_new-description        = ls_plko-ltxa1.       "工序短文字
                gs_act_bus2002_new-control_key        = ''."gs_activity-steus.       "控制碼-內協(ZPS1)和成本(ZPS3)
                CALL FUNCTION 'CONVERSION_EXIT_KONPT_OUTPUT'
                  EXPORTING
                    input  = ls_plko-zbzwbs
                  IMPORTING
                    output = lv_bzwbs.
                gs_act_bus2002_new-wbs_element = lv_new_pspid && lv_bzwbs+11."工作分解結構元素 (WBS 元素)
                gs_act_bus2002_new-duration_normal        = ls_plko-dauno.       "工作時間
                gs_act_bus2002_new-duration_normal_unit        = ls_plko-daune.       "工作時間單位
                gs_act_bus2002_new-work_cntr          = ''."gs_activity-arbpl.       "工作中心
                gs_act_bus2002_new-work_activity      = ''."gs_activity-arbei.       "工作(時間單位H)
                APPEND gs_act_bus2002_new TO gt_act_bus2002_new.
                CLEAR:ls_plko.
              ENDLOOP.

              CALL FUNCTION 'BAPI_PS_INITIALIZATION'.

              CALL FUNCTION 'CONVERSION_EXIT_ALPHA_INPUT'
                EXPORTING
                  input  = lv_aufnr
                IMPORTING
                  output = lv_aufnr.

              CALL FUNCTION 'BAPI_BUS2002_ACT_CREATE_MULTI'
                EXPORTING
                  i_number    = lv_aufnr
                TABLES
                  it_activity = gt_act_bus2002_new
                  et_return   = gt_bapiret2.
              CLEAR:lv_check,lv_message.
              LOOP AT gt_bapiret2 INTO gs_bapiret2 WHERE type CA 'AEX'.
                lv_check = 'E'.
                lv_message = lv_message && gs_bapiret2-message.
                CLEAR:gs_bapiret2.
              ENDLOOP.

              IF lv_check = 'E'.
                "錯誤後初始化
                CALL FUNCTION 'ZPS01_PS_FLAG'.

                e_return-type = 'E'.
                e_return-message = lv_message.
                RETURN.
              ELSE.
                CLEAR:ls_return.
                "成功時提交
                CALL FUNCTION 'ZPS01_PS_PRECOMMIT'
                  IMPORTING
                    e_return = ls_return.
                IF ls_return-type = 'E'.
                  e_return-type = 'E'.
                  e_return-message = ls_return-message.
                  RETURN.
                ENDIF.
              ENDIF.
            ELSE.
              e_return-type = 'E'.
              e_return-message = '標準專案擡頭WBS' && ls_prpss-pspnr && '的作業不存在'.
              RETURN.
            ENDIF.
          ENDIF.
        ENDIF.
      ELSE.
        e_return-type = 'E'.
        e_return-message = '標準WBS不存在'.
        RETURN.
      ENDIF.
    ENDIF.
  ELSE.
    e_return-type = 'E'.
    e_return-message = '標準專案不存在'.
    RETURN.
  ENDIF.

  "如果預算為空,則不維護預算
  IF i_input-wtges IS NOT INITIAL.
    "維護預算
    "設定成本控制範圍
    SET PARAMETER ID 'CAC' FIELD 'LRCG'.
    "呼叫BDC
    REFRESH:gt_bdcdata[].
    PERFORM bdc_dynpro      USING 'SAPMKBUD' '0200'.
    PERFORM bdc_field       USING 'BDC_OKCODE' '=MYENTER'.
    PERFORM bdc_field       USING 'BDC_CURSOR' 'PROJ-PSPID'.
    PERFORM bdc_field       USING 'PROJ-PSPID' lv_new_pspid."專案定義

    PERFORM bdc_dynpro      USING 'SAPLKBPP' '0320'.
    PERFORM bdc_field       USING 'BDC_OKCODE' '=POST'.
    PERFORM bdc_field       USING 'BDC_CURSOR' 'BPDY-WERT1(03)'.
    CLEAR:lv_wtges.
    lv_wtges = i_input-wtges.
    CONDENSE lv_wtges NO-GAPS.
    PERFORM bdc_field       USING 'BPDY-WERT1(01)' lv_wtges."專案預算

    lv_ctumode = 'N'.    "N就是一步完成,A是分步enter完成
    REFRESH gt_messtab[].
    CALL TRANSACTION 'CJ30' USING gt_bdcdata
          MODE lv_ctumode
          UPDATE 'S'
          MESSAGES INTO gt_messtab.
    CLEAR:lv_message,gt_messtab.
    LOOP AT gt_messtab.
      CLEAR:lv_msg.
      CALL FUNCTION 'MESSAGE_TEXT_BUILD'
        EXPORTING
          msgid               = gt_messtab-msgid
          msgnr               = gt_messtab-msgnr
          msgv1               = gt_messtab-msgv1
          msgv2               = gt_messtab-msgv2
          msgv3               = gt_messtab-msgv3
          msgv4               = gt_messtab-msgv4
        IMPORTING
          message_text_output = lv_msg.
      CONCATENATE lv_message lv_msg INTO lv_message.
    ENDLOOP.

    READ TABLE gt_messtab WITH KEY msgtyp = 'S'
                                      msgid = 'BP'
                                      msgnr = '043'.
    IF sy-subrc = 0 .
      e_return-type = 'S'.
      e_return-message = '專案建立成功'.
      e_return-message_v1 = lv_new_pspid.
    ELSE.
      e_return-type = 'E'.
      e_return-message = '專案建立成功,但預算維護失敗'.
      e_return-message_v1 = lv_new_pspid.
    ENDIF.
  ELSE.
    e_return-type = 'S'.
    e_return-message = '專案建立成功'.
    e_return-message_v1 = lv_new_pspid.
  ENDIF.
ENDFUNCTION.
"-----------------------------@斌將軍-----------------------------

程式中因為多次呼叫提交和初始化邏輯,因此封裝成一個函數

初始化函數

"-----------------------------@斌將軍-----------------------------
FUNCTION zps01_ps_flag.
*"----------------------------------------------------------------------
*"*"本地介面:
*"----------------------------------------------------------------------

  CALL FUNCTION 'PS_FLAG_INIT_GLOBAL_FLAGS'.

  CALL FUNCTION 'PS_FLAG_SET_GLOBAL_FLAGS'
    EXPORTING
      i_precommit_ok = 'Y'.

ENDFUNCTION.
"-----------------------------@斌將軍-----------------------------

BAPI提交函數

"-----------------------------@斌將軍-----------------------------
FUNCTION zps01_ps_precommit.
*"----------------------------------------------------------------------
*"*"本地介面:
*"  EXPORTING
*"     REFERENCE(E_RETURN) TYPE  BAPIRETURN
*"----------------------------------------------------------------------

  DATA:gt_return TYPE TABLE OF bapiret2,
       gs_return TYPE bapiret2.
  DATA:lv_check   TYPE char1,
       lv_message TYPE char200.

  CALL FUNCTION 'BAPI_PS_PRECOMMIT'
    TABLES
      et_return = gt_return.

  CLEAR:lv_check,lv_message.
  lv_check = 'S'.
  LOOP AT gt_return INTO gs_return WHERE type CA 'AEX'.
    lv_check = 'E'.
    lv_message = lv_message && gs_return-message.
    CLEAR:gs_return.
  ENDLOOP.
  IF sy-subrc EQ 0.
    CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.

    CALL FUNCTION 'ZPS01_PS_FLAG'.
  ELSE.

    CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
      EXPORTING
        wait = 'X'.
  ENDIF.

  e_return-type = lv_check.
  e_return-message = lv_message.
ENDFUNCTION.
"-----------------------------@斌將軍-----------------------------