Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Run tests using testcontainers #198

Merged
merged 13 commits into from
Feb 24, 2022
Merged

Conversation

remcowesterhoud
Copy link
Contributor

@remcowesterhoud remcowesterhoud commented Feb 21, 2022

Description

This PR adds a new module, extension-testcontainer. This module provides users with an annotation that will run their tests in a testcontainer. Achieving this required a couple of steps:

  1. Creating the module
  2. Creating the extension. This extension is responsible for managing the lifecycle of the testcontainer.
  3. Duplicating all the QA tests. By doing this and changing the @ZeebeProcessTest annotation to the one from extension-testcontainer we can run the same QA tests with the testcontainer. This introduces a lot of duplication. This will be solved in Remove QA test duplication #195
  4. Update the CI to run the QA tests with both extensions, and making sure it will update the configuration files. This has to be done to make sure release X.Y.Z will be created with the proper tag of the testcontainer. This step also involved creating maven profiles to exclude running certain tests in specific scenarios.

Note: Documentation is not updated yet. In #176 I will revisit the documentation and write a finalised version. This will also include the usage of this new extension.

Related issues

closes #192

Definition of Done

Not all items need to be done depending on the issue and the pull request.

Code changes:

  • The changes are backwards compatibility with previous versions
  • If it fixes a bug then PRs are created to backport the fix

Testing:

  • There are unit/integration tests that verify all acceptance criterias of the issue
  • New tests are written to ensure backwards compatibility with further versions
  • The behavior is tested manually

Documentation:

  • Javadoc has been written
  • The documentation is updated

@github-actions
Copy link

github-actions bot commented Feb 21, 2022

Unit Test Results

120 files  120 suites   6m 14s ⏱️
320 tests 320 ✔️ 0 💤 0
768 runs  768 ✔️ 0 💤 0

Results for commit 18820ce.

♻️ This comment has been updated with latest results.

@remcowesterhoud remcowesterhoud force-pushed the 192-testcontainer-extension branch 17 times, most recently from c4ee775 to 44d8d31 Compare February 22, 2022 10:38
@remcowesterhoud
Copy link
Contributor Author

@korthout Would you mind reviewing this one?

It seems like a huge change at first glance. While it certainly isn't a small change, the bulk of the changes are because of commit 0c553a6 where we duplicated the tests. I recommend reviewing this PR by commit. I've tried to split it up in small reviewable chunks.

@remcowesterhoud remcowesterhoud changed the title WIP: testcontainer extension Add testcontainer extension Feb 22, 2022
@remcowesterhoud remcowesterhoud changed the title Add testcontainer extension Run tests using testcontainers Feb 22, 2022
@korthout
Copy link
Member

korthout commented Feb 22, 2022

Thanks @remcowesterhoud, I'll make sure to check it out. Please note that there is a conflict.

This module will be used to run the tests in a testcontainer as opposed to the regular extension module.
@remcowesterhoud remcowesterhoud force-pushed the 192-testcontainer-extension branch from 26729d5 to c2e9cd6 Compare February 22, 2022 16:43
Copy link
Member

@korthout korthout left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice work @remcowesterhoud I have some comments and questions. Most are simply suggestions and I don't think any of them is blocking. So, LGTM 🎸 But, please do have a look at my comments

return;
}
final RecordResponse response = RecordResponse.newBuilder()
.setRecordJson(record.toJson())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@npepinpe We talked about deprecating .toJson(), but it currently isn't. Perhaps we decided against it. 🤷 Still protocol-jackson describes the use of ObjectMapper.writeValueAsString instead of the toJson. Do you feel strongly towards a specific approach?

This extension makes it possible to run tests against a testcontainer. The extension is responsible for managing the testcontainer lifecycle. It will start the container once for the entire testsuite. This is done in the beforeAll() method. The EngineContainer singleton will make sure it only gets created once.

Before each test the engine gets reset. This is done in the beforeEach() method, instead of in the afterEach(). The reasoning behind this is that the jUnit lifecycle calls afterEach() before testFailed(). We want to access the record stream upon test failure. If we reset the engine in the afterEach() method we will lose our access to the record stream in the testFailed() method.
Records have their own toJson() method which does the same thing as manually mapping it using the ObjectMapper. Using this toJson() method simplifies the code.
The toJson() method on Records is not threadsafe at the moment. This is because some Records contain an ArrayProperty. During serializationa new Record will be created (eg. a DeploymentRecord). This is an UnpackedObject which contains an ArrayProperty. The ArrayProperty has an ArrayValue.
Serializing an ArrayValue modifies the object. This means that multiple threads trying to serialize the same DeploymentRecord at a time will modify the ArrayValue at the same time. This results in exceptions.

Making it thread-safe this way a quick-fix. It would be nice if we can map and store the records as they come in. This way the requests themselves only have to return a list of mapped records, instead of mapping all records.
We want to verify both our extensions. Therefore, it makes sense to run all our QA tests against both extensions. For now all the tests are duplicated to achieve this. This, of course, is not ideal in maintaining the tests. In #195 we will get rid of this and find a more generic solution.
The image name, tag and ports used were hardcoded. In our workflow we'll have to modify at least the tag so we can run QA tests against the correct versions. This is easier to do if we store these options in a properties file.

This commit also removed the BindableService vararg. This was never used.
We have 2 kinds of tests in our QA module. The regular ones, and the ones that will run using testcontainers. The regular ones will be ran against 3 OS (ubuntu, windows and mac OS). This hard to achieve in a generic way with testcontainers. This is because with tetcontainers we should build the docker image first, so we ensure we run the tests against the latest code. There is multiple issues with this:

1. Windows uses the wrong daemon and is unable to build the image.
2. GitHub's macos-latest container does not have docker installed.

There is probably ways to switch the daemon and install docker. However, there is not much value in running all the tests 2 times on different OSs. Besides this, the execution will increase dramatically. Because of this we will run the testcontainer tests on 1 OS (ubuntu).
When a new commit gets pushed to master, or a new release is created we should update the configuration files so that the future QA tests will be using the correct image.
We used to run the maven and docker release jobs simultaneously. Now that the docker job has been changed to update the configuration files we have to make sure the maven release job runs after this is finished. If we don't we introduce a race-condition.
If the maven release job completes before the docker job updated the configuration files, it results in the maven release running tests on the wrong container.
@remcowesterhoud remcowesterhoud force-pushed the 192-testcontainer-extension branch from c2e9cd6 to 18820ce Compare February 24, 2022 08:35
@remcowesterhoud remcowesterhoud merged commit d9fe0ce into main Feb 24, 2022
@remcowesterhoud remcowesterhoud deleted the 192-testcontainer-extension branch February 24, 2022 08:35
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Use testcontainers in the extension
2 participants