Thanks to visit codestin.com
Credit goes to github.com

Skip to content

[FrameworkBundle] Extract KernelTestCase from WebTestCase #7704

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

Closed
wants to merge 1 commit into from

Conversation

johnkary
Copy link
Contributor

Q A
Bug fix? No
New feature? No
BC breaks? No
Deprecations? No
Tests pass? Yes
Fixed tickets None
License MIT
Doc PR symfony/symfony-docs#3311

This idea came to me while reading the Cookbook article How to create a Console Command - Testing Commands and I wanted to hear feedback from others before submitting a patch.

Basically the Cookbook article states that when testing a Command that extending WebTestCase is a good way to get access to the Kernel and thus the Container. This struck me as weird because I was wanting to test a Command, which doesn't really have anything to do with "the web."

Currently WebTestCase doesn't do anything internally that looks like web-specific work, and the class docblock itself states "WebTestCase is the base class for functional tests.".

I'm not sure how far-reaching this class is used by others, so I'm not sure on the BC implications. I think we could go one of two ways:

  1. Rename WebTestCase to FunctionalTestCase, thus removing WebTestCase. Add a note in the UPGRADE documentation to note the new class name and action required by someone upgrading their application. This issue should be noticed pretty quickly by anyone upgrading as their test suite would break. But finding the easy fix in UPGRADE should require little work from project owners.
  2. Move WebTestCase to FunctionalTestCase, then change WebTestCase to extend FunctionalTestCase but contain no functionality. Then add a @deprecated flag for WebTestCase to be removed in Symfony 2.4 after 2.3 LTS. This would ensure all existing bundles using WebTestCase would still work, but we could encourage a more-properly named class starting in 2.4.

Do you agree, and if so, which method sounds best?

EDIT 1:
@beberlei made a great third suggestion below that I think is better than the two above:

  1. Extract a new class KernelTestCase from WebTestCase and instead allow WebTestCase to extend KernelTestCase. Pull all methods up into KernelTestCase except createClient() because createClient() is focused solely on creating a Client for issuing web-based requests.

Benjamin's solution provides us a clear extension point from KernelTestCase for Command-based tests and also provides 100% backwards-compatibility without the need to deprecate WebTestCase.

@lsmith77
Copy link
Contributor

I understand you reasoning. not sure if this enough for a BC break so if at all I would go with 2)

@stefanosala
Copy link

FunctionalTestCase is definitely more consistent, but I would go with 2) too.

@Bendihossan
Copy link

+1 for the second method.

@beberlei
Copy link
Contributor

I have a KernelTestCase that duplicates the WebTestCase in kernel and container booting for exactly that cases.

@m43nu
Copy link

m43nu commented Apr 18, 2013

👍 for the second way

@egulias
Copy link
Contributor

egulias commented Apr 18, 2013

I'm with @lsmith77 for option 2, taking into account Fabien's post about stabilising Symfony.

@dolbertz
Copy link

+1 for the second proposal

@davedevelopment
Copy link
Contributor

👍 for option 2

@beberlei
Copy link
Contributor

Both options are weird imho, because FunctionalTestCase would then have createClient, which is wrong in the context. We need to extract a KernelTestCase class from the WebTestCase, ending up with two.

@0x46616c6b
Copy link

+1 for the second way

@johnkary
Copy link
Contributor Author

@beberlei I like your suggestion and think it makes better sense.

To be more specific, are you suggesting extracting KernelTestCase from WebTestCase and instead allowing WebTestCase to extend KernelTestCase? And we would then pull all methods up into KernelTestCase except createClient?

This solution would give us a clear extension point in KernelTestCase that could be extended for Command-based tests. When testing Commands it would have no knowledge of the Client normally used to make web requests.

This solution would also be 100% backwards-compatible.

Assuming we proceed with the above, should we stick with WebTestCase or also rename it to FunctionalTestCase? I think WebTestCase would still make sense because it's focused solely on creating a Client to issue web requests.

@lsmith77
Copy link
Contributor

btw LiipFunctionalTestBundle has a method to run commands. maybe we should have another class for command testing?

@willdurand
Copy link
Contributor

I'd go with 3.

@asm89
Copy link
Contributor

asm89 commented Apr 18, 2013

+1 on KernelTestCase (#3)

@marijn
Copy link

marijn commented Apr 18, 2013

👍 for the suggestion by @beberlei

@fazy
Copy link

fazy commented Apr 18, 2013

It might be good to keep WebTestCase but pull most of its functionality up to a new KernelTestCase (or FunctionalTestCase) (option 3).

@lsmith77 I'm using your command method, and your fixtures loader, they are very handy. This gives rise to a concern though; what if you have a hierachy like this:

  • KernelTestCase
    • CommandTestCase
    • FixturesTestCase
    • WebTestCase

...but you want to use some of the functionality in WebTestCase and CommandTestCase. Perhaps your tests should be in separate classes, but not always.

I would this is a good use case for traits, but they require PHP 5.4, so presumably we are a long way off from being able to use this.

A monolothic KernelTestCase containing all the above, perhaps (with delegation where possible)?

@gunnarlium
Copy link
Contributor

+1 on option 3.

I believe WebTestCase is just as good, or perhaps even better than FunctionalTestCase. What it does is expose getClient(), which is specifically used for testing web requests. Functional tests can be written for other stuff than web requests, and I would assume you could also use the client in non-functional tests.

@evillemez
Copy link

+1 on option 2. WebTestCase really has just one method that's specific to web - the createClient method. Personally I think it makes most since to keep it in FunctionalTestCase, but also provide a simple way for running commands. I agree it could be abstracted out into all kinds of special test cases, but I don't see any practical benefit precisely because of the concerns raised by @fazy.

My organization uses Symfony mostly for serving HTTP APIs, where we often asynchronously process data via Symfony commands. A common test scenario for us to make several API requests, do some assertions, run a command to process some data, make a few more requests, and do more assertions. If the test cases are split out into a bunch of different classes, it's not really saving anyone work.

@fabpot
Copy link
Member

fabpot commented Jun 13, 2013

Any news on this issue? Is it worth doing something about the current state?

@johnkary
Copy link
Contributor Author

I will submit a PR for review this weekend based on @beberlei's ideas above.

@mpdude
Copy link
Contributor

mpdude commented Nov 23, 2013

Just had to explain folks why they need to use the WebTestCase for tests that just need the container. The name is misleading, so ping @johnkary :-)

Ideal base class that needs access to a Kernel but not a Client such as
when testing a Command.
@johnkary
Copy link
Contributor Author

I've submitted code for this PR against the 2.4 branch because there are no BC breaks. Docs PR is here and is also against 2.4: symfony/symfony-docs#3244

@wouterj
Copy link
Member

wouterj commented Nov 30, 2013

New features should be placed in 2.5, no matter if it has bc breaks or not.

@johnkary johnkary closed this Dec 11, 2013
fabpot added a commit that referenced this pull request Mar 3, 2014
…se (johnkary)

This PR was merged into the 2.5-dev branch.

Discussion
----------

[FrameworkBundle] Extract KernelTestCase from WebTestCase

| Q             | A
| ------------- | ---
| Bug fix?      | No
| New feature?  | Yes
| BC breaks?    | No
| Deprecations? | No
| Tests pass?   | Yes
| Fixed tickets | None
| License       | MIT
| Doc PR        | symfony/symfony-docs#3311

Previous discussion is in #7704. Opened new PR to target master branch.

This idea came to me while reading the Cookbook article [How to create a Console Command - Testing Commands](http://symfony.com/doc/master/cookbook/console/console_command.html#testing-commands) and I wanted to hear feedback from others before submitting a patch.

Basically the Cookbook article states that when testing a Command that extending `WebTestCase` is a good way to get access to the Kernel and thus the Container. This struck me as weird because I was wanting to test a Command, which doesn't really have anything to do with "the web."

Currently `WebTestCase` doesn't do anything internally that looks like web-specific work, and the class docblock itself states "WebTestCase is the base class for functional tests.".

After a suggestion in #7704 by @beberlei, I decided to take his advice and now have the following implementation:

Extracted a new class `KernelTestCase` from `WebTestCase` and instead allow WebTestCase to extend KernelTestCase. Pulled all methods up into KernelTestCase except `createClient()` because `createClient()` is focused solely on creating a Client for issuing web-based requests.

Benjamin's solution provides us a clear extension point from `KernelTestCase` for Command-based tests and also provides 100% backwards-compatibility without the need to deprecate WebTestCase.

Commits
-------

c4f14fb Extract new base test class KernelTestClass
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.