Skip to content

Commit

Permalink
Allow programatically uploading files to EtherealGambi
Browse files Browse the repository at this point in the history
  • Loading branch information
MrPowerGamerBR committed Oct 14, 2024
1 parent 7a94e36 commit 9401900
Show file tree
Hide file tree
Showing 7 changed files with 107 additions and 7 deletions.
1 change: 1 addition & 0 deletions backend/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ dependencies {
implementation(libs.ktor.server.caching.headers)
implementation(libs.ktor.server.cors)
implementation(libs.kotlinx.serialization.json)
implementation(libs.kotlinx.serialization.hocon)

implementation(project(":common"))

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,18 +16,16 @@ import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
import mu.KotlinLogging
import net.perfectdreams.etherealgambi.backend.routes.GetFileRoute
import net.perfectdreams.etherealgambi.backend.routes.api.v1.PostUploadFileRoute
import net.perfectdreams.etherealgambi.backend.routes.api.v1.PostVariantsRoute
import net.perfectdreams.etherealgambi.backend.utils.GIFImageInfo
import net.perfectdreams.etherealgambi.backend.utils.ImageInfo
import net.perfectdreams.etherealgambi.backend.utils.PNGImageInfo
import net.perfectdreams.etherealgambi.backend.utils.SimpleImageInfo
import net.perfectdreams.etherealgambi.backend.utils.*
import net.perfectdreams.etherealgambi.data.*
import java.io.File
import java.util.concurrent.ConcurrentHashMap
import kotlin.concurrent.thread
import kotlin.system.exitProcess

class EtherealGambi {
class EtherealGambi(val config: EtherealGambiConfig) {
companion object {
const val OPTIMIZATION_VERSION = 0
private val logger = KotlinLogging.logger {}
Expand All @@ -54,7 +52,8 @@ class EtherealGambi {

private val routes = listOf(
GetFileRoute(this),
PostVariantsRoute(this)
PostVariantsRoute(this),
PostUploadFileRoute(this)
)

var originalImageInfos = ConcurrentHashMap<String, ImageInfo>()
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,17 @@
package net.perfectdreams.etherealgambi.backend

import com.typesafe.config.ConfigFactory
import kotlinx.coroutines.runBlocking
import kotlinx.serialization.hocon.Hocon
import kotlinx.serialization.hocon.decodeFromConfig
import net.perfectdreams.etherealgambi.backend.utils.EtherealGambiConfig
import java.io.File

object EtherealGambiLauncher {
@JvmStatic
fun main(args: Array<String>) {
val m = EtherealGambi()
val config = Hocon.decodeFromConfig<EtherealGambiConfig>(ConfigFactory.parseString(File("ethereal-gambi.conf").readText(Charsets.UTF_8)).resolve())
val m = EtherealGambi(config)

runBlocking {
m.start()
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package net.perfectdreams.etherealgambi.backend.routes.api.v1

import io.ktor.server.application.*
import io.ktor.server.request.*
import io.ktor.server.response.*
import kotlinx.serialization.decodeFromString
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
import net.perfectdreams.etherealgambi.backend.EtherealGambi
import net.perfectdreams.etherealgambi.data.DefaultImageVariantPreset
import net.perfectdreams.etherealgambi.data.ScaleDownToWidthImageVariantPreset
import net.perfectdreams.etherealgambi.data.api.UploadFileRequest
import net.perfectdreams.etherealgambi.data.api.UploadFileResponse
import net.perfectdreams.etherealgambi.data.api.requests.ImageVariantsRequest
import net.perfectdreams.etherealgambi.data.api.responses.ImageVariantsResponse
import net.perfectdreams.sequins.ktor.BaseRoute
import java.io.File
import java.util.*

class PostUploadFileRoute(val m: EtherealGambi) : BaseRoute("/api/v1/upload") {
override suspend fun onRequest(call: ApplicationCall) {
val authorization = call.request.header("Authorization")
if (authorization == null) {
call.respondText(Json.encodeToString(UploadFileResponse.Unauthorized))
return
}

val authorizationToken = m.config.authorizationTokens.firstOrNull { it.token == authorization }
if (authorizationToken == null) {
call.respondText(Json.encodeToString(UploadFileResponse.Unauthorized))
return
}

val request = Json.decodeFromString<UploadFileRequest>(call.receiveText())

val fileData = Base64.getDecoder().decode(request.dataBase64)

val file = File(m.files, request.path)
val folder = file.parentFile
folder.mkdirs()
file.writeBytes(fileData)

call.respondText(Json.encodeToString(UploadFileResponse.Success))
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package net.perfectdreams.etherealgambi.backend.utils

import kotlinx.serialization.Serializable

@Serializable
data class EtherealGambiConfig(
val authorizationTokens: List<AuthorizationToken>
) {
@Serializable
data class AuthorizationToken(
val name: String,
val token: String
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,11 @@ import io.ktor.http.*
import kotlinx.serialization.decodeFromString
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
import net.perfectdreams.etherealgambi.data.api.UploadFileRequest
import net.perfectdreams.etherealgambi.data.api.requests.ImageVariantsRequest
import net.perfectdreams.etherealgambi.data.api.responses.ImageVariantsResponse
import java.io.Closeable
import java.util.*

class EtherealGambiClient(baseUrl: String) : Closeable {
private val http = HttpClient(CIO)
Expand All @@ -30,6 +32,21 @@ class EtherealGambiClient(baseUrl: String) : Closeable {
)
}

suspend fun uploadFile(token: String, path: String, data: ByteArray) {
return Json.decodeFromString(
http.post("$baseUrl/api/v1/upload") {
header(HttpHeaders.Authorization, token)

setBody(
TextContent(
Json.encodeToString(UploadFileRequest(path, Base64.getEncoder().encodeToString(data))),
ContentType.Application.Json
)
)
}.bodyAsText()
)
}

override fun close() {
http.close()
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package net.perfectdreams.etherealgambi.data.api

import kotlinx.serialization.Serializable

@Serializable
data class UploadFileRequest(
val path: String,
val dataBase64: String
)

@Serializable
sealed class UploadFileResponse {
@Serializable
data object Success : UploadFileResponse()

@Serializable
data object Unauthorized : UploadFileResponse()
}

0 comments on commit 9401900

Please sign in to comment.