Example #1
0
        public ChangeSubscriptionResponse Invoke(ChangeSubscriptionRequest request)
        {
            Trace("Starting...");

            var organisation = Session.MasterRaven.Load <Organisation>(request.CurrentUser.ActiveOrganisation.Id);

            if (organisation == null)
            {
                return(new ChangeSubscriptionResponse(ignoreCache: true)
                {
                    Status = ChangeSubscriptionStatus.OrganisationNotFound
                });
            }

            if (!organisation.Subscription.ChargifyId.HasValue)
            {
                return(new ChangeSubscriptionResponse(ignoreCache: true)
                {
                    Status = ChangeSubscriptionStatus.SubscriptionNotFound
                });
            }

            var plans = _getAvailablePaymentPlansQuery.Invoke(new GetAvailablePaymentPlansRequest()).Plans;
            var stats = _getOrganisationStatisticsQuery.Invoke(new GetOrganisationStatisticsRequest()).Statistics;

            //if we are downgrading check the organisations stats to make sure they can
            if (request.Downgrading)
            {
                var plan = plans.FirstOrDefault(p => p.Id == PaymentPlan.GetId(request.NewPlanId));

                if (plan != null)
                {
                    var quotas = PlanQuotas.FromStats(stats, plan);

                    if (quotas.IssuesExceededBy > 0)
                    {
                        return(new ChangeSubscriptionResponse(ignoreCache: true)
                        {
                            Status = ChangeSubscriptionStatus.QuotasExceeded,
                            Quotas = quotas
                        });
                    }
                }
            }

            var chargifyConnect = new ChargifyConnect(_configuration.ChargifyUrl, _configuration.ChargifyApiKey, _configuration.ChargifyPassword);
            var subscription    = chargifyConnect.LoadSubscription(organisation.Subscription.ChargifyId.Value);

            if (subscription == null)
            {
                return(new ChangeSubscriptionResponse(ignoreCache: true)
                {
                    Status = ChangeSubscriptionStatus.SubscriptionNotFound
                });
            }

            var newPlan = plans.First(p => p.Id == PaymentPlan.GetId(request.NewPlanId));

            if (newPlan.IsFreeTier)
            {
                chargifyConnect.DeleteSubscription(organisation.Subscription.ChargifyId.Value, "Downgrade");
                organisation.Subscription.ChargifyId = null;
                organisation.Subscription.Status     = SubscriptionStatus.Trial;
            }
            else
            {
                subscription = chargifyConnect.EditSubscriptionProduct(organisation.Subscription.ChargifyId.Value, request.NewPlanName.ToLowerInvariant());
                organisation.Subscription.ChargifyId = subscription.SubscriptionID;
                organisation.Subscription.Status     = SubscriptionStatus.Active;
            }

            organisation.PaymentPlanId             = PaymentPlan.GetId(request.NewPlanId);
            organisation.PaymentPlan               = newPlan;
            organisation.Subscription.LastModified = DateTime.UtcNow.ToDateTimeOffset(organisation.TimezoneId);

            //if status is quotas exceeded, check again and update if necessary
            if (organisation.Status == OrganisationStatus.PlanQuotaExceeded)
            {
                var quotas = PlanQuotas.FromStats(stats, newPlan);

                if (quotas.IssuesExceededBy <= 0)
                {
                    organisation.Status = OrganisationStatus.Active;
                }
            }

            Session.SynchroniseIndexes <Indexing.Organisations, Indexing.Users>();
            Session.AddCommitAction(new SendMessageCommitAction(
                                        new SubsciptionChangedEmailInfo
            {
                OrganisationName     = organisation.Name,
                SubscriptionId       = subscription.SubscriptionID.ToString(),
                UserName             = request.CurrentUser.FirstName,
                BillingAmount        = string.Format(CultureInfo.GetCultureInfo(1033), "{0:C}", newPlan.Price),
                BillingPeriodEndDate = organisation.Subscription.CurrentPeriodEndDate.ToLocalFormatted(),
                OldPlanName          = request.OldPlanName,
                NewPlanName          = newPlan.Name
            },
                                        _configuration.GetNotificationsQueueAddress(organisation.RavenInstanceId)));

            return(new ChangeSubscriptionResponse(organisation.Id, request.CurrentUser.Email)
            {
                Status = ChangeSubscriptionStatus.Ok
            });
        }