¿Cómo sería posible generar una cadena aleatoria y única usando números y letras para usar en un enlace de verificación? Al igual que cuando crea una cuenta en un sitio web, y le envía un correo electrónico con un enlace, y tiene que hacer clic en ese enlace para verificar su cuenta ... sí ... uno de esos.
¿Cómo puedo generar uno de esos usando PHP?
Actualización: Acabo de recordar sobre uniqid()
. Es una función PHP que genera un identificador único basado en el tiempo actual en microsegundos. Creo que usaré eso.
php
string
random
uniqueidentifier
Andrés
fuente
fuente
Scott
la respuesta correcta. Scott está utilizando el generador de números psudoaleatorios criptográficamente seguros de OpenSSL (CSPRNG) que elegirá la fuente de entropía más segura en función de su plataforma.uniqid
son inseguros. Usa algo comoRandom::alphanumericString($length)
oRandom::alphanumericHumanString($length)
.Respuestas:
Si no necesita que sea absolutamente único con el tiempo:
md5(uniqid(rand(), true))
De lo contrario (dado que ya ha determinado un inicio de sesión único para su usuario):
fuente
Estaba buscando cómo resolver este mismo problema, pero también quiero que mi función cree un token que también se pueda usar para recuperar la contraseña. Esto significa que necesito limitar la capacidad del token para ser adivinado. Debido a que
uniqid
se basa en el tiempo, y de acuerdo con php.net "el valor de retorno es un poco diferente de microtime ()",uniqid
no cumple con los criterios. PHP recomienda usar en suopenssl_random_pseudo_bytes()
lugar para generar tokens criptográficamente seguros.Una respuesta rápida, breve y directa es:
que generará una cadena aleatoria de caracteres alfanuméricos de longitud = $ bytes * 2. Desafortunadamente, esto solo tiene un alfabeto de
[a-f][0-9]
, pero funciona.A continuación se muestra la función más potente que podría hacer que satisfaga los criterios (esta es una versión implementada de la respuesta de Erik)
crypto_rand_secure($min, $max)
funciona como una caída en reemplazo derand()
omt_rand
. Utiliza openssl_random_pseudo_bytes para ayudar a crear un número aleatorio entre $ min y $ max.getToken($length)
crea un alfabeto para usar dentro del token y luego crea una cadena de longitud$length
.EDITAR: Olvidé citar la fuente: http://us1.php.net/manual/en/function.openssl-random-pseudo-bytes.php#104322
EDITAR (PHP7): con el lanzamiento de PHP7, la biblioteca estándar ahora tiene dos nuevas funciones que pueden reemplazar / mejorar / simplificar la función crypto_rand_secure anterior.
random_bytes($length)
yrandom_int($min, $max)
http://php.net/manual/en/function.random-bytes.php
http://php.net/manual/en/function.random-int.php
Ejemplo:
fuente
base64_encode
lugar debin2hex
obtener una cadena más corta con un alfabeto más grande.Versión orientada a objetos de la solución más votada
He creado una solución orientada a objetos basada en la respuesta de Scott :
Uso
Alfabeto personalizado
Puede usar un alfabeto personalizado si es necesario. Simplemente pase una cadena con caracteres compatibles al constructor o setter:
Aquí están las muestras de salida
Espero que ayude a alguien. ¡Salud!
fuente
$obj = new RandomStringGenerator;
pero ¿a qué método debería llamar? Gracias.generate
método como en el ejemplo anterior. Simplemente pase un número entero para especificar la longitud de la cadena resultante.Custom Alphabet
no lo hizo. Obtuve salida vacía cuando echo. De todos modos, ni siquiera estoy seguro de cuál es el uso del segundo ejemplo,Custom Alphabet
así que creo que me quedo con el primer ejemplo. Gracias.Llego tarde pero estoy aquí con algunos buenos datos de investigación basados en las funciones proporcionadas por la respuesta de Scott . Así que configuré una gota Digital Ocean solo para esta prueba automatizada de 5 días y almacené las cadenas únicas generadas en una base de datos MySQL.
Durante este período de prueba, utilicé 5 longitudes diferentes (5, 10, 15, 20, 50) y se insertaron +/- 0.5 millones de registros para cada longitud. Durante mi prueba, solo la longitud 5 generó +/- 3K duplicados de 0.5 millones y las longitudes restantes no generaron duplicados. Entonces podemos decir que si usamos una longitud de 15 o más con las funciones de Scott, entonces podemos generar cadenas únicas altamente confiables. Aquí está la tabla que muestra mis datos de investigación:
Actualización: creé una aplicación Heroku simple usando estas funciones que devuelve el token como una respuesta JSON. Se puede acceder a la aplicación en https://uniquestrings.herokuapp.com/api/token?length=15
Espero que esto ayude.
fuente
Puede usar UUID (Identificador único universal), puede usarse para cualquier propósito, desde la cadena de autenticación del usuario hasta la identificación de la transacción de pago.
Un UUID es un número de 16 octetos (128 bits). En su forma canónica, un UUID está representado por 32 dígitos hexadecimales, que se muestran en cinco grupos separados por guiones, en la forma 8-4-4-4-12 para un total de 36 caracteres (32 caracteres alfanuméricos y cuatro guiones).
// llamando a la función
algunos resultados de ejemplo serán como:
Espero que ayude a alguien en el futuro :)
fuente
Esta función generará una clave aleatoria usando números y letras:
Salida de ejemplo:
fuente
Yo uso este one-liner:
donde longitud es la longitud de la cadena deseada (divisible por 4, de lo contrario se redondea al número más cercano divisible por 4)
fuente
==
base64url_encode
puede usarse en su lugar, ver aquí: php.net/manual/en/function.base64-encode.phpUtilice el siguiente código para generar el número aleatorio de 11 caracteres o cambie el número según sus requisitos.
o podemos usar una función personalizada para generar el número aleatorio
fuente
substr(str_shuffle(str_repeat('0123456789abcdefghijklmnopqrstvwxyz', 36)), 0, 11);
por ejemplo (en pseudocódigo)
fuente
Aquí está el último generador de identificación único para usted. hecho por mi.
puedes hacer eco de cualquier 'var' para tu identificación como quieras. pero $ mdun es mejor, puede reemplazar md5 a sha1 para obtener un código mejor, pero eso será muy largo y es posible que no lo necesite.
Gracias.
fuente
Para cadenas realmente aleatorias, puede usar
salidas:
así que incluso si intentas generar cadenas varias veces al mismo tiempo, obtendrás resultados diferentes.
fuente
Cuando intentas generar una contraseña aleatoria, intentas:
Primero genere un conjunto criptográficamente seguro de bytes aleatorios
El segundo es convertir esos bytes aleatorios en una cadena imprimible
Ahora, hay múltiples formas de generar bytes aleatorios en php como:
Luego, desea convertir estos bytes aleatorios en una cadena imprimible:
Puedes usar bin2hex :
o base64_encode :
Sin embargo, tenga en cuenta que no controla la longitud de la cadena si usa base64. Puede usar bin2hex para hacer eso, usar 32 bytes se convertirá en una cadena de 64 caracteres . Pero solo funcionará así en una cadena INCLUSO .
Entonces básicamente puedes hacer :
fuente
Esto es lo que uso:
fuente
fuente
Esta es una función simple que le permite generar cadenas aleatorias que contienen letras y números (alfanuméricos). También puede limitar la longitud de la cadena. Estas cadenas aleatorias se pueden utilizar para diversos fines, que incluyen: Código de referencia, Código promocional, Código de cupón. La función se basa en las siguientes funciones de PHP: base_convert, sha1, uniqid, mt_rand
fuente
Después de leer ejemplos anteriores se me ocurrió esto:
Duplico 10 veces la matriz [0-9, AZ] y barajo los elementos, después de obtener un punto de inicio aleatorio para que substr () sea más 'creativo' :) puedes agregar [az] y otros elementos a la matriz, duplicar más o menos, sé más creativo que yo
fuente
Me gusta usar claves hash cuando trato con enlaces de verificación. Recomendaría usar el microtiempo y el hash que usando MD5 ya que no debería haber ninguna razón por la cual las teclas deberían ser las mismas ya que se basa en el microtiempo.
$key = md5(rand());
$key = md5(microtime());
fuente
la función anterior generará una cadena aleatoria que tiene una longitud de 11 caracteres.
fuente
Si desea generar una cadena única en PHP, intente lo siguiente.
En esto,
uniqid()
- Generará una cadena única. Esta función devuelve un identificador único basado en marca de tiempo como una cadena.mt_rand()
- Generar número aleatorio.md5()
- Generará la cadena hash.fuente
Scott, sí, eres muy escritor y una buena solución. Gracias.
También debo generar un token API único para cada usuario. El siguiente es mi enfoque, utilicé información de usuario (ID de usuario y nombre de usuario):
Eche un vistazo y avíseme si puedo hacer alguna mejora. Gracias
fuente
Esto es lo que estoy usando en uno de mis proyectos, está funcionando muy bien y genera un TOQUE RANDOM ÚNICO :
Tenga en cuenta que multipliqué la marca de tiempo por tres para crear una confusión para quien sea que el usuario se pregunte cómo se genera este token;)
Espero que ayude :)
fuente
Creo que este es el mejor método para usar.
fuente
podemos usar estas dos líneas de código para generar cadenas únicas que han probado alrededor de 10000000 veces de iteración
fuente
Siempre uso esta función para generar una cadena alfanumérica aleatoria personalizada ... Espero que esto sea de ayuda.
Genera, por ejemplo: Y1FypdjVbFCFK6Gh9FDJpe6dciwJEfV6MQGpJqAfuijaYSZ86g
Si desea comparar con otra cadena para asegurarse de que es una secuencia única, puede usar este truco ...
genera dos cadenas únicas:
qsBDs4JOoVRfFxyLAOGECYIsWvpcpMzAO9pypwxsqPKeAmYLOi
Ti3kE1WfGgTNxQVXtbNNbhhvvapnaUfGMVJecHkUjHbuCb85pF
Espero que esto sea lo que estás buscando ...
fuente
Una solución simple es convertir la base 64 a alfanumérica descartando los caracteres no alfanuméricos.
Este usa random_bytes () para un resultado criptográficamente seguro.
fuente
Creo que esta es una mejor solución.
fuente
Creo que el problema con todas las ideas existentes es que probablemente sean únicas, pero no definitivamente únicas (como se señala en la respuesta de Dariusz Walczak al loletech). Tengo una solución que en realidad es única. Requiere que su script tenga algún tipo de memoria. Para mí esta es una base de datos SQL. También podría simplemente escribir en un archivo en alguna parte. Hay dos implementaciones:
Primer método: tener DOS campos en lugar de 1 que proporcionan unicidad. El primer campo es un número de ID que no es aleatorio pero es único (el primer ID es 1, el segundo 2 ...). Si está utilizando SQL, simplemente defina el campo ID con la propiedad AUTO_INCREMENT. El segundo campo no es único pero es aleatorio. Esto se puede generar con cualquiera de las otras técnicas que la gente ya ha mencionado. La idea de Scott era buena, pero md5 es conveniente y probablemente lo suficientemente buena para la mayoría de los propósitos:
Segundo método: Básicamente, la misma idea, pero inicialmente elige un número máximo de cadenas que se generarán. Esto podría ser un número realmente grande como un billón. Luego haga lo mismo, genere una ID, pero rellene con cero para que todas las ID tengan el mismo número de dígitos. Luego solo concatena la ID con la cadena aleatoria. Será lo suficientemente aleatorio para la mayoría de los propósitos, pero la sección de ID se asegurará de que también sea único.
fuente
Puedes usar este código, espero que te sea útil.
Detalles sobre el generador de código aleatorio en PHP
fuente
Simplificando el código de Scotts anterior eliminando bucles innecesarios que se ralentizan mucho y no lo hacen más seguro que llamar a openssl_random_pseudo_bytes solo una vez
fuente
openssl
no está causando esto, es debido al sesgo de módulo en su declaración de devolución. 100 (rango) no divide 255 (1 byte) de manera uniforme y causa estos resultados. Mi mayor problema con su respuesta es que usted declara que la función es tan segura como usar un bucle, que es falso. Su implementación de crypto_rand_secure no es criptográficamente segura y es engañosa.openssl
más seguro, pero lo más importante es que no lo hace menos seguro, esta respuesta sí. El código anterior toma un número aleatorio perfectamente bueno y lo manipula sesgándolo hacia números más bajos. Si pone un descargo de responsabilidad en su respuesta indicando que es más rápido (al eliminar el bucle) pero no es un CSPRNG, resolvería este problema. Por amor a la criptografía, informe a los usuarios que la salida de esta función podría estar sesgada y no es una solución equivalente. El bucle no solo está ahí para molestarte.