Thursday, May 29, 2008

Implementing logic in the proxy and consuming the service in .NET

First the good news :)
I managed to create the service and was able to consume it from .NET.
Here were the open questions from the last post....
1) How to write some logic in the server proxy
2) Where and how to find the wsdl with binding information so that i can consume it from .NET

In order to write the logic into proxy i went to the package in which i generated the proxy. In that package i found that an interface has been generated for the message interface we generated in ESR and a class to implement the interface. I found the method instance method of the class and went ahead editing the method implementation. My first unassisted ABAP code. Here's how it looked like....


OUTPUT-GET_EMPLOYEE_OUTPUT-ID = INPUT-GET_EMPLOYEE_INPUT.
OUTPUT-GET_EMPLOYEE_OUTPUT-NAME-FIRST_NAME = 'Abhishek'.
OUTPUT-GET_EMPLOYEE_OUTPUT-NAME-LAST_NAME = 'Kumar'.


Once done i went to the transaction SOAMANAGER. This is the new transaction which replaces the transactions WSADMIN and WSCONFIG. This opened a webdynpro UI with a tab Business Administration on which there's a link Web Service Administration. There i can search for the design time component i want to configure. (EmployeeService) in my case. Once selecting the service i can go to Configurations tab where i select to Create a Service. I can choose a name for the service and binding. Whatever i choose here appears in the final wsdl as service and binding. Once done I can choose a type of authentication. I chose http authentication. and saved the configuration.

On the same page i found the link to the wsdl with all the binding and port information. On having a look at the wsdl i confirmed that binding and service tags are available.
Copy the link to the wsdl and try setting the reference to this wsdl in Visual Studio. Once done i am able to call the service easily from .NET.

Now the second question which was how to add more then one operation to the Message Interface. This is a limitation in 700 release of BASIS. And unfortunately the sandbox system has a 700 release of BASIS. According to some documentation i found i can add more then 1 operations in the message interface. So i parked it for the time being.....

~Abhishek

PS :- This was my hello world to the world of ABAP. i.e. a first program in ABAP. This post is the last in the series of blogs i started on May 23rd 2008 :)

Tuesday, May 27, 2008

Generating a Proxy

Here's what i did next. I just added a message interface called EmployeeService in the Message interfaces of my . I marked it as inbound synchronous method in the option. I couldn't find much documentation about what the various options mean however i assume that inbound means inbound message coming from client to the server and synchronous means that server would process them and give the results back to client then and there itself.
Now i selected the input and output messages and there you go . I got a nice wsdl which looks like the following....

<?xml version="1.0" encoding="ISO-8859-1"?>

<wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:p1="http://sap.office.tst" name="EmployeeService" targetNamespace="http://sap.office.tst">
<wsdl:types>
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://sap.office.tst" targetNamespace="http://sap.office.tst">
<xsd:element name="GetEmployeeInput" type="EmployeeId" />
<xsd:element name="GetEmployeeOutput" type="Employee" />
<xsd:simpleType name="EmployeeId">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
a64268c22be811dda00f000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:restriction base="xsd:string" />
</xsd:simpleType>
<xsd:complexType name="Employee">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
a644d9c02be811dd90e2000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:sequence>
<xsd:element name="Id" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
4ca5845028aa11ddb1c2001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="Name" type="Name">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
4ca5845128aa11ddb4a1001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
<xsd:complexType name="Name">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
a64994b02be811ddc2e4000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:sequence>
<xsd:element name="FirstName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b028aa11ddcc0b001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="LastName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b128aa11ddb07c001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:schema>
</wsdl:types>
<wsdl:message name="GetEmployeeInput">
<wsdl:documentation>
Input to GetEmployee Operation
</wsdl:documentation>
<wsdl:part name="GetEmployeeInput" element="p1:GetEmployeeInput" />
</wsdl:message>
<wsdl:message name="GetEmployeeOutput">
<wsdl:part name="GetEmployeeOutput" element="p1:GetEmployeeOutput" />
</wsdl:message>
<wsdl:portType name="EmployeeService">
<wsdl:operation name="EmployeeService">
<wsdl:input message="p1:GetEmployeeInput" />
<wsdl:output message="p1:GetEmployeeOutput" />
</wsdl:operation>
</wsdl:portType>
<ifr:properties xmlns:ifr="urn:com-sap:ifr:v2:wsdl">
<ifr:category>
ifmmessif
</ifr:category>
<ifr:methods>
<ifr:method name="EmployeeService">
<ifr:isSynchron>
true
</ifr:isSynchron>
<ifr:isInbound>
true
</ifr:isInbound>
<ifr:interfaceCategory>
inbound
</ifr:interfaceCategory>
</ifr:method>
</ifr:methods>
<ifr:messages>
<ifr:message name="GetEmployeeInput">
<ifr:messType>
ifmmessage
</ifr:messType>
<ifr:technicalNamespace>
http://sap.office.tst
</ifr:technicalNamespace>
</ifr:message>
<ifr:message name="GetEmployeeOutput">
<ifr:messType>
ifmmessage
</ifr:messType>
<ifr:technicalNamespace>
http://sap.office.tst
</ifr:technicalNamespace>
</ifr:message>
</ifr:messages>
</ifr:properties>
</wsdl:definitions>

As soon as i was done with this i though of generating a .NET proxy for this wsdl. (Me being a .NET developer i couldn't control my instincts and stay away from Visual Studio too long :) )

Anyways i tried to generate a proxy and failed. Basically nothing is generated. On looking closely at the wsdl i found that wsdl:service and wsdl:binding tags are missing. Which is understandable. If i was designing the ESR i wouldn't want the information about binding and implementation address in my repository. I would probably keep it somewhere else like UDDI. This is an open question that i need to figure out now. Where doesn SAP keep this information. I'll touch this back once i am sure that implementation works.

So leaving the visual studio i came back to my ABAP system and started sproxy to generate a implementation proxy for my wsdl. After struggling a lot with package concept of ABAP i was suggested to make the proxy as a local object. I still can't figure out why it can't be a server object.... Everyone i contacted gave me different reasons however i chose to believe that i do not have appropriate permissions to create a server side object. (Sad and interesting, since this is a sandbox i thought i have all the permissions)

So i have managed to generate a proxy for this wsdl in ABAP and now comes the first place where i would code. All i want to do is to give back the employee with some hardcoded name and passed id from the method. Once i am able to do this i would actually go ahead and find the answer to my first question i.e. where to find the binding and service info for this interface.

Another open question which looms large is to add another method to this interface. I choose to address this at the end.

~Abhishek

Sunday, May 25, 2008

Show a document on the post

One of my friends wanted to post a pdf document on the blog. On doing a quick google i found a nice tool to post documents on the blog.
Check out http://www.scribd.com/ for finding how to upload and show documents on your blog.....

~Abhishek

Friday, May 23, 2008

Posting xml on the blog

Here's a simple javascript web application application that will format source code text into html for inserting into your blog.

http://formatmysourcecode.blogspot.com/

~Abhishek

Defining the Interface using Integration builder

In the previous steps I am done with setting the prereqs to start defining an interface in the ESR. I started with defining the interface now. Here are the steps
1) Login to the PI system
2) Double click on User Menu -> Exchange Infrastructure ->SXMB_IFR - Start Integration Builder. Alternatively execute the transaction SXMB_IFR.
3) This should open an internet explorer window with links to various tools. Click on Integration Repository
4) Step 3 would download and install a Java application (jnlp file) to your system
5) Provide credentials to login to the integration builder
6) Once the integration builder starts go to Tools -> Transfer from System Landscape Directory -> Import Software Component Versions
7) Select the software component in which we want to develop our interface and import it
8) Once we do this select the Software Component Version in the left naviagtion menu. Right click and add a namespace in which we would be doing the development
9) Expand the interface objects -> Data Types and right click on Data Types to add Data Types
10) Add the Data Types Employee, EmployeeId, Name

Here's how various structures look like after editing them using Integration Builder ...

a) Name
<?xml version="1.0" encoding="ISO-8859-1"?>

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://sap.office.tst" targetNamespace="http://sap.office.tst">
<xsd:complexType name="Name">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
1a2def0028c111dd8c9c000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:sequence>
<xsd:element name="FirstName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b028aa11ddcc0b001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="LastName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b128aa11ddb07c001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:schema>


b) EmployeeId
<?xml version="1.0" encoding="ISO-8859-1"?>

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://sap.office.tst" targetNamespace="http://sap.office.tst">
<xsd:simpleType name="EmployeeId">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
b58a93e028c111ddcfe2000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:restriction base="xsd:string" />
</xsd:simpleType>
</xsd:schema>


c) Name
<?xml version="1.0" encoding="ISO-8859-1"?>

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://sap.office.tst" targetNamespace="http://sap.office.tst">
<xsd:complexType name="Name">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
1a2def0028c111dd8c9c000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:sequence>
<xsd:element name="FirstName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b028aa11ddcc0b001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="LastName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b128aa11ddb07c001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:schema>

Next we go ahead and define 2 Message Types as input and output message of the operation we want to define in our wsdl . ( I am unable to find how to have more then 2 messages in my interface for wsdl and hence i am adding only 2 Message Types as off now. To Add a message type in the Navigation Tree we can right click on Message Type and add a new one

Here are 2 schemas of 2 message types i added

a) GetEmployeeInput
<?xml version="1.0" encoding="ISO-8859-1"?>

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://sap.office.tst" targetNamespace="http://sap.office.tst">
<xsd:element name="GetEmployeeInput" type="EmployeeId" />
<xsd:simpleType name="EmployeeId">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
02f3c70028c211ddad54000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:restriction base="xsd:string" />
</xsd:simpleType>
</xsd:schema>

b) GetEmployeeOutput
<?xml version="1.0" encoding="ISO-8859-1"?>

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://sap.office.tst" targetNamespace="http://sap.office.tst">
<xsd:element name="GetEmployeeOutput" type="Employee" />
<xsd:complexType name="Employee">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
886faed028c211dd8216000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:sequence>
<xsd:element name="Id" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
4ca5845028aa11ddb1c2001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="Name" type="Name">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
4ca5845128aa11ddb4a1001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
<xsd:complexType name="Name">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
88721fd228c211ddb301000bcd9b93dd
</xsd:appinfo>
</xsd:annotation>
<xsd:sequence>
<xsd:element name="FirstName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b028aa11ddcc0b001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="LastName" type="xsd:string">
<xsd:annotation>
<xsd:appinfo source="http://sap.com/xi/TextID">
93b077b128aa11ddb07c001321f4509b
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:schema>
Once done with adding these 2 MessageTypes i have added a MessageInterface to my little POC using the Add New MessageInterface wizard which we again get by right clicking the MessageInterfaces node on the navigation tree in my SCV
Here's where my confusions have started as there are various options on what type of Message Interfaces do i want. So i am stopping this blog post here and would write the next steps in my next post.....

~Abhishek

PS: Its relatively simple to write a service in .NET since we follow inside out approach of defining a wsdl i.e. we define our classes first and wsdl is generated out of the box by the Visual Studio. This approach is time consuming however this way i have more control over how my wsdl, schemas etc. should look like so i like this more then .NET :) . Its taking lot of time since it is my first time i am doing this however i am sure with time it would become easier for me to use outside in approach of defining a web service.....

Settnig the prereqs.....

According to various documents on SDN i found out that ESR will be the repository in which the interface of a service will be stored. While the implementation of this system will lie in a business system
Now the first question is how to define the interface. The tool which can be used for defining this interface is Integration Builder. Now in order to work with the Integration builder one needs a Software Component Version and for defining a Software Component Version one needs to have a Product.
So the first step is to create a Product. Here are the steps to do this
1) Login to your PI system
2) Double click on User Menu -> Exchange Infrastructure -> Administration -> SLDCHECK - Test SLD Connection. Alternatively execute transaction SLDCHECK
3) Step 2 should open the SLD UI in an internet explorer
4) Click on the link Products
5) Add a new Product Version by clicking "New Product Version"
6) Come back to the SLD UI in internet explorer (You can use Home link on your page or use the back button in the browser)
7) Click on the Software Components link
8) Add a New Software Component Version by clicking the button
9) In the Add New Software Component Version Select the product as the product you defined in the step 5
Once we are done with this we have got the first 2 prerequisites ready to develop our interface.
Next is to use the integration builder to start defining the interface....

~Abhishek

Initial setup

After struggling through at least 30-40 pdf documents on SDN over 100 google searches i finally figured out a system where SAP allows me to develop and test in
The system is HU6 and the details can be found in ES Workplace handbook Page 67.(https://www.sdn.sap.com/irj/sdn/go/portal/prtroot/docs/library/uuid/d91e4d16-0b01-0010-57b5-c4473111136f)
There are some very specific settings which you need to do if you are accessing this system from your corporate machine. Its actually a DMZ system and you need SAP Log on to access this system.
If you are in SAP Corporate network then you need not enter any SAP Router String which is given inside the above document.
Anyways by the time i figured out the workaround to access this system i figured out a SAP internal system with a similar BASIS Component release which is there on the system HU6 which you can use for your development. Most of the things in the blog series i would be posting should work as it is on HU6.
So my intial setup was over as soon as i configured HU6 i knew i have access to a XI system which by this time i came to know is called PI and not XI anymore.
For anyone out there who wants to play with PI add HU6 system to your SAP Log on utility and off you go....
I would play with ESR now....
~Abhishek

Playing with ESR and XI

After struggling with SAP systems from outside for around 3 years now i decided to go and do something inside it. I say struggling from outside since all i did with SAP systems till now was to look at the interfaces and consume the interfaces to make something in .NET world or to look at the Netweaver screens with horror, look at the ABAP developers in awe as to how they work on such complex looking UI and look at the ABAP technology stack as a neutral observer and sometimes criticising it.
This time i decided to go in and develop at least something in the Netweaver ABAP stack myself and get rid of this fear, awe and helplessness when some discussion happens around ABAP stack.

So here's the POC which i decided to do around a week back
1) Define a simple service interface in ESR
2) Provide an implementation in ABAP stack
3) Consume the service from .NET and prove that service works

Over the period of last week it gor refined to
1) The service should have 2 methods GetEmployeeIds and GetEmployeeById
2) Use ESR, XI Integration builder and implement the service in ABAP

I'll be posting my struggles in a series of blogs and will tag this series with ESR/XI/PI

~Abhishek