Skip to content
This repository has been archived by the owner on Jan 15, 2021. It is now read-only.

Commit

Permalink
Merge pull request #13 from FAIRDataTeam/release/0.2.0
Browse files Browse the repository at this point in the history
Release 0.2.0
  • Loading branch information
MarekSuchanek authored Jul 13, 2020
2 parents 7c21045 + d3c84b2 commit 0714148
Show file tree
Hide file tree
Showing 60 changed files with 2,414 additions and 146 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
node/
node_modules/
target/
pom.xml.tag
pom.xml.releaseBackup
Expand Down
12 changes: 10 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,14 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

## [Unreleased]
## [0.2.0]

### Added

- Metadata retrieval after receiving ping as async event with possibility to resume
- Info page for each entry with details including retrieved metadata
- States of entries with possible filtering
- Configurable rate limit per IP for receiving pings

## [0.1.1]

Expand All @@ -23,6 +30,7 @@ Initial version for simple list of FAIR Data Points.
- REST API to retrieve entries list (both all and paged) documented using Swagger/OpenAPI
- Simple webpage with table to browse entries including sorting and pagination

[Unreleased]: /../../compare/v0.1.1...develop
[Unreleased]: /../../compare/v0.2.0...develop
[0.1.0]: /../../tree/v0.1.0
[0.1.1]: /../../tree/v0.1.1
[0.2.0]: /../../tree/v0.2.0
5 changes: 5 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
"bootstrap": "^4.5.0",
"copyfiles": "^2.1.0",
"jquery": "^3.5.1",
"node-sass": "4.14.1"
"node-sass": "4.14.1",
"popper.js": "^1.16.1"
}
}
19 changes: 18 additions & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@

<groupId>solutions.fairdata</groupId>
<artifactId>fairdatapoint-index</artifactId>
<version>0.1.1</version>
<version>0.2.0</version>

<inceptionYear>2020</inceptionYear>

Expand All @@ -45,6 +45,7 @@
<license-plugin.version>3.0</license-plugin.version>
<mongobee.version>0.13</mongobee.version>
<node.version>v12.16.3</node.version>
<rdf4j.version>3.2.2</rdf4j.version>
<spotbugs.version>4.0.0</spotbugs.version>
<springdoc.version>1.3.9</springdoc.version>
</properties>
Expand Down Expand Up @@ -76,6 +77,18 @@
<artifactId>mongobee</artifactId>
<version>${mongobee.version}</version>
</dependency>
<!-- rdf4j -->
<dependency>
<groupId>org.eclipse.rdf4j</groupId>
<artifactId>rdf4j-rio-api</artifactId>
<version>${rdf4j.version}</version>
</dependency>
<dependency>
<groupId>org.eclipse.rdf4j</groupId>
<artifactId>rdf4j-rio-turtle</artifactId>
<version>${rdf4j.version}</version>
<scope>runtime</scope>
</dependency>
<!-- springdoc -->
<dependency>
<groupId>org.springdoc</groupId>
Expand Down Expand Up @@ -115,6 +128,10 @@
<directory>${project.basedir}/node_modules/bootstrap/dist/js</directory>
<targetPath>static/js/bootstrap</targetPath>
</resource>
<resource>
<directory>${project.basedir}/node_modules/popper.js/dist</directory>
<targetPath>static/js/popper</targetPath>
</resource>
</resources>
<plugins>
<plugin>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@

@SpringBootApplication
public class FairDataPointIndexApplication {

public static void main(String[] args) {
SpringApplication.run(FairDataPointIndexApplication.class, args);
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
/**
* The MIT License
* Copyright © 2020 https://fairdata.solutions
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
package solutions.fairdata.fdp.index.api.controller;

import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import solutions.fairdata.fdp.index.api.dto.ErrorDTO;
import solutions.fairdata.fdp.index.exceptions.IndexException;

@ControllerAdvice
public class ApiExceptionHandler {

@ExceptionHandler(IndexException.class)
public ResponseEntity<ErrorDTO> handleIndexException(IndexException exception) {
return new ResponseEntity<>(exception.getErrorDTO(), exception.getStatus());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
import org.springframework.data.domain.Pageable;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import solutions.fairdata.fdp.index.api.dto.IndexEntryDTO;
import solutions.fairdata.fdp.index.service.IndexEntryService;
Expand All @@ -45,8 +46,8 @@ public class EntriesController {
private IndexEntryService service;

@GetMapping("")
public Page<IndexEntryDTO> getEntriesPage(Pageable pageable) {
return service.getEntriesPage(pageable).map(service::toDTO);
public Page<IndexEntryDTO> getEntriesPage(Pageable pageable, @RequestParam(defaultValue = "all") String state) {
return service.getEntriesPage(pageable, state).map(service::toDTO);
}

@GetMapping("/all")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,16 +23,26 @@
package solutions.fairdata.fdp.index.api.controller;

import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.media.Content;
import io.swagger.v3.oas.annotations.media.ExampleObject;
import io.swagger.v3.oas.annotations.media.Schema;
import io.swagger.v3.oas.annotations.parameters.RequestBody;
import io.swagger.v3.oas.annotations.responses.ApiResponse;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.bind.annotation.RestController;
import solutions.fairdata.fdp.index.api.dto.PingDTO;
import solutions.fairdata.fdp.index.service.IndexEntryService;
import solutions.fairdata.fdp.index.entity.events.Event;
import solutions.fairdata.fdp.index.service.EventService;

import javax.validation.Valid;
import javax.servlet.http.HttpServletRequest;

@Tag(name = "Ping")
@RestController
Expand All @@ -41,14 +51,37 @@ public class PingController {
private static final Logger logger = LoggerFactory.getLogger(PingController.class);

@Autowired
private IndexEntryService service;
private EventService eventService;

@Operation(hidden = true)
@Operation(
description = "Inform about running FAIR Data Point. It is expected to send pings regularly (at least weekly). There is a rate limit set both per single IP within a period of time and per URL in message.",
requestBody = @RequestBody(
description = "Ping payload with FAIR Data Point info",
required = true,
content = @Content(
mediaType = "application/json",
examples = {
@ExampleObject(value = "{\"clientUrl\": \"https://example.com\"}")
},
schema = @Schema(
type = "object",
title = "Ping",
implementation = PingDTO.class
)
)
),
responses = {
@ApiResponse(responseCode = "204", description = "Ping accepted (no content)"),
@ApiResponse(responseCode = "400", description = "Invalid ping format"),
@ApiResponse(responseCode = "429", description = "Rate limit exceeded")
}
)
@PostMapping
@ResponseStatus(HttpStatus.NO_CONTENT)
public void receivePing(@RequestBody @Valid PingDTO ping) {
logger.info("Received ping from {}", ping);

service.storeEntry(ping.getClientUrl());
public void receivePing(HttpEntity<String> httpEntity, HttpServletRequest request) {
logger.info("Received ping from {}", request.getRemoteAddr());
final Event incomingPingEvent = eventService.acceptIncomingPing(httpEntity, request);
logger.info("Triggering metadata retrieval for {}", incomingPingEvent.getRelatedTo().getClientUrl());
eventService.triggerMetadataRetrieval(incomingPingEvent);
}
}
33 changes: 33 additions & 0 deletions src/main/java/solutions/fairdata/fdp/index/api/dto/ErrorDTO.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
/**
* The MIT License
* Copyright © 2020 https://fairdata.solutions
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
package solutions.fairdata.fdp.index.api.dto;

import lombok.AllArgsConstructor;
import lombok.Data;

@Data
@AllArgsConstructor
public class ErrorDTO {
private int code;
private String message;
}
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@
import org.hibernate.validator.constraints.URL;

import javax.validation.constraints.NotNull;
import java.time.OffsetDateTime;

@Data
@Schema(name = "Entry")
Expand All @@ -37,8 +36,11 @@ public class IndexEntryDTO {
private String clientUrl;

@NotNull
private OffsetDateTime registrationTime;
private String state;

@NotNull
private OffsetDateTime modificationTime;
private String registrationTime;

@NotNull
private String modificationTime;
}
34 changes: 34 additions & 0 deletions src/main/java/solutions/fairdata/fdp/index/config/AsyncConfig.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
/**
* The MIT License
* Copyright © 2020 https://fairdata.solutions
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
package solutions.fairdata.fdp.index.config;

import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Profile;
import org.springframework.scheduling.annotation.EnableAsync;
import solutions.fairdata.fdp.index.Profiles;

@Configuration
@EnableAsync
@Profile(Profiles.NON_TESTING)
public class AsyncConfig {
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
/**
* The MIT License
* Copyright © 2020 https://fairdata.solutions
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
package solutions.fairdata.fdp.index.config;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Scope;
import solutions.fairdata.fdp.index.entity.config.EventsConfig;

import java.time.Duration;

@Configuration
public class CustomConfig {

@Bean
@Scope(ConfigurableBeanFactory.SCOPE_SINGLETON)
public EventsConfig eventsConfig(
@Value("${fdp-index.events.retrieval.rateLimitWait:PT10M}") String cfgRetrievalRateLimitWait,
@Value("${fdp-index.events.retrieval.timeout:PT1M}") String cfgRetrievalTimeout,
@Value("${fdp-index.events.ping.validDuration:P7D}") String cfgPingValidDuration,
@Value("${fdp-index.events.ping.rateLimitDuration:PT6H}") String cfgPingRateLimitDuration,
@Value("${fdp-index.events.ping.rateLimitHits:10}") int cfgPingRateLimitHits
) {
return EventsConfig.builder()
.retrievalRateLimitWait(Duration.parse(cfgRetrievalRateLimitWait))
.retrievalTimeout(Duration.parse(cfgRetrievalTimeout))
.pingValidDuration(Duration.parse(cfgPingValidDuration))
.pingRateLimitDuration(Duration.parse(cfgPingRateLimitDuration))
.pingRateLimitHits(cfgPingRateLimitHits)
.build();
}
}
Loading

0 comments on commit 0714148

Please sign in to comment.