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

Mock mix pl tests #482

Merged
merged 17 commits into from
Jan 15, 2021
Merged

Mock mix pl tests #482

merged 17 commits into from
Jan 15, 2021

Conversation

XiangRongLin
Copy link
Collaborator

@XiangRongLin XiangRongLin commented Dec 15, 2020

  • I carefully read the contribution guidelines and agree to them.
  • I have tested the API against NewPipe.
  • I agree to create a pull request for NewPipe as soon as possible to make it compatible with the changed API.

My first draft to address the points abount mocking the responses in #481. Not yet merge ready, but before that i wanted to get some opinions on this type of solution.

  1. RecordingDownloader relays request to the existing DownloaderTestImpl, but saves the request/response pair into a json file inside a folder specific to the test class. This should be done locally when the requests that are made by a test class change.
  2. MockDownloader relies on the json files created by the RecordingDownloader. PR/Push CI jobs should then use this downloader.
  3. To change the downloader type during development on the local machine change DownloaderFactory.DEFAULT_DOWNLOADER
  4. To change the downloader depending on CI jobs, add a system property to gradle commands: -Ddownloader=ABCD, where ABCD is one of DownloaderType
  5. The downloader specified through gradle takes precedence over the one specified inside DownloaderFactory. If none is giving it falls back to that one.

Some sitenotes:

  • YoutubeParsingHelper holds a global state about client version and client key. The first test class that gets executed with the RecordingDownloader makes a request and gets that request saved. Other test classes also need that request saved, but since the global state is then already initialized, that request won't be made. Currently I added that request as shared and add them to all MockDownloaders
  • apache-commons-io can be removed if needed. Was needed to clear the directories before RecordingDownloader fills them.
  • Gson is used over nanojson, because nanojson couldn't serialize the responseBody
  • I couldn't test if gradle aggregatedJavadocs -Ddownloader=xyz works because it won't work on windows due to file encoding. I only tried gradle extractor:test -Ddownloader=xyz
  • Ignore the first (move package) and last commit (generated jsons) for easier diffs
  • What is that design pattern called, where you get a specific implementation based on an input. I don't think it's factory

@XiangRongLin
Copy link
Collaborator Author

Running gradle extractor:test -Ddownloader=RECORDING does use the RecordingDownloader (tried with debugger) but does not create the files, which i don't understand.

@XiangRongLin
Copy link
Collaborator Author

Sooo, are there any opinions about this approach?

Because i don't want to put more time into it if the approach is already not good.

@Stypox
Copy link
Member

Stypox commented Jan 3, 2021

I missed this 20 days ago and I don't really have much time to dedicate to NewPipe currently, I may try to look at it the day after tomorrow.

Copy link
Member

@Stypox Stypox left a comment

Choose a reason for hiding this comment

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

I like this approach, it allows for expansion and is simple to migrate to. Thank you for your dedication :-D

RecordingDownloader relies on the real downloader and saves the request/response pair into a json file.
MockDownloader uses json files from above and mocks responses for specific requests.
…ables.

If the system property 'downloader' is set that use that specific downloader. This is used from gradle by appending `-Ddownloader=ABCD to the command.
ABCD is one of DownloaderType.
The other variable is the static property `DEFAULT_DOWNLOADER` in DownloaderFactory, which can be easily changed as needed inside the IDE according to development needs`.

Normal workflow would be to first use the recording downloader and afterwards only use mocks, if the requests are always staying the same.
This is needed so that a request is made for each test class when running multiple at once. This way RecordingDownloader records all necessary requests.
This works as long as tests are run sequentially and not in parallel.
@XiangRongLin
Copy link
Collaborator Author

XiangRongLin commented Jan 10, 2021

@Stypox i rebased on top of dev.
The new changes are seperate commits for easier reviewing. For the actual changes see commit history.
My first sitenote about the global state in YoutubeParsingHelper i just band-aid style fixed it with a reset method.

I will regenerate the mock files, when the pr is ready to be merged.

edit: easier reviewing as in you only have to check the new commits. (after jsom generation)

@XiangRongLin XiangRongLin marked this pull request as ready for review January 10, 2021 20:00
@TobiGr
Copy link
Member

TobiGr commented Jan 11, 2021

  1. RecordingDownloader relays request to the existing DownloaderTestImpl, but saves the request/response pair into a json file inside a folder specific to the test class. This should be done locally when the requests that are made by a test class change.
  1. MockDownloader relies on the json files created by the RecordingDownloader. PR/Push CI jobs should then use this downloader.
  2. To change the downloader type during development on the local machine change DownloaderFactory.DEFAULT_DOWNLOADER
  3. To change the downloader depending on CI jobs, add a system property to gradle commands: -Ddownloader=ABCD, where ABCD is one of DownloaderType

Can you put that info to a place where it can be found later? [To be honest, I don't know a good place for that]

@XiangRongLin
Copy link
Collaborator Author

@TobiGr I added to the classes/methods themselves. Anywhere else it would just get out of date.

Only thing thats missing is that CI jobs should use MockDownloader, but i would add that to the CI job itself.

Copy link
Member

@Stypox Stypox left a comment

Choose a reason for hiding this comment

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

Almost ready, imo

Copy link
Member

@Stypox Stypox left a comment

Choose a reason for hiding this comment

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

Thank you, this now looks good to me. Do you still want to implement something else or is this ready @XiangRongLin ? @TobiGr I'll let you merge, since you also reviewed this PR.

@XiangRongLin
Copy link
Collaborator Author

I'll just recreate the json files later. Then it can be merged

Copy link
Member

@Stypox Stypox left a comment

Choose a reason for hiding this comment

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

Looking good to me, and the relevant tests succeed. Great :-D

@Stypox Stypox merged commit c2c4d97 into TeamNewPipe:dev Jan 15, 2021
@XiangRongLin XiangRongLin deleted the mock_mix_pl_test branch January 15, 2021 12:20
@TobiGr TobiGr mentioned this pull request Jan 18, 2021
14 tasks
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.

3 participants