Skip to content

Unable to call getFileStatus, could not find writer for content-type application/json #102

Closed
@Kernald

Description

@Kernald

When using the Files API to call getFileStatus, I'm getting a RESTEASY004655 error:

Exception in thread "main" com.smartling.api.v2.client.exception.RestApiRuntimeException: http_status=500, method=getFileStatus, fileUri=video-feature/src/main/res/values/strings.xml/HEAD
        at com.smartling.api.v2.client.exception.RestApiExceptionHandler.createRestApiException(RestApiExceptionHandler.java:44)
        at com.smartling.api.v2.client.exception.RestApiExceptionHandler.createRestApiException(RestApiExceptionHandler.java:23)
        at com.smartling.api.v2.client.ExceptionDecoratorInvocationHandler.invoke(ExceptionDecoratorInvocationHandler.java:65)
        at com.sun.proxy.$Proxy14.authenticate(Unknown Source)
        at com.smartling.api.v2.client.auth.Authenticator.getAccessTokenInternal(Authenticator.java:121)
        at com.smartling.api.v2.client.auth.Authenticator.refreshOrRequestNewAccessToken(Authenticator.java:100)
        at com.smartling.api.v2.client.auth.Authenticator.getAccessToken(Authenticator.java:76)
        at com.smartling.api.v2.client.auth.BearerAuthSecretFilter.getTokenString(BearerAuthSecretFilter.java:28)
        at com.smartling.api.v2.client.auth.AbstractBearerAuthFilter.filter(AbstractBearerAuthFilter.java:19)
        at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.filterRequest(ClientInvocation.java:687)
        at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.invoke(ClientInvocation.java:489)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invokeSync(ClientInvoker.java:152)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invoke(ClientInvoker.java:115)
        at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientProxy.invoke(ClientProxy.java:76)
        at com.sun.proxy.$Proxy21.getFileStatus(Unknown Source)
        at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.base/java.lang.reflect.Method.invoke(Method.java:566)
        at com.smartling.api.v2.client.ExceptionDecoratorInvocationHandler.invoke(ExceptionDecoratorInvocationHandler.java:50)
        at com.sun.proxy.$Proxy22.getFileStatus(Unknown Source)
        at com.foo.bar.MainKt$downloadStrings$fileStatuses$1$1$1.invokeSuspend(Main.kt:226)
        at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
        at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)
        at kotlinx.coroutines.internal.LimitedDispatcher.run(LimitedDispatcher.kt:42)
        at kotlinx.coroutines.scheduling.TaskImpl.run(Tasks.kt:95)
        at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:570)
        at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.executeTask(CoroutineScheduler.kt:750)
        at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.runWorker(CoroutineScheduler.kt:677)
        at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:664)
        Suppressed: com.smartling.api.v2.client.exception.RestApiRuntimeException: http_status=500, method=getFileStatus, fileUri=prelaunch-screen-feature/src/main/res/values/strings.xml/HEAD
                ... 30 more
        Caused by: javax.ws.rs.ProcessingException: RESTEASY004655: Unable to invoke request: javax.ws.rs.ProcessingException: RESTEASY003215: could not find writer for content-type application/json type: com.smartling.api.v2.authentication.pto.AuthenticationRequest
                at org.jboss.resteasy.client.jaxrs.engines.ManualClosingApacheHttpClient43Engine.invoke(ManualClosingApacheHttpClient43Engine.java:299)
                at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.invoke(ClientInvocation.java:492)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invokeSync(ClientInvoker.java:152)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invoke(ClientInvoker.java:115)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientProxy.invoke(ClientProxy.java:76)
                at com.sun.proxy.$Proxy13.authenticate(Unknown Source)
                at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
                at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
                at java.base/java.lang.reflect.Method.invoke(Method.java:566)
                at com.smartling.api.v2.client.ExceptionDecoratorInvocationHandler.invoke(ExceptionDecoratorInvocationHandler.java:50)
                ... 27 more

These are the dependencies I'm using (trying to follow the versions from the SDK and adding as runtime deps what I hoped would help - it didn't, more on this below):

    implementation("com.smartling.api:smartling-api-sdk:1.9.0")
    implementation("org.jetbrains.kotlinx:kotlinx-cli:0.3.5")
    implementation("org.jetbrains.kotlinx:kotlinx-coroutines-core:1.6.4")
    runtimeOnly("org.jboss.resteasy:resteasy-client:4.6.1.Final")
    runtimeOnly("org.glassfish.jersey.core:jersey-client:2.34")
    runtimeOnly("org.jboss.resteasy:resteasy-jackson2-provider:4.6.1.Final")
    runtimeOnly("org.jboss.resteasy:resteasy-multipart-provider:4.6.1.Final")
    runtimeOnly("com.fasterxml.jackson.core:jackson-databind:2.12.3")
    runtimeOnly("javax.xml.bind:jaxb-api:2.4.0-b180830.0359")
    runtimeOnly("org.jboss.resteasy:resteasy-jaxb-provider:4.6.1.Final")

This is how I create the API client:

  val clientFactory = ClientFactory()
  val clientConfiguration: ClientConfiguration = DefaultClientConfiguration.builder().build()
  val authenticationApi = AuthenticationApiFactory(clientFactory)
      .buildApi(clientConfiguration)
  val authenticator = Authenticator(userIdentifier, userSecret, authenticationApi)
  val bearerAuthSecretFilter = BearerAuthSecretFilter(authenticator)
  return FilesApiFactory(clientFactory).buildApi(bearerAuthSecretFilter, clientConfiguration)

And below, how it's used:

smartlingFilesApi.getFileStatus(
  projectId,
  "$relativePath/$key",
)

Without the additional runtime dependencies, the call to getFileStatus works, but then a call to downloadTranslatedFile fails trying to parse XML (as far as I can tell - it does dump the Android strings XML files as the request body in the exception details as well):

Exception in thread "main" com.smartling.api.v2.client.exception.RestApiRuntimeException: http_status=500, method=downloadTranslatedFile, fileUri=foo-bar/src/main/res/values$
        at com.smartling.api.v2.client.exception.RestApiExceptionHandler.createRestApiException(RestApiExceptionHandler.java:44)
        at com.smartling.api.v2.client.ExceptionDecoratorInvocationHandler.invoke(ExceptionDecoratorInvocationHandler.java:63)
        at com.sun.proxy.$Proxy22.downloadTranslatedFile(Unknown Source)
        at com.foo.bar.MainKt$downloadFiles$3$1$1.invokeSuspend(Main.kt:338)
        at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
        at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)
        at kotlinx.coroutines.internal.LimitedDispatcher.run(LimitedDispatcher.kt:42)
        at kotlinx.coroutines.scheduling.TaskImpl.run(Tasks.kt:95)
        at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:570)
        at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.executeTask(CoroutineScheduler.kt:750)
        at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.runWorker(CoroutineScheduler.kt:677)
        at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:664)

[...]

        Caused by: javax.ws.rs.client.ResponseProcessingException: javax.ws.rs.ProcessingException: Error during response processing:
        type: java.io.InputStream
        genericType: class java.io.InputStream
        annotations: [
                @javax.ws.rs.GET()
                @javax.ws.rs.Path(value="/projects/{projectId}/locales/{localeId}/file")
                @javax.ws.rs.Produces(value={"*/*"})
        ]
        headers: [Cache-Control=no-cache,Connection=keep-alive,Content-Disposition=attachment; filename="foo-bar/src/main/res/values/strings.xml/HEAD";,Content-T$
        media type: application/xml;charset=UTF-8
        body: <?xml version="1.0" encoding="UTF-8"?> [here goes the whole XML file]
                at org.jboss.resteasy.client.jaxrs.internal.ClientInvocation.extractResult(ClientInvocation.java:201)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.extractors.BodyEntityExtractor.extractEntity(BodyEntityExtractor.java:64)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invokeSync(ClientInvoker.java:154)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientInvoker.invoke(ClientInvoker.java:115)
                at org.jboss.resteasy.client.jaxrs.internal.proxy.ClientProxy.invoke(ClientProxy.java:76)
                at com.sun.proxy.$Proxy21.downloadTranslatedFile(Unknown Source)
                at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
                at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
                at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
                at java.base/java.lang.reflect.Method.invoke(Method.java:566)
                at com.smartling.api.v2.client.ExceptionDecoratorInvocationHandler.invoke(ExceptionDecoratorInvocationHandler.java:50)
                ... 10 more

[...]

        Caused by: javax.ws.rs.ProcessingException: RESTEASY003145: Unable to find a MessageBodyReader of content-type application/xml;charset=UTF-8 and type class java.io.InputS$
                at org.jboss.resteasy.core.interception.jaxrs.ClientReaderInterceptorContext.throwReaderNotFound(ClientReaderInterceptorContext.java:47)
                at org.jboss.resteasy.core.interception.jaxrs.AbstractReaderInterceptorContext.getReader(AbstractReaderInterceptorContext.java:133)
                at org.jboss.resteasy.core.interception.jaxrs.AbstractReaderInterceptorContext.proceed(AbstractReaderInterceptorContext.java:75)
                at com.smartling.api.v2.client.unmarshal.RestApiResponseReaderInterceptor.aroundReadFrom(RestApiResponseReaderInterceptor.java:46)
                ... 25 more

This is the PTO passed to downloadTranslatedFile:

DownloadTranslationPTO(
            uri, // fileStatus.fileUri, with fileStatus being the response of getFileStatus above
            RetrievalType.PUBLISHED,
            true,
        )

I'm assuming I'm either missing some runtime dependencies or initialisation to add a JSON and/or XML parser to RESTEasy (I'm not familiar with that at all). Is there a set-up part that's not documented/that I missed?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions