[15.x] Refactor subscription type handling #1621
Closed
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Alternative to #1619
This PR contains a few scary changes and may seem like a big breaking change but it should not be. I'll try to explain below so bare with me.
What this PR mainly tries to achieve is better support for apps which offer multiple subscriptions. Imagine the following scenario: we have a gym type subscription but also a tennis subscription for a customer. Right now, there's no way to do a single check if the customer is subscribed at all to either of them. You'd have to do:
Each subscription type need to be checked individually. With the changes of this PR you could simply do:
And this would return
true
if the customer is subscribed to either a gym subscription or a tennis subscription.So you might think this does implies a breaking change because the
default
fallback is now changed tonull
but in reality there shouldn't be a realistic scenario where this breaks any app. I'll try to explain in the scenarios below:Single type subscription apps which use
default
as their type should be the majority of use cases and aren't affected because the changes made accommodate to fallback to the single subscription type. So basically->subscribed()
is still the same as doing->subscribed('default')
. The same can be said for subscriptions which use a different type name thandefault
. They are already doing->subscribed('gym')
in their apps so they shouldn't need to do any changes to their codebase.Multi type subscriptions probably are largely unaffected as well. Since they mostly work with dedicated types they are already doing
$user->subscribed('gym')
and$user->subscribed('tennis')
checks by providing the correct type. So these apps also don't have to change anything to their codebase.The only scenario I foresee a breaking change is when a multi type subscription app uses the
default
type in combination with other "types" of subscriptions. For example,default
andgym
. In this scenario, the changes will return the first matching result for either of the subscription types when using->subscribed()
while before it would always return the result ofdefault
. In this situation, we should encourage apps who work with multiple subscription types to always provide the type when calling any of the changed methods.Lastly I'd like to demonstrate how the result set is determined for these changes. Imagine the following database table (
subscriptions
) and its values:Now we'll do
$user->subscribed()
on this set of values. Here's how Cashier checked the results before this PR:And here's how Cashier will check the results after this PR:
We now check every subscription type but we still only check the lastly added result of a certain subscription type. This is how Cashier handled things before as well so nothing changes here.
I think the best example of how little this breaks is that I didn't have to make any changes to the existing test suite. Everything still works as before.