如何在Go中验证UUID v4?

Rob*_*ces 13 go

我有以下代码:

func GetUUIDValidator(text string) bool {
    r, _ := regexp.Compile("/[a-f0-9]{8}-[a-f0-9]{4}-4[a-f0-9]{3}-[89aAbB][a-f0-9]{3}-[a-f0-9]{12}/")
    return r.Match([]byte(text))
}
Run Code Online (Sandbox Code Playgroud)

但是当我fbd3036f-0f1c-4e98-b71c-d4cd61213f90作为一个值传递时,我得到了false,而实际上它是一个UUID v4.

我究竟做错了什么?

Pat*_*nio 28

试试......

func IsValidUUID(uuid string) bool {
    r := regexp.MustCompile("^[a-fA-F0-9]{8}-[a-fA-F0-9]{4}-4[a-fA-F0-9]{3}-[8|9|aA|bB][a-fA-F0-9]{3}-[a-fA-F0-9]{12}$")
    return r.MatchString(uuid)
}
Run Code Online (Sandbox Code Playgroud)

实例:https://play.golang.org/p/a4Z-Jn4EvG

  • 你在第三部分检查[1-5],这允许它匹配非uuid 4字符串.这个问题的标题要求uuid v4.将[1-5]更改为4并按要求工作. (3认同)

mat*_*tes 21

正则表达式很贵.以下方法比正则表达式版本快约18倍.

请改用https://godoc.org/github.com/google/uuid#Parse.

import "github.com/google/uuid"

func IsValidUUID(u string) bool {
    _, err := uuid.Parse(u)
    return err == nil
 }
Run Code Online (Sandbox Code Playgroud)

  • 我相信 Go 的实现是线性的 O(n) 而不是常数 O(1)。由于 UUID 的大小是固定的,因此我认为这并不重要。我运行了一个快速基准测试,正则表达式版本为 628 ns/op,“uuid.Parse”方法为 34.8 ns/op。https://gist.github.com/mattes/69a4ab7027b9e8ee952b5843e7ca6955 (3认同)

小智 7

您可以使用satori / go.uuid包来完成此操作:

import "github.com/satori/go.uuid"

func IsValidUUID(u string) bool {
  _, err := uuid.FromString(u)
  return err == nil
}
Run Code Online (Sandbox Code Playgroud)

该软件包被广泛用于UUID操作:https : //github.com/satori/go.uuid

  • 我将https://gist.github.com/mattes/69a4ab7027b9e8ee952b5843e7ca6955更新为基准satori / go.uuid与google / uuid。Google的UUID检查比该检查快3.3倍。 (2认同)

Osc*_*ely 5

如果您将其验证为结构体的属性,有一个直接来自 Go 的很棒的 golang 库,称为验证器https://godoc.org/gopkg.in/go-playground/validator.v9,您可以使用它来验证通过提供的内置验证器以及完整的自定义验证方法来实现各种字段嵌套结构。您所需要做的只是在字段中添加适当的标签

import "gopkg.in/go-playground/validator.v9"

type myObject struct {
    UID string `validate:"required,uuid4"`
}

func validate(obj *myObject) {
    validate := validator.New()
    err := validate.Struct(obj)
}
Run Code Online (Sandbox Code Playgroud)

它提供结构化字段错误和其他相关数据。