Skip to content

Commit

Permalink
entitlement: Refactor and simplify EventsStream class
Browse files Browse the repository at this point in the history
Remove unused api `getCurrentStateForService(final String serviceName)`. The api is useful but the implementation was (probably) incorrect and since this is unused i went for simplification
Simplify EventsStream (the entitlement system *only* cancels at the subscription level) so no need to check at bundle or account level. Also there was a bug in that logic anyways.
Addresses Code review remark for fd7c0c1
  • Loading branch information
sbrossie committed Nov 2, 2015
1 parent b79573b commit 9480895
Show file tree
Hide file tree
Showing 3 changed files with 24 additions and 86 deletions.
Expand Up @@ -56,8 +56,6 @@ public interface EventsStream {

boolean isSubscriptionCancelled();

Collection<BlockingState> getCurrentSubscriptionEntitlementBlockingStatesForServices();

Collection<BlockingState> getPendingEntitlementCancellationEvents();

BlockingState getEntitlementCancellationEvent();
Expand Down
Expand Up @@ -18,22 +18,15 @@

package org.killbill.billing.entitlement.api;

import java.util.Collection;
import java.util.List;

import org.joda.time.DateTime;
import org.joda.time.LocalDate;

import com.google.common.base.Predicate;
import com.google.common.collect.Iterables;

public class DefaultSubscription extends DefaultEntitlement implements Subscription {

private final Collection<BlockingState> currentSubscriptionBlockingStatesForServices;

DefaultSubscription(final DefaultEntitlement entitlement) {
super(entitlement);
this.currentSubscriptionBlockingStatesForServices = eventsStream.getCurrentSubscriptionEntitlementBlockingStatesForServices();
}

@Override
Expand Down Expand Up @@ -66,22 +59,6 @@ public LocalDate getChargedThroughDate() {
return getSubscriptionBase().getChargedThroughDate() != null ? new LocalDate(getSubscriptionBase().getChargedThroughDate(), getAccountTimeZone()) : null;
}

@Override
public String getCurrentStateForService(final String serviceName) {
if (currentSubscriptionBlockingStatesForServices == null) {
return null;
} else {
final BlockingState blockingState = Iterables.<BlockingState>tryFind(currentSubscriptionBlockingStatesForServices,
new Predicate<BlockingState>() {
@Override
public boolean apply(final BlockingState input) {
return serviceName.equals(input.getService());
}
}).orNull();
return blockingState == null ? null : blockingState.getService();
}
}

@Override
public List<SubscriptionEvent> getSubscriptionEvents() {
return SubscriptionEventOrdering.sortedCopy(this, getAccountTimeZone());
Expand Down
Expand Up @@ -71,11 +71,6 @@ public class DefaultEventsStream implements EventsStream {

private BlockingAggregator blockingAggregator;
private List<BlockingState> subscriptionEntitlementStates;
private List<BlockingState> bundleEntitlementStates;
private List<BlockingState> accountEntitlementStates;
private List<BlockingState> currentSubscriptionEntitlementBlockingStatesForServices;
private List<BlockingState> currentBundleEntitlementBlockingStatesForServices;
private List<BlockingState> currentAccountEntitlementBlockingStatesForServices;
private LocalDate entitlementEffectiveEndDate;
private BlockingState entitlementCancelEvent;
private EntitlementState entitlementState;
Expand Down Expand Up @@ -152,11 +147,6 @@ public boolean isBlockChange() {
return blockingAggregator.isBlockChange();
}

@Override
public List<BlockingState> getCurrentSubscriptionEntitlementBlockingStatesForServices() {
return currentSubscriptionEntitlementBlockingStatesForServices;
}

public boolean isEntitlementFutureCancelled() {
return entitlementCancelEvent != null && entitlementCancelEvent.getEffectiveDate().isAfter(utcNow);
}
Expand Down Expand Up @@ -187,34 +177,27 @@ public Collection<BlockingState> getBlockingStates() {

@Override
public Collection<BlockingState> getPendingEntitlementCancellationEvents() {
return getPendingEntitlementEvents(DefaultEntitlementApi.ENT_STATE_CANCELLED);
}

@Override
public BlockingState getEntitlementCancellationEvent() {
return entitlementCancelEvent;
}

public Collection<BlockingState> getPendingEntitlementEvents(final String... types) {
final List<String> typeList = ImmutableList.<String>copyOf(types);
return Collections2.<BlockingState>filter(subscriptionEntitlementStates,
new Predicate<BlockingState>() {
@Override
public boolean apply(final BlockingState input) {
return !input.getEffectiveDate().isBefore(utcNow) &&
typeList.contains(input.getStateName()) &&
DefaultEntitlementApi.ENT_STATE_CANCELLED.equals(input.getStateName()) &&
(
// ... for that subscription
BlockingStateType.SUBSCRIPTION.equals(input.getType()) && input.getBlockedId().equals(subscription.getId()) ||
// ... for the associated base subscription
BlockingStateType.SUBSCRIPTION.equals(input.getType()) && input.getBlockedId().equals(baseSubscription.getId()) ||
// ... for that bundle
BlockingStateType.SUBSCRIPTION_BUNDLE.equals(input.getType()) && input.getBlockedId().equals(bundle.getId()) ||
// ... for that account
BlockingStateType.ACCOUNT.equals(input.getType()) && input.getBlockedId().equals(account.getId())
BlockingStateType.SUBSCRIPTION.equals(input.getType()) && input.getBlockedId().equals(baseSubscription.getId())
);
}
});

}

@Override
public BlockingState getEntitlementCancellationEvent() {
return entitlementCancelEvent;
}

public BlockingState getEntitlementCancellationEvent(final UUID subscriptionId) {
Expand Down Expand Up @@ -370,24 +353,27 @@ public BlockingState apply(final SubscriptionBase input) {
private void setup() {
computeEntitlementBlockingStates();
computeBlockingAggregator();
computeEntitlementEffectiveEndDate();
computeEntitlementCancelEvent();
computeStateForEntitlement();
}

private void computeBlockingAggregator() {
currentAccountEntitlementBlockingStatesForServices = filterCurrentBlockableStatePerService(accountEntitlementStates);
currentBundleEntitlementBlockingStatesForServices = filterCurrentBlockableStatePerService(bundleEntitlementStates);
currentSubscriptionEntitlementBlockingStatesForServices = filterCurrentBlockableStatePerService(subscriptionEntitlementStates);
blockingAggregator = blockingChecker.getBlockedStatus(currentAccountEntitlementBlockingStatesForServices,
currentBundleEntitlementBlockingStatesForServices,
currentSubscriptionEntitlementBlockingStatesForServices,

final List<BlockingState> currentSubscriptionBlockingStatesForServices = filterCurrentBlockableStatePerService(BlockingStateType.SUBSCRIPTION);
final List<BlockingState> currentBundleBlockingStatesForServices = filterCurrentBlockableStatePerService(BlockingStateType.SUBSCRIPTION_BUNDLE);
final List<BlockingState> currentAccountBlockingStatesForServices = filterCurrentBlockableStatePerService(BlockingStateType.ACCOUNT);
blockingAggregator = blockingChecker.getBlockedStatus(currentAccountBlockingStatesForServices,
currentBundleBlockingStatesForServices,
currentSubscriptionBlockingStatesForServices,
internalTenantContext);
}

private List<BlockingState> filterCurrentBlockableStatePerService(final Iterable<BlockingState> allBlockingStates) {
private List<BlockingState> filterCurrentBlockableStatePerService(final BlockingStateType type) {
final Map<String, BlockingState> currentBlockingStatePerService = new HashMap<String, BlockingState>();
for (final BlockingState blockingState : allBlockingStates) {
for (final BlockingState blockingState : blockingStates) {
if (blockingState.getType() != type) {
continue;
}
if (blockingState.getEffectiveDate().isAfter(utcNow)) {
continue;
}
Expand All @@ -401,29 +387,6 @@ private List<BlockingState> filterCurrentBlockableStatePerService(final Iterable
return ImmutableList.<BlockingState>copyOf(currentBlockingStatePerService.values());
}

private void computeEntitlementEffectiveEndDate() {
LocalDate result = null;
BlockingState lastEntry;

lastEntry = (!subscriptionEntitlementStates.isEmpty()) ? subscriptionEntitlementStates.get(subscriptionEntitlementStates.size() - 1) : null;
if (lastEntry != null && DefaultEntitlementApi.ENT_STATE_CANCELLED.equals(lastEntry.getStateName())) {
result = new LocalDate(lastEntry.getEffectiveDate(), account.getTimeZone());
}

lastEntry = (!bundleEntitlementStates.isEmpty()) ? bundleEntitlementStates.get(bundleEntitlementStates.size() - 1) : null;
if (lastEntry != null && DefaultEntitlementApi.ENT_STATE_CANCELLED.equals(lastEntry.getStateName())) {
final LocalDate localDate = new LocalDate(lastEntry.getEffectiveDate(), account.getTimeZone());
result = ((result == null) || (localDate.compareTo(result) < 0)) ? localDate : result;
}

lastEntry = (!accountEntitlementStates.isEmpty()) ? accountEntitlementStates.get(accountEntitlementStates.size() - 1) : null;
if (lastEntry != null && DefaultEntitlementApi.ENT_STATE_CANCELLED.equals(lastEntry.getStateName())) {
final LocalDate localDate = new LocalDate(lastEntry.getEffectiveDate(), account.getTimeZone());
result = ((result == null) || (localDate.compareTo(result) < 0)) ? localDate : result;
}

entitlementEffectiveEndDate = result;
}

private void computeEntitlementCancelEvent() {
entitlementCancelEvent = Iterables.<BlockingState>tryFind(subscriptionEntitlementStates,
Expand All @@ -433,6 +396,7 @@ public boolean apply(final BlockingState input) {
return DefaultEntitlementApi.ENT_STATE_CANCELLED.equals(input.getStateName());
}
}).orNull();
entitlementEffectiveEndDate = entitlementCancelEvent != null ? new LocalDate(entitlementCancelEvent.getEffectiveDate(), account.getTimeZone()) : null;
}

private void computeStateForEntitlement() {
Expand All @@ -446,17 +410,16 @@ private void computeStateForEntitlement() {
}

private void computeEntitlementBlockingStates() {
subscriptionEntitlementStates = filterBlockingStatesForTypeAndId(BlockingStateType.SUBSCRIPTION, subscription.getId());
bundleEntitlementStates = filterBlockingStatesForTypeAndId(BlockingStateType.SUBSCRIPTION_BUNDLE, subscription.getBundleId());
accountEntitlementStates = filterBlockingStatesForTypeAndId(BlockingStateType.ACCOUNT, account.getId());
subscriptionEntitlementStates = filterBlockingStatesForEntitlementService(BlockingStateType.SUBSCRIPTION, subscription.getId());
}

private List<BlockingState> filterBlockingStatesForTypeAndId(final BlockingStateType blockingStateType, @Nullable final UUID blockableId) {
private List<BlockingState> filterBlockingStatesForEntitlementService(final BlockingStateType blockingStateType, @Nullable final UUID blockableId) {
return ImmutableList.<BlockingState>copyOf(Iterables.<BlockingState>filter(blockingStates,
new Predicate<BlockingState>() {
@Override
public boolean apply(final BlockingState input) {
return blockingStateType.equals(input.getType()) &&
EntitlementService.ENTITLEMENT_SERVICE_NAME.equals(input.getService()) &&
input.getBlockedId().equals(blockableId);
}
}));
Expand Down

0 comments on commit 9480895

Please sign in to comment.