Learn how to a build a cloud-first strategyRegister Now

x
?
Solved

Anyone used Apache AXIS

Posted on 2005-04-20
69
Medium Priority
?
1,830 Views
Last Modified: 2010-10-05


Anyone use Apache Axis ????
0
Comment
Question by:code_123
  • 45
  • 22
  • 2
69 Comments
 
LVL 29

Expert Comment

by:bloodredsun
ID: 13823421
A lilttle, yes, what do you want to know?
0
 
LVL 29

Expert Comment

by:bloodredsun
ID: 13823682
I know I'm trying to pre-empt your questions here but I'll give it a go...

What is Axis?
A Java or C++ platform for creating and deploying web services applications.

Where can I find it?
http://ws.apache.org/axis/

What's the current version?
1.1 with 1.2 as the next gen.

What does it do, really?
It allows you to create web services: from simple *.jws (Java web services) type ones to full on production grade ones with WDSL, UDDI and all the bells and whistles

What's a good book?
ALthough I'm not generally a fan of Wrox books, they had a very good book called "Java Web Services". But as they went bust, try "Developing Java Web Services: Architecting and Developing Secure Web Services Using Java" by  Nagappan,  Skoczylas, and Sriganesh.
0
 

Author Comment

by:code_123
ID: 13823750



No, I want to create a custom header, but having trouble doing so.  There's no documentation (well i can't find any) on apache site or using google

because i'm new to this i'm not too sure what to

once i've created the header i want to add a string value to it so a calling web service can pick it up

I'm not sure how to deal with the handle response and requests


    public boolean addSOAPHeader(MessageContext context) throws Exception
    {
        context = MessageContext.getCurrentContext();
        Message message = context.getRequestMessage();
        SOAPEnvelope envelope = message.getSOAPEnvelope();

SOAPEnvelope envelope = message.getSOAPEnvelope();
SOAPHeaderElement element = envelope.addHeader("myHeaderNAme");
0
Independent Software Vendors: We Want Your Opinion

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 15

Expert Comment

by:aozarov
ID: 13824163
code_123, I don't understand (I gave you a link before in two different threads) which has an example of how to do exactly that in Apache soap.
And even your code extract is even from there.

You add the soap header this way (from the same article):
 SOAPHeaderElement element = new SOAPHeaderElement("http://psol.com/2003/tips/header",
                                     "priority"); // create a header name "priority"
element.setObjectValue(priority); // set the header "priority" with a value
call.addHeader(element); // add the alement to the soap envelope!
0
 

Author Comment

by:code_123
ID: 13824393


OK, OK, OK

I didn't understand what it was doing, now with comments it makes sense (kind of)

Sorry
0
 

Author Comment

by:code_123
ID: 13824751


A question :))

In this bit

SOAPHeaderElement element = new SOAPHeaderElement("http://psol.com/2003/tips/header","priority");

"http://psol.com/2003/tips/header" - what does this oart mean, what would normally go here

Many thanks
 
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13824817
URI of the namespace. you can put any url there (basically it is something like java package to scope the variable, just in case there is anohter different "priority" element will be added).
0
 

Author Comment

by:code_123
ID: 13824973


OK understands that bit now

Another thing

On this line
SOAPHeaderElement element = new SOAPHeaderElement("http://localhost/.....","TokenHeader");

My ide doesn't like it - it gives me the error - Cannot instantiate the type SOAPHeaderElement, do you know what this means

Many Thanks
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13825035
You need to import org.apache.axis.message.SOAPHeaderElement and not javax.xml.soap.SOAPHeaderElement
0
 

Author Comment

by:code_123
ID: 13825147


Sorry for al these daft questions
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13825328
Thats ok :-)
0
 

Author Comment

by:code_123
ID: 13825651


Another one

I have my method, which i call from another class, but SOAPHandler.addSOAPHeader(token);   This gives me an error of 'Unhandled exception type Exception'.  Can you tell me how i fix this.  Do i need some exception handling in my addSOAPHeader method

Should it be a static string ?

Thanks again

    public static String addSOAPHeader(String token) throws Exception
    {
       
        URL endpoint = new URL("http://localhost:8080/....");
       
        Service service = new Service();
       
        Call call = (Call)service.createCall();
   
        // create a SOAP header called "TokenHeader"
        SOAPHeaderElement midentityTokenHeader = new SOAPHeaderElement("http://localhost...","TokenHeader");
       
        // set the header "TokenHeader" with the vaue of token
        tokenHeader.setObjectValue(token);
       
        // add the "TokenHeader" to the SOAP envelope
        call.addHeader(tokenHeader);  
       
        return token;
    }
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13825874
I think your problem is that you need try ~ catch (Exception ex) {} in the code that calls addSOAPHeader...
BTW,
what is the point to add a header to Call if you are not going to use it? you probably want to pass Call to this method (which will add the header to it)
and then use call to submit your soap request.
0
 

Author Comment

by:code_123
ID: 13825952

Sorry don't understand

On the client side - my login handler is called and validate credentials - at this point there are no soap headers

Then, login handler generates a token (just a string)

Then, the soap header is created with the token value and passes this back to the client

Now the client sees the newly added soap header with a value

The client can then make sure the value in the soap header is valid by sending the value back to a back-end db table and doing some checks.

Am i going about this the wrong way ?


0
 
LVL 15

Expert Comment

by:aozarov
ID: 13826031
1. I assumed you fixed the compilation problem by adding try~catch.
2. Ok, but then what is the point to return the same value given as input in your addSOAPHeader method?
0
 

Author Comment

by:code_123
ID: 13826124


yeah sorry - try catch orked a treat fanks

When i have my token it is save along with username expiry date and some other stuff to a back-end table

I then lookup the token value in the db table to make sure it hasn't expired

So i create the token, save to db table, create a soap header and pass this back to client.  when the client makes calls i then pass this token back to the db to check it's valid

It may sound convoluted but the data we hold is confidential, that's why i'm doinf it this way

Also by using token in headers it is transparent to the user/clinet and they don't have to keep logging in/out unless they let the token expire

Is this all rubbish !!!
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13826291
No it fine, but if the client is doing soap calls then it should add it to the header itself (using the same way).
0
 

Author Comment

by:code_123
ID: 13831663

Cheers

If the client creates the header am i right in thinking the server-side can take the vlaue of the header and process it i.e. make sure it is valid.  

Then can the server-side write back to the client header e.g. if the token is about to expire, and the clinet wants a new one, ten the serve-side can update the token value

Do you know of any links/examples of soap handle Response/Request ?

Many thanks






0
 

Author Comment

by:code_123
ID: 13831700


Some soap tutorials for the thickee would be good !!
0
 

Author Comment

by:code_123
ID: 13841126


Ok, i think i'm barking up the wrong tree - surely it can't be this hard !!!!

Most of the code i'm writing at the moment is server-side, so i haven't done any of the wsdl files yet

If my client creates a header and goes off to my server-side to do validation stuff, how do i return a string from my server-side to the client ???

what is the best way for my client to tlk to my servoer- side code and visa versa ????


Thanks for any help
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13844334
Hi code_123,
Regarding this and http://www.experts-exchange.com/Programming/Programming_Languages/Java/Q_21397334.html
You need to provide more details if you want someone to help you.
what form of communication is done between the client and the "server-side"?
Is the server-side a servlet/EJB/web service?
Are there any other elements involved beside this client and the server-side component?
Do you expect the token returned by the "server-side" to be used by the client in its further communication
as a proof of authenticated client?
0
 

Author Comment

by:code_123
ID: 13857008


I have a .java file which connects t s db to check login parameters.  The stage i am at nowis trying to wrirte a clinet that will connect to the login java file - I don't know how to write a client to send parameter to the login java file

The server-side is just a java file

There will be other components involved but i jst want the communication working between the client and server-side first

Yes, i want the token returned by the server-sdie to be used by the client in its further communication as proof of authentication

Many thanks for your help


0
 
LVL 15

Expert Comment

by:aozarov
ID: 13858590
Just two more clarification.
Is your "just a java file" server-side an RMI service, Servlet, EJB, Axis web service,.. ?

>> I have a .java file which connects t s db to check login parameters
Is that done in your server-side part?
0
 

Author Comment

by:code_123
ID: 13865112


It's a servlet

Yes, the "connects to a db to check login parameters" is done in the server-side part

Many Thansk
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13868619
Ok,
So you have a servlet that getts client requests and use the DB to check the user credentials.
I assume this is a plain servlet (and not an Axis web service dispatched by Axis)??
How does your client interact with that servlet? (if the above servlet is a web service servlet, dispatched by Axis)?
Just in case is that both the client is an Axis soap client (uses the Call API) and the server side is a Servlet dispatched by Axis then you
can "ping pong" the tokens this way:
1.a read the header
after calling invoke call this method: http://ws.apache.org/axis/java/apiDocs/org/apache/axis/client/Call.html#getResponseMessage()
and get the soap header via getSOAPEnvelope().getHeaderByName(("http://localhost...","TokenHeader")

1.b set back the header (use the code mentioned above)
 SOAPHeaderElement midentityTokenHeader = new SOAPHeaderElement("http://localhost...","TokenHeader");
 tokenHeader.setObjectValue(token);
 call.addHeader(tokenHeader);  


2. for the servlet side you can do (see  this article for more details http://www-128.ibm.com/developerworks/xml/library/x-tipsoap.html)
get soap envelope
MessageContext context = MessageContext.getCurrentContext();
Message message = context.getRequestMessage();
SOAPEnvelope envelope = message.getSOAPEnvelope();
and then read it/set it for each call. (to read the header use getHeaderByName(("http://localhost...","TokenHeader"), to set the header call addHeader(SOAPHeaderElement hdr) )
0
 

Author Comment

by:code_123
ID: 13874033


Yes this is a plain servlet

<<How does your client interact with that servlet?
At the moment all i've created is a simple html page that uses the post method <form action="CheckLogin" method=post>, just to make sure I'm getting the credentials.  I haven't created any client services yet


How do i 'convert' my servlet to be a web service servlet?



What i'm confused about is how i get the client and server-side to talk to each other.  I'm also confused about where wsdd fits in.  I know that wsdl will fit in when i write a service that exposes methods o which the clinet can call, but at the moment all i want to do is make sure i can set the header and read the values


Thank you for your help , i realise i must be annoying !

I started to write a soap hanlder like this


public void invoke(MessageContext msgContext) throws AxisFault
    {
        handleRequest(msgContext);
        super.invoke(msgContext);
    }

           
    public boolean handleResponse(MessageContext msgContext)
    {
        try
        {
            Message message = msgContext.getRequestMessage();
            SOAPEnvelope requestEnvelope = message.getSOAPEnvelope();
            SOAPHeaderElement headerElement = requestEnvelope.getHeaderByName("http://domain","TokenHeader");
           
            if (headerElement != null)
            {
                String headerElementValue = (String)headerElement.getValue();
               
                // make sure the headerElementValue is valid
                validateTokenValue(headerElementValue);              
            }
            else
            {
                // something's gone wrong
                                     
                //SOAPHeaderElement responseHeaderElement = new SOAPHeaderElement("http://domain","TokenHeader");
                //responseHeaderElement.setObjectValue(sTokenValue);                
            }            
        }
        catch(Exception e)
        {
            System.out.println(e);
        }
       
        return true;
    }
   
   
    public boolean handleRequest(MessageContext msgContext)
    {
        try
        {
            //SOAPEnvelope responseEnvelope = msgContext.getResponseMessage().getSOAPEnvelope();
            Message message = msgContext.getResponseMessage();
            SOAPEnvelope responseEnvelope = message.getSOAPEnvelope();          
           
        }
        catch(Exception e)
        {
            System.out.println(e);
        }
       
        return true;
    }
0
 

Author Comment

by:code_123
ID: 13876940

Would it be best to write server-side web services that exposes methods using wsdl.

Then the client web-service can call the methods on the server-side web service, then it can ping-pong the ws as you said above?
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13877176
>> What i'm confused about is how i get the client and server-side to talk to each other.
You need a real client and not a browser (unless you want your communication to sum up with sending http requests and reponse with html pages).

>> Thank you for your help , i realise i must be annoying !
No, you are fine.

>> Would it be best to write server-side web services that exposes methods using wsdl.
That should not matter.
I advice you to read: http://www.javaworld.com/javaworld/jw-01-2002/jw-0125-axis_p.html
and take the code and try it yourself (simple Axis web service client/server).

After you have that running fine and you understand the concept you can modify the server side and the client side
and add your functionaly as well as applying my suggestion above to set/read the SOAP headers with the tokens.
Once you setup your client/server I can help you with any issues you encounter.
0
 

Author Comment

by:code_123
ID: 13883737


Cheers - i'll leave you alone for a bit until i get something working - then i'll be back asking more dumb-a"se  questions !

0
 

Author Comment

by:code_123
ID: 13884120


The class Client1 iswrong, i've tried to rewtie it but fail, can you help ?
0
 

Author Comment

by:code_123
ID: 13884337


Dopesn't matter sorted it

0
 

Author Comment

by:code_123
ID: 13943505


Hello again

Are you able to help me?

I'm trying to get this working http://www.developertutorials.com/tutorials/xml/better-soap-interfaces/page3.html

But for some reason the headerclient isn't creating the header.  It's going to the line 'System.out.println("No priority set for request");'

Thanks very much

0
 
LVL 15

Expert Comment

by:aozarov
ID: 13946169
Are you calling the HeaderService exectly as in the example?
0
 

Author Comment

by:code_123
ID: 13957798


Yes,

I'm using eclipse with the wtp tools

Imported the HeaderClient.java ->right-clicked created a web service

Then iimported the HeaderClient.java

It is here i'm not sure how to implement the HeaderClient file to test it

0
 

Author Comment

by:code_123
ID: 13958411


The only thing i've changed is the URL endpoint in HeaderClient.java

to this URL endpoint = new URL("http://localhost:8080/Test/services/HeaderService");
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13960631
Look at this links: http://www.experts-exchange.com/Programming/Programming_Languages/Java/Q_21414966.html
See if my last reply there helps you.
0
 

Author Comment

by:code_123
ID: 13960941


At last i've got it working

I used TCPMon on port 6822 and change my endpoint to http://localhost:6822/Test/services/HeaderService

I can now see all requests/responses - yiippppppeeee !
0
 

Author Comment

by:code_123
ID: 13961008


I've just looked at your last post.  One question, about the URL endpoint.  If you are calling an external web service, they only expose their wdsl - wouldn't you put the pat of their wsdl in this situation because you wouldn't know the location of their web service?  



0
 
LVL 15

Expert Comment

by:aozarov
ID: 13961011
:-)
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13961037
>> wouldn't you put the pat of their wsdl in this situation
Yes you would, this part of the WSDL is for publishing what I said "the path to your web service" :)
0
 

Author Comment

by:code_123
ID: 13968640

Hello again

Would it be possible to help

I've eventually got samples working, now i'm trying to implement this into my own code.

I have a web service with some methods - when i publish it not all methods will be exposed, but those that are exposed will call the unexposed methods

One unexposed method is addSOAPHeader, which gets called when a user is validated.  

When I call the addSOAPHeader method i need to call the handleRequest/Response method with the MessageContext.  

I'm doing it like this but doesn't work

MessageContext context = MessageContext.getCurrentContext();

handleResponse(context);

Am i missing something in my addSOAPHeader method?

Thanks for your help




public static String addSOAPHeader(String token) throws Exception
{  
  Service service = new Service();
     
  Call call = (Call)service.createCall();
       
  SOAPHeaderElement tokenHeader = new SOAPHeaderElement("","TokenHeader");
       
  tokenHeader.setObjectValue(token);
       
  call.addHeader(tokenHeader);  
       
  return token;
}



I SOAPHandler class

public void invoke(MessageContext msgContext) throws AxisFault
    {
      handleResponse(msgContext);
        super.invoke(msgContext);
    }


public static boolean handleResponse(MessageContext msgContext)
    {
        try
        {
            Message message = msgContext.getResponseMessage();
            SOAPEnvelope responseEnvelope = message.getSOAPEnvelope();
            SOAPHeaderElement headerElement = responseEnvelope.getHeaderByName("","TokenHeader");
           
            if (headerElement != null)
            {
                String headerElementValue = (String)headerElement.getValue();
               
                // make sure the headerElementValue is valid
                validateTokenValue(headerElementValue);
                        
            }
            else
            {
                // something's gone wrong
                               
            }            
        }
        catch(Exception e)
        {
            System.out.println(e);
        }
       
        return true;
    }

    public static boolean handleRequest(MessageContext msgContext)
    {
             try
        {
            Message message = msgContext.getRequestMessage();
            SOAPEnvelope requestEnvelope = message.getSOAPEnvelope();
            SOAPHeaderElement headerElement = requestEnvelope.getHeaderByName("","TokenHeader");
           
            if (headerElement != null)
            {
                String headerElementValue = (String)headerElement.getValue();
               
                // make sure the headerElementValue is valid
                validateTokenValue(headerElementValue);              
            }
            else
            {
                // something's gone wrong
             
            }            
        }
        catch(Exception e)
        {
            System.out.println(e);
        }

        return true;      
    }
0
 

Author Comment

by:code_123
ID: 13970110


I think i'm missing the endpoint.  But if the code is on the webservice (server), the endpoint will be itself !?

0
 
LVL 15

Expert Comment

by:aozarov
ID: 13971287
>> But if the code is on the webservice (server), the endpoint will be itself !?
Right, no need for it there.

>> addSOAPHeader
Still I am not sure why you are using Call in the server side as it should be used in the client side. (you discard the call after adding the header so what is the point).
your addSoapheader should do as I already described before:
MessageContext context = MessageContext.getCurrentContext();
Message message = context.getRequestMessage();
SOAPEnvelope envelope = message.getSOAPEnvelope();
SOAPHeaderElement tokenHeader = new SOAPHeaderElement("","TokenHeader");
envelope.addChild(tokenHeader);
0
 

Author Comment

by:code_123
ID: 13975778
> (you discard the call after adding the header so what is the point).
What do you mean by this?  Sorry for the dumb question


The web service i'm creating will be exposed externally, so when i create the wsdl should i be exposing a method for the 'client' to create a soap header and tell them this in documentation?

So my addSoapHeader should look like this :

public static String addSOAPHeader(String token) throws Exception
{      
MessageContext context = MessageContext.getCurrentContext();
Message message = context.getRequestMessage();
SOAPEnvelope envelope = message.getSOAPEnvelope();
SOAPHeaderElement tokenHeader = new SOAPHeaderElement("","TokenHeader");
envelope.addChild(tokenHeader);

call other methods to get a values to return to the client to put in their header

}


If the client calls this method - how would they set the values?  I have code that generates a string that i would put in the SOAP header


I hava a method that creates the token value and i want to put this value in the SOAP header

    public static String getToken(String uniqueUserId, String applicationId)
    {
        String token = null;
        token = uniqueUserId;
       
        BASE64Encoder encoder = new BASE64Encoder();
        String encodedToken = encoder.encodeBuffer(token.getBytes()) + ":" + applicationId;

        return encodedToken;
    }

How do i do that when the 'client' calls the addsoapheaderr method - I assume in the documetnation for the web service anyone using the service will have to know to call the header 'TokenHeader'

If the client creates the header, how do i keep checking the vlaue in that header - so that i know it is valid?  So for every call the 'client' makes i will need a methd that checks the header value?

Where will me SOAPHandler come into play?

Is there a server-side version of Call ?  Or should i concentrate on moving thie addsoapheader method so the client creates this?

Many thanks for all your help

0
 

Author Comment

by:code_123
ID: 13976204


If the web service methods doesn't reuqire parameters can you use call.invoke(); client side?

All examples i've seen is soemthing like this
String result = (String)call.invoke(new Object[]{param1, param2.....});
0
 

Author Comment

by:code_123
ID: 13978251


Ok, i've made a test client with the code
Now i've got the client creating the header - i've got to test this yet, my eclipse has just crashed on me!

Anyway, the client calls the addsoapheader method which goes off to the soaphandler to get the messagcontext and get the value in the header.and does some checks to make sure it;s valid.  If the value in the header is not valid i need to update the client side header - how do i do this

To read the header i use theb handleRequest with this line
SOAPHeaderElement element = envelope.getHeaderByName("","TokenHeader");

To set the header - this will be done Clientside?  Then the public static void main(String [] args) method

How do i 'ping-pong' between the web service and clinet.  Everytime the clients calls the web service i have to check it's header

I've hardcoded a value to test it at the momet, but i'm going to have to figure out how i get a values from the server-sdide to the client


Many Thanks for your help




Client

public static void main(String [] args)
{
try
{
  URL endpoint = new URL("http://localhost:6822/Test/services/TestService");
  Service  service = new Service();
  Call call = (Call)service.createCall();
  call.setTargetEndpointAddress(endpoint);
  call.setOperationName("addSOAPHeader");
  String ret = (String)(call.invoke(new Object[]{ }));
      
  System.out.println("String ret :" + ret);
}
catch (Exception e)
{
  System.err.println(e.toString());
}
}


Server
public static void addSOAPHeader() throws Exception
{
      SOAPHandler.handleRequest();
}


SOAPHandler class

public static boolean handleRequest()
    {
 try
        {
      MessageContext context = MessageContext.getCurrentContext();
      Message message = context.getRequestMessage();

            SOAPEnvelope envelope = message.getSOAPEnvelope();
            SOAPHeaderElement element = envelope.getHeaderByName("","TokenHeader");

if (element != null)
            {
                String headerElementValue = (String)element.getValue();
               
      System.out.println("headerElementValue" + headerElementValue);
                        
                // make sure the headerElementValue is valid
                validateTokenValue(headerElementValue);              
            }
            else
            {
              //do soemthing
            }

        catch(Exception e)
        {
            System.out.println(e);
        }
}
0
 

Author Comment

by:code_123
ID: 13978316


Sorry missed some bit of the test clinet method
public static void main(String [] args)
      {
            String tokenValue = args[0];
            try
            {
                  URL endpoint = new URL("http://localhost:6822/Test/services/TestService");                  
                  Service  service = new Service();
                  Call call = (Call)service.createCall();
                  call.setTargetEndpointAddress(endpoint);
                  call.setOperationName("addSOAPHeader");
                  SOAPHeaderElement element = new SOAPHeaderElement("", "TokenHeader");
                  element.setObjectValue(tokenValue);
                                    
                  String ret = (String)(call.invoke(new Object[]{ }));
                  
                  System.out.println("String ret :" + ret);
            }
            catch (Exception e)
            {
                  System.err.println(e.toString());
            }
      }
}
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13979398
>> What do you mean by this?  Sorry for the dumb question
Call is a client based class to dispatch web request. There is no point of assigning header to it but then discard it.

>> The web service i'm creating will be exposed externally, so when i create the wsdl should i be exposing a method for the 'client' to create a soap header and tell them this in documentation?
That is ok, if you want the client to call this method before it calls the other web methods as the other methods will validate the client token.
Though this method can return void as that token will be inserted in the header. The client will take that token from the response header and will add it to each one of its calls.

>> How do i do that when the 'client' calls the addsoapheaderr method
Generate the header using that function and add it to the header as shown above (see my previous response)

>> String result = (String)call.invoke(new Object[]{param1, param2.....}); with no params
you can call: call.invoke() or call.invoke(new Object[]{});

>> To set the header - this will be done Clientside? (ping/pong)
In the client call.addHeader(the header you got from the response or one that you keep holding)
In the service (now I realize that you want to take from request and put in response):
MessageContext context = MessageContext.getCurrentContext();
Message request  = context.getRequestMessage();
Message response = context.getResponseMessage();
SAOPHeaderElement receivedHeader = request .getSOAPEnvelope().getHeaderByName("", "TokenHeader");
SOAPEnvelope envelope = response.getSOAPEnvelope();
envelope.addChild(tokenHeader); // add request header to response header
0
 

Author Comment

by:code_123
ID: 13979603


When you say this
>Though this method can return void
Do you mean public viod?

In the handleRequest (SOAPHandler), do i add a bit at the end to call SOAPHandler.handleResponse and in my handleResponse I have this
public handleResponse
{
MessageContext context = MessageContext.getCurrentContext();
Message request  = context.getRequestMessage();
Message response = context.getResponseMessage();
SAOPHeaderElement receivedHeader = request .getSOAPEnvelope().getHeaderByName("", "TokenHeader");
SOAPEnvelope envelope = response.getSOAPEnvelope();
envelope.addChild(tokenHeader); // add request header to response header
}


So when first starting out a client calls the addsoapheader

addsoapheader calls handleresqeust ( server side  )
then handleresquest calls handleresponse

then when the client makes another call to my ws i call handlerequest

Is that right ?




0
 

Author Comment

by:code_123
ID: 13979624


slowly i think i'm understanding  :)

0
 
LVL 15

Expert Comment

by:aozarov
ID: 13980186
>Do you mean public viod?
right public void addHeader(....

>In the handleRequest (SOAPHandler), do i add a bit at
I don't think you need the use of SOAPHandler. That method addHeader
can be exposed as another web service method (in your regualr service).
The client first calls this method (which doesn't check if token header exists but rather set in the header a new token).
Then the client get the header from the response and will add it to each one of the other service methods.
The service will extract that given header (by the client) in each method and check its validity before doing its operation.
If needed the service methods can set that header back (though the client can use what it got in the first place instead).
0
 

Author Comment

by:code_123
ID: 13984321
Ok.


I'm not too sure how to write this


I expose the method addSOAPHeader which the client first calls.  Then (for example) the client calls another method from my web service e.g.  getSomeData.  In the getSomeData method i make a call to getSOAPHeader method which is something like this.

Is this the right way to do it ?


public void getSOAPHeader()
{
      try
      {
            MessageContext context = MessageContext.getCurrentContext();
            Message request  = context.getRequestMessage();
            Message response = context.getResponseMessage();
            SAOPHeaderElement receivedHeader = request.getSOAPEnvelope().getHeaderByName("", "TokenHeader");
            SOAPEnvelope envelope = response.getSOAPEnvelope();
            envelope.addChild(tokenHeader);
      }
      catch ........
}


public void addSOAPHeader() --- should rename to setSOAPHeader
{
      String headerElementValue = null;
      
      try
      {
            MessageContext context = MessageContext.getCurrentContext();
            Message message = context.getRequestMessage();      
            SOAPEnvelope envelope = message.getSOAPEnvelope();
                 SOAPHeaderElement element = envelope.getHeaderByName("","TokenHeader");
            
            if (element != null)
            {
                  headerElementValue = (String)element.getValue();
                  System.out.println("headerElementValue " + headerElementValue);

                  // do some validating
            }
            else
            {
                  System.out.println("element is null ");
            }
      }
      catch (Exception e)
      {
             System.err.println(e.toString());
      }
      
      //System.out.println("In addSOAPHeader method" + headerElementValue);                        
}
0
 

Author Comment

by:code_123
ID: 13984564

Ok, it should all be in one method like this

But i don't know where to put the envelope.addChild(what goes in here?).  Also, when the client calls another method i expose how the header value will get set

Many thanks for your help


public void addSOAPHeader()
try
{
      MessageContext context = MessageContext.getCurrentContext();
      Message requestMessage  = context.getRequestMessage();
      Message responseMessage = context.getResponseMessage();
      SOAPEnvelope envelope = responseMessage.getSOAPEnvelope();
      SOAPHeaderElement receivedHeader = requestMessage.getSOAPEnvelope().getHeaderByName("", "TokenHeader");                                                      
                  
      if (receivedHeader != null)
      {            
                                headerElementValue = (String)receivedHeader.getValue();            
            System.out.println("headerElementValue " + headerElementValue);
      }
0
 

Author Comment

by:code_123
ID: 13984943


If i do this
envelope.addHeader(requestMessage.getSOAPEnvelope().getHeaderByName("", "TokenHeader"));
envelope.addChild(receivedHeader);


I get an error :

org.xml.sax.SAXException: No custom elements allowed at top level until after the <body> tag

but I get this in the output

<?xml version="1.0" encoding="UTF-8"?>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
 <TokenHeader soapenv:mustUnderstand="0" xsi:type="xsd:string">fhfhfhfhfhf</TokenHeader>
 <soapenv:Header>
  <TokenHeader soapenv:mustUnderstand="0" xsi:type="xsd:string">fhfhfhfhfhf</TokenHeader>
 </soapenv:Header>
 <soapenv:Body>
  <getSOAPHeaderResponse soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
 </soapenv:Body>
</soapenv:Envelope>


How do i change my code to stop getting the erro

Many thanks for your help

0
 

Author Comment

by:code_123
ID: 13985088


I've got rid of the envelope.addChild(receivedHeader);

and use this
envelope.addHeader(requestMessage.getSOAPEnvelope().getHeaderByName("", "TokenHeader"));

and i get this output


Am i correct in not using the envelope.addChild ?

Can you explain what this is please


Many thanks for your help






<?xml version="1.0" encoding="UTF-8"?>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
 <soapenv:Header>
  <TokenHeader soapenv:mustUnderstand="0" xsi:type="xsd:string">fhfhfhfhfhf</TokenHeader>
 </soapenv:Header>
 <soapenv:Body>
  <getSOAPHeaderResponse soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
 </soapenv:Body>
</soapenv:Envelope>
0
 

Author Comment

by:code_123
ID: 13987189

This is frustrating :(

once the client creates the header i can receive it it my addsoapheader method and do this
envelope.addHeader(requestMessage.getSOAPEnvelope().getHeaderByName("", "TokenHeader"));

i can see in the tcpmon the soap

But when i call another method say test(), this then calls the addsoapheader method, but it doesn't see the soap message i've created

The header is null - even though it's been set.  Is it losing it somewhere?

Many thanks for your help

request/response

<?xml version="1.0" encoding="UTF-8"?>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
 <soapenv:Header>
  <TokenHeader soapenv:mustUnderstand="0" xsi:type="xsd:string">fhfhfhfhfhf</TokenHeader>
 </soapenv:Header>
 <soapenv:Body>
  <getSOAPHeader soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
 </soapenv:Body>
</soapenv:Envelope>

<?xml version="1.0" encoding="UTF-8"?>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
 <soapenv:Header>
  <TokenHeader soapenv:mustUnderstand="0" xsi:type="xsd:string">fhfhfhfhfhf</TokenHeader>
 </soapenv:Header>
 <soapenv:Body>
  <getSOAPHeaderResponse soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
 </soapenv:Body>
</soapenv:Envelope>

0
 

Author Comment

by:code_123
ID: 13987632


Am i doing this all wrong

I've created a dummy client that first calls the addsoapheader method then call the test method

When the client calls the addsoapheader method i can see the response/resquest soap in tcpmon

So now a header with a value is created

The client then calls the test method whcih calls the addsoapheader method but the request/response soap is empty, just this, whcih suggests the soap from addsoapheader is't being passed to test method

My test method is simply this
public void test()
{
addSOAPHeader();
}


Thanks for your help

<?xml version="1.0" encoding="UTF-8"?>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
 <soapenv:Body>
  <test soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
 </soapenv:Body>
</soapenv:Envelope>
0
 

Author Comment

by:code_123
ID: 13988127


Could you help me write this as i'm struggling

Many thanks for your help
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13992442
> Am i correct in not using the envelope.addChild ?
Yes, in effect that is really adding a child to your Header (as you saw) but Axis prefers to use its API for that.

> The client then calls the test method whcih calls the addsoapheader method but the request/response soap is empty,
Your client should keep the header retreived from the first call to addHeader and keep adding it to the Call for every subsequent
request to the server. The other server method should not call addSoapHeader but rather only validate the header sent by the client.
0
 

Author Comment

by:code_123
ID: 13993979



How does a 'client' keep the header retrieved and add it to every other call it makes to the server?

Are you saying the 'client'  must set a header in every call it makes to the server?

Like this e.g.

try
{
URL endpoint = new URL("http://localhost:6822/TestService/services/TestService");                  
Service  service = new Service();
Call call = (Call)service.createCall();
                  
call.setTargetEndpointAddress(endpoint);
call.setOperationName("addSOAPHeader");
SOAPHeaderElement element = new SOAPHeaderElement("", "TokenHeader");
element.setObjectValue(tokenValue);
call.addHeader(element);
                                    
String ret = (String)(call.invoke(new Object[]{ }));
                  
System.out.println("String ret :" + ret);      
      
Service service1 = new Service();
Call call1 = (Call)service1.createCall();
call1.setTargetEndpointAddress(endpoint);
call1.setOperationName("test");            

SOAPHeaderElement element = new SOAPHeaderElement("", "TokenHeader");
element.setObjectValue(tokenValue);
call1.addHeader(element);
                  
String result = (String)(call1.invoke(new Object[]{ }));
}
......



0
 

Author Comment

by:code_123
ID: 13994500


Please could you help me write the server code for addsoapheader ?

Many thanks for your help
0
 
LVL 15

Expert Comment

by:aozarov
ID: 13996439
>> Are you saying the 'client'  must set a header in every call it makes to the server?
correct, though the first call made by the client (to addHeader) should not provide the header but rather take it from the response.
and then the same header given by the response should be used in each call (so the client doesn't need to create SOAPHeaderElement himself).

>> Please could you help me write the server code for addsoapheader ?
public void addSoapHeader()
{
String token = call here the function that generates the token;
MessageContext context = MessageContext.getCurrentContext();
Message responseMessage = context.getResponseMessage();
SOAPEnvelope envelope = responseMessage.getSOAPEnvelope();
SOAPHeaderElement tokenHeader = new SOAPHeaderElement("", "TokenHeader");
tokenHeader.addTextNode(token);
envelope.addHeader(tokenHeader);
}
0
 

Author Comment

by:code_123
ID: 13997049


Sorry for being stupid

>>correct,
though the first call made by the client (to addHeader) should not provide the header but rather take it from the response and then the same header given by the response should be used in each call (so the client doesn't need to create SOAPHeaderElement himself).


How would a client do this ?

This is where i'm confused


0
 

Author Comment

by:code_123
ID: 13997085


i've got this on my client

try
            {
                  URL endpoint = new URL("http://localhost:6822/TestService/services/TestService");                  
                                    
                  Service  service = new Service();
                  Call call = (Call)service.createCall();
                  call.setTargetEndpointAddress(endpoint);
                  call.setOperationName("getUserNamePassword");             
                  tokenValue = (String)(call.invoke(new Object[]{userName, password}));
                  
                  if (tokenValue != null)
                  {
                        // call addSOAPHeader method
                        Service  service1 = new Service();
                        Call call1 = (Call)service1.createCall();
                        call1.setTargetEndpointAddress(endpoint);
                        call1.setOperationName("getSOAPHeader");                                          
                        SOAPHeaderElement element = new SOAPHeaderElement("", "TokenHeader");
                        element.setObjectValue(tokenValue);
                        call1.addHeader(element);
                        call1.invoke(new Object[]{ });


//call another method
                        Service service2 = new Service();
                        Call call2 = (Call)service2.createCall();                  
                        call2.setTargetEndpointAddress(endpoint);
                        call2.setOperationName("test");      
                        SOAPHeaderElement element = new SOAPHeaderElement("", "TokenHeader");
                        element.setObjectValue(tokenValue);
                        call2.addHeader(element);                  
                        String result = (String)(call2.invoke(new Object[]{ }));
                  }

                  }
                                          
                        



0
 

Author Comment

by:code_123
ID: 13997400


Please can you help me write a test client - that takes the header from the response and then same header given by response should be used in each call

- First it calls the addSoapHeader then it calls the test method


Please can you help me write the test method - what will it need to get the request/response ?


Many many thanks for your help

0
 

Author Comment

by:code_123
ID: 13997467


What do i need to do in each serverside method to get the response/request

Many thanks for your help
0
 
LVL 15

Accepted Solution

by:
aozarov earned 400 total points
ID: 13997667
>> that takes the header from the response and then same header given by response should be used in each call
// This should be the first method the client uses
// call addSOAPHeader method
Service  service1 = new Service();
Call call1 = (Call)service1.createCall();
call1.setTargetEndpointAddress(endpoint);
call1.setOperationName("addSOAPHeader");    
call1.invoke();
Message message = call1.getResponseMessage();
SOAPEnvelope envelope = message.getSOAPEnvelope();
SOAPHeaderElement tokenHeader = envelope.getHeaderByName("","TokenHeader");

then add tokenHeader to each one of your clients call (by calling call.addHeader(tokenHeader))

>> What do i need to do in each serverside method to get the response/request
Each other method should do that (or delegate it to "validate" method):
MessageContext context = MessageContext.getCurrentContext();
Message requestMessage  = context.getRequestMessage();
SOAPHeaderElement receivedHeader = requestMessage.getSOAPEnvelope().getHeaderByName("", "TokenHeader");      
String tokenValue = receivedHeader.getValue();
// use here the tokenValue to check if that token is OK (probably should check it against the same logic that created that token)
0
 

Author Comment

by:code_123
ID: 13997848


Thankyou very much for your help

I will try what you said and hopefully get it working


 

0

Featured Post

Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Introduction This article is the second of three articles that explain why and how the Experts Exchange QA Team does test automation for our web site. This article covers the basic installation and configuration of the test automation tools used by…
Introduction This article is the last of three articles that explain why and how the Experts Exchange QA Team does test automation for our web site. This article covers our test design approach and then goes through a simple test case example, how …
Viewers learn how to read error messages and identify possible mistakes that could cause hours of frustration. Coding is as much about debugging your code as it is about writing it. Define Error Message: Line Numbers: Type of Error: Break Down…
Viewers will learn how to properly install Eclipse with the necessary JDK, and will take a look at an introductory Java program. Download Eclipse installation zip file: Extract files from zip file: Download and install JDK 8: Open Eclipse and …
Suggested Courses
Course of the Month21 days, 5 hours left to enroll

810 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question