apina icon indicating copy to clipboard operation
apina copied to clipboard

Support plain-text responses

Open jvmlet opened this issue 5 years ago • 1 comments

Hello We have Spring MVC RestEndpoint that returns ResponseEntity<String> :

 @PutMapping(value = "/path", produces = MediaType.TEXT_PLAIN_VALUE)
    public ResponseEntity<String> method(){
        return ResponseEntity.ok()
       .contentType(MediaType.TEXT_PLAIN)
       .body("Some String Value"));
    }

When invoking the http request , the reponseType option is not passed:


//from generated endpoint.ts 
request(data: RequestData): Observable<any> {
....
        return this.httpClient.request(data.method, url, { params: params, body: data.requestBody })
            .pipe(map(r => data.responseType ? this.config.deserialize(r, data.responseType) : r));
    }

and defaults to json

//  http.d.ts
request(method: string, url: string, options?: {
        body?: any;
        headers?: HttpHeaders | {
            [header: string]: string | string[];
        };
        observe?: 'body';
        params?: HttpParams | {
            [param: string]: string | string[];
        };
        responseType?: 'json';
        reportProgress?: boolean;
        withCredentials?: boolean;
    }): Observable<Object>;

which yields JSON parsing error :

//from  http.js
if (req.responseType === 'json' && typeof body === 'string') {
                    // Save the original body, before attempting XSSI prefix stripping.
                    var originalBody = body;
                    body = body.replace(XSSI_PREFIX, '');
                    try {
                        // Attempt the parse. If it fails, a parse error should be delivered to the user.
                        body = body !== '' ? JSON.parse(body) : null;
                    }
....
)

While the straight forward work-around is to return StringWrapper object as json media-type:

@Data
class StringWrapper {
private String string;
}

@PutMapping(value = "/path")
    public ResponseEntity<StringWrapper> method() {
        return ResponseEntity.ok()
       .body(new StringWrapper ("SomeString Value")));
    }

it would be great to support such case out of the box. Thanks

jvmlet avatar Apr 21 '20 15:04 jvmlet

Right, this seems like a reasonable enhancement. I think supporting just text/plain is a good start with obvious implementation, but this could even be enhanced to support other types in the future (probably that would mean that you'd need to register a custom deserializer on the client).

komu avatar Apr 24 '20 05:04 komu