REST-Apache CXF-Schema validation - apache

I am using RESTful Webservice using Apache CXF (blended with spring).
I am exposing two services in my WADL.
For every request to my Webservice,I need to validate request to a particular schema.One of my exposed service use a specific schema and other service complies to other specific schema.
Can you help me?

There is a couple of ways to do what you need. One way is using jaxrs:schemaLocations element:
<beans>
<jaxrs:server address="/" serviceClass="com.something.ServiceClass">
<jaxrs:schemaLocations>
<jaxrs:schemaLocation>classpath:/schemas/a.xsd</jaxrs:schemaLocation>
<jaxrs:schemaLocation>classpath:/schemas/b.xsd</jaxrs:schemaLocation>
</jaxrs:schemaLocations>
</jaxrs:server>
</beans>
For more information and examples please see this link.

Related

Add authentication to an existed API using WSO2 AM

I have created an API using WSO2 EI that looks like https://localhost:8243/services/ABC.
Then I want to create another API that gets above API as the endpoint in order to add authentication. So how can I pass value to URL pattern and endpoint to get that?
When URL pattern is /xyz, and the endpoint is https://localhost:8243/services/ABC. It points to https://localhost:8243/services/ABC/xyz that not my endpoint.
Thank you so much!
You can attach a custom sequence to the API.
<sequence xmlns="http://ws.apache.org/ns/synapse" name="header_sequence">
<property name="REST_URL_POSTFIX" scope="axis2" action="remove"/>
</sequence>
This drops the resources and not appending to the path.
Please refer - https://apim.docs.wso2.com/en/latest/deploy-and-publish/deploy-on-gateway/api-gateway/message-mediation/mapping-the-parameters-of-your-backend-urls-with-the-api-publisher-urls/#mapping-the-parameters-of-your-backend-urls-with-the-api-publisher-urls
As per my understanding, you are trying to invoke the backend https://localhost:8243/services/ABC via the API created in APIM. You can try out the following to achieve it,
In the API created in APIM, you can simply add the URL https://localhost:8243/services as the endpoint and then create a resource path as /ABC.

Grails 3 and Spring Security: return 401 when user is not logged in

In my Grails 3.2.9 web-app I'm using Spring Security plugin to manage user session. This is the depencency:
compile "org.grails.plugins:spring-security-core:3.1.1"
The natural (years-long) evolution of the app brought to have basically all actions in all controllers, mostly secured using #Secured annotations, to return a JSON, with something like
return map as JSON // grails.converters.JSON
That means that all actions are basically acting like APIs.
But since they're secured, when user is not logged, a redirect is performed to /login/auth (login page), which is something you wouldn't expect. This is why I'm searching for a way to return 401 unauthorized status instead of letting Spring Security perform a redirect.
So far I've looked into pessimistic lockdown, and searches across the web also lead me to Spring Security Core REST plugin, but both ways don't seem to adapt to my case (to me at last, but maybe I'm missing something).
So any suggestion is welcome, thanks in advance!
Register the following in resources.groovy
authenticationEntryPoint(Http401AuthenticationEntryPoint, 'Bearer')
I do not have experience in Grails but perhaps what you are looking for can be implemented by providing a different implementation of org.springframework.security.web.AuthenticationEntryPoint in your Spring security configuration. By default for form authentication Spring uses org.springframework.security.web.authentication.LoginUrlAuthenticationEntryPoint which performs redirect to the given login page. On the other hand org.springframework.security.web.authentication.HttpStatusEntryPoint just returns the desired status.
In our project entry point is set in the old fashioned way through XML configuration:
<http pattern="/**" auto-config="false" entry-point-ref="yourAuthenticationEntryPoint">

Adding header with username into request to backend in wso2 apimanager for all service

I am using apimanger 1.9.
I read this already : Add header with username into request to backend in wso2 apimanager.
I am able to add and forward username to backend in wso2 apimanager for specific service; but I want this for all service. I am modifying admin--<api_name>_<version>.xml for all services(50 services), which is very much manual. Something it leads to manual error.
Is there a single place configuration where I can set this (forward username to backend endpoint) for all service?
One more question - if I create and publish the APIs using "Publisher API" feature, is there a way to post something to set up the add header for each API?
Modify the velocity_template.xml which decides the template of an API. Please read my answer given to a similar requirement. You need to modify the relevant section in the velocity_template.xml.

One Apigee Api Proxy with a different target endpoint for each environment

I am an Apigee beginner. We are doing a migration to Apigee.
We have our environments in our host names, for example:
something.int.other.thing.co.uk
something.test.other.thing.co.uk
something.stage.other.thing.co.uk
something.prod.other.thing.co.uk
I would like to be able to map them to the 4 environments of the apigee api proxy itself, respectively int, test, stage, prod.
I currently have one Rest resource for them, for example: /resource
Basically I would like the apigee api proxy with one rest resource, to map to 4 different target endpoints, depending on the environment.
So far I have tried to do it from the UI and have not been able to do so.
I have been going through the documentation and I have found these so far:
According to this it should be possible:
"An API proxy can contain zero or more TargetEndpoints." (TargetEndpoint section)
http://apigee.com/docs/api-services/content/api-proxy-configuration-reference
According to these, you can make routerules to the proxy endpoint, but I have not been able to implement it to the targetendpoint:
Create a New Endpoint on an existing API Proxy with "No Target Endpoint"
One API proxy calling two different target endpoints
I also tried doing something along the lines of this, for TargetEndpoint, where I tested for the environment name, but it didn't work:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<TargetEndpoint name="default">
<Description/>
<Flows/>
<PreFlow name="PreFlow">
<Request/>
<Response/>
</PreFlow>
<HTTPTargetConnection>
<URL>something.int.other.thing.co.uk</URL>
</HTTPTargetConnection>
<RouteRule name="int">
<Condition>environment.name == "int"</Condition>
<TargetEndpoint>something.int.other.thing.co.uk</TargetEndpoint>
</RouteRule>
<RouteRule name="test">
<Condition>environment.name == "test"</Condition>
<TargetEndpoint>something.test.other.thing.co.uk/</TargetEndpoint>
</RouteRule>
<RouteRule name="stage">
<Condition>environment.name == "stage"</Condition>
<TargetEndpoint>something.stage.other.thing.co.uk/</TargetEndpoint>
</RouteRule>
<RouteRule name="prod">
<Condition>environment.name == "prod"</Condition>
<TargetEndpoint>something.prod.other.thing.co.uk</TargetEndpoint>
</RouteRule>
<PostFlow name="PostFlow">
<Request/>
<Response/>
</PostFlow>
</TargetEndpoint>
So is this possible?
Apigee supports the concept of Target Servers -which abstracts the backend host from the proxies and also provides load balancing. Same target servers can be configured to point to different host for each environment (this concept is built in to Apigee already).
Take a look, this should help.
Srikanth
LoadBalancer and TargetServer settings go in the TargetEndpoint definition, specifically in the HTTPTargetConnection element.
Check the example here:
http://apigee.com/docs/api-services/content/load-balancing-across-backend-servers
If you do want to curl a TargetEndpoint definition to your API proxy, have a look at the following sample script to see working API calls:
https://github.com/apigee/api-platform-samples/blob/master/tools/proxy_gen.sh
This script shows you how to create an API proxy and update ProxyEndpoint and TargetEndpoints via API calls.

How to detect user agent in WCF web service

How can I detect the user agent in a web service? My web service is implemented using a WCF webservice with basicHTTPBinding. It will be a post from some SOAP clients. I wish to know the user-agent from the clients.
I shall like to see some sample code for this.
I am using a WCF based web service and in the svc.cs, I tried to catch this.Context.Request.UserAgent. But it gives the following error:
this.Context.Request.UserAgent 'MySoapService.MyService' does not contain a definition for 'Context' and no extension method 'Context' accepting a first argument of type 'MySoapService.MyService' could be found (are you missing a using directive or an assembly reference?)
I also tried System.Web.HttpContext.Current.Request.UserAgent and it says:
'System.Web.HttpContext.Current' is null
Edit note:
I tried to activate the ASP.NET compatibility mode. I added <serviceHostingEnvironment aspNetCompatibilityEnabled="true" /> in the config file and added [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Required)] on the top of the class that implements the service interface. Then using System.Web.HttpContext.Current.Request.UserAgent gives me the user agent as desired.
There is another way to get the user agent without enabling ASP.NET compatibility in web.config:
string userAgent = WebOperationContext.Current.IncomingRequest.Headers["User-Agent"];
You can use also:
WebOperationContext.Current.IncomingRequest.UserAgent
You can read user agent from the HttpContext.Current.Request object if you enable ASP.NET compatibility in web.config:
What a totally unhelpful response!
This is not a trivial task. Yes it is obviously possible to get te user-agent string but how does one actually do it? I spent 2 hours checking google and so on but found the answer buried in MSDN documentation. In Visual Studio, from within a WebMethod try
this.Context.Request.UserAgent
That should do it!
User-Agent is a standard HTTP header. It'll be available to your web service just like it's available to anything CGI-like.
Did you even bother searching for this before posting your question? There must be millions of hits for it on Google.