I want make Swagger specification for my API. But customers use my API can create and delete some entity on server. Each entity have only one type and can include other entity.
Example of API:
http:/localhost/api/<entity_lv_1>
http:/localhost/api/<entity_lv_1>/<entity_lv_2>
http:/localhost/api/<entity_lv_1>/<entity_lv_2>/<entity_lv_3>
And my rest controller have mapping /** for catch all of them.
I try make mapping with regexp:
#GetMapping(value = /{entityLv1}/{entityLv2:[a-z0-9_-]+/*})
But it not work fine, because server can't processed request with entity_lv_3 correctly.
Related
I want to sort my Schemas generated for my Entity classes, DTO classes in Springdoc UI.
I am able to sort the tags and operations using the below configuration in yml file but my schemas are not in the sorted order.
springdoc:
swagger-ui:
disable-swagger-default-url: true
tags-sorter: alpha
operations-sorter: alpha
doc-expansion: none
How could I sort my schemas.
Thanks.
You can have full control of the schemas order using OpenApiCustomiser.
This is a sample code that you can customize using Comparators, depending on the sorting logic you want:
#Bean
public OpenApiCustomiser sortSchemasAlphabetically() {
return openApi -> {
Map<String, Schema> schemas = openApi.getComponents().getSchemas();
openApi.getComponents().setSchemas(new TreeMap<>(schemas));
};
}
If you are interested on the sorting on the swagger-ui, not on the server side, then you can log a feature request on the swagger-ui project.
Scenario A: Suppose you have several databases on the same SQL Server/SQL Azure instance sharing the exact same structure, where the database names are convention based, like db001, db002, ... and a single RESTier service must be able to address the correct database for each REST call, depending on some characteristic to be provided on the request header or on the URI path or query string.
Scenario B: A single RESTier service must be able to address more than one connection string, defined on the web.config file, depending on some characteristic to be provided on the request.
In both scenarios the base issue is the same, a single RESTier service to be able to address requests for more than one database, where the client must submit on each request a hint to the database to be used, a typical multitenant scenario. I'm using RESTier version 0.6 and the entity sets are automatically exposed from a Entity Framework model:
public class Entities : EntityFrameworkApi<SalesEntities> {
Question is, how would you advise to implement this kind of multi-tenant scenarios?
You could use a parameterized routePrefix like below and parse that part of the URL (HttpContext.Current.Request.RawUrl).
config.MapRestierRoute<Entities>("EntitiesApi", "api/{entitiesConfig}", new RestierBatchHandler(server));
Retrieve the correct connectionString from your Web.config and use that to create the DbContext:
Match match = Regex.Match(HttpContext.Current.Request.RawUrl, #"/api/(?<entitiesConfig>[A-Za-z0-9\-]+)/", RegexOptions.IgnoreCase);
string entitiesConfig = "DefaultEntitiesContext";
if (match.Success)
entitiesConfig = match.Groups["entitiesConfig"];
string connectionString = System.Configuration.ConfigurationManager.ConnectionStrings[entitiesConfig].ConnectionString;
var db = new SalesEntities(connectionString);
For your scenario, I think you will have two DbContext, each one connect to one DB instance, then will something like this will work for you?
In the configure method, we call MapRestierRoute twice, and each one will handle one DbContext with different route prefix, and when user initiate the request, the request URL will contain prefix and will auto route to related DB instance.
config.MapRestierRoute>( "TrippinApi", "api/TrippinA", new RestierBatchHandler(server));
config.MapRestierRoute>( "TrippinApi", "api/TrippinB", new RestierBatchHandler(server));
Let me if you have any issues with this.
I'm using OData with Entity Framework to select some records from a database. The records each have a path to a file with text content. In a single service call I'd like to be able to filter the DB records as well as filter the resulting objects based on the content of the files that the records point to. Because I can't mix LINQ to EF with LINQ to Objects, I believe the easiest way to accomplish this is to add an additional query parameter to the standard OData parameters that defines how to filter for file content after the standard odata filters have been applied.
Is looks like the entity query's "withParameters" method is the way to add a non-standard parameter but it doesn't seem to work with version 1.4.9 of breeze.
Am I doing something wrong or is there any intention to make this method work for the OData service provider?
As a workaround to this shortcoming, I've found that you can declare your entity to query with the parameters as part of the entity name, like so:
var entityId = 4;
var answerId = 6;
var entityToQuery = "MyEntity(EntityId=" + entityId + ",answerId=" + answerId + ")";
Then, build your breeze query:
var query = breeze.EntityQuery.from(entityToQuery);
This would map to an OData endpoint such as:
public IQueryable<MyEntity> GetMyEntity([FromODataUri] int entityId, [FromODataUri] int answerId)
{
}
No, you need to use the WebApi adapter. This is not a breeze shortcoming, it's a OData shortcoming because OData doesn't support this syntax.
However, the WebApi adapter does do everything you want and this is the Breeze default. Please see the docs for more information.
I am writing a Web API that clients can make requests to to return data in XML format. I am implementing this in .NET using Enterprise Foundation and MVC4.
I am struggling a bit with how to only return a subset of some fields from my Models in my Controllers.
For arguments sake, lets say I have a Product model that contains attributes "Id", "Name", "Price" and "Actual Cost" (I am using an example from http://www.asp.net/web-api/overview/creating-web-apis/using-web-api-with-entity-framework/using-web-api-with-entity-framework,-part-6)
I need to expose a Web API for clients to query a specific Product to get its name and price, but in this response I don't want to return the "Actual Cost" property (because this is our secret).
Now in the link I provide this is exactly the problem they are attempting to solve by the use of DTO's (they define a DTO called ProductDTO that contains only the subsets I want to return). I have implemented this solution and I am indeed now able to return only the fields I specify in the DTO.
The problem is that the naming used for the returned entity in XML is now ProductDTO rather than Product, i.e. the returned XML is
{"ProductDTO":[{"Id":1,"Name":"Tomato Soup","Price":1.39}, {"Id":3,"Name":"Yo yo","Price":6.99]}
rather than
{"Product":[{"Id":1,"Name":"Tomato Soup","Price":1.39}, {"Id":3,"Name":"Yo yo","Price":6.99]}
That means that all of our clients currently using our API and expects a "Product" to be returned will now get a "ProductDTO" returned, which means that they will have to make changes to their code and which is unacceptable. I need to provide them with a "Product" with only the relevant set of sub-fields as they are currently getting. How do I achieve this? I cannot simply "ignore" a data member as suggested in prevent property from being serialized in web api because I also have some API cases where I indeed DO need to return ALL the attributes and not only a subset.
Just some background: We have an existing API server interface that was written in Ruby on Rails and we are now moving this over to C# and .NET MVC4. We also have a bunch of client applications already interfacing to our existing, older, Ruby on Rails API Server and we don't want clients to make any changes to their code. We are simply moving our API server code over from Ruby on Rails to C#. In Ruby on Rails I was simply able to apply a filter to the XML Serializer when I need to only return a subset of attributes on certain calls.
If you want to continue down the DTO route that you have started, which IMHO is a good idea as it gives you control of what you export without polluting your internal classes with export specific stuff, you can add a DataContract attribute to your ProductDTO class.
[DataContract(Name="Product")]
public class ProductDTO
{
[DataMember]
public int Id {get;set;}
[DataMember]
public string Name {get;set;}
}
The default XML formatter used in Web API is the DataContractSerializer.
You can read more about this here
Suppose you have a class like
public class product
{
public string Name{get; set;}
..
}
and you don't want to appear it in the response you can just use [XMLIgnore] attribute
[XMLIgnore]
public string Name{get; set;}
hopes this helps.
I have created a POX client (generated from jaxb2 from XSD) using spring-ws, but am confused as to how to create a SOAP client (generated from a WSDL). I am using wsimport to generate stubs, but it seems like this goes 1 step too far for use with spring-ws. The stub actually handles the transport, where as with the POX client, spring handles the transport. So, my question is: is it possible to generate just the transport objects through wsimport, or jaxb2 (like the POX client), or what do I call/send in the WebServiceTemplate?
Yes, you can.
Make sure your XSD is imported from and not embedded in your wsdl.
Point xjc (from Jaxb2) at your xsd and let it generate your classes.
Now check your schema.
If your request and response element have embedded complex types use this:
RequestElement requestElement = new RequestElement();
ResponseElement responseElement = (ResponseElement) webServiceTemplate.marshalSendAndReceive(requestElement);
otherwise (referenced complex types) use this:
RequestType requestType = new RequestType();
JAXBElement<RequestType> request = new ObjectFactory().createRequestType(requestType);
ResponseType responseType = ((JAXBElement<ResponseType>) webServiceTemplate.marshalSendAndReceive(request)).getValue();
RequestElement, ResponseElement, RequestType and ResponseType are of course just examples. Substitute them with whatever classes Xjc generated from your schema.