willlma
willlma

Reputation: 7533

Test authenticated Cloud Endpoints methods offline

I'm going on a long flight tomorrow and I'd like to be able to keep testing my cloud endpoints REST API while offline. The problem is that the User object is integral to most of my methods, and I need an internet connection to create valid OAuth tokens to call them from the client side (JavaScript).

On the Dev server though, no matter what account you log in on, the user is always the same (with email [email protected]). But if you feed it bogus tokens, it throws an OAuthRequestException.

Is there any way I can generate valid test tokens offline for the dev server or a way to access the User object without providing tokens at all?

Here's an example of a method I'd like to test while offline:

@ApiMethod(name = "hylyts.get")
public Hylyt getHylyt(@Named("url") String url, @Named("id") long id, User user)
        throws OAuthRequestException, UnauthorizedException {
    return ofy().load().type(Hylyt.class).parent(util.getArticleKey(url, user)).id(id).now();
}

Upvotes: 1

Views: 66

Answers (1)

David
David

Reputation: 5519

There's a little documented way to inject a custom Authenticator class in Cloud Endpoints. This allows you to change the way the User is detected.

Here's how it works :

@Api(name = "myapi", version = "v1", authenticators  = {MyDummyAuthenticator.class})
public class MyAPI {
  @ApiMethod(name = "hylyts.get")
  public Hylyt getHylyt(@Named("url") String url, @Named("id") long id, User user)
        throws OAuthRequestException, UnauthorizedException {
    return ofy().load().type(Hylyt.class).parent(util.getArticleKey(url, user)).id(id).now();
  }
}

And here's what your Authenticator implementation could look like :

public class MyDummyAuthenticator implements Authenticator {
    @Override
    public User authenticate(HttpServletRequest httpServletRequest) {
        return new User("[email protected]");
    }
}

You can of course make it more complicated. Since you have access to the HttpServletRequest you can get the user's email from a HTTP header or something like it.

Note that with an Authenticator you have access to the session in the local server but not in production. In production, httpServletRequest.getSession() will return null. THere's a trick to still fetch the session from the datastore, which I explain here.

Then there's the question of how to keep both the normal authentication solution and your DummyAuthenticator implementation. I think you can chain authenticators, but I'm not sure how it works. In the worst case, you can just swap the Authenticator implementation during your flights.

Upvotes: 2

Related Questions