【问题标题】:create unique 8 digit number创建唯一的 8 位数字
【发布时间】:2020-01-31 11:46:29
【问题描述】:

我现在正在创建一个应用程序,该应用程序需要为用户提供一个唯一的 8 位代码(仅限数字),他们可以输入该代码以访问我网站的受限部分,将其视为基本身份验证,即输入密码,密码匹配用户,返回用户。我遇到的问题是创建一个唯一的 8 位代码。我知道 PHP 有 uniqid() 但它返回的字符串太长了。

我考虑过创建 time() 和用户 IP 地址的哈希,但 laravel 的 Hash::create 返回整数和字符。

谁能指出创建随机 8 位代码的方向?我也尝试过mt_rand,但显然这可能会创建匹配的数字,除非我在保存之前检查数据库中的代码,如果存在则重新生成?

【问题讨论】:

  • 这个前提有些不对劲,8 位数字也不是很独特(即使您有成千上万的用户,冲突也可能半频繁地发生)。您为什么不在这里使用标准的授权/身份验证方法?
  • 另外,从用户体验的角度来看,一个随机的 8 位字符串可能比用户为自己设置的几个随机单词或密码更难记住。我认为上面关于身份验证角色的两点是要走的路:)但是如果你继续使用 8 位数字,一定要检查 db 是否有重复的 uid
  • 请试试这个hashids.org/php
  • @YaserDarzi 如何用这个创建 8 位数字哈希?
  • @kerbholz 看到这个 repo github.com/amamarul/integer-hashids

标签: php laravel random hash


【解决方案1】:

这是我生成随机数的代码:

public function generateRandomNumber($length = 8)
{
  $random = "";
  srand((double) microtime() * 1000000);

  $data = "123456123456789071234567890890";
  // $data .= "aBCdefghijklmn123opq45rs67tuv89wxyz"; // if you need alphabatic also

  for ($i = 0; $i < $length; $i++) {
          $random .= substr($data, (rand() % (strlen($data))), 1);
  }

  return $random;

}

【讨论】:

  • 这看起来很有用,是否存在两个输出可能相同的情况?您能否进一步解释 $data 字符串只是用于生成输出的可用字符列表?
  • $data string 进一步只是生成输出的可用字符列表? -> 是的,你需要作为输出的字符
  • 重复的变化很少,但如果你把它保存在数据库中,你可以检查它并再次调用它(使其成为递归函数)
  • 如果是严格的 8 位数字代码,那么可能的代码只有 1 亿个。在生成 10,000 个代码后,生成重复代码的可能性约为 50%。我不建议使用这种方法。
【解决方案2】:

我的建议是一个do-while循环,如果随机字符串已经存在,它会生成一个新的。根据需要生成代码,但 Laravel 实际上有一个助手 (str_random()) 来处理这个问题。

/**
* Create a unique code
*
* @return string;
*/
if ( ! function_exists('generateUniqueCode')) {
    function generateUniqueCode()
    {
        do {
            $unique_code = str_random(12);
        } while (\App\User::where('code', $unique_code)->count() > 0);


        return $unique_code;
    }
}

【讨论】:

  • 注意:从 5.7 开始是 Str::random() 而不是 str_random()
  • str_random() 是一个 Laravel 助手,你可以使用它来代替导入类。你可以在所有当前版本的 Laravel 中使用它
  • 我不这么认为,您对此是否 100% 确定? Documentation since Laravel 5.7 说是Str:_random()
  • 抱歉,我可能没有说清楚。您可以使用最适合您的方法。辅助方法没有被弃用,你可以使用vendor/laravel/framework/src/Illuminate/Support/helpers.php中的辅助方法
  • 没关系。你需要在 Laravel 6 中安装 laravel/helpers 包才能使用 str_random()。在普通的 Laravel 6 安装中,vendor/laravel/framework/src/Illuminate/Support/helpers.php 中没有函数 str_random()
【解决方案3】:

号码存在或不存在都需要登录数据库

$randnum = rand(11111111,99999999);

这将生成一个随机的 8 位数字

【讨论】:

    【解决方案4】:
    rand(10000000, 99999999);
    

    你有 1/89999999 的机会落在同一个号码上,所以你可以检查它是否已经被使用过;)

    【讨论】:

    【解决方案5】:

    试试这个函数 Laravel 它将返回 8 位数字,并在 db 中也具有唯一性。

    在控制器功能中

    $expense_id = Expense::get_random_string();
    

    模态

    public static function get_random_string()
    {
        if (function_exists('com_create_guid') === true)
        {
            return trim(com_create_guid(), '{}');
        }
        $random_unique  =  sprintf('%04X%04X', mt_rand(0, 65535), mt_rand(0, 65535), mt_rand(0, 65535), mt_rand(16384, 20479), mt_rand(32768, 49151), mt_rand(0, 65535), mt_rand(0, 65535), mt_rand(0, 65535));
    
        $expense = Expense::where('expense_id', '=', $random_unique)->first();
        if ($expense != null) {
            $random_unique = $this->get_random_string();
        }
        return $random_unique;
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-04-30
      • 1970-01-01
      • 2015-07-29
      • 1970-01-01
      • 2018-08-14
      相关资源
      最近更新 更多