新增learn-kubernetes(https://github.com/yyong-brs/learn-kubernetes)相关文件
This commit is contained in:
@@ -0,0 +1,17 @@
|
||||
FROM maven:3.6.3-jdk-11 AS builder
|
||||
|
||||
WORKDIR /usr/src/iotd
|
||||
COPY pom.xml .
|
||||
RUN mvn -B dependency:go-offline
|
||||
|
||||
COPY . .
|
||||
RUN mvn package
|
||||
|
||||
# app
|
||||
FROM openjdk:11.0.11-jre-slim
|
||||
|
||||
WORKDIR /app
|
||||
COPY --from=builder /usr/src/iotd/target/iotd-service-0.1.0.jar .
|
||||
|
||||
EXPOSE 80
|
||||
ENTRYPOINT ["java", "-jar", "/app/iotd-service-0.1.0.jar"]
|
||||
@@ -0,0 +1,23 @@
|
||||
|
||||
Facade over NASA Astronomy Picture of the Day (APOD)
|
||||
|
||||
ENV for API_KEY
|
||||
```
|
||||
https://api.nasa.gov/planetary/apod?api_key=DEMO_KEY
|
||||
```
|
||||
|
||||
Full returns:
|
||||
|
||||
```
|
||||
{"copyright":"Michel Loic","date":"2019-06-28","explanation":"The night of June 21 was the shortest night for planet Earth's northern latitudes, so at latitude 48.9 degrees north, Paris was no exception. Still, the City of Light had an exceptionally luminous evening. Its skies were flooded with silvery night shining or noctilucent clouds after the solstice sunset. Hovering at the edge of space, the icy condensations on meteoric dust or volcanic ash are still in full sunlight at the extreme altitudes of the mesophere. Seen at high latitudes in summer months, stunning, wide spread displays of northern noctilucent clouds are now being reported.","hdurl":"https://apod.nasa.gov/apod/image/1906/D7X7411-2Loic.jpg","media_type":"image","service_version":"v1","title":"A Solstice Night in Paris","url":"https://apod.nasa.gov/apod/image/1906/D7X7411-2Loic_1024.jpg"}
|
||||
```
|
||||
|
||||
facade returns:
|
||||
|
||||
```
|
||||
{
|
||||
"url":""
|
||||
"caption":""
|
||||
"copyright":""
|
||||
}
|
||||
```
|
||||
@@ -0,0 +1,63 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<groupId>com.sixeyed.diamol</groupId>
|
||||
<artifactId>iotd-service</artifactId>
|
||||
<version>0.1.0</version>
|
||||
|
||||
<parent>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-parent</artifactId>
|
||||
<version>2.3.1.RELEASE</version>
|
||||
</parent>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-web</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-aop</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.ehcache</groupId>
|
||||
<artifactId>ehcache</artifactId>
|
||||
<version>3.8.1</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-test</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.jayway.jsonpath</groupId>
|
||||
<artifactId>json-path</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>io.micrometer</groupId>
|
||||
<artifactId>micrometer-registry-prometheus</artifactId>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<properties>
|
||||
<java.version>1.8</java.version>
|
||||
</properties>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-maven-plugin</artifactId>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
</project>
|
||||
@@ -0,0 +1,20 @@
|
||||
package iotd;
|
||||
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
@SpringBootApplication
|
||||
@RestController
|
||||
public class Application {
|
||||
|
||||
@RequestMapping("/")
|
||||
public String home() {
|
||||
return "Nothing to see here, try /image";
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(Application.class, args);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
package iotd;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
|
||||
public class BeanConfiguration {
|
||||
|
||||
@Bean
|
||||
public CacheService cacheService() {
|
||||
return new MemoryCacheService();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
package iotd;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.EnableAspectJAutoProxy;
|
||||
import io.micrometer.core.aop.TimedAspect;
|
||||
import io.micrometer.core.instrument.MeterRegistry;
|
||||
|
||||
@Configuration
|
||||
@EnableAspectJAutoProxy
|
||||
public class RegistryConfiguration {
|
||||
|
||||
@Bean
|
||||
TimedAspect timedAspect(MeterRegistry registry) {
|
||||
return new TimedAspect(registry);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
package iotd;
|
||||
|
||||
import io.micrometer.core.annotation.Timed;
|
||||
import io.micrometer.core.instrument.MeterRegistry;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
@RestController
|
||||
public class ImageController {
|
||||
|
||||
private static final Logger log = LoggerFactory.getLogger(ImageController.class);
|
||||
|
||||
@Autowired
|
||||
CacheService cacheService;
|
||||
|
||||
@Autowired
|
||||
MeterRegistry registry;
|
||||
|
||||
@Value("${apod.url}")
|
||||
private String apodUrl;
|
||||
|
||||
@Value("${apod.key}")
|
||||
private String apodKey;
|
||||
|
||||
@RequestMapping("/image")
|
||||
@Timed()
|
||||
public Image get() {
|
||||
log.debug("** GET /image called");
|
||||
|
||||
Image img = cacheService.getImage();
|
||||
if (img == null) {
|
||||
RestTemplate restTemplate = new RestTemplate();
|
||||
ApodImage result = restTemplate.getForObject(apodUrl+apodKey, ApodImage.class);
|
||||
|
||||
log.info("Fetched new APOD image from NASA");
|
||||
registry.counter("iotd_api_image_load", "status", "success").increment();
|
||||
|
||||
img = new Image(result.getUrl(), result.getTitle(), result.getCopyright());
|
||||
cacheService.putImage(img);
|
||||
}
|
||||
else {
|
||||
log.debug("Loaded APOD image from cache");
|
||||
registry.counter("iotd_api_image_load", "status", "cached").increment();
|
||||
}
|
||||
return img;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
package iotd;
|
||||
|
||||
public class ApodImage {
|
||||
|
||||
private String url;
|
||||
private String title;
|
||||
private String copyright;
|
||||
|
||||
public String getUrl() {
|
||||
return url;
|
||||
}
|
||||
|
||||
public void setUrl(String url) {
|
||||
this.url = url;
|
||||
}
|
||||
|
||||
public String getTitle() {
|
||||
return title;
|
||||
}
|
||||
|
||||
public void setTitle(String title) {
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
public String getCopyright() {
|
||||
return copyright;
|
||||
}
|
||||
|
||||
public void setCopyright(String copyright) {
|
||||
this.copyright = copyright;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
package iotd;
|
||||
|
||||
public class Image {
|
||||
|
||||
private String url;
|
||||
private String caption;
|
||||
private String copyright;
|
||||
|
||||
public Image() {}
|
||||
|
||||
public Image(String url, String caption, String copyright) {
|
||||
setUrl(url);
|
||||
setCaption(caption);
|
||||
setCopyright(copyright);
|
||||
}
|
||||
|
||||
public String getUrl() {
|
||||
return url;
|
||||
}
|
||||
|
||||
public void setUrl(String url) {
|
||||
// if it's a YouTube link need to format the URL to get the thumbnail:
|
||||
// https://www.youtube.com/embed/ts0Ek3nLHew?rel=0 ->
|
||||
// https://img.youtube.com/vi/ts0Ek3nLHew/0.jpg
|
||||
if (url.startsWith("https://www.youtube.com/embed/")) {
|
||||
url = "https://img.youtube.com/vi/" + url.substring(30, url.length()-6) + "/0.jpg";
|
||||
}
|
||||
this.url = url;
|
||||
}
|
||||
|
||||
public String getCaption() {
|
||||
return caption;
|
||||
}
|
||||
|
||||
public void setCaption(String caption) {
|
||||
this.caption = caption;
|
||||
}
|
||||
|
||||
public String getCopyright() {
|
||||
return copyright;
|
||||
}
|
||||
|
||||
public void setCopyright(String copyright) {
|
||||
this.copyright = copyright;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
package iotd;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
public interface CacheService {
|
||||
Image getImage();
|
||||
void putImage(Image img);
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
package iotd;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import org.ehcache.config.CacheConfiguration;
|
||||
import org.ehcache.config.builders.CacheConfigurationBuilder;
|
||||
import org.ehcache.config.builders.CacheManagerBuilder;
|
||||
import org.ehcache.config.builders.ResourcePoolsBuilder;
|
||||
import org.ehcache.CacheManager;
|
||||
import org.ehcache.Cache;
|
||||
import org.ehcache.expiry.Duration;
|
||||
import org.ehcache.expiry.Expirations;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
@Service("CacheService")
|
||||
public class MemoryCacheService implements CacheService {
|
||||
private static Cache<String, Image> _ImageCache;
|
||||
|
||||
public MemoryCacheService() {
|
||||
CacheManager cacheManager = CacheManagerBuilder.newCacheManagerBuilder().withCache("ImageCache",
|
||||
CacheConfigurationBuilder.newCacheConfigurationBuilder(String.class,Image.class,
|
||||
ResourcePoolsBuilder.heap(100))
|
||||
.withExpiry(Expirations.timeToLiveExpiration(new Duration(2, TimeUnit.HOURS)))
|
||||
.build()).build(true);
|
||||
_ImageCache = cacheManager.getCache("ImageCache", String.class, Image.class);
|
||||
}
|
||||
|
||||
public Image getImage(){
|
||||
return (Image) _ImageCache.get("_Image");
|
||||
}
|
||||
|
||||
public void putImage(Image img){
|
||||
_ImageCache.put("_Image", img);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
server.port=80
|
||||
apod.url=https://api.nasa.gov/planetary/apod?api_key=
|
||||
apod.key=DEMO_KEY
|
||||
management.endpoints.web.exposure.include=health,info,prometheus
|
||||
Reference in New Issue
Block a user