2015-04-27 12 views
8

Sollte ich die CreditCardAttribute von Microsoft verwenden, um Kreditkartennummern so zu validieren?Sollte ich das CreditCardAttribute verwenden, um Kreditkartennummern zu validieren?

[Required, CreditCard] 
public string CreditCardNumber { get; set; } 

Oder sollte ich das Zahlungs-Gateway damit umgehen lassen, oder etwas anderes tun? Ich frage dies nach der Entdeckung einige Kunden waren nicht in der Lage, Zahlung mit ihren Kreditkarteninformationen vorzulegen. Glücklicherweise konnte ich mit einem dieser Kunden zusammenarbeiten und stellte fest, dass die Visa-Karte nach dem Entfernen der CreditCardAttribute problemlos verarbeitet wurde. Diese Frage ist zum Teil rhetorisch, aber ich würde gerne von den Gedanken und Erfahrungen anderer Entwickler profitieren und andere Entwickler auf die Risiken der Verwendung des CreditCardAttribute aufmerksam machen, indem ich die Frage stelle.

+0

Ein Link zu Die Dokumentation des betreffenden Attributs wäre sehr hilfreich. –

+0

@OndrejTucny [Hier gehts] (https://msdn.microsoft.com/en-us/library/system.componentmodel.dataannotations.creditcardattribute%28v=vs.110%29.aspx). Die schnelle Google-Suche ist ein langer Weg. –

+1

[Diese Frage] (http://stackoverflow.com/q/12580450/3199927) gibt einen Einblick, wie das "CreditCardAttribute" Eingaben validiert. – Tom

Antwort

3

Ich denke, der beste Weg, dies herauszufinden, ist es einfach zu testen:

using System; 
using System.Linq; 
using System.Text; 
using System.IO; 

namespace SO 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      string[] cards = new string[] { 
       //http://www.paypalobjects.com/en_US/vhelp/paypalmanager_help/credit_card_numbers.htm 
       "378282246310005", // American Express 
       "4012888888881881", // Visa 
       "6011111111111117", // Discover 
       "4222222222222", // Visa 
       "76009244561", // Dankort (PBS) 
       "5019717010103742", // Dakort (PBS) 
       "6331101999990016", // Switch/Solo (Paymentech) 
       "30569309025904", // Diners Club 
       //http://www.getcreditcardnumbers.com/ 
       "5147004213414803", // Mastercard 
       "6011491706918120", // Discover 
       "379616680189541", // American Express 
       "4916111026621797", // Visa 
      }; 

      foreach (string card in cards) 
      { 
       Console.WriteLine(IsValid(card)); 
      } 

      Console.ReadLine(); 
     } 

     public static bool IsValid(object value) 
     { 
      if (value == null) 
      { 
       return true; 
      } 

      string ccValue = value as string; 
      if (ccValue == null) 
      { 
       return false; 
      } 
      ccValue = ccValue.Replace("-", ""); 
      ccValue = ccValue.Replace(" ", ""); 

      int checksum = 0; 
      bool evenDigit = false; 

      // http://www.beachnet.com/~hstiles/cardtype.html 
      foreach (char digit in ccValue.Reverse()) 
      { 
       if (digit < '0' || digit > '9') 
       { 
        return false; 
       } 

       int digitValue = (digit - '0') * (evenDigit ? 2 : 1); 
       evenDigit = !evenDigit; 

       while (digitValue > 0) 
       { 
        checksum += digitValue % 10; 
        digitValue /= 10; 
       } 
      } 

      return (checksum % 10) == 0; 
     } 
    } 
} 

Die IsValid Verfahren aus der ursprünglichen C# CreditCardAttribute Klasse ist. 1 aus den 12 Zahlen fehlgeschlagen:

 True 
     True 
     True 
     True 
     False //"76009244561", // Dankort (PBS) 
     True 
     True 
     True 
     True 
     True 
     True 
     True 

Also, sollten Sie es verwenden? Nein, offensichtlich erkennt es nicht alle Nummern. Obwohl Sie ihren Code nehmen und verbessern können!

+0

Sehr schönes Problem! Ich wünschte, es würde mir das Vertrauen geben, eine "verbesserte" Validierung zu verwenden. Leider scheint es genau zu zeigen, was ich fürchte. Die Liste der Kreditkartennummern scheint unvollständig zu sein, da mir gesagt wurde, dass es sich um eine Visa-Karte handelt. Ich habe erwartet, dass einer der Scheitern Visa ist. Der Kunde mag sich geirrt haben, aber ich bezweifle das. Es scheint mir immer noch, dass die Verwendung einer Kreditkartenvalidierung auf diese Weise riskant ist, selbst wenn Sie eine Menge gefälschter Kreditkartennummern zum Testen haben. Immerhin könnte Visa morgen neue Zahlen herausgeben, dass meine benutzerdefinierte, völlig aktuelle Validierung fehlschlagen könnte. –

+0

In der Tat wurde dies bereits mehrfach im Internet diskutiert, die Verwendung des Luhn-Algorithmus deckt nicht alle existierenden Kreditkarten ab. Ich denke, der einzige Weg, 100% sicher zu sein, besteht darin, es zu validieren, indem Sie die Transaktion tatsächlich ausführen. –

+0

Wenn ich das gesagt habe, wenn ich gezwungen war, aus irgendeinem Grund in meinem Code zu validieren, dann ist es definitiv der richtige Weg einen Einheitentest zu machen. Zusätzlich würde ich Logging wollen (nicht die Kreditkartennummern!), Aber die Anzahl der Validierungen scheitert, so dass ich vielleicht in Betracht ziehen kann, ob mein Validator falsche Negative produziert. –

1

In der code hinter der Kreditkarte attribute, es ist einfach eine Luhn Prüfung durchzuführen.

Alle Zahlungskarten (*) folgen derzeit dem Standard ISO/IEC/7812, der als letzte Ziffer eine Prüfziffer hat.

Dieser luhn-Check wird lediglich verwendet, um Transpositionsfehler zu vermeiden. Es ist nützlich, um eine Plausibilitätsprüfung durchzuführen, bevor Kartennummern an ein Zahlungs-Gateway gesendet werden, aber nicht geeignet, um absolut zu überprüfen, ob eine Nummer eine gültige Kartennummer ist.

Gültige Kartennummernbereiche ändern sich monatlich, und die einzige Möglichkeit, eine Nummer absolut zu verifizieren, besteht darin, sie über ein Zahlungsgateway zu validieren. Wenn nur versucht wird, eine Karte zu validieren (anstatt sie zu laden), sollte dies mit einer Null-Wert-Prüfung nur für Autorisierung getan werden.

(*) Die einzige Ausnahme ist ein Kartentyp in China bekannt als China UnionPay
(historisch ein Diner Club gibt es auch 'enRoute' Marke, die im Jahr 1992 zurückgezogen wurde)

+0

Würden Sie einige Beweise liefern, die Ihre Behauptung unterstützen, dass "alle Zahlungskarten derzeit dem Luhn-Algorithmus folgen"? Es scheint entweder Microsoft hat einen einfachen und gut bekannten Algorithmus falsch implementiert, oder Ihre Behauptung ist falsch. –

+1

Es ist nichts falsch mit der Implementierung von Microsoft. Es ist ein gültiger Luhn-Check-Algorithmus. Wenn Sie jedoch ungültige Testdaten eingeben, erhalten Sie ein ungültiges Testergebnis. Wie erwartet. Der letzte verbleibende Test, den Sie nicht bestanden haben, ist eine 11-stellige Zahl. Dies ist zu kurz für eine gültige Kartennummer, die * in der Regel * mindestens 16 Ziffern lang ist. (Format ist normalerweise eine 6-stellige IIN, letzte Ziffer als Prüfziffer, Rest als eindeutige Kontonummer). Dies würde bedeuten, dass die Dankort-Karte nur 10.000 gültige Kontonummern hat? Scheint unwahrscheinlich :) – PaulG

+0

Vielleicht missverstehe ich Sie, aber es scheint, dass Sie glauben, dass das Problem, das ich angetroffen habe, nicht existiert. Ich hatte das Glück, dieses Problem frühzeitig zu lösen :) Von etwa 20 Kunden, die auf die Bezahlseite gelangten, mindestens eine von ihnen, mit einer 16-stelligen Visa-Kartennummer, blieb bei der CreditCardAttribute-Validierung stecken. Sobald ich dieses Attribut entfernt hatte, konnte der Kunde seine Zahlung ohne Problem einreichen. Ich verstehe, dass Luhn ein Standard ist und glaube auch, dass die Implementierung von MS in Ordnung ist, aber zu finden, dass einer der ersten 20 Kunden eine "nicht-standardmäßige" Kreditkartennummer hatte, ist überraschend. –

Verwandte Themen