/// <summary> /// Place the order with data collected in the provided <see cref="Atomia.Store.Core.OrderContext"/>. /// </summary> /// <param name="orderContext">Context with cart, contact and other relevant data.</param> /// <returns>The results of placing the order</returns> public OrderResult PlaceOrder(OrderContext orderContext) { var publicOrderContext = new PublicOrderContext(orderContext); // Add some extra data that might be needed by order handlers. foreach (var cartItem in orderContext.Cart.CartItems) { var product = productProvider.GetProduct(cartItem.ArticleNumber); var renewalPeriodId = renewalPeriodProvider.GetRenewalPeriodId(cartItem); publicOrderContext.AddItemData(new ItemData(cartItem, product, renewalPeriodId)); } var paymentHandler = paymentDataHandlers.FirstOrDefault(h => h.Id == orderContext.PaymentData.Id); if (paymentHandler == null) { throw new InvalidOperationException(String.Format("Payment data handler is not available for {0}.", orderContext.PaymentData.Id)); } var createdOrder = orderCreator.CreateOrder(publicOrderContext, paymentHandler); var redirectUrl = urlProvider.SuccessUrl; if (paymentHandler.PaymentMethodType == PaymentMethodEnum.PayByCard && createdOrder.Total > Decimal.Zero) { redirectUrl = paymentTransactionCreator.CreatePaymentTransaction(publicOrderContext, createdOrder, paymentHandler); } return new OrderResult { RedirectUrl = redirectUrl }; }
protected PublicOrder PrepareOrder(PublicOrderContext publicOrderContext, PaymentDataHandler paymentHandler) { var newOrder = new PublicOrder() { OrderItems = new PublicOrderItem[0], CustomData = new PublicOrderCustomData[0] }; foreach (var handler in orderDataHandlers) { newOrder = handler.AmendOrder(newOrder, publicOrderContext); if (newOrder == null) { throw new InvalidOperationException("OrderDataHandler must return a non-null order from AmendOrder."); } } newOrder.PaymentMethod = paymentHandler.PaymentMethodType; // Only run the selected payment handler. newOrder = paymentHandler.AmendOrder(newOrder, publicOrderContext.PaymentData); if (newOrder == null) { throw new InvalidOperationException("PaymentDataHandler must return a non-null order from AmendOrder."); } return newOrder; }
/// <summary> /// Set order reseller id from current reseller /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var resellerId = resellerProvider.GetReseller().Id; order.ResellerId = resellerId; return order; }
/// <summary> /// Set order currency from customer's currency preference /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var currency = currencyPreferenceProvider.GetCurrentCurrency(); order.Currency = currency.Code; return order; }
/// <summary> /// Amends order based on how subclass overrides virtual methods /// </summary> public sealed override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var domainItems = orderContext.ItemData.Where(i => this.HandledCategories.Intersect(i.Categories.Select(c => c.Name)).Count() > 0); foreach (var domainItem in domainItems) { var customData = new List<PublicOrderItemProperty>(); var domainName = GetDomainName(domainItem); var connectedItem = GetConnectedItem(orderContext.ItemData, domainItem, domainName); customData.Add(new PublicOrderItemProperty { Name = "DomainName", Value = domainName }); if (connectedItem != null) { var atomiaService = GetAtomiaService(connectedItem); customData.Add(new PublicOrderItemProperty { Name = "AtomiaService", Value = atomiaService }); var extraProperties = GetAtomiaServiceExtraProperties(domainItem); if (!String.IsNullOrEmpty(extraProperties)) { customData.Add(new PublicOrderItemProperty { Name = "AtomiaServiceExtraProperties", Value = extraProperties }); } } else { customData.Add(new PublicOrderItemProperty { Name = "AtomiaService", Value = DefaultAtomiaService }); } var domainRegContactProvider = new DomainRegContactProvider(orderContext); if (!string.IsNullOrEmpty(domainRegContactProvider.DomainRegContactData)) { customData.Add(new PublicOrderItemProperty { Name = "DomainRegContact", Value = domainRegContactProvider.DomainRegContactData }); } foreach(var extraData in GetExtraCustomData(domainItem)) { customData.Add(extraData); } var orderItem = new PublicOrderItem { ItemId = Guid.Empty, ItemNumber = domainItem.ArticleNumber, Quantity = 1, RenewalPeriodId = domainItem.RenewalPeriodId, CustomData = customData.ToArray() }; Add(order, orderItem); } return order; }
/// <summary> /// Create PublicPaymentTransaction and call MakePayment in Atomia Billing Public Service. /// </summary> /// <param name="publicOrderContext">Order data</param> /// <param name="order">The order object returned from CreateOrder call in Atomia Billing Public Service</param> /// <param name="paymentHandler">Handler for customer's selected payment method</param> /// <returns>URL to redirect to for finishing or seeing result of payment transaction.</returns> public string CreatePaymentTransaction(PublicOrderContext publicOrderContext, PublicOrder order, PaymentDataHandler paymentHandler) { var paymentTransaction = new PublicPaymentTransaction { GuiPluginName = paymentHandler.Id, Attributes = new AttributeData[0], CurrencyCode = order.Currency, TransactionReference = order.Number, Amount = order.Total }; paymentTransaction = paymentHandler.AmendPaymentTransaction(paymentTransaction, publicOrderContext.PaymentData); if (paymentTransaction == null) { throw new InvalidOperationException("PaymentDataHandler must return a non-null payment transaction from AmendTransaction."); } foreach (var handler in transactionDataHandlers) { paymentTransaction = handler.AmendPaymentTransaction(paymentTransaction, publicOrderContext); if (paymentTransaction == null) { throw new InvalidOperationException("ExtraTransactionDataHandlers must return a non-null payment transaction from AmendTransaction."); } } PublicPaymentTransaction createdTransaction; try { createdTransaction = BillingApi.MakePayment(paymentTransaction); } catch (SoapException ex) { logger.LogException(ex, "MakePayment failed."); return urlProvider.FailureUrl; } if (createdTransaction.Status.ToUpper() == "IN_PROGRESS" && !string.IsNullOrEmpty(createdTransaction.RedirectUrl)) { return createdTransaction.RedirectUrl; } else if (createdTransaction.Status.ToUpper() == "OK") { return urlProvider.SuccessUrl; } else if (createdTransaction.Status.ToUpper() == "FRAUD_DETECTED" || createdTransaction.Status.ToUpper() == "FAILED") { return urlProvider.FailureUrl; } else { return createdTransaction.ReturnUrl; } }
public DomainRegContactProvider(PublicOrderContext orderContext) { if (orderContext == null) { throw new ArgumentNullException("orderContext"); } var whoisContact = orderContext.ContactData.OfType<WhoisContactModel>().FirstOrDefault(); // No separate WHOIS contact added by customer. if (whoisContact == null || String.IsNullOrEmpty(whoisContact.Email)) { _domainRegContactData = ""; } else { var phone = FormattingHelper.FormatPhoneNumber(whoisContact.Phone, whoisContact.Country); var fax = FormattingHelper.FormatPhoneNumber(whoisContact.Fax, whoisContact.Country); string org = ""; string orgNo = ""; string vatNo = ""; if (whoisContact.CompanyInfo != null && !string.IsNullOrEmpty(whoisContact.CompanyInfo.CompanyName)) { org = whoisContact.CompanyInfo.CompanyName; orgNo = whoisContact.CompanyInfo.IdentityNumber; vatNo = whoisContact.CompanyInfo.VatNumber; } else { orgNo = whoisContact.IndividualInfo.IdentityNumber; } var domainRegContact = new DomainRegContact { City = OrderDataHandler.NormalizeData(whoisContact.City), Country = OrderDataHandler.NormalizeData(whoisContact.Country), Email = OrderDataHandler.NormalizeData(whoisContact.Email), Fax = OrderDataHandler.NormalizeData(fax), Name = OrderDataHandler.NormalizeData(whoisContact.FirstName) + " " + OrderDataHandler.NormalizeData(whoisContact.LastName), Org = OrderDataHandler.NormalizeData(org), OrgNo = OrderDataHandler.NormalizeData(orgNo), Street1 = OrderDataHandler.NormalizeData(whoisContact.Address), Street2 = OrderDataHandler.NormalizeData(whoisContact.Address2), VatNo = OrderDataHandler.NormalizeData(vatNo), Voice = OrderDataHandler.NormalizeData(phone), Zip = OrderDataHandler.NormalizeData(whoisContact.Zip) }; _domainRegContactData = new JavaScriptSerializer().Serialize(domainRegContact); } }
/// <summary> /// Amend order with "Language" custom attribute from customer's language preference. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var language = languagePreferenceProvider.GetCurrentLanguage(); Add(order, new PublicOrderCustomData { Name = "Language", Value = language.Tag }); return order; }
/// <summary> /// Amend order with "CampaignCode" custom attribute /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { if (!String.IsNullOrEmpty(orderContext.Cart.CampaignCode)) { Add(order, new PublicOrderCustomData { Name = "CampaignCode", Value = orderContext.Cart.CampaignCode }); } return order; }
/// <summary> /// Remove invalid VAT number from order. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { if (!string.IsNullOrEmpty(order.LegalNumber)) { var validationResult = vatNumberValidator.ValidateCustomerVatNumber(); if (!validationResult.Valid) { order.LegalNumber = String.Empty; } } return order; }
/// <summary> /// Amend order with custom attributes from cart /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { if (orderContext.Cart.CustomAttributes != null) { foreach (var attr in orderContext.Cart.CustomAttributes) { Add(order, new PublicOrderCustomData { Name = attr.Name, Value = attr.Value }); } } return order; }
/// <summary> /// Amend payment transaction with all request headers as custom attributes. /// </summary> public override PublicPaymentTransaction AmendPaymentTransaction(PublicPaymentTransaction paymentTransaction, PublicOrderContext orderContext) { var attributes = new List<AttributeData>(paymentTransaction.Attributes); var request = orderContext.ExtraData.OfType<HttpRequestBase>().FirstOrDefault(); if (request != null) { foreach (var key in GuiPaymentPluginRequestHelper.RequestToCustomAttributes(request)) { attributes.Add(new AttributeData { Name = key.Key, Value = key.Value }); } } paymentTransaction.Attributes = attributes.ToArray(); return paymentTransaction; }
/// <summary> /// Amend order with any items that have not been added to order yet. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var unprocessedItems = orderContext.ItemData.Where(i => !OrderItemsContain(order, i)); foreach (var item in unprocessedItems) { Add(order, new PublicOrderItem { ItemId = Guid.Empty, ItemNumber = item.ArticleNumber, RenewalPeriodId = item.RenewalPeriodId, Quantity = item.Quantity }); } return order; }
/// <summary> /// Add any setup fees to order /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var setupFeeItems = orderContext.ItemData.Where(i => this.HandledCategories.Intersect(i.Categories.Select(c => c.Name)).Count() > 0); foreach (var item in setupFeeItems) { Add(order, new PublicOrderItem { ItemId = Guid.Empty, ItemNumber = item.ArticleNumber, RenewalPeriodId = item.RenewalPeriodId, Quantity = 1 }); } return order; }
/// <summary> /// Create PublicOrder and call CreateOrder in Atomia Billing Public Service. /// </summary> /// <param name="publicOrderContext">Order data</param> /// <param name="paymentHandler">Handler for customer's selected payment method</param> /// <returns>The order object returned from Atomia Billing Public Service</returns> public override PublicOrder CreateOrder(PublicOrderContext publicOrderContext, PaymentDataHandler paymentHandler) { var newOrder = PrepareOrder(publicOrderContext, paymentHandler); var createdOrder = BillingApi.CreateOrder(newOrder); if (createdOrder == null) { throw new InvalidOperationException("Order could not be created."); } if (this.auditLogger != null) { this.auditLogger.Log(AuditActionTypes.OrderCreated, string.Empty, createdOrder.CustomerId.ToString(), createdOrder.Email, createdOrder.Id.ToString(), null); } return createdOrder; }
/// <summary> /// Remove any item with category "PostOrder" from order items. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var postOrderItems = orderContext.ItemData.Where(i => this.HandledCategories.Intersect(i.Categories.Select(c => c.Name)).Count() > 0); var orderItems = new List<PublicOrderItem>(order.OrderItems); foreach (var postOrderItem in postOrderItems) { var existingItem = ExistingOrderItem(order, postOrderItem); if (existingItem != null) { orderItems.Remove(existingItem); } } order.OrderItems = orderItems.ToArray(); return order; }
/// <summary> /// Amend order with billing contact data collected from customer, falling back to collected main contact data. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var billingContact = orderContext.ContactData.OfType<BillingContactModel>().First(); // Email is a required field on BillingContactModel, // so if it is not present it means no separate billing contact was provided. if (String.IsNullOrWhiteSpace(billingContact.Email)) { var mainContact = orderContext.ContactData.OfType<MainContactModel>().First(); AddContactData(order, mainContact); } else { AddContactData(order, billingContact); } return order; }
/// <summary> /// Amend payment transaction with payment profile attributes /// </summary> public override PublicPaymentTransaction AmendPaymentTransaction(PublicPaymentTransaction paymentTransaction, PublicOrderContext orderContext) { var paymentData = orderContext.PaymentData; if (paymentData.SaveCcInfo) { var attributes = new List<AttributeData>(paymentTransaction.Attributes); attributes.Add(new AttributeData { Name = "cc_saveccinfo", Value = "true" }); if (paymentData.AutoPay) { attributes.Add(new AttributeData { Name = "cc_autopay", Value = "true" }); } paymentTransaction.Attributes = attributes.ToArray(); } return paymentTransaction; }
/// <summary> /// Amend order with main contact data collected from customer. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var mainContact = orderContext.ContactData.OfType<MainContactModel>().First(); order.Email = Normalize(mainContact.Email); order.FirstName = Normalize(mainContact.FirstName); order.LastName = Normalize(mainContact.LastName); order.Address = Normalize(mainContact.Address); order.Address2 = Normalize(mainContact.Address2); order.Zip = Normalize(mainContact.Zip); order.City = Normalize(mainContact.City); order.Country = Normalize(mainContact.Country); var fax = FormattingHelper.FormatPhoneNumber(mainContact.Fax, mainContact.Country); order.Fax = Normalize(fax); var phone = FormattingHelper.FormatPhoneNumber(mainContact.Phone, mainContact.Country); order.Phone = Normalize(phone); if (mainContact.CustomerType == "individual" && mainContact.IndividualInfo != null) { order.CompanyNumber = Normalize(mainContact.IndividualInfo.IdentityNumber); } else if (mainContact.CustomerType == "company" && mainContact.CompanyInfo != null) { order.Company = Normalize(mainContact.CompanyInfo.CompanyName); order.CompanyNumber = Normalize(mainContact.CompanyInfo.IdentityNumber); order.LegalNumber = Normalize(mainContact.CompanyInfo.VatNumber); } if (AtomiaCommon.Instance.SeparateUsernameAndEmail) { var customAttributes = new List<PublicOrderCustomData>(order.CustomData); customAttributes.Add(new PublicOrderCustomData { Name = "Username", Value = Normalize(mainContact.Username) }); order.CustomData = customAttributes.ToArray(); } return order; }
/// <summary> /// Amend order with "IpAddress" custom attribute for IP the order was placed from. /// </summary> public override PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext) { var request = orderContext.ExtraData.OfType<HttpRequestBase>().FirstOrDefault(); if (request != null) { var ip = request.ServerVariables["HTTP_X_FORWARDED_FOR"]; if (!String.IsNullOrEmpty(ip)) { var ipRange = ip.Split(','); var trueIp = ipRange[0]; Add(order, new PublicOrderCustomData { Name = "IpAddress", Value = trueIp }); } else { ip = request.ServerVariables["REMOTE_ADDR"]; Add(order, new PublicOrderCustomData { Name = "IpAddress", Value = ip }); } } return order; }
/// <summary> /// Amend order with data from context /// </summary> /// <param name="order">The order to amend</param> /// <param name="orderContext">The order data</param> /// <returns>The amended order</returns> public abstract PublicOrder AmendOrder(PublicOrder order, PublicOrderContext orderContext);
/// <summary> /// Amend payment transaction with order data. /// </summary> /// <param name="paymentTransaction">The payment transaction to amend</param> /// <param name="orderContext">The order data</param> /// <returns>The amended transaction</returns> public abstract PublicPaymentTransaction AmendPaymentTransaction(PublicPaymentTransaction paymentTransaction, PublicOrderContext orderContext);
public abstract PublicOrder CreateOrder(PublicOrderContext publicOrderContext, PaymentDataHandler paymentHandler);
public override PublicOrder CreateOrder(PublicOrderContext publicOrderContext, PaymentDataHandler paymentHandler) { var newOrder = this.PrepareOrder(publicOrderContext, paymentHandler); this.AddCustomAttributes(newOrder); string token = string.Empty; var resellerRootDomain = this.GetResellerRootDomain(); var createdOrder = BillingApi.CreateOrderWithLoginToken(newOrder, resellerRootDomain, out token); if (createdOrder == null) { throw new InvalidOperationException("Order could not be created."); } urlProvider.SuccessUrl = GetTokenLoginUrl(createdOrder.Email, token); return createdOrder; }