105 votes

Maquette de serveur de rétrofit Square pour les essais

Quelle est la meilleure façon de simuler un serveur à des fins de test lorsque l'on utilise la fonction cadre de rétrofit carré .

Des moyens potentiels :

  1. Créer une nouvelle rénovation client et le définir dans la méthode RestAdapter.Builder().setClient(). Cela implique d'analyser l'objet Request et de renvoyer le json en tant qu'objet Response.

  2. Implémentez cette interface annotée en tant que classe fantaisie et utilisez-la à la place de la version fournie par RestAdapter.create() (pour tester la sérialisation gson).

  3. ?

Idéalement, je voudrais que le serveur fictif fournisse des réponses json afin de pouvoir tester la sérialisation gson en même temps.

Tout exemple serait grandement apprécié.

112voto

Demandes de test pour Mock Retrofit 2.0

Comme les anciens mécanismes comme la création MockClient et l'implémenter à partir de Client ne fonctionnent plus avec Retrofit 2.0, je décris ici une nouvelle façon de le faire. Tout ce que vous devez faire maintenant est de ajoutez vos intercepteurs personnalisés pour OkHttpClient comme indiqué ci-dessous . FakeInterceptor ne fait que remplacer la classe intercept et dans le cas où l'application est en DEBUG mode retourne le JSON donné.

RestClient.java

public final class RestClient {

    private static IRestService mRestService = null;

    public static IRestService getClient() {
        if(mRestService == null) {
            final OkHttpClient client = new OkHttpClient();
            // ***YOUR CUSTOM INTERCEPTOR GOES HERE***
            client.interceptors().add(new FakeInterceptor());

            final Retrofit retrofit = new Retrofit.Builder()
                            // Using custom Jackson Converter to parse JSON
                            // Add dependencies:
                            // com.squareup.retrofit:converter-jackson:2.0.0-beta2
                    .addConverterFactory(JacksonConverterFactory.create())
                            // Endpoint
                    .baseUrl(IRestService.ENDPOINT)
                    .client(client)
                    .build();

            mRestService = retrofit.create(IRestService.class);
        }
        return mRestService;
    }
}

IRestService.java

public interface IRestService {

    String ENDPOINT = "http://www.vavian.com/";

    @GET("/")
    Call<Teacher> getTeacherById(@Query("id") final String id);
}

FakeInterceptor.java

public class FakeInterceptor implements Interceptor { 
    // FAKE RESPONSES.
    private final static String TEACHER_ID_1 = "{\"id\":1,\"age\":28,\"name\":\"Victor Apoyan\"}";
    private final static String TEACHER_ID_2 = "{\"id\":1,\"age\":16,\"name\":\"Tovmas Apoyan\"}";

    @Override
    public Response intercept(Chain chain) throws IOException {
        Response response = null;
        if(BuildConfig.DEBUG) {
            String responseString;
            // Get Request URI.
            final URI uri = chain.request().url().uri();
            // Get Query String.
            final String query = uri.getQuery();
            // Parse the Query String.
            final String[] parsedQuery = query.split("=");
            if(parsedQuery[0].equalsIgnoreCase("id") && parsedQuery[1].equalsIgnoreCase("1")) {
                responseString = TEACHER_ID_1;
            }
            else if(parsedQuery[0].equalsIgnoreCase("id") && parsedQuery[1].equalsIgnoreCase("2")){
                responseString = TEACHER_ID_2;
            }
            else {
                responseString = "";
            }

            response = new Response.Builder()
                    .code(200)
                    .message(responseString)
                    .request(chain.request())
                    .protocol(Protocol.HTTP_1_0)
                    .body(ResponseBody.create(MediaType.parse("application/json"), responseString.getBytes()))
                    .addHeader("content-type", "application/json")
                    .build();
        }
        else {
            response = chain.proceed(chain.request());
        }

        return response;
    }
}

Code source du projet sur GitHub

86voto

Alec Holmes Points 602

J'ai décidé d'essayer la méthode 1 comme suit

public class MockClient implements Client {

    @Override
    public Response execute(Request request) throws IOException {
        Uri uri = Uri.parse(request.getUrl());

        Log.d("MOCK SERVER", "fetching uri: " + uri.toString());

        String responseString = "";

        if(uri.getPath().equals("/path/of/interest")) {
            responseString = "JSON STRING HERE";
        } else {
            responseString = "OTHER JSON RESPONSE STRING";
        }

        return new Response(request.getUrl(), 200, "nothing", Collections.EMPTY_LIST, new TypedByteArray("application/json", responseString.getBytes()));
    }
}

Et l'utiliser en :

RestAdapter.Builder builder = new RestAdapter.Builder();
builder.setClient(new MockClient());

Cela fonctionne bien et vous permet de tester vos chaînes json sans avoir à contacter le vrai serveur !

22voto

Jake Wharton Points 26095

Tester la désérialisation de JSON vers vos objets (vraisemblablement avec TypeAdapters ?) semble être un problème distinct qui nécessite des tests unitaires distincts.

J'utilise personnellement la version 2. Elle permet d'obtenir un code sûr du point de vue du type, facile à remanier, qui peut être facilement débogué et modifié. Après tout, à quoi bon déclarer vos API sous forme d'interfaces si vous ne créez pas d'autres versions de celles-ci pour les tester ! Polymorphisme pour la victoire.

Une autre option consiste à utiliser un programme Java Proxy . C'est en fait la façon dont Retrofit implémente (actuellement) son interaction HTTP sous-jacente. Il est vrai que cela nécessitera plus de travail, mais cela permettrait de créer des objets fantaisie beaucoup plus dynamiques.

10voto

mato Points 1361

Vous pouvez également utiliser quelque chose comme Webservermock de Squareup ! --> https://github.com/square/okhttp/tree/master/mockwebserver

8voto

jpotter6 Points 660

Je suis un grand fan de Apiary.io pour simuler une API avant de passer à un serveur réel.

Vous pouvez également utiliser des fichiers plats .json et les lire à partir du système de fichiers.

Vous pouvez également utiliser des API accessibles au public comme Twitter, Flickr, etc.

Voici d'autres ressources intéressantes sur Retrofit.

Diapositives : https://docs.google.com/presentation/d/12Eb8OPI0PDisCjWne9-0qlXvp_-R4HmqVCjigOIgwfY/edit#slide=id.p

Vidéo : http://www.youtube.com/watch?v=UtM06W51pPw&feature=g-user-u

Exemple de projet : https://github.com/dustin-graham/ucad_twitter_retrofit_sample

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X