Buscar este blog

jueves, 29 de julio de 2010

Blackberry Truco #3 Youtube en la Blackberry usando Wifi // Blackberry Tip #3: Youtube on the Blackberry using Wi-Fi

Español / Spanish

Hola, quizas se te este presentando el mismo problema que tuve al tratar de ver videos de youtube desde una blackberry 8520 usando la conexion wifi.

Inicialmente uno puede pensar que es por falta de algun codec, archivo o modulo, pero no es asi, resulta que por algun tipo de bloqueo en algun puerto que aun desconozco el router o ap wifi no tiene la capacidad de transmitir el streaming de youtube a la bb.

La solucion mas rapida a este problema fue la siguiente, simplemente averiguas la ip del wifi que tiene tu bb y la agregas al DMZ de tu router o firewall.

Si no sabes que significa o que es el DMZ de tu router, la explicacion simple es, una zona desmilitarizada, esto quiere decir que no hay proteccion en esta zona, no hay bloqueo de ningun tipo de puertos o trafico. Todos los routers caseros actuales y de oficina tienen esta caracteristica.

Si desconoces como averiguar la ip de tu wifi en la bb, puedes hacer los siguiente:


1. Menu principal
2. Opciones
3. Wi-fi
4. Seleccionar el perfil activo o conexion activa
5. Presionas el boton blackberry
6. Herramientas de Wi-fi
7. Diagnosticos de Wi-fi
8. Direccion IP local (esta es la que buscas)

Esta ip es la que debes agregar en la DMZ.

Importante: esta configuracion es por cada punto de acceso wifi que quieras configurar para acceder a youtube.

English / Ingles

Youtube on the Blackberry using Wi-Fi

Hey, maybe this will be presenting the same problem I had when trying to watch videos on youtube from a blackberry 8520 using the wifi connection.

Initially one may think it's for lack of any codec, file or module, but it is not, is that some sort of lock on any port that still do not know the router or wireless AP does not have the ability to transmit streaming YouTube the bb.

The quickest solution to this problem was next, just find out the ip of the wifi you have your bb and add the DMZ of your router or firewall.

If you do not know that signifies or is the DMZ of your router, the explanation is simple, a demilitarized zone, this means that there is no protection in this area, there is no type of blocking ports or traffic. All current routers home and office have this feature.

Not familiar with how to find out the ip of your wifi on bb, you can do the following:

1. Main Menu
2. Options
3. Wi-fi
4. Select the active profile or active connection
5. Press the blackberry button
6. Wi-Fi Tools
7. Wi-Fi Diagnostics
8. Local IP address (this is the one you want)

This ip is what you add in the DMZ.

Important: This setting is for each wireless access point you want to configure access to youtube.

viernes, 23 de julio de 2010

Probando el NMH300 de Linksys (Cisco) / Disco duro en red / NAS

He decidido probar un sistema de backup nuevo para mi, aunque el NAS (Network attached storage) no es algo nuevo, el dispositivo del cual voy a comentar si es nuevo para mi.

El "media hub" NMH300 de Linksys es una enclosure o box (caja) donde se pueden acoplar hasta 2 discos duros SATA.

Cuenta con un ventilador en la parte posterios, dos puertos usbs (frontal y posterior), 1 puerto ethernet. 

Mi real interes por este llamativo dispositivo surgio de la necesidad de contar con un sistema de respaldo centralizado, desatendido y que no requiriera demasiada administracion. Normalmente para soluciones mas robustas de copias de respaldo se utilizan servidores dedicados, pero a veces ese tipo de soluciones sobrepasa el presupuesto destinado para eso.

Una interfaz sencilla, intuitiva, amigable hace que sea facil de configurar y de explorar, su instalacion relativamente rapida y guiada a traves de un simple asistente nos deja ponerlo en marcha en tan solo 15 minutos con las opciones por defecto.



Lo que toma mas tiempo durante la instalacion es la configuracion y formateo de los discos, los cuales pueden ser configurados en 3 formas distintas:

1. En solitario: solo toma el primer disco duro, el segundo esta inactivo (opcion por defecto).

2. Expandir capacidad: une la capacidad de ambos discos y los muestra como un solo volumen de almacenamiento. Ej: 2 discos de 1TB son mostrados como 1 solo volumen de 2TB.

3. Raid 1 Incrementar proteccion: este es el modo mas recomendable para copias de seguridad con respaldo. Este modo lo que permite es utilizar los disco en espejo o mirroring, teniendo como resultado un sistema de respaldo con otro subsistema de respaldo.

Funcionalidades de red 

Gracias a su interface de red, el NMH300 puede conectarse a una LAN a traves del protocolo TCP/IP obteniendo una direccion ip. Puede ser explorado por su nombre host o por su direccion ip, asi como puede ser mapeado en una unidad de red windows como una carpeta compartida de un pc.

Tambien  nos brinda la funcionalidad de FTP lo cual permite a clientes ftp usarlo como sitio de descargas o almacenamiento.

Mi experiencia
  • El formateo inicial de los discos tomo aproximadamente 10 minutos.
  • El formateo y sincronizacion en modo RAID 1 tomo cerca de 2 horas.
  • La interface web puede ponerse un poco pesada a veces.

martes, 13 de julio de 2010

Optimización en la actualización de lote de registros en una tabla en la base de datos

Me han encargado el desarrollo de un programa que mezcle ciertos códigos que se encuentran en dos tablas en la base de datos con unos código fijos que se generan desde un arreglo en el código fuente. El numero de código en total son 5’000.000 de los cuales 700.000 salen de la base de datos. El núcleo de la aplicación radica en la aleatoriedad que deben tener estos 700.000 en los 5 millones evitándose periodicidades o agrupamientos.

Se crearon los métodos que se encargan de la aleatoriedad y su funcionamiento fue adecuado, pero todo se complico cuando en la primera simulación el cálculo estimado de tiempo que tomaría ejecutar el programa para todos los registros arrojo un valor cercano a las 30 horas.

Viendo esto llegamos a la conclusión era que las operaciones que se realizaban con la base de datos hacían que el proceso tomara este tiempo.

Realmente las operaciones eran sencillas, un SELECT que retornaba un solo registro de dos columnas y  si la operación era exitosa un UPDATE que me actualizaba este registró para cambiar su estado.

Pero estas dos simples operaciones más las comprobaciones internas del SqlConnection hacían que la ejecución total tomara tanto tiempo, fue entonces que decidí optimizar esto y el resultado fue que una reducción de 30 horas a aproximadamente 10 minutos, una reducción muy notoria.

Mi primer error fue utilizar de forma inadecuada las clases que provee el ADO.net y mi segundo error fue realizar constantes consultas la bd en vez de hacerlo sobre datos de acceso más rápido, por ejemplo en memoria.

Finalmente la solución fue muy sencilla, trabajar sobre una tabla replica de los registros en memoria realizar las operaciones de consulta y actualización sobre estos y luego actualizar la base de datos físicamente.

En el siguiente código traemos los primeros 1000 registros que deseamos utilizar, en su caso pueden traer los registros que desean con la consulta que ustedes utilicen.

Consulta y llenado
Luego con los métodos .FillSchema y .Fill del DataAdapter realizamos respectivamente un mapeo en memoria de la estructura de la tabla en un DataSet y luego procedemos a llenarlo con los datos que retorna la consulta SELECT, de esta forma tenemos en memoria una copia exacta de la tabla tanto de su estructura como de sus datos – los datos retornados en la consulta-.
string sql = @"SELECT TOP 1000 [id], [estado] FROM [tabla] WHERE [estado] <> 1 ORDER BY code ASC";

            daContenido = new SqlDataAdapter(sql, conn);
            dsContenido = new DataSet("Tabla");

            try
            {

                daContenido.FillSchema(dsContenido, SchemaType.Source, "tabla");
                daContenido.Fill(dsContenido, "tabla");

                tblContenido = dsContenido.Tables["tabla"];
            }
            catch (SqlException ex)
            {
                Console.WriteLine(ex.Message);
            }

Teniendo ya una copia de la tabla a consultar y modificar en memoria aseguramos no tenes que realizar consultas directas sobre la base de datos mejorando los tiempos de ejecucion.

Importante: lo negativo de este enfoque radica en la frecuencia de actualizacion sobre la tabla fisica por parte de otras aplicaciones y usuarios, ya que en un entorno donde la tabla fisica es actualizada frecuentemente en lapsos cortos de tiempo facilmente se puede presentar una falla en la integridad de los datos porque se estaria trabajando con una copia en memoria de la tabla que posiblemente haya sido modificada.

Sub-Selección de registros
Hasta este punto hemos avanzado hasta el punto de tener los datos y la estructura de la tabla en memoria, pero debemos poder consultarla como si fuera la tabla física en la base de datos, para esto en el siguiente segmento de código brevemente vemos una consulta básica.
Fácilmente se pueden construir consultas que devuelvan varios registros con varias columnas.
string codigo = "";

DataRow current;

/* Esto equivale a un SELECT de la tabla con un WHERE donde estado <> 1 y ordenado por codigo de forma ascendente */
DataRow[] filas = tblContenido.Select("estado <> 1", "code ASC");
           
if (filas.GetLength(0) > 0)
{
/* En este caso solo requiero el primer registro que cumpla las condiciones sin importar cual sea */
current = filas[0];

/* Me guarda el valor de la llave primaria de este registro en un string */
codigo = current[0].ToString();



Modificación de un registro
En cuanto a la modificacion de un registro sobre esta tabla en memoria es un proceso muy simple y puede realizarce para todos los registros en la tabla disponible en memoria.

DataRow current;
try
{
/* Este metodo retorna un Datarow donde la llave primaria concuerde con el parametro pasado */
current = tblContenido.Rows.Find(code);

/* Se inicia el proceso de modificado*/
current.BeginEdit();
               
/* Se modifican las columnas deseadas */
current[1] = true;
               
/* Se finaliza el proceso de modificacion del registro */
current.EndEdit();
}
catch
{
Console.WriteLine("Excepcion");
}

Actualización de tabla original
Ya hemos realizado la modificación de los registros necesarios durante la ejecución del programa, a este punto lo que falta es actualizar estos cambios en la base de datos físicamente, actualizar la tabla. Para esto recurriremos al método .Update del DataAdapter.

try
{
/* Con el objeto SqlCommandBuilder nos encargamso de crear las plantillas de cadenas utilizadas para realizar los UPDATES sobre la tabla real en la base de datos */
SqlCommandBuilder objCommandBuilder = new SqlCommandBuilder(daContenido);

/* Actualizamos la tabla con el contenido actualizado del DataSet */
daContenido.Update(dsContenido, "tabla");
}
catch (SqlException ex)
{
      Console.WriteLine(ex.Message);
}

Con esto ya nuestras modificaciones sobre los registros en memoria seran actualizados de forma casi transparente para nosotros sin tener que realizar numerosas consultas.

Espero esto sea de utilidad a la hora de resolver problemas parecidos. De cualquiero forma dejo el link de MSDN donde encontre la informacion necesaria para realizar mi programa.

http://support.microsoft.com/kb/301248/es