domingo, 27 de diciembre de 2009

port scanner usando la Task Parallel Library

Poderoza la Task Parallel Library, dejo un ejemplo bastante simple de un port scanner que hace su trabajo en paralelo pero sin crear un solo thread en forma explícita. Toda la magia está en:

Parallel.For(from, to, (port) => {});



class Program
{
static void Main(string[] args)
{
if (args.Length < 2 || args.Length > 3)
throw new ArgumentException();

var to = 0;
var from = 0;
var host = args[0];

#region argument validation
//...
#endregion

Console.WriteLine("Scanning {0} ports from: {1} to {2}", host, from, to - 1);

// parallel port scan
Parallel.For(from, to, (port) =>
{
var tcpScan = new TcpClient();

try
{
tcpScan.Connect(host, port);

if (tcpScan.Connected)
Console.WriteLine("Listening on port: {0}", port);
}
catch (Exception)
{
}
finally
{
if (tcpScan.Connected)
tcpScan.Close();
}
});

Console.ReadKey();
}
}

jueves, 19 de noviembre de 2009

wii sports fail

Parece que a la gente de nintendo no se le ocurrió que alguien podía jugar al wii sports hasta romper el indicador de puntaje.

sábado, 1 de noviembre de 2008

Hola Flex

Ahi van mis primeras lineas en Flex:


<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" xmlns:ns1="*">
<mx:Button label="Saludo" id="btnSaludo" enabled="true" click="saludar()" />
<mx:Script >
<![CDATA[
import mx.controls.Alert;
import mx.rpc.events.ResultEvent;

private function saludar():void{
Alert.show('hola');
}
]]>
</mx:Script>
</mx:Application>

domingo, 22 de junio de 2008

datamapper

Una de las cosas que mas me gusta de DataMapper es que partís definiendo los atributos de tu modelo en el modelo mismo. En lugar de armar scripts (migrations), o definir a mano la base de datos y que luego levante el modelo de la base.

Pero había algo bastante feo en la version 0.3; cada vez que modificabas el modelo y le decías que actualice la base de datos, borraba todos los datos que tenías en ella.

Con la salida de la versión 0.9 de DataMapper se solucionó el problema de perder todos los datos de la base por cada dm:db:automigrate. Ahora existe dm:db:autoupgrade que se encarga de actualizar la base de datos según lo definición de los modelos preservando la información que está en las tablas. Parece ser una buena solución frente al problema que tiene ActiveRecord cuando no se trata de un proyecto de una sola persona (se crean muchos conflictos con los commits de los migrations). La solución de DataMapper es olvidarse de la base de datos, actualizo mis modelos aplicando patchs, haciendo merges, lo que fuera. Luego hago un upgrade y la base siempre corresponde a la definicón de los modelos.

Otro cambio importante es que ya no es necesario que las clases que nos interesa persistir hereden de una clase especial como sucede con la mayoría de los ORM's. Entonces nos queda la herencia disponible para algún uso más interesante.

  class Page
    include DataMapper::Resource

 end


También perdió un poco de automagia que tenía respecto a la definición de las primary keys. Ahora hay que definir a mano la pk de cada modelo, como cualquier otro atributo:

  class Page
    include DataMapper::Resource

    property :id, Integer, :serial => true

  end


Está muy buena la sintaxis para definir las relaciones "has_many":

  class Page
    include DataMapper::Resource

    property :id, Integer, :serial => true

    has 1..3, :columns
    has n, :html_controls
  end

viernes, 11 de abril de 2008

árbol en rails


Si querés implementar una estructura con forma de árbol n-ario en rails, podés usar este pluging:  ActsAsTree
 
ActsAsTree lo que hace es crear una tabla en donde guarda el nombre de la clase, la primary key y el parent_id de cada instancia de cada modelo que nos interese que se comporte como árbol. Con esta tabla puede dar soporte a todos los modelos ActiveRecord que tengas definidos, además en cada modelo vas a tener acceso a estos métodos:

children() – all immediate children of current object
parent() – first ancestor of the current object
siblings() – all children of my parent excluding me
self_and_siblings() all children of my parent including me
ancestors() all parent, grandparent, etc… object up to root
root() the base object we descended from in the tree





Otra forma de hacer casi lo mismo pero sin un plugin y sin guardar las relaciones entre nodos en una tabla externa es la siguiente:

Suponiendo que tenemos el modelo "Box", lo que vamos a hacer es crear una estructura que permita guardar cajas dentro de cajas. Sólo vamos a guardar la relación de cada nodo con su padre.

primero hay que agregar el campo "parent_id" en la tabla "boxes":

  class BoxAddReferenceToParent <>
    def self.up 
      add_column :boxes, 
                 :parent_id, 
                 :integer 
    end 

    def self.down 
      remove_column :boxes, 
                    :parent_id 
    end 
  end


segundo, agregamos la relación en el modelo de cada nodo con su parent (en este caso el parent es la caja que contiene a cada instancia):

  class Box < ActiveRecord::Base
    belongs_to :parent, 
               :class_name => "Box", 
               :foreign_key => "parent_id"
  end

tercero y último, agregamos la relación de cada caja con las que están dentro de ellas:

  class Box < ActiveRecord::Base
    belongs_to :parent, 
               :class_name => "Box", 
               :foreign_key => "parent_id"

    has_many :children, 
             :class_name => "Box", 
             :foreign_key => "parent_id"
  end


listo!



Desde la consola de rails podés crear un par de cajas y probar algo como esto:

b = Box.find 17 
b.parent         # es la caja que contiene a b
b.children       # es un Array de los objetos Box que están dentro de b  

Esta solución no es tan automágica como ActsAsTree pero me parece mucho mas prolija, las relaciones entre los nodos están donde deben estar.


miércoles, 6 de febrero de 2008

mootools: sortable of sortables

Armé una demo de un sortable que contiene a otros tres sortables. Hace un tiempo había hecho la misma prueba pero con prototype+scriptaculus, la verdad que es mucho mas transparente con mootools y el código queda mucho mas limpio:


var master = new Sortables('master', { handle: 'span'});

var mySortables = new Sortables([$('lista_A'), $('lista_B'), $('lista_C')], {
cloneOpacity: 0.4,
elementOpacity: 0.8
});


La demo está funcionando en opera, safari, firefox, iexplorer y camino sin tener que hacer ningún hack por el browser; mootools se encarga solito!

En la demo  se pueden dragear los items dentro de una misma lista, entre las listas y también se puede hacer un drag desde la parte naranja para intercambiar una lista completa con otra.

Esta es otra demo que encontré pero usa scriptaculus.


martes, 5 de febrero de 2008

script tag

Haciendo unas pruebas con los sortables de mootools me encuentro con que el ejemplo que armé no funciona en FF pero si en Safari. Me pongo a tratar de encontrar el error y para eso voy sacando todo el código que encuentro por el camino con la idea de aislarlo. Llego al punto en el que simplemente defino una función en js y la llamo en el onclick de un button (nada mas simple); pero en FF me tira un error diciendo que la función no está definida. Pruebo de borrar una referencia a un js externo y comienza a funcionar.

¿Qué pasó? No había cerrado el tag de script en forma explícita.
Para el tag script la w3c dice: Start tag: required, End tag: required

<script scr="mootools.js" />

La forma correcta es:
<script scr="mootools.js"></script>

Dejo 2 links al respecto: