Validador de targetes de crèdit pel symfony

symfony.gifMalgrat els molts validadors de camps de formularis que inclou el famework symfony no n’inclou un de força important. El validador dels codis de les targetes de crèdit. Com segur que sabeu, els codi d’una targeta de crèdit és autoverificable. És a dir compleix un algoritme matemàtic entre els seus grups de 4 números. Doncs bé com que no tenia cap ganes d’implementar el que ja esta implementat moltes vegades, vaig trobar que a phpclasses.org un tal Harish Chauhan havia penjat una classe programada en PHP4 que implementava un validador de força tipus de targetes de crèdit (VISA, MASTERCARD, DISCOVER, AMEX, DINERS, JCB, Australian Bankcard, EnRoute i Switch Solo). Així doncs, vaig decidir integrar aquesta classe amb el sistema de validador de camps de formularis del symfony.

El primer que vaig fer va ser declarar els mètodes orginals com a privats i després extendre la classe sfValidator que és la usada pels validadors de symfony. Creant un parell de mètodes públics estàndards pels validadors, bàsicament serveixen per instanciar el mètode del validador real i per capturar els paràmetres rebuts des del fitxer yml corresponent.

Doncs bé si voleu consultar el codi de la classe i un exemple d’ús a part de poder-ho consultar en la part extesa d’aques article podeu mirar als snippets de symfony, concretament a Credit Card validator.

Codi del validador:

getParameterHolder()->get('num');
		$num = $this->getContext()->getRequest()->getParameter($num_param);
		$tipo_param = $this->getParameterHolder()->get('tipo');
		$tipo = $this->getContext()->getRequest()->getParameter($tipo_param);
		// Lanzamos la validación
		$validada=$this->_isVAlidCreditCard($num,$tipo,false);
		// Informamos de como ha ido la validación
		sfContext::getInstance()->getLogger()->info("CCVAL.class.php: Tipo: ".$tipo." Num: ".$num." Validada: ".$validada);
		if ($validada==false)
		{
			$error = $this->getParameterHolder()->get('error');
			return false;
		}
		return true;
	}
	public function initialize ($context, $parameters = null)
	{
		// initialize parent
		parent::initialize($context);
		$this->getParameterHolder()->add($parameters);
		return true;
	}
	/**
	 * Testing checksum
	 *
	 * @param integer $ccnum
	 * @return boolean
	 */
	private function _checkSum($ccnum)
	{
		$checksum = 0;
		for ($i=(2-(strlen($ccnum) % 2)); $i<=strlen($ccnum); $i+=2)
		{
			$checksum += (int)($ccnum{$i-1});
		}
		// Analyze odd digits in even length strings or even digits in odd length strings.
		for ($i=(strlen($ccnum)% 2) + 1; $i< 10)
			{ $checksum += $digit; }
			else
			{ $checksum += ($digit-9); }
		}
		if (($checksum % 10) == 0)
		return true;
		else
		return false;
	}
	/**
	 * Launch validation
	 *
	 * @param integer $ccnum
	 * @param string $type
	 * @param boolean $returnobj
	 * @return boolean
	 */
	private function _isVAlidCreditCard($ccnum,$type="",$returnobj=false)
	{
		$creditcard=array(  "visa"=>"/^4d{3}-?d{4}-?d{4}-?d{4}$/",
		"mastercard"=>"/^5[1-5]d{2}-?d{4}-?d{4}-?d{4}$/",
		"discover"=>"/^6011-?d{4}-?d{4}-?d{4}$/",
		"amex"=>"/^3[4,7]d{13}$/",
		"diners"=>"/^3[0,6,8]d{12}$/",
		"bankcard"=>"/^5610-?d{4}-?d{4}-?d{4}$/",
		"jcb"=>"/^[3088|3096|3112|3158|3337|3528]d{12}$/",
		"enroute"=>"/^[2014|2149]d{11}$/",
		"switch"=>"/^[4903|4911|4936|5641|6333|6759|6334|6767]d{12}$/");
		if(empty($type))
		{
			$match=false;
			foreach($creditcard as $type=>$pattern)
			if(preg_match($pattern,$ccnum)==1)
			{
				$match=true;
				break;
			}
			if(!$match)
			return false;
			else
			{
				if($returnobj)
				{
					$return=new stdclass;
					$return->valid=$this->_checkSum($ccnum);
					$return->ccnum=$ccnum;
					$return->type=$type;
					return $return;
				}
				else
				return $this->_checkSum($ccnum);
			}
		}
		else
		{
			if(@preg_match($creditcard[strtolower(trim($type))],$ccnum)==0)
			return false;
			else
			{
				if($returnobj)
				{
					$return=new stdclass;
					$return->valid=$this->_checkSum($ccnum);
					$return->ccnum=$ccnum;
					$return->type=$type;
					return $return;
				}
				else
				return $this->_checkSum($ccnum);
			}
		}
	}
}
?>

Un exemple de com es crida el validador des dels fitxers yml de configuració al directori validate:

methods:
  post: [ntarjeta]
names:
  ntarjeta:
    required:     Yes
    required_msg: Credit Card number is required
    validators:   validarCC
validarCC:
    class:       CCVAL
    param:
      num:       ntarjeta
      tipo:      tipoCC
      error:     Your credit card number is invalid

Escriptori en 3D i nous conceptes d’usabilitat

Gràcies pel video Oriol, realment interessant. Us el recomano moltíssim ja que exposa idees de possibles futurs sistemes d’escriptoris en tres dimensions i sistemes d’interacció amb els documents/icones/programes/etc realment molt innovadors, almenys sota el meu punt de vista:

Amplificadors de 0.5W compatible amb 802.11b a 802.11g

amplificador.jpg

Renasis té un petit amplificador de 0.5W amb connectors RP-SMA i TNC, a escollir. Obviament va alimentat externament i la mini-antena que porta incorporada porta un connector RP-SMA en el que si fa falta es pot connectar una antena més potent. Així doncs es poden fer coses molt interessants amb aquests dispositius. Ja sabeu que en aquest país emetre en més de 100mW és il·legal així doncs això només és per fer proves 😉

Si no sabeu on aconseguir-lo m’ho dieu en privat i us ho dic, a més el preu és molt atractiu al voltant dels 100€.

Si voleu donar un cop d’ull al datasheet.

Un parell d’enllaços molt bons sobre UTF-8 i PHP

Primer una cosa realment útil, un detector de quin format té un text per poder-lo transformar a UTF8 si cal. Sembla una tonteria però el no tenir-ho sempre et fa anar de corcoll: Detectando UTF8 en PHP (local).

L’altre enllaç és d’un wiki, on ens parlen del comportament de diverses funcions de PHP amb UTF8 i com jugar amb elles sense morir en l’intent i alguna coseta més:

Primeres conseqüències de la calor…

senzillament aquesta nit (jo que em pensava que a la nit refresca) el transformador del switch que ja portava els seus dos anyets (aprox) sense parar-se ha fet figa. Així que m’he aixecat i he comprovat que no tenia xarxa després de comprobar que tot estava bé i que no tenia connectivitat entre ordinadors he vist que tots els llums del switch estaben apagats i per sort només he hagut de posar un altre transformador perquè tornessin a fer pampallugues…uf!!! sinó ja em veia jo tot el dia sense switch :'(

Doncs tot arreglat… a veure si cauran gaires més coses aquest estiu, ja que la calor no para!

Scroll to Top