wcatron / ionic-cloud-sdk-php

Ionic Cloud SDK for PHP
MIT License
2 stars 2 forks source link

Dependency Injection for Testing #3

Closed wcatron closed 8 years ago

wcatron commented 8 years ago

Okay so guzzle has testing capabilities which could severely help with testing. However I feel we should still test separately. We create an API layer which handles interactions with the HTTP API and then the exposed library is build on top of that. The clients can depend on a test API layer for testing. Then we can have special test cases for the API layer that rely on the actual API. I have that setup in the tests/Client directory. It requires a tests/config.ini file with the api_token. If that's not present it just skips it.

| Users Client | Push Client | Package Client | Deploy Client |
|----                      Client                         ----|
|----                        API                          ----|

Client has all api requests as php functions and the API has the guzzle calls. Test the individual clients with a mock Client. Test the client with a mock API or guzzle mock handlers or the real thing.

Alternative:

| Users Client | Push Client | Package Client | Deploy Client |
|----                        API                          ----|

Split the Client between the individual clients and the API layer. The clients would deal directly with the API. Then test the clients using guzzle mock handler. This has the benefit of simplicity but the downfall of being a bit harder to test. The API layer would be handling configuration, and arbitrary http calls. I like that it splits the api calls among the clients though compared to the Client having a ton of functions.

imhoffd commented 8 years ago

We should never have to connect to the real API to run tests. Take a look at VCR or similar projects. Additionally, mocking HTTP endpoints can be done manually with a bunch of JSON files as test fixtures. Tests in this library should be localized and run fast. I should be able to run them out of the box and they should run in under a minute for sure.

As far as the architecture, the guzzle library is really good. We could probably use their client directly and inject it into all the classes that need it. We can even supply our own base_uri: http://docs.guzzlephp.org/en/latest/quickstart.html#creating-a-client

wcatron commented 8 years ago

Alright so I setup an http_handler which subclasses the guzzle client and handles authentication and base_uri. It can be easily replaced with a guzzle mock handler. We can look at VCR however it hasn't been updated since January and I couldn't get it to save guzzle requests, it's supposed to but I just couldn't. I setup a it'll do alternative using json files.

Tests run completely independently of the API I have one setup that can run live tests to figure out the real results and test that the request is properly sent (query parameter, uri, etc) but it's just skipped if you don't have a config file setup. Perhaps we need a better way to test that the requests are being generated properly. Regardless let me know if you think this solves dependency issues and is a good setup moving forward.

wcatron commented 8 years ago

A mock HTTPHandler can easily be injected into the Client class.