JavaScript/jQuery VIN Validator

筅森魡賤 提交于 2019-12-19 02:06:34

问题


Has anyone ever created a VIN Validator? I am trying to create a textbox where the user will enter in a Vehicle Identification Number and then JS/jQuery will validate if its correct or not in case they mistype the number.

I am very new to JS/jQuery and have found some examples but of course have not been able to get them to work correctly... Any one with any ideas or suggestions it would be greatly appreciated, especially if you can tell me how to set up what I have below to work properly!

Note: The isVin() function is courtesy of cflib.org

HTML:

<label name="vin">VIN</label>
<input type="text" name="vin" />

ColdFusion:

<cfscript>
/**
 * US Vehicle Identification Number (VIN) validation.
 * version 1.0 by Christopher Jordan
 * version 1.1 by RHPT, Peter Boughton &amp; Adam Cameron (original function rejected valid VINs)
 * 
 * @param v      VIN to validate (Required)
 * @return Returns a boolean. 
 * @author Christopher Jordan (cjordan@placs.net) 
 * @version 1, February 19, 2013 
 */
function isVIN(v) {
    var i = "";
    var d = "";
    var checkDigit = "";
    var sum = 0;
    var weights = [8, 7, 6, 5, 4, 3, 2, 10, 0, 9, 8, 7, 6, 5, 4, 3, 2];
    var transliterations = {
        a = 1,    b = 2, c = 3, d = 4, e = 5, f = 6,    g = 7, h = 8,
        j = 1,    k = 2, l = 3, m = 4, n = 5,         p = 7,            r = 9,
                s = 2, t = 3, u = 4, v = 5, w = 6,    x = 7, y = 8,    z = 9
    };
    var vinRegex = "(?x)    ## allow comments
        ^                    ## from the start of the string
                            ## see http://en.wikipedia.org/wiki/Vehicle_Identification_Number for VIN spec
        [A-Z\d]{3}            ## World Manufacturer Identifier (WMI)
        [A-Z\d]{5}            ## Vehicle decription section (VDS)
        [\dX]                ## Check digit
        [A-Z\d]                ## Model year
        [A-Z\d]                ## Plant
        \d{6}                ## Sequence
        $                    ## to the end of the string
    ";

    if (! REFindNoCase(vinRegex, arguments.v)) {
        return false;
    }

    for (i = 1; i <= len(arguments.v); i++) {
        d = mid(arguments.v, i, 1);

        if (! isNumeric(d)) {
            sum += transliterations[d] * weights[i];
        } else {
            sum += d * weights[i];
        }
    }

    checkDigit = sum % 11;

    if (checkDigit == 10) {
        checkDigit = "x";
    }
    return checkDigit == mid(arguments.v, 9, 1);
}
</cfscript>

Test Code:

    <cfoutput>
<cfset vin = "1GNDM19ZXRB170064">
#vin#: #isVin(vin)#<br />
<cfset vin = "1FAFP40634F172825">
#vin#: #isVin(vin)#<br />
</cfoutput>

回答1:


Here's a client-side solution using Regular Expressions.

$(function() {
  $("#vin").on("keyup blur", function() {
    if (validateVin($("#vin").val()))
      $("#result").html("That's a VIN");
    else
      $("#result").html("Not a VIN");
  }).trigger("blur");
});
  
function validateVin(vin) {
  var re = new RegExp("^[A-HJ-NPR-Z\\d]{8}[\\dX][A-HJ-NPR-Z\\d]{2}\\d{6}$");
  return vin.match(re);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<label name="vin">VIN</label>
<input type="text" id="vin" value="1FAFP40634F172825" />
<span id="result"></span>



回答2:


If you're decoding VINs for vehicles sold in North America1, you can validate the following:

  1. That the VIN is 17 digits in length
  2. If 17 digits, that the check digit (9th position) is correct

As you'll be checking the VIN in real time as the user types it in, it's important to be efficient. This means failing fast while the user is typing it in. While you can use regex for this task, it's far slower than simply checking the VIN's length. Once the VIN is 17 digits long then you can validate the check digit (which, incidentally, is itself also faster than regex - see below).

Regular expressions are not a good fit for VIN validation for a couple reasons:

  1. Performance. It's not as fast as simply checking the length, and the trade-off for speed doesn't net you that much of an improvement in accuracy because you can't validate the check digit.

  2. Accuracy. While it's true you can ensure a VIN meets the correct pattern in terms of length and valid characters, that is not enough. KNDJB723025140702 is a valid VIN while KNDJB723025140703 is not (the only difference is the last number). A regex solution will show both VINs as being valid, with the second being a false-positive and therefore incorrect.

Wikipedia has a really good script for performing check digit validation that also fails quickly by only validating the check digit if the VIN is 17 digits.

In my own testing, the script below is much, must faster (roughly 40x) than using regex to validate a VIN, and it has the added benefit of returning accurate results.

$(function() {
  var $ctrl = $('#vin'),
    $msg = $('#validation-message');

  $ctrl.keyup(function() {
    if (validateVin($ctrl.val())) {
      $msg.html("VIN is valid!");
    } else {
      $msg.html("VIN is not valid");
    }
  });
});

function validateVin(vin) {
  return validate(vin);


  // source: https://en.wikipedia.org/wiki/Vehicle_identification_number#Example_Code
  // ---------------------------------------------------------------------------------
  function transliterate(c) {
    return '0123456789.ABCDEFGH..JKLMN.P.R..STUVWXYZ'.indexOf(c) % 10;
  }

  function get_check_digit(vin) {
    var map = '0123456789X';
    var weights = '8765432X098765432';
    var sum = 0;
    for (var i = 0; i < 17; ++i)
      sum += transliterate(vin[i]) * map.indexOf(weights[i]);
    return map[sum % 11];
  }

  function validate(vin) {
      if (vin.length !== 17) return false;
      return get_check_digit(vin) === vin[8];
    }
    // ---------------------------------------------------------------------------------
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

VIN:
<input id="vin" type="text" />
<span id="validation-message"></span>

[1] Vehicles sold in the EU don't typically use a check digit, and for some cars can even be 18 digits in length (Mercedes).



来源:https://stackoverflow.com/questions/26407015/javascript-jquery-vin-validator

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!