Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added more unit tests - connects to #24 #32

Merged
merged 1 commit into from
Nov 15, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 18 additions & 4 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ plugins {
id "net.ltgt.apt-eclipse" version "0.21"
id "com.github.johnrengelman.shadow" version "5.0.0"
id "application"
id 'java'
id 'groovy'
id 'jacoco'
id 'org.sonarqube' version '3.0'
Expand Down Expand Up @@ -57,6 +58,7 @@ dependencies {
testImplementation group: 'org.spockframework', name: 'spock-core', version: '1.3-groovy-2.5'
testImplementation group: 'cglib', name: 'cglib-nodep', version: '3.3.0'
testImplementation group: 'org.objenesis', name: 'objenesis', version: '3.1'
testImplementation group: 'com.github.tomakehurst', name: 'wiremock', version: '2.27.2'
}

test.classpath += configurations.developmentOnly
Expand Down Expand Up @@ -87,10 +89,22 @@ run {
ext.jacoco = [
exclusions: [
'io/github/devatherock/Application.class',
'io/github/devatherock/test/ArtifactoryController.class',
// Excluded for now till tests are written
'io/github/devatherock/artifactory/service/DockerBadgeService.class',
'io/github/devatherock/artifactory/util/BadgeGenerator.class'
'io/github/devatherock/test/ArtifactoryController.class'
],
// Should be removed when all tests have been written
coverageThresholds: [
'io.github.devatherock.artifactory.service.DockerBadgeService': [
'BRANCH': 0.28,
'COMPLEXITY': 0.32,
'INSTRUCTION': 0.70,
'LINE': 0.70
],
'io.github.devatherock.artifactory.util.BadgeGenerator': [
'BRANCH': 0.50,
'COMPLEXITY': 0.50,
'INSTRUCTION': 0.10,
'LINE': 0.14
]
]
]
apply from: '../gradle-includes/checks.gradle'
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import io.micronaut.http.annotation.QueryValue;
import io.micronaut.http.client.annotation.Client;

@Client(value = "https://img.shields.io")
@Client(value = "${artifactory.badge.shields-io.url}")
public interface ShieldsIOClient {

@Get(value = "/static/v1")
Expand Down
6 changes: 5 additions & 1 deletion src/main/resources/application.yml
Original file line number Diff line number Diff line change
Expand Up @@ -29,4 +29,8 @@ micronaut:
mapping: /swagger/**
swagger-ui:
paths: classpath:META-INF/swagger/views/swagger-ui
mapping: /swagger-ui/**
mapping: /swagger-ui/**
artifactory:
badge:
shields-io:
url: https://img.shields.io
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ class AppConfigSpec extends Specification {
@Subject
AppConfig appConfig = new AppConfig()

def 'test initialize http client'() {
void 'test initialize http client'() {
given:
HttpClient httpClient = Mock()
BlockingHttpClient outputClient = Mock()
Expand Down
Original file line number Diff line number Diff line change
@@ -1,76 +1,141 @@
package io.github.devatherock.artifactory.controllers

import io.github.devatherock.artifactory.service.DockerBadgeService
import com.github.tomakehurst.wiremock.WireMockServer
import com.github.tomakehurst.wiremock.client.WireMock
import io.micronaut.http.HttpRequest
import io.micronaut.http.client.HttpClient
import io.micronaut.http.client.annotation.Client
import io.micronaut.http.uri.UriBuilder
import io.micronaut.test.annotation.MockBean
import io.micronaut.test.extensions.spock.annotation.MicronautTest
import spock.lang.Shared
import spock.lang.Specification

import javax.inject.Inject

import static com.github.tomakehurst.wiremock.client.WireMock.equalTo;

/**
* Test class for {@link DockerController}
*/
@MicronautTest(propertySources = 'classpath:application-test.yml')
class DockerControllerSpec extends Specification {

@Inject
DockerBadgeService badgeService
@Shared
WireMockServer mockServer = new WireMockServer(8081)

@Inject
@Client('/')
HttpClient httpClient

void setupSpec() {
WireMock.configureFor(8081)
mockServer.start()
}

void cleanupSpec() {
mockServer.stop()
}

void cleanup() {
mockServer.resetRequests()
}

void 'test get image pull count - default label'() {
given:
String packageName = 'docker/devatherock/simple-slack'

and:
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}")
.willReturn(WireMock.okJson(getFoldersResponse())))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/1.1.0/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('1.1.0', 10))))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/1.1.2/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('1.1.2', 20))))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/latest/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('latest', 30))))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/abcdefgh/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('abcdefgh', 40))))
WireMock.givenThat(WireMock.get(WireMock.urlPathEqualTo('/static/v1'))
.withQueryParam('label', equalTo('docker pulls'))
.withQueryParam('message', equalTo('100'))
.withQueryParam('color', equalTo('blue'))
.willReturn(WireMock.okXml('dummyBadge')))

when:
String badge = httpClient.toBlocking().retrieve(
HttpRequest.GET(UriBuilder.of('/docker/pulls')
.queryParam('package', packageName).build()))

then:
1 * badgeService.getPullsCountBadge(packageName, 'docker pulls') >> 'dummyBadge'
badge == 'dummyBadge'
}

void 'test get image pull count - custom label'() {
given:
String packageName = 'docker/devatherock/simple-slack'

and:
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}")
.willReturn(WireMock.okJson(getFoldersResponse())))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/1.1.0/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('1.1.0', 10))))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/1.1.2/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('1.1.2', 20))))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/latest/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('latest', 30))))
WireMock.givenThat(WireMock.get("/artifactory/api/storage/${packageName}/abcdefgh/manifest.json?stats")
.willReturn(WireMock.okJson(getManifestStats('abcdefgh', 40))))
WireMock.givenThat(WireMock.get(WireMock.urlPathEqualTo('/static/v1'))
.withQueryParam('label', equalTo('downloads'))
.withQueryParam('message', equalTo('100'))
.withQueryParam('color', equalTo('blue'))
.willReturn(WireMock.okXml('dummyBadge')))

when:
String badge = httpClient.toBlocking().retrieve(
HttpRequest.GET(UriBuilder.of('/docker/pulls')
.queryParam('package', packageName)
.queryParam('label', 'downloads').build()))

then:
1 * badgeService.getPullsCountBadge(packageName, 'downloads') >> 'dummyBadge'
badge == 'dummyBadge'
}

void 'test get image size - default label and tag'() {
given:
String packageName = 'docker/devatherock/simple-slack'

and:
WireMock.givenThat(WireMock.get("/artifactory/${packageName}/latest/manifest.json")
.willReturn(WireMock.okJson(getManifest())))
WireMock.givenThat(WireMock.get(WireMock.urlPathEqualTo('/static/v1'))
.withQueryParam('label', equalTo('image size'))
.withQueryParam('message', equalTo('11 MB'))
.withQueryParam('color', equalTo('blue'))
.willReturn(WireMock.okXml('dummyBadge')))

when:
String badge = httpClient.toBlocking().retrieve(
HttpRequest.GET(UriBuilder.of('/docker/image-size')
.queryParam('package', packageName).build()))

then:
1 * badgeService.getImageSizeBadge(packageName, 'latest', 'image size') >> 'dummyBadge'
badge == 'dummyBadge'
}

void 'test get image size - custom label and tag'() {
given:
String packageName = 'docker/devatherock/simple-slack'

and:
WireMock.givenThat(WireMock.get("/artifactory/${packageName}/1.2.0/manifest.json")
.willReturn(WireMock.okJson(getManifest())))
WireMock.givenThat(WireMock.get(WireMock.urlPathEqualTo('/static/v1'))
.withQueryParam('label', equalTo('size'))
.withQueryParam('message', equalTo('11 MB'))
.withQueryParam('color', equalTo('blue'))
.willReturn(WireMock.okXml('dummyBadge')))

when:
String badge = httpClient.toBlocking().retrieve(
HttpRequest.GET(UriBuilder.of('/docker/image-size')
Expand All @@ -79,28 +144,44 @@ class DockerControllerSpec extends Specification {
.queryParam('label', 'size').build()))

then:
1 * badgeService.getImageSizeBadge(packageName, '1.2.0', 'size') >> 'dummyBadge'
badge == 'dummyBadge'
}

void 'test get layers - default label and tag'() {
given:
String packageName = 'docker/devatherock/simple-slack'

and:
WireMock.givenThat(WireMock.get("/artifactory/${packageName}/latest/manifest.json")
.willReturn(WireMock.okJson(getManifest())))
WireMock.givenThat(WireMock.get(WireMock.urlPathEqualTo('/static/v1'))
.withQueryParam('label', equalTo('layers'))
.withQueryParam('message', equalTo('2'))
.withQueryParam('color', equalTo('blue'))
.willReturn(WireMock.okXml('dummyBadge')))

when:
String badge = httpClient.toBlocking().retrieve(
HttpRequest.GET(UriBuilder.of('/docker/layers')
.queryParam('package', packageName).build()))

then:
1 * badgeService.getImageLayersBadge(packageName, 'latest', 'layers') >> 'dummyBadge'
badge == 'dummyBadge'
}

void 'test get layers - custom label and tag'() {
given:
String packageName = 'docker/devatherock/simple-slack'

and:
WireMock.givenThat(WireMock.get("/artifactory/${packageName}/1.2.0/manifest.json")
.willReturn(WireMock.okJson(getManifest())))
WireMock.givenThat(WireMock.get(WireMock.urlPathEqualTo('/static/v1'))
.withQueryParam('label', equalTo('number of layers'))
.withQueryParam('message', equalTo('2'))
.withQueryParam('color', equalTo('blue'))
.willReturn(WireMock.okXml('dummyBadge')))

when:
String badge = httpClient.toBlocking().retrieve(
HttpRequest.GET(UriBuilder.of('/docker/layers')
Expand All @@ -109,12 +190,72 @@ class DockerControllerSpec extends Specification {
.queryParam('label', 'number of layers').build()))

then:
1 * badgeService.getImageLayersBadge(packageName, '1.2.0', 'number of layers') >> 'dummyBadge'
badge == 'dummyBadge'
}

@MockBean(DockerBadgeService)
DockerBadgeService badgeService() {
Mock(DockerBadgeService)
String getFoldersResponse() {
"""{
"repo": "docker",
"path": "/devatherock/simple-slack",
"created": "2018-09-23T18:02:56.147Z",
"createdBy": "devatherock",
"lastModified": "2018-09-23T18:02:56.147Z",
"modifiedBy": "devatherock",
"lastUpdated": "2018-09-23T18:02:56.147Z",
"children": [
{
"uri": "/1.1.0",
"folder": true
},
{
"uri": "/1.1.2",
"folder": true
},
{
"uri": "/latest",
"folder": true
},
{
"uri": "/abcdefgh",
"folder": true
}
],
"uri": "http://localhost:8081/artifactory/api/storage/docker/devatherock/simple-slack"
}"""
}

String getManifestStats(String tag, int downloadCount) {
"""{
"uri": "http://localhost:8081/artifactory/docker/devatherock/simple-slack/${tag}/manifest.json",
"downloadCount": ${downloadCount},
"lastDownloaded": 1602863958001,
"lastDownloadedBy": "devatherock",
"remoteDownloadCount": 0,
"remoteLastDownloaded": 0
}"""
}

String getManifest() {
"""{
"schemaVersion": 2,
"mediaType": "application/vnd.docker.distribution.manifest.v2+json",
"config": {
"mediaType": "application/vnd.docker.container.image.v1+json",
"size": 3027,
"digest": "sha256:9fe1c24da9391a4d7346200a997c06c7c900466181081af7953a2a15c9fffd7c"
},
"layers": [
{
"mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip",
"size": 10485760,
"digest": "sha256:e7c96db7181be991f19a9fb6975cdbbd73c65f4a2681348e63a141a2192a5f10"
},
{
"mediaType": "application/vnd.docker.image.rootfs.diff.tar.gzip",
"size": 1048576,
"digest": "sha256:f910a506b6cb1dbec766725d70356f695ae2bf2bea6224dbe8c7c6ad4f3664a2"
}
]
}"""
}
}
5 changes: 4 additions & 1 deletion src/test/resources/application-test.yml
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
artifactory:
url: http://localhost:8081
api-key: dummyKey
api-key: dummyKey
badge:
shields-io:
url: http://localhost:8081