How to generate a serial key that contains a prefix in the first 5 characters?

7
I have a script in PHP that generates a serial key , but I need this script to generate this " serial key " with a default at the beginning, as if it were a prefix.

The code I already have is:

<?php
$chars = array(0,1,2,3,4,5,6,7,8,9,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z');
$serial = '';
$max = count($chars)-1;
for($i=0;$i<20;$i++){
    $serial .= (!($i % 5) && $i ? '-' : '').$chars[rand(0, $max)];
}
echo $serial;
?>

That generates a serial like this:

  • "HJMW0-5RRXT-CS853-BD888"

I want the first 5 characters (the first set before the "-") of all generated serials to be the same, and the others are just numbers, without letters, like this:

  • "XYAMN-97354-81037-01936"

  • "XYAMN-75903-81938-01936"

asked by anonymous 20.11.2017 / 02:45

4 answers

3

I do not know if I understand correctly, but the prefix of your serial will be a fixed text that you will choose yourself ?? If it is you can make a very simple change in your code, which is to take all the letters of the array, and decrease the count of the for 20 to 15 digits, and put your prefix text manually, like this:

$chars = array(0,1,2,3,4,5,6,7,8,9);
$serial = '';
$max = count($chars)-1;
for($i=0;$i<15;$i++){
    $serial .= (!($i % 5) && $i ? '-' : '').$chars[rand(0, $max)];
}
echo 'XYAMN-'.$serial;

Now if you want the prefix to be random letters, you can separate it into 2 arrays, one for numbers and one for letters, and create 2 for . But I would suggest a simplified form without arrays using the chr function of php, like this:

for($i=0; $i<5; $i++){
    $prefixo .= strtoupper(chr(rand(97, 122))); //97 é o codigo ascii para 'a' e 122 para z
}

for($i=0; $i<15; $i++){
    $serial .= (!($i % 5) && $i ? '-' : '').rand(0, 9);
}
echo $prefixo.'-'.$serial;

And if you create functions and classes to make your serial generator much more dynamic. For example, make a modifier for the digit separator, use a single for for both situations, and so on. For example:

function Serial($tipo = '', $qtdigitos = 5, $qtdbaterias = 4, $separador = '-') {
    $qtdtotal = $qtdbaterias * $qtdigitos;
    $letrasnumeros = array_merge(range(0,9), range('A', 'Z')); // Cria um array de letras e numeros de forma simplificada

    for($i=0; $i < $qtdtotal; $i++){

        if ($tipo == 'numeros') { $digito = rand(0, 9); } 
        else if($tipo == 'letras') { $digito = chr(rand(65, 90)); }   //65 é o codigo ascii para 'A' e 90 para 'Z'
        else { $digito = $letrasnumeros[rand(0, count($letrasnumeros) - 1)]; }

        $serial .= (!($i % $qtdigitos) && $i ? $separador : '').$digito;
    }
  return $serial;
}

And then you can use the function in several ways:

// Retorna serial com letras e numeros, 
// Ex: RQ4BD-1NSBA-PXUD9-DOKS6
echo Serial(); 

// Retorna serial só com números, 
// Ex: 07295-31860-33824-63832
echo Serial('numeros'); 

// Retorna serial só com letras, 
// Ex: CDMIC-AXLET-BRMGW-QUVWL
echo Serial('letras'); 

// Retorna serial só com números mas quantidade diferente de caracteres, 
// Ex: 339-671-633-081-731-120
echo Serial('numeros', 3, 6); 

// Utilizar separadores diferentes,
// Ex: 2CQHJ.SF1E6.D5SOG.UA10K
echo Serial('aleatorio', 5, 4, '.');

// Juntar formas e quantidades diferentes,
// Ex: AMQGUUY-82468-32482-84190
echo Serial('letras', 7, 1).'-'.Serial('numeros', 5, 3);

// Juntar texto fixo com serial
// Ex: XYAMN-16697-17479-56095
echo 'XYAMN-'.Serial('numeros', 5, 3);

I hope I have helped

    
20.11.2017 / 10:39
3

Separate in two functions as in the code below:


function prefixo(){
    $chars = array(0,1,2,3,4,5,6,7,8,9,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z');
    $prefixo = '';
    $max = count($chars)-1;
    for($i=0;$i&lt5;$i++){
        $prefixo .= (!($i % 5) && $i ? '-' : '').$chars[rand(0, $max)];
    }
    return $prefixo;
}

function serial(){
    $chars = array(0,1,2,3,4,5,6,7,8,9);
    $serial = '';
    $max = count($chars)-1;
    for($i=0;$i&lt15;$i++){
        $serial .= (!($i % 5) && $i ? '-' : '').$chars[rand(0, $max)];
    }
    return $serial;
}
echo prefixo()."-".serial();
    
20.11.2017 / 03:07
2

I think you should use random_bytes or random_int instead of rand() . The difference is that random_* will use the CSRPNG present in the operating system, which is more secure than LGC or Mersenne Twister.

You can use random_int with pack , as follows:

function letra(int $limite) : string {
    $b = '';

    while(strlen($b) < $limite){
        $b .= pack('C', random_int(65, 90));
    }

    return $b;
}

function numero(int $limite) : string{
    return str_pad(
        random_int(0, str_repeat(9, $limite)),
        $limite, '0', STR_PAD_LEFT);
}

echo letra(5) . '-' . numero(5) . '-' . numero(5) . '-' . numero(5);
    
04.12.2017 / 01:08
1

You can create a class , example:

  

Class serial.class.php

class Serial
{
  private $prefixo = "";
  public $letras = array('A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z');
  public $numeros = array(0,1,2,3,4,5,6,7,8,9);

  /* 
   * Método construtor
   * Cria um prefixo para cada objeto criado
   */
  public function __construct() {
    $max = count($this->letras)-1;
    for($a=0;$a<5;$a++) {
      $this->prefixo .= $this->letras[rand(0, $max)];
    }
    return $this;
  }

  /* 
   * Método get
   * Gera um serial de 15 digitos toda vez que o método for chamado
   */
  public function get() {
    $serial = '';
    $max = count($this->numeros)-1;
    for($b=0;$b<15;$b++){
      $serial .= (!($b % 5) && $b ? '-' : ''). $this->numeros[rand(0, $max)];
    }
    echo $this->prefixo."-".$serial."\n";
    return $this;
  }

}
  

How to use:

require_once('serial.class.php');

$serial_A = new Serial();
$serial_A->get()->get()->get()
         ->get()->get()->get()
         ->get()->get()->get()
         ->get()->get()->get()
         ->get()->get()->get()
         ->get()->get()->get();
  

Output example

MPRDM-68308-47678-09412
MPRDM-34567-47698-43685
MPRDM-79111-86573-68267
MPRDM-78570-58526-57259
MPRDM-89941-85110-50824
MPRDM-41477-69233-60018
MPRDM-76481-63231-98672
MPRDM-14028-03542-56162
MPRDM-41338-20932-00450
MPRDM-72468-49538-39004
MPRDM-82852-74510-92625
MPRDM-34866-98635-93850
MPRDM-42227-33041-72832
MPRDM-15014-94731-68651
MPRDM-12007-58515-50146
MPRDM-27148-78106-34490
MPRDM-99967-35102-51586
MPRDM-47226-20839-60614
  

You can see it working at repl.it

    
20.11.2017 / 05:24