RN code-push: testing component that hooks into codePushStatusDidChange - react-native

I'm using the react-native-code-push codePush HOC, and running some logic in response to a codePushStatusDidChange event hook, in particular, when the status is SyncStatus.UPDATE_INSTALLED.
I haven't had luck finding out whether there is a way to emulate code push events when running in dev mode, to verify that our code is responding properly to the event hook. Is this possible, or is it necessary to release new versions to the code push server?
Side question: if the installMode is set to codePush.InstallMode.ON_NEXT_SUSPEND, is the event hook supposed to receive a SyncStatus.UPDATE_INSTALLED on the next restart? (I suppose once I can get the first question figured out, I can answer the second one on my own!).

#twelve17 Hi.
I can share my experience regarding testing & CodePush usage.
We have both e2e tests (detox + jet) and unit tests (react-native-test-utils + jest).
When we run our e2e tests we specify the environment and switch codePush setting in the root HOC:
checkFrequency: isTest()
? codePush.CheckFrequency.MANUAL
: codePush.CheckFrequency.ON_APP_START,
In this case (manual check & update), codePush doesn't do anything while the app is running. It works fine with e2e testing because you really don't need any codePush tasks while running them, definitely.
Regarding unit tests: we don't test the HOC itself (for now), we've just covered only some stateless components, so here I can only recommend you either skip such tests (because codePush is the 3rd-party lib) or write your own wrapper for any of its commands and mock/stub them in case of tests are running.

Related

How exactly does jest's code coverage work during integration tests?

While doing integration tests on my express server, the code coverage feature of jest seems to only be working when the server is running in the same process as the test. For example:- importing express app and passing it to the supertest function, or importing the express app in the test file, initializing it and making requests to the endpoint it's running at.
When the express server is run in a seperate process the code coverage is always 0. By running in a seperate process I mean running the server in a different terminal or running it in through jest's global setup option.
I wanted to know is this an expected behavior and is this how jest fundamentally works? Or am I making some mistake here?

How to run E2E test with Cypress if backend and frontend are on different repos?

I have a React frontend and a Node backend, I've made several E2E tests with Cypress for the frontend and run them locally. I love how end to end testing allows me to catch errors in the frontend as well as on the backend! so I'd like to have a way to run them automatically when sending a PR.
I'm using bitbucket pipelines, and I've configured it to run the npm test command which works perfectly to run my unit tests, but what I still don't understand is how to be able to run my Cypress tests automatically, because I'd need to have access to the backend repository from my pipeline that runs on the frontend repo.
What I've tried
I've read the documentation and played with the example repo, but I still don't understand how could I automate running my tests, on the example both backend and frontend are on the same repository.
I'm sorry if this is a vague question, I just don't seem to get if this is even possible with bitbucket pipelines, if it's not, what other tool could help me run my Cypress test in a similar way that I do locally? (running both backend and frontend).
I've really tried to search for an answer to this, maybe it's too obvious and I'm just missing something but I don't seem to find anything on the internet about this, any help will be very appreciated!
When your frontend and backend are versioned in different repositories, then you have to check out at least one of the two repositories (e.g. the other for which the pipeline is not currently being executed) during the pipeline execution to get access to the code and thus have the possibility to start frontend and backend together locally to run your tests.
This question has also already been asked and answered here:
https://community.atlassian.com/t5/Bitbucket-questions/Access-multiple-Bitbucket-repositories-from-a-single-Pipeline/qaq-p/1783419

Are there any fastlane actions or plugins that allow you to execute scripts between tests?

I've searched quite a bit today but have not found any solid yes or no.
I'd like to know are there any plugins or actions for fastlane that allow you to execute a shell script between each test execution.
The reason I ask is that, while testing I spin up a server locally with docker.
I'd like to be able to either clear this servers queues or tear it down and recreate between tests.
I have a fastlane plugin test_center that will allow you to provide a callback that is called between "test runs".
If you set the :batch_count parameter to the number of tests you want to run, the callback will be called after each batch.
That would allow you to make a shell call to docker to tear it down and spin it back up again.

Hot Reload during Unit testing

I develop right now a small flutter app. I think as everyone, I fell in love with the hot reload feature.
So now I'm wondering if there is any possibility to have the same developer experience during unit test. Do have to turn a flag somewhere or is it right know just no possible.
If is not possible, are there any plans to make it possible?
I guess what you want is to run the new tests as soon as they changed. But in that case it's not a hot reload. Simply a watcher that detect whenever your sources or your tests have changed and restart them.
Flutter, and the lower layers, don't implement "watch" yet. Although you can achieve a similar effect quite easily using a node packages
npm i -g watch which will install watch globally so that you can use it in as a command line.
and then in your terminal do
watch "flutter test" lib test which will run flutter test everytime something change inside lib and test folders
You need to run the unit test as an app to be able to use hot reload.
In IntelliJ you can copy the run configuration for lib/main.dart and then select the file test/my_test.dart in the copy.
There is no support to run single tests from a set of tests in a test file in IntelliJ (don't know other IDEs) when you run a test this way.
In my opinion, if you run it as unit test, hot reload doesn't bring much benefit anyway because execution is very fast.

With Continuous Integration, why are tests run after committing instead of before?

While I only have a github repository that I'm pushing to (alone), I often forget to run tests, or forget to commit all relevant files, or rely on objects residing on my local machine. These result in build breaks, but they are only detected by Travis-CI after the erroneous commit. I know TeamCity has a pre-commit testing facility (which relies on the IDE in use), but my question is with regards to the current use of continuous integration as opposed to any one implementation. My question is
Why aren't changes tested on a clean build machine - such as those which Travis-CI uses for post-commit tesing - before those changes are committed?
Such a process would mean that there would never be build breaks, meaning that a fresh environment could pull any commit from the repository and be sure of its success; as such, I don't understand why CI isn't implemented using post-commit testing.
I preface my answer with the details that I am running on GitHub and Jenkins.
Why should a developer have to run all tests locally before committing. Especially in the Git paradigm that is not a requirement. What if, for instance, it takes 15-30 minutes to run all of the tests. Do you really want your developers or you personally sitting around waiting for the tests to run locally before your commit and push your changes?
Our process usually goes like this:
Make changes in local branch.
Run any new tests that you have created.
Commit changes to local branch.
Push local changes remotely to GitHub and create pull request.
Have build process pick up changes and run unit tests.
If tests fail, then fix them in local branch and push them locally.
Get changes code reviewed in pull request.
After approval and all checks have passed, push to master.
Rerun all unit tests.
Push artifact to repository.
Push changes to an environment (ie DEV, QA) and run any integration/functional tests that rely on a full environment.
If you have a cloud then you can push your changes to a new node and only after all environment tests pass reroute the VIP to the new node(s)
Repeat 11 until you have pushed through all pre-prod environments.
If you are practicing continuous deployment then push your changes all the way to PROD if all testing, checks, etc pass.
My point is that it is not a good use of a developers time to run tests locally impeding their progress when you can off-load that work onto a Continuous Integration server and be notified of issues that you need to fix later. Also, some tests simply can't be run until you commit them and deploy the artifact to an environment. If an environment is broken because you don't have a cloud and maybe you only have one server, then fix it locally and push the changes quickly to stabilize the environment.
You can run tests locally if you have to, but this should not be the norm.
As to the multiple developer issue, open source projects have been dealing with that for a long time now. They use forks in GitHub to allow contributors the chance to suggest new fixes and functionality, but this is not really that different from a developer on the team creating a local branch, pushing it remotely, and getting team buy-in via code review before pushing. If someone pushes changes that break your changes then you try to fix them yourself first and then ask for their help. You should be following the principle of "merging early and often" as well as merging in updates from master to your branch periodically.
The assumption that if you write code and it compiles and tests are passed locally, no builds could be broken is wrong. It is only so, if you are the only developer working on that code.
But let's say I change the interface you are using, my code will compile and pass tests
as long as I don't get your updated code That uses my interface.
Your code will compile and pass tests as long as you don't get my update in the interface.
And when we both check in our code, the build machine explodes...
So CI is a process which basically say: put your changes in as soon as possible
and test them in the CI server (it should be of course compiled and tested locally first).
If all developers follow those rules,
the build will still break, but we will know about it sooner rather than later.
The CI server is not the same as the version control system. The CI server, too, checks the code out of the repository. And therefore the code has already been committed when it gets tested on the CI server.
More extensive tests may be run periodically, rather than at time of checking in, on whatever is the current version of the code at the time of testing. Think of multi-platform tests or load tests.
Generally, of course, you'll unit test your code on your development machine before checking it in.