【问题标题】:How to use GraphQL with Retrofit on Android?如何在 Android 上使用 GraphQL 和 Retrofit?
【发布时间】:2017-04-14 01:04:56
【问题描述】:

我是 GraphQL 的新手,但我已经使用 Retrofit 有一段时间了,它易于使用且速度快。就你如何传递数据而言,GraphQL 与 rest api 有很大不同。真的没有太多关于在 Android 中使用 GraphQL 的教程,我只能找到这个视频 (https://www.youtube.com/watch?v=P0uJHI7GjIc&t=1s) 但里面没有真正的代码。

在我当前的改造调用代码中,我设置了一个端点,如下所示:

final RestAdapter restAdapter = new RestAdapter.Builder()
                .setEndpoint(endPoint)
                .build();
        T service = restAdapter.create(clazz);

然后我像这样调用休息服务:

@GET("/users/{login}")
    Observable<Github> getUser(@Path("login") String login);

现在使用 GraphQL,您只有一个基本 url,没有服务路径。此外,如果您像 userId=1 一样查询,那么您必须作为带有 Body 参数的 Post 发送:

operationName: arbitrary name ,
query: "{users(userid:$userId){username}}, 
variables: "{"userId":1}"

我只是不确定这如何转化为改造

【问题讨论】:

  • 您需要创建一个 JSON 正文,其中包含您的 queryoperationNamevariables,然后安排 Retrofit 将该 JSON POST 到服务器,发送到其指定的 GraphQL URL。我不相信 Retrofit 会比仅使用 OkHttp 和 Gson 为 GraphQL 带来更多好处。
  • 好的,我在这里了解如何为改造创建 JSON 主体:stackoverflow.com/questions/21398598/…。但是 Post 路径应该是什么?即:我的 Graphql 服务器只有一个基本网址。
  • “但是 Post 路径应该是什么”——GraphQL 服务器通常只有一个端点。因此,请使用您已有的基本 URL,特别是如果它以 /graphql 结尾。
  • 我最终只使用了 OkHttp --- 在这种情况下更容易。

标签: android retrofit graphql


【解决方案1】:

在你的清单中添加

<uses-permission android:name="android.permission.INTERNET"/>

你的依赖

// Kotlin Coroutines
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.3.4'

//OkHttp
implementation ("com.squareup.okhttp3:okhttp:3.12.12"){
  force = true //API 19 support
}
implementation 'com.squareup.okhttp3:logging-interceptor:3.12.12'

//retrofit
implementation "com.squareup.retrofit2:retrofit:2.7.1"
implementation "com.squareup.retrofit2:converter-scalars:$2.7.1"

还有 Java 8 兼容性

android {

    ...
    compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }

    kotlinOptions {
        jvmTarget = "1.8"
    }
}

有服务

import retrofit2.Response
import retrofit2.http.Body
import retrofit2.http.Headers
import retrofit2.http.POST

interface GraphQLService {

    @Headers("Content-Type: application/json")
    @POST("/")
    suspend fun postDynamicQuery(@Body body: String): Response<String>
}

你可以创建一个对象

import retrofit2.Retrofit
import retrofit2.converter.scalars.ScalarsConverterFactory

object GraphQLInstance {

    private const val BASE_URL: String = "http://192.155.1.55:2000/"

    val graphQLService: GraphQLService by lazy {
        Retrofit
            .Builder()
            .baseUrl(BASE_URL)
            .addConverterFactory(ScalarsConverterFactory.create())
            .build().create(GraphQLService::class.java)
    }
}

在activity中你可以创建这个方法

private fun post(userId: String){
    val retrofit = GraphQLInstance.graphQLService
    val paramObject = JSONObject()
    paramObject.put("query", "query {users(userid:$userId){username}}")
    GlobalScope.launch {
        try {
            val response = retrofit.postDynamicQuery(paramObject.toString())
            Log.e("response", response.body().toString())
        }catch (e: java.lang.Exception){
            e.printStackTrace()
        }
    }
}

您可以查看the example in GitHubmy post

注意:如果需要突变应该改变这一行

paramObject.put("query", "query {users(userid:$userId){username}}")

paramObject.put("query", "mutation {users(userid:$userId){username}}")

【讨论】:

  • 我总是得到状态码 400 >> 必须提供查询字符串。 ,有什么帮助吗?
  • 你能在你的 Playground graphQL 中检查你的查询吗?也许你能找到错误。
【解决方案2】:

为 GraphQL 构建查询和解析响应并不简单。 如果您在宠物项目中使用它,我建议您开始探索 Apollo。该客户端正在认真开发中,但您已经可以试一试了。

https://github.com/apollographql/apollo-android

到目前为止,我很喜欢与 Apollo 合作,他们的路线图上有很多不错的功能:RxJava 集成、改造、订阅和对 AutoValue 的支持

【讨论】:

  • 如何修复 Apollo 示例应用程序?我得到的只是 HTTP 404 或 GitHuntFeedActivity: Failed to parse http response
  • 为什么这是一个答案,这应该是一个评论
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-11-23
  • 2017-09-29
  • 2016-11-18
  • 2017-09-03
  • 2020-05-31
  • 2016-10-01
相关资源
最近更新 更多