Skip to content

Commit

Permalink
Issue 19 - Added basic rerun functionality (#27)
Browse files Browse the repository at this point in the history
  • Loading branch information
LachlanMcKee authored Sep 24, 2020
1 parent 7da17bd commit 979257a
Show file tree
Hide file tree
Showing 36 changed files with 574 additions and 325 deletions.
3 changes: 3 additions & 0 deletions core-impl/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ dependencies {
implementation "io.ktor:ktor-client-logging:$ktor_version"
implementation "io.ktor:ktor-client-logging-jvm:$ktor_version"

// XML parsing
implementation "com.fasterxml.jackson.dataformat:jackson-dataformat-xml:2.11.2"

implementation 'com.google.dagger:dagger:2.28.3'
kapt 'com.google.dagger:dagger-compiler:2.28.3'

Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package net.lachlanmckee.bitrise.core.data

import com.fasterxml.jackson.dataformat.xml.XmlMapper
import com.fasterxml.jackson.module.kotlin.registerKotlinModule
import com.google.gson.TypeAdapterFactory
import dagger.Binds
import dagger.Module
Expand All @@ -19,6 +21,8 @@ import net.lachlanmckee.bitrise.core.data.datasource.remote.BitriseDataSource
import net.lachlanmckee.bitrise.core.data.datasource.remote.BitriseDataSourceImpl
import net.lachlanmckee.bitrise.core.data.datasource.remote.BitriseService
import net.lachlanmckee.bitrise.core.data.datasource.remote.BitriseServiceImpl
import net.lachlanmckee.bitrise.core.data.mapper.TestSuitesMapper
import net.lachlanmckee.bitrise.core.data.mapper.TestSuitesMapperImpl
import javax.inject.Singleton

@Module(includes = [CoreSerializationModule::class])
Expand Down Expand Up @@ -55,5 +59,16 @@ internal abstract class CoreDataModule {
configDataSource = configDataSource
)
}

@Provides
@Singleton
internal fun provideTestSuitesMapper(): TestSuitesMapper {
return TestSuitesMapperImpl(
xmlMapper = XmlMapper.Builder(XmlMapper())
.defaultUseWrapper(false)
.build()
.registerKotlinModule()
)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,23 @@ package net.lachlanmckee.bitrise.core.data.datasource.remote

import net.lachlanmckee.bitrise.core.data.datasource.local.ConfigDataSource
import net.lachlanmckee.bitrise.core.data.entity.*
import net.lachlanmckee.bitrise.core.data.mapper.TestSuitesMapper
import javax.inject.Inject

internal class BitriseDataSourceImpl @Inject constructor(
private val bitriseService: BitriseService,
private val configDataSource: ConfigDataSource
private val configDataSource: ConfigDataSource,
private val testSuitesMapper: TestSuitesMapper
) : BitriseDataSource {

override suspend fun getBuilds(workflow: String): Result<List<BuildsResponse.BuildData>> {
override suspend fun getBuilds(workflow: String): Result<List<BuildDataResponse>> {
return bitriseService.getBuilds(workflow)
}

override suspend fun getBuildDetails(buildSlug: String): Result<BuildDataResponse> {
return bitriseService.getBuildDetails(buildSlug)
}

override suspend fun getArtifactDetails(buildSlug: String): Result<BitriseArtifactsListResponse> {
return bitriseService.getArtifactDetails(buildSlug)
}
Expand All @@ -21,8 +27,21 @@ internal class BitriseDataSourceImpl @Inject constructor(
return bitriseService.getArtifact(buildSlug, artifactSlug)
}

override suspend fun getArtifactText(url: String): Result<String> {
return bitriseService.getArtifactText(url)
override suspend fun getArtifactText(
artifactDetails: BitriseArtifactsListResponse,
buildSlug: String,
fileName: String
): Result<String> = runCatching {
val artifactDetail = artifactDetails
.data
.firstOrNull { it.title == fileName }
?: throw IllegalStateException("Unable to find artifact with file name: $fileName")

val artifact = getArtifact(buildSlug, artifactDetail.slug)
.getOrThrow()

bitriseService.getArtifactText(artifact.expiringDownloadUrl)
.getOrThrow()
}

override suspend fun triggerWorkflow(triggerData: WorkflowTriggerData): Result<BitriseTriggerResponse> {
Expand All @@ -32,4 +51,13 @@ internal class BitriseDataSourceImpl @Inject constructor(
workflowId = flankWorkflowId
)
}

override suspend fun getTestResults(buildSlug: String): Result<List<TestSuite>> {
return getArtifactDetails(buildSlug)
.map { artifactDetails ->
getArtifactText(artifactDetails, buildSlug, "JUnitReport.xml")
.getOrThrow()
}
.mapCatching { testSuitesMapper.mapTestSuites(it).testsuite }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -19,10 +19,10 @@ internal class BitriseServiceImpl(
return "https://api.bitrise.io/v0.1/apps/${configDataSource.getConfig().bitrise.appId}"
}

override suspend fun getBuilds(workflow: String): Result<List<BuildsResponse.BuildData>> =
override suspend fun getBuilds(workflow: String): Result<List<BuildDataResponse>> =
kotlin.runCatching {
client
.get<BuildsResponse>("${createAppUrl()}/builds?workflow=$workflow&sort_by=created_at") {
.get<MultipleBuildsResponse>("${createAppUrl()}/builds?workflow=$workflow&sort_by=created_at") {
auth()
}
.data
Expand All @@ -37,6 +37,15 @@ internal class BitriseServiceImpl(
}
}

override suspend fun getBuildDetails(buildSlug: String): Result<BuildDataResponse> =
kotlin.runCatching {
client
.get<SingleBuildResponse>("${createAppUrl()}/builds/$buildSlug") {
auth()
}
.data
}

override suspend fun getArtifactDetails(buildSlug: String): Result<BitriseArtifactsListResponse> =
kotlin.runCatching {
client
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package net.lachlanmckee.bitrise.core.data.mapper

import com.fasterxml.jackson.databind.ObjectMapper
import com.fasterxml.jackson.module.kotlin.readValue
import net.lachlanmckee.bitrise.core.data.entity.TestSuites

interface TestSuitesMapper {
fun mapTestSuites(xmlText: String): TestSuites
}

internal class TestSuitesMapperImpl(
private val xmlMapper: ObjectMapper
) : TestSuitesMapper {
override fun mapTestSuites(xmlText: String): TestSuites {
return xmlMapper.readValue(xmlText)
}
}
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
package net.lachlanmckee.bitrise.core.domain.mapper

import net.lachlanmckee.bitrise.core.data.entity.BuildDataResponse
import net.lachlanmckee.bitrise.core.data.entity.BuildsData
import net.lachlanmckee.bitrise.core.data.entity.BuildsResponse
import net.lachlanmckee.bitrise.core.data.entity.MultipleBuildsResponse
import javax.inject.Inject

internal class BuildsMapperImpl @Inject constructor() : BuildsMapper {
override fun mapBuilds(data: List<BuildsResponse.BuildData>): BuildsData {
override fun mapBuilds(data: List<BuildDataResponse>): BuildsData {
return BuildsData(
branches = data
.map { it.branch }
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
package net.lachlanmckee.bitrise.domain.mapper

import net.lachlanmckee.bitrise.core.data.entity.BuildDataResponse
import net.lachlanmckee.bitrise.core.data.entity.BuildsData
import net.lachlanmckee.bitrise.core.data.entity.BuildsResponse
import net.lachlanmckee.bitrise.core.data.entity.EnvironmentValueResponse
import net.lachlanmckee.bitrise.core.domain.mapper.BuildsMapperImpl
import org.junit.jupiter.api.Assertions.assertEquals
import org.junit.jupiter.api.Test
Expand All @@ -22,7 +23,7 @@ class BuildsMapperTest {
fun givenBuildDataExists_whenMap_thenAssertBuildsData() {
testMapBuilds(
listOf(
BuildsResponse.BuildData(
BuildDataResponse(
branch = "dev",
statusText = "status-text-dev-1",
commitHash = "commit-hash-dev-1",
Expand All @@ -32,10 +33,10 @@ class BuildsMapperTest {
triggeredAt = "2020-09-01T16:00:00Z",
finishedAt = "2020-09-01T17:00:00Z",
originalEnvironmentValueList = listOf(
BuildsResponse.EnvironmentValue("ENV1", "VALUE1")
EnvironmentValueResponse("ENV1", "VALUE1")
)
),
BuildsResponse.BuildData(
BuildDataResponse(
branch = "dev",
statusText = "status-text-dev-2",
commitHash = "commit-hash-dev-2",
Expand All @@ -46,7 +47,7 @@ class BuildsMapperTest {
finishedAt = "2020-09-01T17:00:00Z",
originalEnvironmentValueList = emptyList()
),
BuildsResponse.BuildData(
BuildDataResponse(
branch = "dev",
statusText = "status-text-dev-3",
commitHash = "commit-hash-dev-3",
Expand All @@ -57,7 +58,7 @@ class BuildsMapperTest {
finishedAt = "2020-09-01T17:00:00Z",
originalEnvironmentValueList = emptyList()
),
BuildsResponse.BuildData(
BuildDataResponse(
branch = "feature1",
statusText = "status-text-feature-1",
commitHash = "commit-hash-feature-1",
Expand Down Expand Up @@ -123,7 +124,7 @@ class BuildsMapperTest {
)
}

private fun testMapBuilds(data: List<BuildsResponse.BuildData>, expected: BuildsData) {
private fun testMapBuilds(data: List<BuildDataResponse>, expected: BuildsData) {
assertEquals(expected, BuildsMapperImpl().mapBuilds(data))
}
}
3 changes: 3 additions & 0 deletions core/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ dependencies {
implementation "net.lachlanmckee:gsonpath-kt:4.0.0"
kapt "net.lachlanmckee:gsonpath-compiler:4.0.0"

// XML parsing
api "com.fasterxml.jackson.module:jackson-module-kotlin:2.11.2"

implementation 'com.google.dagger:dagger:2.28.3'
kapt 'com.google.dagger:dagger-compiler:2.28.3'
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,21 @@ package net.lachlanmckee.bitrise.core.data.datasource.remote
import net.lachlanmckee.bitrise.core.data.entity.*

interface BitriseDataSource {
suspend fun getBuilds(workflow: String): Result<List<BuildsResponse.BuildData>>
suspend fun getBuilds(workflow: String): Result<List<BuildDataResponse>>

suspend fun getBuildDetails(buildSlug: String): Result<BuildDataResponse>

suspend fun getArtifactDetails(buildSlug: String): Result<BitriseArtifactsListResponse>

suspend fun getArtifact(buildSlug: String, artifactSlug: String): Result<BitriseArtifactResponse>

suspend fun getArtifactText(url: String): Result<String>
suspend fun getArtifactText(
artifactDetails: BitriseArtifactsListResponse,
buildSlug: String,
fileName: String
): Result<String>

suspend fun triggerWorkflow(triggerData: WorkflowTriggerData): Result<BitriseTriggerResponse>

suspend fun getTestResults(buildSlug: String): Result<List<TestSuite>>
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@ import net.lachlanmckee.bitrise.core.data.entity.*
import java.io.File

interface BitriseService {
suspend fun getBuilds(workflow: String): Result<List<BuildsResponse.BuildData>>
suspend fun getBuilds(workflow: String): Result<List<BuildDataResponse>>

suspend fun getBuildDetails(buildSlug: String): Result<BuildDataResponse>

suspend fun getArtifactDetails(buildSlug: String): Result<BitriseArtifactsListResponse>

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package net.lachlanmckee.bitrise.core.data.entity

import com.google.gson.FieldNamingPolicy
import com.google.gson.annotations.SerializedName
import gsonpath.annotation.AutoGsonAdapter

@AutoGsonAdapter(fieldNamingPolicy = [FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES])
data class BuildDataResponse(
val branch: String,
val statusText: String,
val commitHash: String,
val commitMessage: String?,
val buildNumber: Int,
val slug: String,
val triggeredAt: String,
val finishedAt: String?,
@SerializedName("original_build_params.environments")
val originalEnvironmentValueList: List<EnvironmentValueResponse>
)

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
package net.lachlanmckee.bitrise.core.data.entity

import com.google.gson.FieldNamingPolicy
import gsonpath.annotation.AutoGsonAdapter

@AutoGsonAdapter(fieldNamingPolicy = [FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES])
data class EnvironmentValueResponse(
val mappedTo: String,
val value: String
)
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package net.lachlanmckee.bitrise.core.data.entity

import com.google.gson.FieldNamingPolicy
import gsonpath.GsonResultList
import gsonpath.annotation.AutoGsonAdapter

@AutoGsonAdapter(fieldNamingPolicy = [FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES])
data class MultipleBuildsResponse(
val data: GsonResultList<BuildDataResponse>,
val paging: Paging
) {
@AutoGsonAdapter(fieldNamingPolicy = [FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES])
data class Paging(
val totalItemCount: Int,
val pageItemLimit: Int,
val next: String
)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package net.lachlanmckee.bitrise.core.data.entity

import com.google.gson.FieldNamingPolicy
import gsonpath.GsonResultList
import gsonpath.annotation.AutoGsonAdapter

@AutoGsonAdapter(fieldNamingPolicy = [FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES])
data class SingleBuildResponse(val data: BuildDataResponse)
Loading

0 comments on commit 979257a

Please sign in to comment.