I want to create an android application, this application will make RESTful calls to a web service to obtain some data.
I know what the RESTful interface will be, but I don't want the hassle of creating my own implementation. Is there an easy way to create a stub RESTful web service that will return some static data without having to write a full blown WS application to do this?
Mocky.io allows you to create stub endpoints and specify the data they return via public URLs.
Runscope (disclaimer, I'm a founder) allows you to capture a real request once, then replay back the response as needed via Response Playback URLs.
I've found using Sinatra really useful for this sort of thing if you want to test the actual HTTP calling code. You can have a endpoint returning data in seconds. Very little Ruby knowledge required.
require 'sinatra'
require 'json'
get '/Person' do
content_type :json
{ :id => 345, :key2 => 'John Doe' }.to_json
end
Is all you would need to return a simple json object.
One of the approaches (similar to Vinnie's) is to make a local implementation of your webservice. For example, your webservice allows you to log a user in and to get a list of users online.
The webservice interface looks like this:
public interface WebService {
public LoginResponse login(String user, String pass) throws Exception;
public UsersOnlineResponse getOnlineUsers() throws Exception;
}
Then, we implement this interface for remote webservice which will be used in production. Remote implementation makes HTTP calls with help of HTTP client, retrieves response and parses it to an appropriate response object. Here is a fragment of it:
public class RemoteWebService implements WebService {
private AndroidHttpClient client = AndroidHttpClient.newInstance(USER_AGENT);
#Override
public LoginResponse login(String user, String pass) throws Exception {
LoginResponse response = client.execute(
createPostRequest(METHOD_LOGIN, user, pass),
new JsonResponseHandler(LoginResponse.class));
handleResponse(response); // verify response, throw exceptions if needed
return response;
}
}
For testing purposes, when webservice is not available or is being developed, we implement local webservice. Local implementation takes predefined JSON responses from assets folder and parses it to an appropriate response object. It's up to you how to implement webservice behaviour: it can be simple static responses or some random/validation-dependent responses. Here is the part of it:
public class LocalWebService implements WebService {
private Context context;
public LocalWebService(Context context) {
this.context = context;
}
#Override
public LoginResponse login(String user, String pass) throws Exception {
Thread.sleep(DELAY); //emulate network delay
if (validateParams(user, pass)) {
return parseAssetsJson("ws/login.json", LoginResponse.class);
} else {
Response response = parseAssetsJson("ws/status_bad_request.json", Response.class);
throw new WebServiceException(response);
}
}
public <T> T parseAssetsJson(String filename, Class<T> klass) throws IOException {
InputStream is = context.getAssets().open(filename);
return JsonParser.getInstance().fromJson(new InputStreamReader(is), klass);
}
}
Next, we want to switch between implementations painlessly. The usage of both implementations of the webservice is transparent, because we use WebService interface. So, we'll configure the WebService instance on app launch. Application class suits our needs:
public class App extends Application {
public static final boolean USE_LOCAL_WS = false;
private static WebService webService;
public static getWebService() {
return webService;
}
#Override
public void onCreate() {
super.onCreate();
webService = USE_LOCAL_WS ? new LocalWebService(this) : new RemoteWebService();
}
}
I'd suggest checking out WireMock (disclaimer - I wrote it):
http://wiremock.org/
You can run it standalone on your laptop, configure stubbed responses and verify that your app send the requests you expected it.
It's configurable via a fluent Java API or JSON (files or over HTTP).
I ended up writing a mock service tool for a similar purpose: https://github.com/clafonta/Mockey/wiki
A mock service is a great tool for quickly building UIs and validating your client code, but it can become a rabbit hole, so I recommend you use something that is already out there before building your own. Github has plenty of results when you search for 'mock'. Regardless of what you do, here are a few key stumbling blocks that you may encounter.
You end up working with the wrong data/JSON format. For example, your app works great with the mock service, but breaks when hitting the real service because your app consumes a JSON object but the real service returns an Array of JSON objects. To avoid this, you could try using JSON Schema to help highlight invalid JSON models in your mock service.
Your app doesn't make a valid request. Your mock service will typically not care about the incoming request. For example, the real service needs a "customerID" and your app never passes it in. To avoid this, you could build some "required request parameter" validation logic in your mock service.
Testing challenges. Your automated functional testing approach needs to interact with your mock service tool if you want to test things beyond the simple "happy path". For example, you run your test "user A logs-in and sees 0 messages" vs. "user B logs-in and sees 20 messages".
You can try Jadler (http://jadler.net). It's an http stubbing/mocking library I've been working on for some time. It should meet all your requirements I believe.
Just in case someone is still looking at this thread at year >= 2017. There's free tool out there now that let's you create mock soap and rest web services in seconds without the need to install or deploy anything on your box.
amock.io
You can select your http method, response code, response message body, content-type, specify custom endpoint, etc.
It's very useful for returning mock data from remote web services to you app, any kind of app.
Disclaimer, I developed this service, out of necessity and I made it free so others can benefit from the solution.
Beeceptor (disclaimer, I'm the author) shall help you for the exact use-case here. Create an API endpoint, define a mock path and response. Use it in hackathons to build mock APIs in seconds.
Beeceptor is more than a mocking service. It is an HTTP proxy for APIs. For example, if you have a real API, use the real API as ultimate target. Beecetor intercepts traffic and using rules,
when rules are matched, APIs are mocked
when no rule matches, your target endpoint is hit as usual.
With Mocky.io, you shall have different API paths, with Beeceptor your base URL is going to be same all the time.
There's pretty new mock API solution called QuickMocker that allows not only stubbing static data, but also generate fake (faker), random and contextual data using shortcodes. Supports multiple HTTP methods and RegExp URL path which allows to create even one single dummy endpoint that can intercept anything you need. And yeah, it allows to debug any request made to your fake API domain.
Probably the best thing to do is create a mock for the REST web service service while you're developing your application code and then replace it with code to call the actual web service returning "real" data, once your application is written.
I'm currently writing a very similar application to yours which (like you) obtains data from a RESTful web application. In my application, I'm following the MVP pattern recommended by GWT and is also documented by Martin Fowler as the PassiveView pattern.
What you want to do is abstract away the code to make the REST web service call into an interface (the Model). The responsibility of this model class is to provide data to the Presenter/Controller. The Presenter will handle all of your business logic and then pass data up to the view (the view should be pretty dumb as well allowing it to also be mocked out). During testing, you will create a MockModel to implement the model interface and pass test data to the Presenter - without making an actual web service call at all! Then, when you're ready, you will replace this class with the actual web service and start your integration testing.
This approach has the added benefit in that it will be easy to create specific (and repeatable) test cases in your mock model. If you don't have control of the actual web service (and I'm assuming you don't), this can be difficult (or even to impossible) to achieve. The result should be a more robust, better tested application without to need to create any test XML or JSON or creating the web services yourself.
Create some files with dummy responses and put into a folder. Now go to command-line and execute the following:
python -m SimpleHTTPServer
You can now access these files and dummy responses at
http://:8000
I suggest taking a look at FakeRest (https://github.com/marmelab/FakeRest), a client-side only Fake Server using XMLHTTPRequest monkey patching.
Disclaimer: I wrote it.
Atmo could be useful.
Disclaimer: I'm the author of atmo.
You can make use of http://maqueapp.com/ to create the mock web service. Its quick and easy. I heard about it on theflexshow episode 157 (not flexshow!)
Related
is there are any way to mock Loopj AndroidAsyncHttp responses?
I am developing application which depends on REST API, but API is not ready yet and I want to develop application independently from API. Retrofit has a lot of mock implementations, but I was not able to find any solutions for AndroidAsyncHttp. Is there are any way?
I tried to send success message to handler on request creation handler.sendSuccessMessage(200, new Header[1], new byte[1]); , but onSuccess or something else is not called.
As example, you may create on any hosting php file with responsing json.
Or you can use my template for this cases http://so.five-dots.ru/api-test.php
Make responsing on this address and implements your logic. Then RESTfull API backend service will be ready, you can replace adresses on real and getting responseBody will reqirement data.
Ok, this may seem as a dumb question, but I am really new when it comes to Cloud Computing/Google App Engine etc. In order to get more familiarized with it, I started to work with some tutorials from developers.google.com, basically following the tutorials and then trying to perform small changes to the provided pieces of code, in order to make sure that I actually understood the way it works, not just copy/paste and take everything for granted.
The problem is that I got a little bit stuck at the following aspect: the way Android and App Engine actually communicate. I am currently doing this tutorial(
https://developers.google.com/eclipse/docs/endpoints-addentities). The problem is the following piece of code (client-side, on Android):
public class EndpointsTask extends AsyncTask<Context, Integer, Long> {
protected Long doInBackground(Context... contexts) {
Noteendpoint.Builder endpointBuilder = new Noteendpoint.Builder(
AndroidHttp.newCompatibleTransport(),
new JacksonFactory(),
new HttpRequestInitializer() {
public void initialize(HttpRequest httpRequest) { }
});
Noteendpoint endpoint = CloudEndpointUtils.updateBuilder(
endpointBuilder).build();
try {
Note note = new Note().setDescription("Note Description");
String noteID = new Date().toString();
note.setId(noteID);
note.setEmailAddress("E-Mail Address");
Note result = endpoint.insertNote(note).execute();
} catch (IOException e) {
e.printStackTrace();
}
return (long) 0;
}
}
As far as my understanding helps me, at this moment, in terms of Cloud Computing, I inferred that the communication between Android and the Cloud is performed via endpoint object, where endpoint is:
Noteendpoint endpoint = CloudEndpointUtils.updateBuilder (endpointBuilder).build();
Also, the updateBuilder() method looks like this:
public static <B extends AbstractGoogleClient.Builder> B updateBuilder(
B builder) {
if (LOCAL_ANDROID_RUN) {
builder.setRootUrl(LOCAL_APP_ENGINE_SERVER_URL_FOR_ANDROID
+ "/_ah/api/");
}
// only enable GZip when connecting to remote server
final boolean enableGZip = builder.getRootUrl().startsWith("https:");
builder.setGoogleClientRequestInitializer(new GoogleClientRequestInitializer() {
public void initialize(AbstractGoogleClientRequest<?> request)
throws IOException {
if (!enableGZip) {
request.setDisableGZipContent(true);
}
}
});
return builder;
}
I do understand that the insertion in the Data Storage is performed via insertNote() - which, basically, performs basic a standard insert method.
My problem is that I cannot really understand where, in the cloud, the information that I've sent from my Android device is caught. To be more specific, I am sending an object, and I cannot really see where that object is received in the Cloud. Probably at this kind of basic application, is not that relevant, but I want to develop an application with the following structure: I am sending data from my Android device using REST. I am developing my server-side code )(which will be in the Cloud). In my server-side code will receive the data I am sending from Android -> process that data -> add something in the database (database stored in the cloud) (this is the basic principle explained in VERY primitive terms). That's why I really want to understand the way this works and so far, I really cannot see where my data is received on the server side. I have assumed that there is probably some automatic mechanism behind this ? If so, I am really interested, if you could indicate me, how can I do that programatically.
Also, I would like to mention that this code works really good, so there are no errors in it, I just have problems in understanding all the details related to it.
Thank you.
LATER EDIT:
My database will be App Engine Datastore. The main problem is that I cannot really understand the way the communication between my Android Application and the Google App Engine Application (where I will be making all the necessary computations with the data I receive from Android) is made. I could really use a more "obvious"/explainatory (for dummies) piece of code where I actually see that the object I send from Android is received in the Google App Engine Application. Of course, I saw the result, using Datastore Viewer, which shows that the data is inserted in the database. What interests me is how I can actually just send the data in my Google App Engine Application, receive it there and perform some operations on it, and ONLY after I will add it in the database.
The updateBuilder() method is not on the server side. It's part of the android code. CloudEndpointUtils is part of android. It's a class you create to handle the boilerplate code for you so you don't have to type it each time you need to access the server. You see the code
Noteendpoint.Builder endpointBuilder = new Noteendpoint.Builder(
AndroidHttp.newCompatibleTransport(),
new JacksonFactory(),
new HttpRequestInitializer() {
public void initialize(HttpRequest httpRequest) { }
});
It's assuming your api is called Noteendpoint and that you are "building" an object to access it. You could have called endpointBuilder.build() to start querying your api. If you look in the CloudEndpointUtils.updateBuilder method closely, you will see that what it is doing is redirect your calls to your localhost as opposed to your deployed code on appengine.
Let me know if you need clarification.
TO ANSWER YOUR EDIT:
Forget for a moment that this is a Google-endpoint application. You are basically designing a system that takes inputs, work on the inputs, and then save the result to a database.
For now let's pretend it does not matter whether the input is coming from a terminal or a file or a call to an api endpoint. What you absolutely must do is create a layer that will manipulate the data and then pass that data to your persistence layer (ie database). So you will need (still ignoring all things Google/appengine):
JPA entity (POJO with getters and setters and JPA annotations only)
Data access layer: This is a class with methods to perform queries on your JPA POJO (using EntityManagerFactory).
Business layer: This is a class where you manipulate the data you receive, then pass the result to the data access layer.
Hence you have Business logic layer => Data access layer => JPA POJO. So create all that not worring whether it's going to run on your local glassfish or wherever.
AFTER you are done, add endpoints annotations to your Business layer methods. Those annotations basically means that after you generate your android endpoint library, your android will be able to call your Business layer methods as if they were right inside your android application codes.
You get it? It will be as if your android and your server were one. Are you using the Google Eclipse plugin for this project?
I really don't understand your question. The "cloud" is represented by a Google App Engine application. That lives on Google's servers, and is served under the URL that you assign when you create the project. The database will presumably be either the App Engine datastore, or the Google Cloud SQL service which uses a version of MySQL.
I have a bunch of WCF SOAP services that serve my WP7 apps. Now I'm writing Android versions of those WP7 apps but SOAP support is practically nonexistent in Android so I must use REST for these Android apps.
So, my plan is to duplicate my WCF SOAP services in ASP.NET Web API. I am new to RESTful services.
Now that I'm getting into the details I think I'm appreciating SOAP a little more.
For instance one of my SOAP methods takes, among other arguments, a "TripLocker_s" object. (SOAP definition pasted below). As you can see a TripLocker_s object is an array TripLegModel_s objects. My various service methods pass all sorts of complex objects as arguments.
When I review any Android tutorials having to do with using HTTP services, nothing more complex than a string and maybe an integer is ever discussed as an argument. I can't find any information on passing complex objects.
How do I pass complex objects as arguments with Web api? Is there a way, for instance, to take a TripLocker_s object and serialize it as http parms (and then back again on the server?)
Thanks, Gary
[DataContract]
public class TripLegModel_s
{
[DataMember]
public string ourDirection; //SE, SW, SSW, etc.
[DataMember]
public double longitude;
[DataMember]
public double latitude;
[DataMember]
public double altitude;
[DataMember]
public DateTimeOffset TimeStamp;
[DataMember]
public double speed;
}
[DataContract]
public class TripLocker_s
{
[DataMember]
public ObservableCollection<TripLegModel_s> BreadCrums = new ObservableCollection<TripLegModel_s>();
Thanks,
No reason you can't pass complex objects as JSON or XML in RESTful APIs via RESTful (http) verbs (get, post, put, etc...). JSON is more web (javascript) friendly and RESTful/hypermedia APIs are typically chosen for web apps. Since it's so web friendly, if you choose it for mobile android consumption the API is also more consumable for web, iOS, win phone etc... Javascript (and therefore JSON) is becoming the language of choice for the web.
If you're creating, you post the serialized object in the body.
See this post for a full example: restful-like CRUD operation url pattern for nested model
If you're using WCF, consider webapi, see http://www.asp.net/web-api
Specifically, checkout: http://www.asp.net/web-api/overview/creating-web-apis/creating-a-web-api-that-supports-crud-operations
For example, in the webapi CRUD sample, it works with a products object:
namespace ProductStore.Models
{
public class Product
{
public int Id { get; set; }
public string Name { get; set; }
public string Category { get; set; }
public decimal Price { get; set; }
}
}
Finally, checkout this read on thinking more RESTful (as opposed to RPC or SOAP)
http://blog.steveklabnik.com/posts/2011-07-03-nobody-understands-rest-or-http
RE: "My plan is to duplicate my WCF SOAP services in ASP.NET Web API."
SUGGESTION: Don't even think about it! There's no need ... you should be able to create REST-based web services just fine. That's where the world is going ... and Microsoft is going along with it. It should't be an issue.
And please don't get hung up on "everything's gotta be an object". It DOESN'T. In particular, why bog down your Android app with an (arguably unnecessary) GSON library, if a simple JSON message will work just as well?
Also, if you're not currently a "Java Guy", you might want to consider coding your Android stuff in a higher-level framework like PhoneGap:
http://www.phonegap.com
Just a suggestion!
1) Why can't you use SOAP if you want to? What specific problems are you having?
2) Why would anybody want to use SOAP if they could use REST instead?
3) Are you familiar with JSON?
Your Android is a web service client, correct? What/where is the web service itself, and is it using SOAP, JSON or "something else"?
Please check out this instructive tutorial on REST:
http://www.ibm.com/developerworks/webservices/library/ws-restful/
These other links might be useful:
JSON Tutorial
Creating a REST Webservice for an Android Client
Getting started with JSON
I made application in ASP.NET MVC3 and I want to connect application with Android.
So first step is to make Web Service, that will communicate with Android.
But I'm new in this area and I don't know how to start.
Does anyone have some tutorial for making Web Service for ASP.NET MVC3 application?
Also I need instructions for connecting Android with that Web Service?
You really have two questions here, and unfortunately the Android one is a little too broad to answer quickly. So... let's tackle your first question.
In MVC it is pretty easy to create a simple web service. Create a controller and return JSON from it:
public class PersonController: Controller{
public JsonResult Index(){
var personList = GetFromDB();
return Json(personList, JsonRequestBehavior.AllowGet);
}
[HttpPost, ActionName("Index")]
public JsonResult CreatePerson(Person newPerson){
var insertedPerson = InsertIntoDB(newPerson);
return Json(insertedPerson);
}
}
Now, with the default routing in place you can simply call those methods with the following URL, and the appropriate HTTP Verb.
http://www.mydomain.com/person
However, it may be worth mentioning this is far easier to do using ASP.Net WebAPI.
I am wondering what is required to setup a server so that you can store data on it, and then have an application send requests to it to store and receive data. More specifically, I am working on an Android application where a user will generate data and then that should be stored on a server so other users can access it. But I do not know how setting up a server to be capable of this works. I have worked on Android applications in the past that sends requests (put, post, get, etc) to a server, but that back end was already set up for me. Any info or resources about setting this up would be great.
There are many, many different ways to accomplish this.
Since you're already working with a Google technology, Android - you could start by creating a Google App Engine project. Following the tutorials you can get started setting up a simple back end solution that will store data for you and you can make requests to it for that data.
Another advantage to this for you is that you don't have to learn how to install software on a server and all the dependencies that arise from that, etc. Simply set up a new account and push-button deploy through Eclipse or command line.
And since you've used Java in Android, you can use JAva for Google App Engine (GAE) too!
Getting started: http://code.google.com/appengine/docs/java/gettingstarted/introduction.html
You can try ready to use BAAS/PAAS services to store your data, e.g. QuickBlox for Android http://quickblox.com/developers/Android, where you can manipulate with your data with few strings
QBLocation location = new QBLocation();
location.setLatitude(35.0);
location.setLongitude(53.0);
location.setStatus("I'm at this place");
String someImportantString = "Dr. Henry Walton Indiana Jones";
QBLocations.createLocation(location, new QBCallbackImpl() {
#Override
public void onComplete(Result result, Object context) {
// retrieve context object inside callback
String passedContextObject = (String) context;
System.out.println(passedContextObject);
// do stuff with result
}
}, someImportantString);
All logic of data exchange with server is encapsulated in framework.