• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

FIWARE / trusted-issuers-list / 79

13 May 2026 10:47AM UTC coverage: 87.146% (+2.6%) from 84.584%
79

Pull #26

github

web-flow
Delete IMPLEMENTATION_PLAN.md
Pull Request #26: enable v5 api

147 of 187 branches covered (78.61%)

Branch coverage included in aggregate %.

497 of 548 new or added lines in 16 files covered. (90.69%)

592 of 661 relevant lines covered (89.56%)

0.9 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

91.76
/src/main/java/org/fiware/iam/rest/TrustedIssuerRegistryController.java
1
/*
2
 * Copyright 2023 FIWARE Foundation e.V. and/or its affiliates
3
 * and other contributors as indicated by the @author tags.
4
 *
5
 * Licensed under the Apache License, Version 2.0 (the "License");
6
 * you may not use this file except in compliance with the License.
7
 * You may obtain a copy of the License at
8
 *
9
 * http://www.apache.org/licenses/LICENSE-2.0
10
 *
11
 * Unless required by applicable law or agreed to in writing, software
12
 * distributed under the License is distributed on an "AS IS" BASIS,
13
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
 * See the License for the specific language governing permissions and
15
 * limitations under the License.
16
 */
17
package org.fiware.iam.rest;
18

19
import io.micronaut.core.annotation.Nullable;
20
import io.micronaut.data.model.Page;
21
import io.micronaut.data.model.Pageable;
22
import io.micronaut.data.model.Sort;
23
import io.micronaut.http.HttpRequest;
24
import io.micronaut.http.HttpResponse;
25
import io.micronaut.http.annotation.Controller;
26
import io.micronaut.http.context.ServerRequestContext;
27
import io.micronaut.http.uri.UriBuilder;
28
import java.net.URI;
29
import java.util.List;
30
import java.util.Optional;
31
import lombok.RequiredArgsConstructor;
32
import lombok.extern.slf4j.Slf4j;
33
import org.fiware.iam.TIRMapper;
34
import org.fiware.iam.filter.ForwardedForFilter;
35
import org.fiware.iam.repository.TrustedIssuer;
36
import org.fiware.iam.repository.TrustedIssuerRepository;
37
import org.fiware.iam.tir.api.TirApi;
38
import org.fiware.iam.tir.model.IssuerEntryVO;
39
import org.fiware.iam.tir.model.IssuerVO;
40
import org.fiware.iam.tir.model.IssuersResponseVO;
41
import org.fiware.iam.tir.model.LinksVO;
42

43
/**
44
 * Implementation of the (EBSI-compatible) trusted issuers registry {@see
45
 * https://api-pilot.ebsi.eu/docs/apis/trusted-issuers-registry/v4#/}
46
 */
47
@Slf4j
1✔
48
@Controller("${general.basepath:/}")
49
@RequiredArgsConstructor
50
public class TrustedIssuerRegistryController implements TirApi {
51

52
  private static final int DEFAULT_PAGE_SIZE = 10;
53
  private static final String ROOT_PATH = "/";
54
  private static final String AFTER_PARAM = "page[after]";
55
  private static final String SIZE_PARAM = "page[size]";
56
  private static final String DEFAULT_SORT = "did";
57

58
  private final TIRMapper trustedIssuerMapper;
59
  private final TrustedIssuerRepository trustedIssuerRepository;
60

61
  @Override
62
  public HttpResponse<IssuerVO> getIssuerV4(String did) {
63
    checkDidFormat(did);
1✔
64
    Optional<TrustedIssuer> optionalTrustedIssuer = trustedIssuerRepository.getByDid(did);
1✔
65
    if (optionalTrustedIssuer.isEmpty()) {
1✔
66
      return HttpResponse.notFound();
1✔
67
    }
68
    return HttpResponse.ok(trustedIssuerMapper.map(optionalTrustedIssuer.get()));
1✔
69
  }
70

71
  // checks the basic structure of a did, will not validate them!
72
  private void checkDidFormat(String did) {
73
    String[] didParts = did.split(":");
1✔
74
    if (didParts.length < 3 || !didParts[0].equals("did")) {
1!
75
      throw new IllegalArgumentException("Provided string is not a valid did.");
1✔
76
    }
77
  }
1✔
78

79
  /** Implements anchor-based pagination on top of the offset-mechanism from the repository. */
80
  @Override
81
  public HttpResponse<IssuersResponseVO> getIssuersV4(
82
      @Nullable Integer pageSize, @Nullable Integer page) {
83

84
    pageSize = Optional.ofNullable(pageSize).orElse(DEFAULT_PAGE_SIZE);
1✔
85
    if (pageSize < 1 || pageSize > 100) {
1✔
86
      throw new IllegalArgumentException("The requested page size is not supported.");
1✔
87
    }
88

89
    Sort didSort = Sort.unsorted().order(DEFAULT_SORT);
1✔
90
    Pageable pagination = Pageable.from(page, pageSize, didSort);
1✔
91
    Page<TrustedIssuer> result = trustedIssuerRepository.findAll(pagination);
1✔
92

93
    if (result.isEmpty()) {
1!
NEW
94
      return HttpResponse.ok(
×
NEW
95
          new IssuersResponseVO().items(List.of()).total(0).pageSize(0).self(getHrefUri("")));
×
96
    }
97

98
    List<IssuerEntryVO> issuerEntries =
1✔
99
        result.getContent().stream()
1✔
100
            .map(entry -> new IssuerEntryVO().did(entry.getDid()).href(getHrefUri(entry.getDid())))
1✔
101
            .toList();
1✔
102
    return HttpResponse.ok(
1✔
103
        new IssuersResponseVO()
104
            .items(issuerEntries)
1✔
105
            .total((int) result.getTotalSize())
1✔
106
            .pageSize(result.getNumberOfElements())
1✔
107
            .self(getHrefUri(""))
1✔
108
            .links(getLinks(result)));
1✔
109
  }
110

111
  private URI getHrefUri(String path) {
112

113
    UriBuilder builder = getBaseUriBuilder();
1✔
114
    if (path != null && !path.isEmpty()) {
1!
115
      builder.path(path);
1✔
116
    }
117
    return builder.build();
1✔
118
  }
119

120
  private UriBuilder getBaseUriBuilder() {
121
    Optional<HttpRequest<Object>> httpRequest = ServerRequestContext.currentRequest();
1✔
122
    if (httpRequest.isPresent()) {
1!
123
      HttpRequest<?> request = httpRequest.get();
1✔
124
      URI baseUri =
1✔
125
          (URI) request.getAttribute(ForwardedForFilter.REQ_ATTR).orElse(URI.create(ROOT_PATH));
1✔
126
      return UriBuilder.of(baseUri).replacePath(request.getPath());
1✔
127
    }
NEW
128
    return UriBuilder.of(ROOT_PATH);
×
129
  }
130

131
  private LinksVO getLinks(Page<?> page) {
132
    LinksVO links = new LinksVO();
1✔
133
    URI baseUri = getHrefUri("");
1✔
134
    int pageSize = page.getSize();
1✔
135

136
    if (page.hasPrevious()) {
1✔
137
      links.prev(
1✔
138
          UriBuilder.of(baseUri)
1✔
139
              .queryParam(AFTER_PARAM, page.getPageable().previous().getNumber())
1✔
140
              .queryParam(SIZE_PARAM, page.getSize())
1✔
141
              .build());
1✔
142
    }
143
    if (page.hasNext()) {
1✔
144
      links.next(
1✔
145
          UriBuilder.of(baseUri)
1✔
146
              .queryParam(AFTER_PARAM, page.getPageable().next().getNumber())
1✔
147
              .queryParam(SIZE_PARAM, pageSize)
1✔
148
              .build());
1✔
149
    }
150

151
    links.first(
1✔
152
        UriBuilder.of(baseUri).queryParam(AFTER_PARAM, 0).queryParam(SIZE_PARAM, pageSize).build());
1✔
153
    links.last(
1✔
154
        UriBuilder.of(baseUri)
1✔
155
            .queryParam(AFTER_PARAM, page.getTotalPages() - 1)
1✔
156
            .queryParam(SIZE_PARAM, pageSize)
1✔
157
            .build());
1✔
158
    return links;
1✔
159
  }
160
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc