1+ package com.cjcrafter.openai
2+
3+ import okhttp3.HttpUrl.Companion.toHttpUrl
4+ import okhttp3.MediaType.Companion.toMediaType
5+ import okhttp3.MultipartBody
6+ import okhttp3.OkHttpClient
7+ import okhttp3.Request
8+ import okhttp3.RequestBody
9+ import okhttp3.RequestBody.Companion.toRequestBody
10+ import java.io.IOException
11+
12+ open class RequestHelper (
13+ protected val apiKey : String ,
14+ protected val organization : String? = null ,
15+ protected val client : OkHttpClient = OkHttpClient (),
16+ protected val baseUrl : String = " https://api.openai.com" ,
17+ ) {
18+ protected val mediaType = " application/json; charset=utf-8" .toMediaType()
19+ protected val objectMapper = OpenAI .createObjectMapper()
20+
21+ open fun buildRequest (request : Any , endpoint : String ): Request .Builder {
22+ val json = objectMapper.writeValueAsString(request)
23+ val body: RequestBody = json.toRequestBody(mediaType)
24+ return Request .Builder ()
25+ .url(" $baseUrl /$endpoint " )
26+ .addHeader(" Content-Type" , " application/json" )
27+ .addHeader(" Authorization" , " Bearer $apiKey " )
28+ .apply { if (organization != null ) addHeader(" OpenAI-Organization" , organization) }
29+ .post(body)
30+ }
31+
32+ open fun buildRequestNoBody (endpoint : String , params : Map <String , Any >? = null): Request .Builder {
33+ val url = " $baseUrl /$endpoint " .toHttpUrl().newBuilder()
34+ .apply {
35+ params?.forEach { (key, value) -> addQueryParameter(key, value.toString()) }
36+ }.build().toString()
37+
38+ return Request .Builder ()
39+ .url(url)
40+ .addHeader(" Authorization" , " Bearer $apiKey " )
41+ .apply { if (organization != null ) addHeader(" OpenAI-Organization" , organization) }
42+ }
43+
44+ open fun buildMultipartRequest (
45+ endpoint : String ,
46+ function : MultipartBody .Builder .() -> Unit ,
47+ ): Request {
48+
49+ val multipartBody = MultipartBody .Builder ()
50+ .setType(MultipartBody .FORM )
51+ .apply (function)
52+ .build()
53+
54+ return Request .Builder ()
55+ .url(" $baseUrl /$endpoint " )
56+ .addHeader(" Authorization" , " Bearer $apiKey " )
57+ .apply { if (organization != null ) addHeader(" OpenAI-Organization" , organization) }
58+ .post(multipartBody).build()
59+ }
60+
61+ open fun executeRequest (httpRequest : Request ): String {
62+ val httpResponse = client.newCall(httpRequest).execute()
63+ if (! httpResponse.isSuccessful) {
64+ val json = httpResponse.body?.byteStream()?.bufferedReader()?.readText()
65+ httpResponse.close()
66+ throw IOException (" Unexpected code $httpResponse , received: $json " )
67+ }
68+
69+ val jsonReader = httpResponse.body?.byteStream()?.bufferedReader()
70+ ? : throw IOException (" Response body is null" )
71+ val responseStr = jsonReader.readText()
72+ OpenAI .logger.debug(responseStr)
73+ return responseStr
74+ }
75+
76+ open fun <T > executeRequest (httpRequest : Request , responseType : Class <T >): T {
77+ val str = executeRequest(httpRequest)
78+ return objectMapper.readValue(str, responseType)
79+ }
80+ }
0 commit comments