API Portal¶
Traefik Enterprise includes an API Portal which groups all the API specifications from your services into a web UI, if they support the OpenAPI format (formerly known as Swagger).
It works by looking for a JSON file on the service endpoint, which should match the file name defined in the configuration, and making it available on the API Portal web app. It does this for all services that expose an API specification file.
The API specifications also allows your services to be tested directly from within the API Portal.
Traefik Enterprise can also generate multiple API Portals, each exposing a subset of your APIs.
Configuration¶
In order to enable the API Portal feature, a path
property must be defined in the static configuration.
API Portal Options¶
path
¶
Required, Default=""
The path
option must be a string representing the name of the specification file to look for on the service endpoint. For example, if spec.json
is defined as path
, the API Portal will try to get this file under the service URL. Thus, the path <service-url>/spec.json
must point to the specification file.
apiportal:
path: spec.json
[apiportal]
path = "spec.json"
Query parameters are allowed and will be included on the request call to the service, for example /spec/api.yaml?variant=b
is a valid path.
It's also possible to define the API spec path on the dynamic configuration, declared on the service definition attached to your router. Doing so overrides the path specified on the static configuration.
API Portal Service Configuration¶
API portal can be further configured on each service that exposes one or more Open API specifications.
path
¶
Optional, Default=""
Overwrites the Open API specification path set in the static configuration for this service.
labels:
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.path=/path/to/spec.json"
apiVersion: v1
kind: Service
metadata:
name: myapi-svc
annotations:
traefik.ingress.kubernetes.io/service.apiportal.path: /path/to/spec.json
spec:
ports:
- name: web
port: 80
selector:
app: traefiklabs
task: whoami
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.path=/path/to/spec.json"
"labels": {
"traefik.http.services.myapi-svc.loadbalancer.apiportal.path": "/path/to/spec.json"
}
labels:
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.path=/path/to/spec.json"
http:
services:
myapi-svc:
loadbalancer:
apiportal:
path: /path/to/spec.json
[http.services.myapi-svc]
[http.services.myapi-svc.loadbalancer.apiportal]
path = "/path/to/spec.json"
groups
¶
Optional, Default=None
You can define in which API Portal a service should expose its API specification by annotating it with the following label. Traefik Enterprise dynamically creates new API Portals for each group referenced this way.
Path to the endpoint serving the API specification file can be configured for each group. Groups that do not set an explicit path default to the path
of the service if set, or to the one defined in the static configuration otherwise.
labels:
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.firstGroup={}"
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.secondGroup.path=/somewhere/spec.json"
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.thirdGroup.path=/elsewhere/spec.json"
apiVersion: v1
kind: Service
metadata:
name: myapi-svc
annotations:
traefik.ingress.kubernetes.io/service.apiportal.groups.firstGroup: ""
traefik.ingress.kubernetes.io/service.apiportal.groups.secondGroup.path: /somewhere/spec.json
traefik.ingress.kubernetes.io/service.apiportal.groups.thirdGroup.path: /elsewhere/spec.json
spec:
ports:
- name: web
port: 80
selector:
app: traefiklabs
task: whoami
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.firstGroup={}"
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.secondGroup.path=/somewhere/spec.json"
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.thirdGroup.path=/elsewhere/spec.json"
"labels": {
"traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.firstGroup": {},
"traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.secondGroup.path": "/somewhere/spec.json",
"traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.thirdGroup.path": "/elsewhere/spec.json"
}
labels:
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.firstGroup={}"
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.secondGroup.path=/somewhere/spec.json"
- "traefik.http.services.myapi-svc.loadbalancer.apiportal.groups.thirdGroup.path=/elsehwere/spec.json"
http:
services:
myapi-svc:
loadbalancer:
apiportal:
groups:
firstGroup: {}
secondGroup:
path: /somewhere/spec.json
thirdGroup:
path: /elsewhere/spec.json
[http.services.myapi-svc]
[http.services.myapi-svc.loadbalancer.apiportal.groups.firstGroup]
[http.services.myapi-svc.loadbalancer.apiportal.groups.secondGroup]
path = "/somewhere/spec.json"
[http.services.myapi-svc.loadbalancer.apiportal.groups.thirdGroup]
path = "/elsewhere/spec.json"
Default Group
Note that all API specifications are always exposed in the default API Portal, regardless of whether they have an explicit group defined or not.
Routing Traffic to API Portals¶
Where is the API Portal served?
Just like the Dashboard, the API Portals are served by Ingress proxies.
Traefik Enterprise creates internal services for each group of APIs you defined. They are named apiportal-$GROUP_NAME@internal
. An additional default service called apiportal@internal
serves all API specifications, regardless of whether they have an explicit group defined or not.
It's then possible to use all of Traefik's routing capabilities to build the most suitable configuration to expose these API Portal services.
Example¶
This example shows how to enable the API Portal on port 8888
of the domain apiportal.domain.org
.
To do so, create a router through the dynamic configuration that routes all requests coming through the internal
entrypoint to the apiportal@internal
service.
In our case, the entrypoint internal
is listening to the address :8888
.
First, the applied static configuration should contain the following elements:
# [...]
entrypoints:
# [...]
internal:
address: ":8888"
apiportal:
path: spec.json
# [...]
[entryPoints]
# [...]
[entryPoints.internal]
address = ":8888"
[apiportal]
path = "spec.json"
Using the teectl apply
command:
teectl apply --file=static.yaml
teectl apply --file=static.toml
Then, apply the following dynamic configuration:
labels:
- "traefik.http.routers.apiportal.rule=Host(`apiportal.domain.org`)"
- "traefik.http.routers.apiportal.service=apiportal@internal"
- "traefik.http.routers.apiportal.entryPoints=internal"
apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
name: apiportal
spec:
entryPoints:
- internal
routes:
- match: Host(`apiportal.domain.org`)
kind: Rule
services:
- name: apiportal@internal
kind: TraefikService
- "traefik.http.routers.apiportal.rule=Host(`apiportal.domain.org`)"
- "traefik.http.routers.apiportal.service=apiportal@internal"
- "traefik.http.routers.apiportal.entryPoints=internal"
"labels": {
"traefik.http.routers.apiportal.rule": "Host(`apiportal.domain.org`)",
"traefik.http.routers.apiportal.service": "apiportal@internal",
"traefik.http.routers.apiportal.entryPoints": "internal"
}
labels:
- "traefik.http.routers.apiportal.rule=Host(`apiportal.domain.org`)"
- "traefik.http.routers.apiportal.service=apiportal@internal"
- "traefik.http.routers.apiportal.entryPoints=internal"
http:
routers:
apiportal:
rule: Host(`apiportal.domain.org`)
service: apiportal@internal
entryPoints:
- internal
[http.routers.apiportal]
rule = "Host(`apiportal.domain.org`)"
service = "apiportal@internal"
entryPoints = ["internal"]
Using the teectl apply
command:
teectl apply --file=dynamic.yaml
teectl apply --file=dynamic.toml
At this point, the API Portal is ready to expose specifications from any service on your network, and the web app is available at apiportal.domain.org
.
There are some examples of valid JSON files on the OpenAPI specification repository.