Skip to content

Commit

Permalink
CID-2732: Address PR comments
Browse files Browse the repository at this point in the history
  • Loading branch information
mohamedlajmileanix committed Jul 4, 2024
1 parent e116e60 commit 30ef674
Show file tree
Hide file tree
Showing 13 changed files with 50 additions and 49 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@ import org.springframework.cloud.openfeign.EnableFeignClients

@SpringBootApplication
@EnableFeignClients(value = ["net.leanix.githubagent.client"])
@EnableConfigurationProperties(value = [net.leanix.githubagent.config.GithubEnterpriseProperties::class])
class GithubAgentApplication
@EnableConfigurationProperties(value = [net.leanix.githubagent.config.GitHubEnterpriseProperties::class])
class GitHubAgentApplication

fun main() {
runApplication<GithubAgentApplication>()
runApplication<GitHubAgentApplication>()
}
Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@
package net.leanix.githubagent.client

import net.leanix.githubagent.dto.GithubAppResponse
import net.leanix.githubagent.dto.GitHubAppResponse
import org.springframework.cloud.openfeign.FeignClient
import org.springframework.web.bind.annotation.GetMapping
import org.springframework.web.bind.annotation.RequestHeader

@FeignClient(name = "githubClient", url = "\${github-enterprise.baseUrl}")
interface GithubClient {
interface GitHubClient {

@GetMapping("/api/v3/app")
fun getApp(
@RequestHeader("Authorization") jwt: String,
@RequestHeader("Accept") accept: String = "application/vnd.github.v3+json"
): GithubAppResponse
): GitHubAppResponse
}
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
package net.leanix.githubagent.config

import jakarta.annotation.PostConstruct
import net.leanix.githubagent.exceptions.GithubEnterpriseConfigurationMissingException
import net.leanix.githubagent.exceptions.GitHubEnterpriseConfigurationMissingException
import org.springframework.stereotype.Component

@Component
class AgentSetupValidation(
private val githubEnterpriseProperties: GithubEnterpriseProperties
private val githubEnterpriseProperties: GitHubEnterpriseProperties
) {

@PostConstruct
Expand All @@ -24,7 +24,7 @@ class AgentSetupValidation(
}

if (missingProperties.isNotEmpty()) {
throw GithubEnterpriseConfigurationMissingException(missingProperties.joinToString(", "))
throw GitHubEnterpriseConfigurationMissingException(missingProperties.joinToString(", "))
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ package net.leanix.githubagent.config
import org.springframework.boot.context.properties.ConfigurationProperties

@ConfigurationProperties(prefix = "github-enterprise")
data class GithubEnterpriseProperties(
data class GitHubEnterpriseProperties(
val baseUrl: String,
val githubAppId: String,
val pemFile: String,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import com.fasterxml.jackson.annotation.JsonIgnoreProperties
import com.fasterxml.jackson.annotation.JsonProperty

@JsonIgnoreProperties(ignoreUnknown = true)
data class GithubAppResponse(
data class GitHubAppResponse(
@JsonProperty("name") val name: String,
@JsonProperty("permissions") val permissions: Map<String, String>,
@JsonProperty("events") val events: List<String>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package net.leanix.githubagent.exceptions

class GithubEnterpriseConfigurationMissingException(properties: String) : RuntimeException(
class GitHubEnterpriseConfigurationMissingException(properties: String) : RuntimeException(
"Github Enterprise properties '$properties' are not set"
)
class GithubAppInsufficientPermissionsException(message: String) : RuntimeException(message)
class GitHubAppInsufficientPermissionsException(message: String) : RuntimeException(message)
class FailedToCreateJWTException(message: String) : RuntimeException(message)
class UnableToConnectToGithubEnterpriseException(message: String) : RuntimeException(message)
class UnableToConnectToGitHubEnterpriseException(message: String) : RuntimeException(message)
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
package net.leanix.githubagent.runners

import net.leanix.githubagent.services.GithubAuthenticationService
import net.leanix.githubagent.services.GitHubAuthenticationService
import org.springframework.boot.ApplicationArguments
import org.springframework.boot.ApplicationRunner
import org.springframework.context.annotation.Profile
import org.springframework.stereotype.Component

@Component
@Profile("!test")
class PostStartupRunner(private val githubAuthenticationService: GithubAuthenticationService) : ApplicationRunner {
class PostStartupRunner(private val githubAuthenticationService: GitHubAuthenticationService) : ApplicationRunner {

override fun run(args: ApplicationArguments?) {
githubAuthenticationService.generateJwtToken()
Expand Down
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
package net.leanix.githubagent.services

import jakarta.annotation.PostConstruct
import net.leanix.githubagent.config.GithubEnterpriseProperties
import net.leanix.githubagent.config.GitHubEnterpriseProperties
import org.springframework.stereotype.Service

@Service
class CachingService(
private val githubEnterpriseProperties: GithubEnterpriseProperties
private val githubEnterpriseProperties: GitHubEnterpriseProperties
) {
private val cache = HashMap<String, String?>()

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ package net.leanix.githubagent.services

import io.jsonwebtoken.Jwts
import io.jsonwebtoken.SignatureAlgorithm
import net.leanix.githubagent.config.GithubEnterpriseProperties
import net.leanix.githubagent.config.GitHubEnterpriseProperties
import net.leanix.githubagent.exceptions.FailedToCreateJWTException
import org.bouncycastle.jce.provider.BouncyCastleProvider
import org.slf4j.LoggerFactory
Expand All @@ -20,9 +20,9 @@ import java.security.spec.PKCS8EncodedKeySpec
import java.util.*

@Service
class GithubAuthenticationService(
class GitHubAuthenticationService(
private val cachingService: CachingService,
private val githubEnterpriseProperties: GithubEnterpriseProperties,
private val githubEnterpriseProperties: GitHubEnterpriseProperties,
private val resourceLoader: ResourceLoader,
private val gitHubEnterpriseService: GitHubEnterpriseService
) {
Expand All @@ -31,7 +31,7 @@ class GithubAuthenticationService(
private const val JWT_EXPIRATION_DURATION = 600000L
private const val pemPrefix = "-----BEGIN RSA PRIVATE KEY-----"
private const val pemSuffix = "-----END RSA PRIVATE KEY-----"
private val logger = LoggerFactory.getLogger(GithubAuthenticationService::class.java)
private val logger = LoggerFactory.getLogger(GitHubAuthenticationService::class.java)
}

fun generateJwtToken() {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
package net.leanix.githubagent.services

import net.leanix.githubagent.client.GithubClient
import net.leanix.githubagent.dto.GithubAppResponse
import net.leanix.githubagent.exceptions.GithubAppInsufficientPermissionsException
import net.leanix.githubagent.exceptions.UnableToConnectToGithubEnterpriseException
import net.leanix.githubagent.client.GitHubClient
import net.leanix.githubagent.dto.GitHubAppResponse
import net.leanix.githubagent.exceptions.GitHubAppInsufficientPermissionsException
import net.leanix.githubagent.exceptions.UnableToConnectToGitHubEnterpriseException
import org.slf4j.LoggerFactory
import org.springframework.stereotype.Service

@Service
class GitHubEnterpriseService(private val githubClient: GithubClient) {
class GitHubEnterpriseService(private val githubClient: GitHubClient) {

companion object {
val expectedPermissions = listOf("administration", "contents", "metadata")
Expand All @@ -22,14 +22,15 @@ class GitHubEnterpriseService(private val githubClient: GithubClient) {
validateGithubAppResponse(githubApp)
logger.info("Authenticated as GitHub App: '${githubApp.name}'")
}.onFailure {
logger.error("Failed to verify JWT token", it)
when (it) {
is GithubAppInsufficientPermissionsException -> throw it
else -> throw UnableToConnectToGithubEnterpriseException("Failed to verify JWT token")
is GitHubAppInsufficientPermissionsException -> throw it
else -> throw UnableToConnectToGitHubEnterpriseException("Failed to verify JWT token")
}
}
}

fun validateGithubAppResponse(response: GithubAppResponse) {
fun validateGithubAppResponse(response: GitHubAppResponse) {
val missingPermissions = expectedPermissions.filterNot { response.permissions.containsKey(it) }
val missingEvents = expectedEvents.filterNot { response.events.contains(it) }

Expand All @@ -44,7 +45,7 @@ class GitHubEnterpriseService(private val githubClient: GithubClient) {
}
message = message.plus("events: $missingEvents")
}
throw GithubAppInsufficientPermissionsException(message)
throw GitHubAppInsufficientPermissionsException(message)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import org.springframework.test.context.ActiveProfiles

@SpringBootTest
@ActiveProfiles("test")
class GithubAgentApplicationTests {
class GitHubAgentApplicationTests {

@Test
fun contextLoads() {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,23 +1,23 @@
import io.mockk.every
import io.mockk.mockk
import net.leanix.githubagent.config.GithubEnterpriseProperties
import net.leanix.githubagent.config.GitHubEnterpriseProperties
import net.leanix.githubagent.services.CachingService
import net.leanix.githubagent.services.GitHubAuthenticationService
import net.leanix.githubagent.services.GitHubEnterpriseService
import net.leanix.githubagent.services.GithubAuthenticationService
import org.junit.jupiter.api.Assertions.assertNotNull
import org.junit.jupiter.api.Assertions.assertThrows
import org.junit.jupiter.api.Test
import org.junit.jupiter.api.assertDoesNotThrow
import org.springframework.core.io.ClassPathResource
import org.springframework.core.io.ResourceLoader

class GithubAuthenticationServiceTest {
class GitHubAuthenticationServiceTest {

private val cachingService = mockk<CachingService>()
private val githubEnterpriseProperties = mockk<GithubEnterpriseProperties>()
private val githubEnterpriseProperties = mockk<GitHubEnterpriseProperties>()
private val resourceLoader = mockk<ResourceLoader>()
private val gitHubEnterpriseService = mockk<GitHubEnterpriseService>()
private val githubAuthenticationService = GithubAuthenticationService(
private val githubAuthenticationService = GitHubAuthenticationService(
cachingService,
githubEnterpriseProperties,
resourceLoader,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,23 +1,23 @@
import io.mockk.every
import io.mockk.mockk
import net.leanix.githubagent.client.GithubClient
import net.leanix.githubagent.dto.GithubAppResponse
import net.leanix.githubagent.exceptions.GithubAppInsufficientPermissionsException
import net.leanix.githubagent.exceptions.UnableToConnectToGithubEnterpriseException
import net.leanix.githubagent.client.GitHubClient
import net.leanix.githubagent.dto.GitHubAppResponse
import net.leanix.githubagent.exceptions.GitHubAppInsufficientPermissionsException
import net.leanix.githubagent.exceptions.UnableToConnectToGitHubEnterpriseException
import net.leanix.githubagent.services.GitHubEnterpriseService
import org.junit.jupiter.api.Assertions.assertThrows
import org.junit.jupiter.api.Test
import org.junit.jupiter.api.assertDoesNotThrow

class GitHubEnterpriseServiceTest {

private val githubClient = mockk<GithubClient>()
private val githubClient = mockk<GitHubClient>()
private val service = GitHubEnterpriseService(githubClient)

@Test
fun `verifyJwt with valid jwt should not throw exception`() {
val jwt = "validJwt"
val githubApp = GithubAppResponse(
val githubApp = GitHubAppResponse(
name = "validApp",
permissions = mapOf("administration" to "read", "contents" to "read", "metadata" to "read"),
events = listOf("label", "public", "repository")
Expand All @@ -32,12 +32,12 @@ class GitHubEnterpriseServiceTest {
val jwt = "invalidJwt"
every { githubClient.getApp(any()) } throws Exception()

assertThrows(UnableToConnectToGithubEnterpriseException::class.java) { service.verifyJwt(jwt) }
assertThrows(UnableToConnectToGitHubEnterpriseException::class.java) { service.verifyJwt(jwt) }
}

@Test
fun `validateGithubAppResponse with correct permissions should not throw exception`() {
val response = GithubAppResponse(
val response = GitHubAppResponse(
name = "validApp",
permissions = mapOf("administration" to "read", "contents" to "read", "metadata" to "read"),
events = listOf("label", "public", "repository")
Expand All @@ -48,27 +48,27 @@ class GitHubEnterpriseServiceTest {

@Test
fun `validateGithubAppResponse with missing permissions should throw exception`() {
val response = GithubAppResponse(
val response = GitHubAppResponse(
name = "validApp",
permissions = mapOf("administration" to "read", "contents" to "read"),
events = listOf("label", "public", "repository")
)

assertThrows(
GithubAppInsufficientPermissionsException::class.java
GitHubAppInsufficientPermissionsException::class.java
) { service.validateGithubAppResponse(response) }
}

@Test
fun `validateGithubAppResponse with missing events should throw exception`() {
val response = GithubAppResponse(
val response = GitHubAppResponse(
name = "validApp",
permissions = mapOf("administration" to "read", "contents" to "read", "metadata" to "read"),
events = listOf("label", "public")
)

assertThrows(
GithubAppInsufficientPermissionsException::class.java
GitHubAppInsufficientPermissionsException::class.java
) { service.validateGithubAppResponse(response) }
}
}

0 comments on commit 30ef674

Please sign in to comment.