SAP'de SOAP Web Servisi Yayınlamak: Fonksiyon Modülünden WSDL'e
RFC'ye açık bir fonksiyon modülünü SOAP web servisine çevirmek, SOAMANAGER'da binding tanımlamak, WSDL'i almak ve test etmek; bir şeyler ters gittiğinde bakılacak araçlarla birlikte.
Bütün ilgi OData ve REST'e gidiyor olsa da gerçek projelerde SOAP hâlâ her yerde: bankalar, lojistik firmaları, kamu portalları ve eski ara katman yazılımları çoğu zaman bir WSDL bekliyor. İşin iyi tarafı şu: SAP ABAP sisteminde mevcut bir fonksiyon modülünden SOAP servisi yayınlamak yaklaşık on beş dakika sürüyor.
Bu yazıda malzeme numarası verildiğinde temel malzeme bilgilerini dönen küçük bir servis yapacağız.
Bu, klasik on-premise yöntemi (S/4HANA ya da ECC). ABAP Cloud ile yapılan yeni geliştirmelerde OData/RAP tercih edilmeli; S/4HANA Cloud'da ise SOAP servisleri communication arrangement'lar üzerinden sunuluyor.
1. RFC'ye açık bir fonksiyon modülü
Fonksiyon modülünden üretilen web servisleri (inside-out) için modülün RFC'ye açık (remote-enabled) olması gerekir. Tüm parametreler değer ile (by value) aktarılmalı.
Önce sonuç için bir yapı:
@EndUserText.label : 'Material info for web service'
@AbapCatalog.enhancement.category : #NOT_EXTENSIBLE
define structure zs_ws_material_info {
matnr : matnr;
maktx : maktx;
mtart : mtart;
matkl : matkl;
meins : meins;
}
Sonra fonksiyon modülü (SE37 ya da ADT). Nitelikler sekmesinde Remote-Enabled Module seçin:
FUNCTION z_ws_get_material_info
IMPORTING
VALUE(iv_matnr) TYPE matnr
VALUE(iv_language) TYPE spras DEFAULT sy-langu
EXPORTING
VALUE(es_material) TYPE zs_ws_material_info
VALUE(ev_message) TYPE bapi_msg.
" Remote-enabled module (SE37 → Attributes → Remote-Enabled Module).
" All parameters are passed by value – required for RFC and web services.
DATA matnr TYPE matnr.
" The caller sends the external format (e.g. without leading zeros)
CALL FUNCTION 'CONVERSION_EXIT_MATN1_INPUT'
EXPORTING input = iv_matnr
IMPORTING output = matnr
EXCEPTIONS OTHERS = 1.
IF sy-subrc <> 0.
ev_message = |Invalid material number { iv_matnr }|.
RETURN.
ENDIF.
SELECT SINGLE FROM mara AS m
LEFT OUTER JOIN makt AS t ON t~matnr = m~matnr
AND t~spras = @iv_language
FIELDS m~matnr, t~maktx, m~mtart, m~matkl, m~meins
WHERE m~matnr = @matnr
INTO CORRESPONDING FIELDS OF @es_material.
IF sy-subrc <> 0.
ev_message = |Material { iv_matnr } not found|.
ENDIF.
ENDFUNCTION.
İleride zaman kazandıran iki ayrıntı:
- Exception fırlatmak yerine bir mesaj alanı dönün. SOAP istemcileri "bulunamadı" durumunda dolu bir alanı, bir SOAP fault'tan çok daha kolay işler.
- Conversion exit'leri kendiniz uygulayın (burada
MATN1): Çağıran taraf dış formatı gönderir.
2. Servis tanımını oluşturmak
SE37'de Utilities → More Utilities → Create Web Service → From the Function Module yolunu izleyin (ya da SE80'de Create → Enterprise Service). Sihirbaz şunları soruyor:
- Servis tanımı adı: örneğin
ZWS_MATERIAL_INFOve kısa bir açıklama. - Endpoint: fonksiyon modülümüz. Eleman adlarının birebir
IV_MATNR,ES_MATERIALkalmasını istiyorsanız Map Name işaretini kaldırın. - SOAP profili: servisin güvenlik seviyesi.
- Paket ve transport request.
Önerim kullanıcı/şifre ve transport garantisi: kimlik doğrulama yalnızca HTTPS üzerinden. Sonunda servis tanımını aktive edin.
3. SOAMANAGER'da binding oluşturmak
Servis tanımı sadece arayüzü tarif eder. Çağrılabilir hâle gelmesi için bir binding (endpoint) gerekir:
- SOAMANAGER işlem kodunu çalıştırın (tarayıcıda açılır).
- Service Administration → Web Service Configuration altında
ZWS_MATERIAL_INFO'yu arayın. - Configurations sekmesinde Create Service'e basın, servis ve binding adını girin.
- Güvenlik: Transport Guarantee = HTTPS, Authentication = User ID/Password.
- Kaydedin; binding hemen aktif olur.
Open Binding WSDL Generation ile WSDL adresini alırsınız. Karşı tarafa göndereceğiniz bağlantı budur.
4. Servisi test etmek
WSDL'i SoapUI'ye (ya da Postman'e) aktarın, basic authentication girin ve bir istek gönderin:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:urn="urn:sap-com:document:sap:rfc:functions">
<soapenv:Header/>
<soapenv:Body>
<urn:Z_WS_GET_MATERIAL_INFO>
<IV_MATNR>MAT-1000</IV_MATNR>
</urn:Z_WS_GET_MATERIAL_INFO>
</soapenv:Body>
</soapenv:Envelope>
Gelen cevap:
<soap-env:Envelope xmlns:soap-env="http://schemas.xmlsoap.org/soap/envelope/">
<soap-env:Header/>
<soap-env:Body>
<n0:Z_WS_GET_MATERIAL_INFOResponse xmlns:n0="urn:sap-com:document:sap:rfc:functions">
<ES_MATERIAL>
<MATNR>MAT-1000</MATNR>
<MAKTX>Laptop 14 Developer Edition</MAKTX>
<MTART>HAWA</MTART>
<MATKL>IT01</MATKL>
<MEINS>ST</MEINS>
</ES_MATERIAL>
<EV_MESSAGE/>
</n0:Z_WS_GET_MATERIAL_INFOResponse>
</soap-env:Body>
</soap-env:Envelope>
Çağıran tarafın servise yetkili bir SAP kullanıcısı olmalı: S_SERVICE yetki nesnesi (ve fonksiyon grubu için S_RFC). Dar bir role sahip bir system ya da communication kullanıcısı en temiz çözüm.
5. Bir şeyler ters giderse
| Belirti | Bakılacak yer |
|---|---|
| HTTP 401 / 403 | Kullanıcı, şifre, S_SERVICE / S_RFC yetkileri (kullanıcı için SU53) |
| HTTP 404 | Binding yok ya da SICF'teki /sap/bc/srt/ düğümü pasif |
| HTTP 500 / SOAP fault | SRT_UTIL işlem kodu: hata günlüğü ve payload izi |
| Yanlış ya da boş değerler | Conversion exit'ler, Map Name ayarı, dil parametresi |
SRT_UTIL'de bir kullanıcı için belirli bir süreliğine payload izini açabilirsiniz. Gerçekte ne gönderildiğini görmenin en hızlı yolu bu.
Özet
- RFC'ye açık fonksiyon modülü, değer ile parametreler, exception yerine mesaj.
- Sihirbazla servis tanımı, HTTPS'li güvenlik profili.
- SOAMANAGER'da binding, karşı tarafa WSDL adresi.
- SoapUI ile test, SRT_UTIL ile analiz.
SOAP göz alıcı değil ama güvenilir. Bu adımlarla "bize WSDL lazım" diyen bir iş ortağı entegrasyonu artık endişe sebebi değil.
Yorumlar