2011-05-24 16 views
5

Estoy trabajando en una plataforma de donaciones sin fines de lucro y estoy utilizando MVC por primera vez. Ya lo entendí la mayor parte, pero ahora tengo un problema que no sé cómo abordar. Estoy usando la clase AthorizeNet.Helpers y cuando agrego el código de las expansiones, funciona en su mayor parte, excepto que toma el formulario y lo pone por encima de la etiqueta, sin embargo, pone los campos del formulario en el lugar correcto. Estoy tratando de encontrar la forma de renderizar la etiqueta en el lugar correcto.Problemas de MVC HtmlHelpers con Razor

@using AuthorizeNet.Helpers; 

@using (Html.BeginSIMForm("http://127.0.0.1:4768", 1.99M, "xxx_key", "yyy_key", true)) 
{ 
    @Html.Raw(Html.CheckoutFormInputs(true)) 
    @Html.Hidden("order_id", "1234") 
    <input type = "submit" value = "Pay" /> 
} 

Así es como se ve en la salida HTML:

<form action = 'https://test.authorize.net/gateway/transact.dll' method = 'post'> 
    <input type = 'hidden' name = 'x_fp_hash' value = '6bef386eaa89944efd62b47b86042910' \> 
    <input type = 'hidden' name = 'x_fp_sequence' value = '117'\> 
    <input type = 'hidden' name = 'x_fp_timestamp' value = 'xxx_key' \> 
    <input type = 'hidden' name = 'x_login' value = 'yyy_key' \> 
    <input type = 'hidden' name = 'x_amount' value = '1.99' \> 
    <input type = 'hidden' name = 'x_relay_url' value = 'http://127.0.0.1:4768' \> 
    <input type = 'hidden' name = 'x_relay_response' value = 'TRUE' \> 
</form><!DOCTYPE html> 
<html> 
<body> 
<h2>Payment Information</h2> 
       <div style = 'border: 1px solid #990000; padding:12px; margin-bottom:24px; background-color:#ffffcc;width:300px'>Test Mode</div> 
       <div style = 'float:left;width:250px;'> 
        <label>Credit Card Number</label> 
        <div id = 'CreditCardNumber'> 
         <input type = 'text' size = '28' name = 'x_card_num' value = '4111111111111111' id = 'x_card_num'/> 
        </div> 
       </div> 
       <div style = 'float:left;width:70px;'> 
        <label>Exp.</label> 
        <div id = 'CreditCardExpiration'> 
         <input type = 'text' size = '5' maxlength = '5' name = 'x_exp_date' value = '0116' id = 'x_exp_date'/> 
        </div> 
       </div> 
       <div style = 'float:left;width:70px;'> 
        <label>CCV</label> 
        <div id = 'CCV'> 
         <input type = 'text' size = '5' maxlength = '5' name = 'x_card_code' id = 'x_card_code' value = '123' /> 
        </div> 
       </div><input id="order_id" name="order_id" type="hidden" value="1234" />  <input type = "submit" value = "Pay" /> 

Respuesta

5

Este tipo de problema generalmente ocurre cuando un ayudante que está escribiendo directamente en el flujo de salida fue escrito para ASP.NET MVC 1 (y los ayudantes que están incluidos están escribiendo directamente en el flujo de salida la mayor parte del tiempo). En ASP.NET MVC 1 se podría escribir a flujo de salida mediante el uso de esto:

htmlHelper.ViewContext.HttpContext.Response.Output 

en adelante versión de ASP.NET MVC usted debe utilizar esto:

htmlHelper.ViewContext.Writer 

Eso asegura la compatibilidad de afeitar. Si tiene acceso al código fuente de AuthorizeNet.Helpers, puede solucionarlo usted mismo, si no lo hace debe contactar a los autores para solucionarlo.

1

Es posible que el ayudante de AuthorizeNet no está escrita correctamente para trabajar con la maquinilla de afeitar. Sin realmente mirar la fuente de su montaje es difícil decir si ese es el caso. Es posible que desee tratar de ponerse en contacto con su servicio de atención al cliente.

12

Así es como lo arreglé.

como ha afirmado, añada @ Html.Raw() alrededor Html.CheckoutFormInputs (verdadero)

El otro cambio que tomar es en

namespace AuthorizeNet.Helpers -> CheckoutFormBuilders.cs 

añadir un uso de

using System.IO; 

Cambiar

HttpResponseBase to TextWriter 

Hice esto en tres puntos.

HttpResponseBase _response; to TextWriter _response; 

public SIMForm(TextWriter response, string returnUrl, decimal amount, 
       string apiLogin, string transactionKey) 
       :this(response,returnUrl,amount,apiLogin,transactionKey,true){} 

public SIMForm(TextWriter response, string returnUrl, decimal amount, 
       string apiLogin, string transactionKey, bool isTest) { 
     _response = response; 
     _amount = amount; 
     _apiLogin = apiLogin; 
     _transactionkey = transactionKey; 
     _returnUrl = returnUrl; 
     _isTest = isTest; 
     OpenForm(); 
} 

Dos cambios más a la izquierda

Como se indica en tpeczek respuesta, es necesario cambiar

helper.ViewContext.HttpContext.Response 

a

helper.ViewContext.Writer 

Esto se verá como

public static SIMForm BeginSIMForm(this HtmlHelper helper, string returnUrl, 
           decimal amount, string apiLogin, 
           string transactionKey) { 

return new SIMForm(helper.ViewContext.Writer, 
        returnUrl,amount,apiLogin, 
        transactionKey,true);} 

public static SIMForm BeginSIMForm(this HtmlHelper helper, string returnUrl, 
           decimal amount, string apiLogin, 
           string transactionKey, bool isTest) { 

return new SIMForm(helper.ViewContext.Writer, 
        returnUrl, amount, apiLogin, 
        transactionKey,isTest);} 
1

Usando el ejemplo de EpicThreeDev anterior, pude obtener el formulario html para que aparezca correctamente. Sin embargo, el botón Pagar se yuxtapuso sobre el campo ccv, por lo tanto, para corregirlo en el Índice.cshtml base de código que cambia el código HTML para

     <br />       
    <input type = "submit" value = "Pay" style="position:relative; top:35px;" />  

vez que hice que yo era capaz de enviar el formulario, sin embargo después de hacer eso me dieron el error que se abordó en el puesto.

http://community.developer.authorize.net/t5/Integration-and-Testing/Having-Trouble-setting-up-MVC3-application-with-DPM/m-p/13226

0

aquí está mi solución. Simplemente imprime los campos ocultos de Authorize.net, por lo que puede escribir su propia etiqueta de formulario. Complete su web.config con los valores de AppSettings relevantes. De esta manera, puede cambiar fácilmente entre desarrollo y producción.

public static class MyAuthNetHelper 
{ 
    public const string TEST_URL = "https://test.authorize.net/gateway/transact.dll"; 
    public const string LIVE_URL = "https://secure.authorize.net/gateway/transact.dll"; 

    public static string ApiLogin 
    { 
     get { return ConfigurationManager.AppSettings["AuthNetAPILogin"]; } 
    } 

    public static string TransactionKey 
    { 
     get { return ConfigurationManager.AppSettings["AuthNetAPITransactionKey"]; } 
    } 

    public static string ReturnUrl 
    { 
     get { return ConfigurationManager.AppSettings["AuthNetReturnUrl"]; } 
    } 

    public static string ThanksUrl 
    { 
     get { return ConfigurationManager.AppSettings["AuthNetThanksUrl"]; } 
    } 

    public static bool TestMode 
    { 
     get { return bool.Parse(ConfigurationManager.AppSettings["AuthNetTestMode"]); } 
    } 

    public static string GatewayUrl 
    { 
     get { return TestMode ? TEST_URL : LIVE_URL; } 
    } 

    public static MvcHtmlString AuthNetDirectPostFields(this HtmlHelper helper, decimal amount) 
    { 

     var seq = Crypto.GenerateSequence(); 
     var stamp = Crypto.GenerateTimestamp(); 

     var fingerPrint = Crypto.GenerateFingerprint(TransactionKey, 
      ApiLogin, amount, seq.ToString(), stamp.ToString()); 

     var str = new StringBuilder(); 

     str.Append(helper.Hidden("x_fp_hash", fingerPrint)); 
     str.Append(helper.Hidden("x_fp_sequence", seq)); 
     str.Append(helper.Hidden("x_fp_timestamp", stamp)); 
     str.Append(helper.Hidden("x_login", ApiLogin)); 
     str.Append(helper.Hidden("x_amount", amount)); 
     str.Append(helper.Hidden("x_relay_url", ReturnUrl)); 
     str.Append(helper.Hidden("x_relay_response", "TRUE")); 

     return MvcHtmlString.Create(str.ToString()); 
    } 
} 

cshtml:

<form id="paymentForm" method="POST" action="@MyAuthNetHelper.GatewayUrl" class="form-horizontal offset1"> 
@Html.AuthNetDirectPostFields(PutYourAmountHere) 
... 
</form> 

ThanksUrl se utiliza en su acción para manejar la respuesta de Authorize.net. Verifique esto para obtener más información: http://developer.authorize.net/integration/fifteenminutes/csharp/