AuthorizeNet / sdk-ruby

Ruby SDK for the Authorize.Net API
Other
87 stars 111 forks source link

Invalid child element 'merchantAuthentication' #191

Open kevinvangelder opened 4 months ago

kevinvangelder commented 4 months ago

I have closely followed the example code and documentation, but no matter whether or not I explicitly include a merchantAuthentication element in my request it always fails with this error:

The element 'ARBCreateSubscriptionRequest' in namespace 'AnetApi/xml/v1/schema/AnetApiSchema.xsd' 
has invalid child element 'merchantAuthentication' in namespace 'AnetApi/xml/v1/schema/AnetApiSchema.xsd'. 
List of possible elements expected: 'refId, subscription' in namespace 'AnetApi/xml/v1/schema/AnetApiSchema.xsd'.

Here's my code:

require 'authorizenet'

include AuthorizeNet::API

class PaymentGateway
  def initialize
    @transaction = AuthorizeNet::API::Transaction.new(ENV["AUTHORIZE_LOGIN"], ENV["AUTHORIZE_KEY"], {gateway: :production})
  end

  def tokenize_card(user, card)
    creditCard = CreditCardType.new(
      cardNumber: card[:number],
      expirationDate: card[:expiration],
      cardCode: card[:code],
    )

    billTo = CustomerAddressType.new(
      firstName: user.first_name,
      lastName: user.last_name,
    )

    payment = PaymentType.new(creditCard)
    paymentProfile = CustomerPaymentProfileType.new(
      billTo: billTo,
      payment: payment,
    )

    profile = CustomerProfileType.new(
      merchantCustomerId: user.id,
      description: user.username,
      email: user.email,
      paymentProfiles: [paymentProfile],
      profileType: CustomerProfileTypeEnum.new("individual"),
    )

    merchantAuth = MerchantAuthenticationType.new(ENV["AUTHORIZE_LOGIN"], ENV["AUTHORIZE_KEY"])

    request = CreateCustomerProfileRequest.new(
      profile: profile,
      validationMode: ValidationModeEnum::LiveMode,
    )

    response = @transaction.create_customer_profile(request)
    if response != nil
      if response.messages.resultCode == MessageTypeEnum::Ok
        return response.customerPaymentProfileId
      else
        return response.messages
      end
    end
  end

  def create_subscription(user, card, selected_subscription)
    start_date = (user.membership_expires_at && user.membership_expires_at > DateTime.now ? user.membership_expires_at : DateTime.now).to_s[0..10]
    subscription = ARBSubscriptionType.new(
      name: selected_subscription[:title],
      paymentSchedule: PaymentScheduleType.new(
        interval: PaymentScheduleType::Interval.new(selected_subscription[:duration], "months"),
        startDate: start_date,
      ),
      amount: selected_subscription[:price][1..].to_f,
      payment: PaymentType.new(CreditCardType.new(
        cardNumber: card[:number],
        expirationDate: card[:expiration],
        cardCode: card[:code],
      )),
      billTo: NameAndAddressType.new(
        firstName: user.first_name,
        lastName: user.last_name,
      ),
    )
    request = ARBCreateSubscriptionRequest.new(
      merchantAuthentication: MerchantAuthenticationType.new(
        name: ENV["AUTHORIZE_LOGIN"],
        transactionKey: ENV["AUTHORIZE_KEY"],
      ),
      refId: '',
      subscription: subscription,
    )

    response = @transaction.create_subscription(request)

    if response != nil
      if response.messages.resultCode == MessageTypeEnum::Ok
        return response.subscriptionId
      else
        return response.messages
      end
    end
  end
end

You'll note the tokenize_card method does not include the merchantAuthentication key and the create_subscription method does, but both return the exact same error other than the request namespace and expected elements. The code samples and documentation make zero mention of the merchantAuthentication key, which makes be believe that it's likely being handled internally by the API::Transaction object, but the error makes me believe it must be doing something incorrectly. I called support and all they could do was point me back to the documentation which holds no answers for this problem.