- Presentación.
Este tutorial está basado en el que se encuentra en los foros de B4A, se trata de tener una base de datos en un servidor web y mediante un programa en el móvil, obtener, ver, buscar, borrar... la información de una base de datos.
Al principio lo explico en un servidor local mediante el Apache, más adelante en un punto posterior lo modifico para que funcione en un servidor web remoto (Internet). Antes de comenzar es conveniente echarle un vistazo a los 7 puntos que componen este tutorial.
Para hacer las pruebas vamos a necesitar un servidor web (Apache) con PHP y MySQL. Podemos instalar fácilmente en nuestro ordenador el paquete WAMP que trae esos servicios. Sitio de WAMP server.
Se instalará en C:\wamp, la carpeta donde tenemos que poner los archivos (.php) es C:\wamp\www
Podemos llegar al administrador WAMP desde un icono situado en el área de notificación, cerca del reloj.
Un cuadrado con una W, que debe estar de color verde.
|
En la línea final, si aparece Put Online, solo podrá ver la web el localhost (es decir, tu ordenador), si aparece Put Offline, la podrá ver otros ordenadores de intranet e internet (si tienes abierto el puerto 80 en el Router). |
Para ver la página de inicio escribimos en un navegador http://localhost.
Debemos crear una base de datos con algunos datos. La base de datos la creamos escribiendo en un navegador
http://localhost/phpmyadmin
_____________________
- Base de datos.
- Nuestra base de datos se llamará android, y tendrá una tabla llamada paises. Esta tabla tendrá tres columnas: ID, nombre y poblacion, son de tipo varchar.
Insertamos 3 países.
ES España 47000
MX México 112000
AR Argentina 40000
Si sabes Importar, también lo puedes hacer así: salva este archivo como paises.sql y lo importas, así se creará automáticamente la tabla.
Es decir, entramos en http://localhost/phmpyadmin, creamos la base de datos: android y luego importamos este archivo: paises.sql
paises.sql
|
CREATE TABLE IF NOT EXISTS `paises` (
`ID` varchar(4) CHARACTER SET utf8 COLLATE utf8_spanish2_ci NOT NULL,
`nombre` varchar(30) CHARACTER SET utf8 COLLATE utf8_spanish2_ci NOT NULL,
`poblacion` varchar(11) CHARACTER SET utf8 COLLATE utf8_spanish2_ci NOT NULL,
PRIMARY KEY (`ID`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1;
INSERT INTO `paises` (`ID`, `nombre`, `poblacion`) VALUES
('ES', 'España', '47000'),
('MX', 'México', '114000'),
('CH', 'Chile', '17000'),
('CO', 'Colombia', '47000'),
('PE', 'Perú', '30000'),
('VE', 'Venezuela', '29000'),
('EC', 'Ecuador', '15000'),
('BO', 'Bolivia', '11000'),
('PA', 'Paraguay', '6000'),
('UR', 'Uruguay', '3000'),
('HO', 'Honduras', '8000'),
('GU', 'Guatemala', '16000'),
('AR', 'Argentina', '40000'),
('CU', 'Cuba', '11000'),
('NI', 'Nicaragua', '6100'),
('CR', 'Costa Rica', '4700');
|
- En el archivo anterior fíjate que todos las líneas de los paises terminan en coma,
excepto el último que pongas, que debe terminar en punto y coma;
Cuando lo importes pones el conjunto de caracteres en iso-8859-1 que corresponde a los caracteres latinos con acentos y demás.
Ya tenemos la base de datos en nuestro ordenador, mediante http://localhost/phpmyadmin, podemos modificarla, añadirle datos, ampliar el número de columnas,...
___________________________
1.- Ver listado de países y su población.
Designer - Layout
|
Librerías necesarias (HTTP y JSON).
|
Mediante el Designer creamos la pantalla que muestro en el dibujo de la izquierda.
Insertamos dos Label: Label1 y Label2
Insertamos un ListView1.
Guardamos el Layout con el nombre: 1
En funcionamiento.
|
- Debes modificar las dos líneas del siguiente código poniendo tu IP:
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
debes poner tu IP local (192.168.-.-)
No pongas localhost, ni 127.0.0.1, es mejor poner tu IP local.
Para ver tu IP local, en el símbolo de sistema escribe ipconfig. (La mía es 192.168.1.3)
Código del Basic4Android
|
' De los tutoriales de b4a
' Adaptado a local por Juan Antonio Villalpando
' juana1991@yahoo.com
Sub Process_Globals
Dim hc As HttpClient
Dim paises, poblacion As Int
paises = 1 ' Es la tarea 1
poblacion = 2 ' Es la tarea 2
End Sub
Sub Globals
' Renglones puede contener dos renglones:
' Renglon1 (ES)
' Renglon2 (España)
Type Renglones (Renglon1 As String, Renglon2 As String)
Dim Label1, Label2 As Label
Dim ListView1 As ListView
End Sub
Sub Activity_Create(FirstTime As Boolean)
If FirstTime Then
hc.Initialize("hc")
End If
Activity.LoadLayout("1")
Buscar_lista_de_paises
End Sub
Sub Buscar_lista_de_paises
ProgressDialogShow("Buscando lista de países.")
Dim req As HttpRequest
Dim Query As String
Query="SELECT nombre, ID FROM paises ORDER BY ID"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, paises) '''''''' En ResponseSuccess hará el Case de paises
End Sub
' Esta es la Respuesta de la orden hc.Execute
Sub hc_ResponseSuccess (Response As HttpResponse, tarea As Int)
Dim res As String
res = Response.GetString("UTF8")
Log("Respuesta del servidor: " & res)
'res = [{"nombre":"Argentina","id":"AR"},.... hasta ....,{"nombre":"Venezuela","id":"VE"}]
Dim parser As JSONParser
parser.Initialize(res)
Select tarea
' ************* PAISES *****************
Case paises
' Añade paises la ListView1
Dim countries As List
countries.Initialize
countries = parser.NextArray
For i = 0 To countries.Size - 1
Dim m As Map
m = countries.Get(i)
Dim Renglon As Renglones
Renglon.Renglon1 = m.Get("ID") ' ES
Renglon.Renglon2 = m.Get("nombre") ' España
ListView1.AddTwoLines2(Renglon.Renglon1, Renglon.Renglon2, Renglon)
Next
ProgressDialogHide
' ************* POBLACION **************
Case poblacion
Dim l As List
l = parser.NextArray
If l.Size = 0 Then
Label1.Text = "N/A"
Else
Dim m As Map
m = l.Get(0)
Label1.Text = NumberFormat2(m.Get("poblacion"),0, 0, 0, True) & ".000"
End If
End Select
Response.Release
End Sub
' Cuando pulsa en el ListView, busca en la BD del Servidor la población
Sub ListView1_ItemClick (Position As Int, Value As Object)
If IsBackgroundTaskRunning(hc, poblacion) Then ' Está ocupado en llamada anterior.
ToastMessageShow("Espera hasta completar la llamada anterior.", False)
Return
End If
Dim Renglon As Renglones
Renglon = Value
Label2.Text = Renglon.Renglon2 ' España
Label1.Text = "Conectando con el servidor..."
Dim req As HttpRequest
Dim Query As String
Query="SELECT poblacion FROM paises WHERE ID='" & Renglon.Renglon1 & "'"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, poblacion) '''''''' En ResponseSuccess hará el Case de poblacion
End Sub
' Error en la conexión con la Base de datos.
Sub hc_ResponseError (Response As HttpResponse, Reason As String, StatusCode As Int, tarea As Int)
Log("Error: " & Reason & ", StatusCode: " & StatusCode)
If Response <> Null Then
Log(Response.GetString("UTF8"))
Response.Release
End If
ProgressDialogHide
End Sub
|
El código lo que hace es ir al archivo paises.php,(ver en la tabla más abajo) este va a la base de datos y mediante la línea:
$query = file_get_contents("php://input");
el paises.php devuelve el listado de todos los paises en un formato muy conocido llamado JSON. (de Json a html).
print json_encode($rows);
El programa B4A, toma los datos del archivo JSON de la forma...
a) cuando pide todos los registros...
Respuesta del servidor: [{"nombre":"Argentina","id":"AR"},{"nombre":"Bolivia","id":"BO"},.... hasta ........,{"nombre":"Venezuela","id":"VE"}]
b) cuando pide población...
Llamada a población: (JSONTokener) at character 0 of [{"poblacion":"15000"}]
lo convierte (parser), lo Mapea, es decir trocea los campos
For i = 0 To countries.Size - 1
Dim m As Map
m = countries.Get(i)
y los presenta en el ListView.
Es un código un poco complicados para los que se inician en este tipo de programación, pero creo que haciendo pruebas le puedes sacar partido y adaptarlo a tus necesidades.
______________________
- Servidor Web.
Si hemos instalado el servidor Web WAMP, vamos a la carpeta C:\wamp\www y grabamos el archivo... paises.php (está en la tabla más abajo).
La base de datos se llama: android.
El nombre del usuario y la contraseña, se refiere a los datos de autentificación que debes poner mediante phpmyadmin en esa base de datos. Mira en Privilegios...
En Privilegios ponemos nombre y contraseña, en nuestro caso ponemos root y 1234 respectivamente.
Pulsamos en root. Editar los privilegios, marcamos todas las opciones.
Bajamos el scroll de la derecha, localizamos contraseña y ponemos 1234.
Ya podemos poner en el código PHP, el nombre de usuario y contraseña:
$databaseusername ="root";
$databasepassword = "1234";
Atención, debes guardar este archivo en C:\wamp\www con el nombre paises.php
paises.php (Copiar este archivo en C:\wamp\www)
|
// De los tutoriales de b4a
// Adaptado a local por Juan Antonio Villalpando
// juana1991@yahoo.com
<?php
$databasehost = "localhost";
$databasename = "android";
$databaseusername ="root";
$databasepassword = "1234";
$con = mysql_connect($databasehost,$databaseusername,$databasepassword) or die(mysql_error()); mysql_set_charset("utf8");
mysql_select_db($databasename) or die(mysql_error());
$query = file_get_contents("php://input");
$sth = mysql_query($query);
if (mysql_errno()) {
header("HTTP/1.1 500 Internal Server Error");
echo $query.'\n';
echo mysql_error();
}
else
{
$rows = array();
while($r = mysql_fetch_assoc($sth)) {
$rows[] = $r;
}
print json_encode($rows);
}
?>
|
¡¡¡¡ No me funcionaaaaaaaaaaaaaaa !!! ARGGGGGGGGGGGGG!!!
- Bien, bien..., mantengamos la calma.
- Aquí tienes un tutorial más sencillo. |
Errores obtenidos. |
NOTA 1:
Algunos usuarios obtienen el siguiente error con este código utilizando versiones de PHP 5.5 o superiores.
Deprecated: mysql_connect(): The mysql extension is deprecated and will be removed in the future: use mysqli or PDO instead in
Para solventarlo prueba poner esta línea azul...
<?php
error_reporting (E_ALL ^ E_NOTICE ^ E_DEPRECATED);
$databasehost = "localhost";
$databasename = "android";
$databaseusername ="root";
$databasepassword = "1234";
$con = mysql_connect($databasehost,$databaseusername,$databasepassword) or die(mysql_error());
mysql_set_charset("utf8");
mysql_select_db($databasename) or die(mysql_error());
$query = file_get_contents("php://input");
....................
O también esta otra manera...
<?php
$databasehost = "localhost";
$databasename = "android";
$databaseusername ="root";
$databasepassword = "1234";
$con = mysqli_connect( $databasehost,$databaseusername,$databasepassword, $databasename ) or die(mysql_error());
mysql_set_charset("utf8");
$query = file_get_contents("php://input" );
...................
_____________________________________________________________________________________
NOTA 2:
Otros usuarios obtienen el error: android.os.NetworkOnMainThreadException
para solucionarlo modificamos la Subrutina Activity_Create de la siguiente manera y activamos las librerías Phone y Reflection.
Sub Activity_Create(FirstTime As Boolean)
If FirstTime Then
hc.Initialize("hc")
End If
Activity.LoadLayout("1")
Buscar_lista_de_paises
' Evita el error android.os.NetworkOnMainThreadException
' Activar librerías Phone y Reflection
Dim p As Phone
If p.SdkVersion >= 9 Then
Dim r As Reflector
r.Target = r.CreateObject("android.os.StrictMode$ThreadPolicy$Builder")
r.Target = r.RunMethod("permitAll")
r.Target = r.RunMethod("build")
r.RunStaticMethod("android.os.StrictMode", "setThreadPolicy", _
Array As Object(r.Target), Array As String("android.os.StrictMode$ThreadPolicy"))
End If
End Sub
|
ERRORES
|
Este error ocurre cuando se utiliza las nuevas versiones a partir de la SDK android 2.3. Para corregirlo hay que cambiar la vieja librería httputils por la nueva okhttp
La librería OkHttp es casi igual que la antigura Http, pero los nombres de los objetos deben comenzar por Ok
(OkHttpClient, OkHttpResponse and OkHttpRequest)
Puedes obtener información en el foro oficial:
https://www.b4x.com/android/forum/threads/okhttp-replaces-the-http-library.54723/#content |
___________________________
2.- Introducir datos en la Base de Datos, MySQL.
Ahora lo vamos a realizar al revés, es decir desde el Android vamos a introducir datos en una base de datos de tipo MySQL en un servidor web.
Vamos a utilizar el mismo servidor visto anteriormente y la misma base de datos.
Designer - Layout
|
Librería necesaria (HTTP. La JSON no es necesaria en este código)
|
Mediante el Designer creamos la pantalla que muestro en el dibujo de la izquierda.
Insertamos tres Label: Label1, Label2 y Label3
Insertamos tres EditText: EditText1, EditText2 y EditText3
Insertamos un Button1
Guardamos el Layout con el nombre: Layout
|
Fíjate en la línea:
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
ahí debes poner tu IP local.
Código del Basic4Android
|
' Juan Antonio Villalpando
' juana1991@yahoo.com
Sub Process_Globals
Dim hc As HttpClient
End Sub
Sub Globals
Dim EditText1, EditText2, EditText3 As EditText
Dim ID, nombre, poblacion, datos As String
End Sub
Sub Activity_Create(FirstTime As Boolean)
If FirstTime Then
hc.Initialize("hc")
End If
Activity.LoadLayout("Layout") ' Cargamos el Designer
End Sub
Sub Activity_Resume
End Sub
Sub Activity_Pause (UserClosed As Boolean)
End Sub
Sub Button1_Click
ID = EditText1.Text
nombre = EditText2.Text
poblacion = EditText3.Text
Dim req As HttpRequest
Dim Query As String
Query="INSERT INTO paises (ID, nombre, poblacion) VALUES ('" & ID & "','" & nombre & "','" & poblacion & "')"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, 1)
End Sub
Sub hc_ResponseSuccess (Response As HttpResponse, tarea As Int)
Dim resultString As String
resultString = Response.GetString("UTF8")
Msgbox("Los datos han sido almacenados", "Éxito de operación")
End Sub
Sub hc_ResponseError (Response As HttpResponse, Reason As String, StatusCode As Int, tarea As Int)
Log("Error: " & Reason & ", StatusCode: " & StatusCode)
If Response <> Null Then
Log(Response.GetString("UTF8"))
Response.Release
End If
End Sub
|
- Ten cuidado en esta línea con las comillas "dobles" y 'simples' y con las '"dos juntas"'
Query="INSERT INTO paises (ID, nombre, poblacion) VALUES ('" & ID & "','" & nombre & "','" & poblacion & "')"
- Fíjate que el archivo paises.php, es el mismo que el del apartado anterior, este archivo no tiene código de inserción. Solo se utiliza para conectar con la base de datos, ya que el código de inserción va en la misma llamada.
Query="INSERT INTO paises (ID, nombre, poblacion) VALUES ('" & ID & "','" & nombre & "','" & poblacion & "')"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
- Con este código podemos poner paises con espacios: Costa Rica, Rep. Dominicana.
___________________________
3.- Borrar datos en la Base de Datos, MySQL.
Vamos a volver al primer programa e insertar un botón de borrado, pulsaremos sobre un país y en caso de que lo queramos borrar pulsamos el botón de "Borrar"
Designer - Layout
|
Librería necesaria (HTTP y JSON)
|
Mediante el Designer creamos la pantalla que muestro en el dibujo de la izquierda.
Está basado en el primer programa, solamente he añadido un Button de "Borrar"
Guardamos el Layout con el nombre: 1
El código es una ampliación del primer programa, solamente he añadido las líneas indicadas.
|
Código del Basic4Android
|
' De los tutoriales de b4a
' Adaptado a local por Juan Antonio Villalpando
' juana1991@yahoo.com
Sub Process_Globals
Dim hc As HttpClient
Dim paises, poblacion As Int
paises = 1 ' Es la tarea 1
poblacion = 2 ' Es la tarea 2
End Sub
Sub Globals
' Renglones puede contener dos renglones:
' Renglon1 (ES)
' Renglon2 (España)
Type Renglones (Renglon1 As String, Renglon2 As String)
Dim Label1, Label2 As Label
Dim ListView1 As ListView
Dim borraID As String ' PARA BORRAR, CÓDIGO JUAN ANTONIO ***************** End Sub
Sub Activity_Create(FirstTime As Boolean)
If FirstTime Then
hc.Initialize("hc")
End If
Activity.LoadLayout("1")
Buscar_lista_de_paises
End Sub
Sub Buscar_lista_de_paises
ProgressDialogShow("Buscando lista de países.")
Dim req As HttpRequest
Dim Query As String
Query="SELECT nombre, ID FROM paises ORDER BY ID"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, paises) '''''''' En ResponseSuccess hará el Case de paises
End Sub
' Esta es la Respuesta de la orden hc.Execute
Sub hc_ResponseSuccess (Response As HttpResponse, tarea As Int)
Dim res As String
res = Response.GetString("UTF8")
Log("Respuesta del servidor: " & res)
'res = [{"name":"Argentina","id":"AR"},.... hasta ....,{"name":"Venezuela","id":"VE"}]
Dim parser As JSONParser
parser.Initialize(res)
Select tarea
' ************* PAISES *****************
Case paises
' Añade paises la ListView1
Dim countries As List
countries.Initialize
countries = parser.NextArray
For i = 0 To countries.Size - 1
Dim m As Map
m = countries.Get(i)
Dim Renglon As Renglones
Renglon.Renglon1 = m.Get("ID") ' ES
Renglon.Renglon2 = m.Get("nombre") ' España
ListView1.AddTwoLines2(Renglon.Renglon1, Renglon.Renglon2, Renglon)
Next
ProgressDialogHide
' ************* POBLACION **************
Case poblacion
Dim l As List
l = parser.NextArray
If l.Size = 0 Then
Label1.Text = "N/A"
Else
Dim m As Map
m = l.Get(0)
Label1.Text = NumberFormat2(m.Get("poblacion"),0, 0, 0, True) & ".000"
End If
End Select
Response.Release
End Sub
' Cuando pulsa en el ListView, busca en la BD del Servidor la población
Sub ListView1_ItemClick (Position As Int, Value As Object)
If IsBackgroundTaskRunning(hc, poblacion) Then ' Está ocupado en llamada anterior.
ToastMessageShow("Espera hasta completar la llamada anterior.", False)
Return
End If
Dim Renglon As Renglones
Renglon = Value
Label2.Text = Renglon.Renglon2 ' España borraID = Renglon.Renglon1 ' PARA BORRAR, CÓDIGO JUAN ANTONIO ******************
Label1.Text = "Conectando con el servidor..."
Dim req As HttpRequest
Dim Query As String
Query="SELECT poblacion FROM paises WHERE ID='" & Renglon.Renglon1 & "'"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, poblacion) '''''''' En ResponseSuccess hará el Case de poblacion
End Sub
' Error en la conexión con la Base de datos.
Sub hc_ResponseError (Response As HttpResponse, Reason As String, StatusCode As Int, tarea As Int)
Log("Error: " & Reason & ", StatusCode: " & StatusCode)
If Response <> Null Then
Log(Response.GetString("UTF8"))
Response.Release
End If
ProgressDialogHide
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'''''''''' ESTA ES LA PARTE DEL CODIGO QUE HACE EL BORRADO
Sub Button1_Click
Dim req As HttpRequest
Dim Query As String
Query="DELETE FROM paises WHERE ID='" & borraID & "'"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, 3) ' La tarea 3 no existe en el Select
ListView1.Clear
Buscar_lista_de_paises
Label1.Text=""
Label2.Text=""
End Sub
|
En el código anterior he actuado en las líneas...
Dim borraID As String ' PARA BORRAR, CÓDIGO JUAN ANTONIO *********
borraID = Renglon.Renglon1 ' PARA BORRAR, CÓDIGO JUAN ANTONIO *******
y la Subrutina final del Button1_Click.
Debes poner tu IP local en...
req.InitializePost2("http://192.168.1.3/paises.php", query.GetBytes("UTF8"))
Cuidado con las comillas dobles y simple:
Query="DELETE FROM paises WHERE ID='" & borraID & "'"
- Fíjate que el archivo paises.php, es el mismo que el del apartado anterior, este archivo no tiene código de borrado. Solo se utiliza para conectar con la base de datos, ya que el código de inserción va en la misma llamada.
Query="DELETE FROM paises WHERE ID='" & borraID & "'"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
__________________________________
Si miras más abajo en los antiguos códigos te darás cuenta que se estudian dos maneras de actuar sobre la base de datos
- una poniendo el Query de la orden MySQL (en este caso el archivo paises.php, solo se utiliza para hacer la conexión con la base de datos, pero el archivo no realiza el borrado).
Query="DELETE FROM paises WHERE ID='" & borraID & "'"
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
- otra llamando a un archivo .php donde se encuentra el código de borrado
datos="http://192.168.1.3/androidbd4.php?ID=" & borraID
Dim req As HttpRequest
req.InitializeGet(datos)
hc.Execute(req, 3)
___________________________
4.- Buscar un país mediante un casillero.
Vamos a seguir modificando el código. Ahora vamos a introducir un casillero (EditText) y otro botón (Button2).
Escribiremos el nombre de cualquier país, que se encuentre en la base de datos. Al pulsar el botón el programa irá a la base de datos, buscará y tomará la información de código, nombre y población de país introducido y lo devolverá al programa.
En los Label1 y Label2 aparecerá el nombre del país y su población.
Designer - Layout
|
|
Mediante el Designer modificamos nuestro Layout como muestro en el dibujo de la izquierda.
Añado un EditText1 y un Button1 cuyo texto es Buscar.
El Layout sigue llamándose 1 como en los apartados anteriores.
|
Vuelvo a poner el código completo con las modificaciones de BUSCAR.
Código del Basic4Android
|
' De los tutoriales de b4a
' Adaptado a local por Juan Antonio Villalpando
' juana1991@yahoo.com
Sub Process_Globals
Dim hc As HttpClient
Dim paises, poblacion, buscar As Int
paises = 1 ' Es la tarea 1
poblacion = 2 ' Es la tarea 2
buscar = 3 ' Es la tarea 3 PARA BUSCAR, CÓDIGO JUAN ANTONIO ------
End Sub
Sub Globals
' Renglones puede contener dos renglones:
' Renglon1 (ES)
' Renglon2 (España)
Type Renglones (Renglon1 As String, Renglon2 As String)
Dim Label1, Label2 As Label
Dim ListView1 As ListView
Dim EditText1 As EditText
Dim borraID As String ' PARA BORRAR, CÓDIGO JUAN ANTONIO *********
End Sub
Sub Activity_Create(FirstTime As Boolean)
If FirstTime Then
hc.Initialize("hc")
End If
Activity.LoadLayout("1")
Buscar_lista_de_paises
End Sub
Sub Buscar_lista_de_paises
ProgressDialogShow("Buscando lista de países.")
Dim req As HttpRequest
Dim Query As String
Query="SELECT nombre, ID FROM paises ORDER BY ID"
' req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
req.InitializePost2("http://elandroide.webatu.com/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, paises) '''''''' En ResponseSuccess hará el Case de paises
End Sub
' Esta es la Respuesta de la orden hc.Execute
Sub hc_ResponseSuccess (Response As HttpResponse, tarea As Int)
Dim res As String
res = Response.GetString("UTF8")
Log("Respuesta del servidor: " & res)
'res = [{"name":"Argentina","id":"AR"},.... hasta ....,{"name":"Venezuela","id":"VE"}]
Dim parser As JSONParser
parser.Initialize(res)
Select tarea
' ************* PAISES *****************
Case paises
' Añade paises la ListView1
Dim countries As List
countries.Initialize
countries = parser.NextArray
For i = 0 To countries.Size - 1
Dim m As Map
m = countries.Get(i)
Dim Renglon As Renglones
Renglon.Renglon1 = m.Get("ID") ' ES
Renglon.Renglon2 = m.Get("nombre") ' España
ListView1.AddTwoLines2(Renglon.Renglon1, Renglon.Renglon2, Renglon)
Next
ProgressDialogHide
' ************* POBLACION **************
Case poblacion
Dim l As List
l = parser.NextArray
If l.Size = 0 Then
Label1.Text = "N/A"
Else
Dim m As Map
m = l.Get(0)
Label1.Text = NumberFormat2(m.Get("poblacion"),0, 0, 0, True) & ".000"
End If
' ************* BUSCAR, CÓDIGO JUAN ANTONIO *****------
Case buscar
Dim l As List
l = parser.NextArray
If l.Size = 0 Then
Label1.Text = "N/A"
Else
Dim m As Map
m = l.Get(0)
Label1.Text = m.Get("nombre")
Label2.Text = m.Get("poblacion")
End If
End Select
Response.Release
End Sub
' Cuando pulsa en el ListView, busca en la BD del Servidor la población
Sub ListView1_ItemClick (Position As Int, Value As Object)
If IsBackgroundTaskRunning(hc, poblacion) Then ' Está ocupado en llamada anterior.
ToastMessageShow("Espera hasta completar la llamada anterior.", False)
Return
End If
Dim Renglon As Renglones
Renglon = Value
Label2.Text = Renglon.Renglon2 ' España
borraID = Renglon.Renglon1 ' PARA BORRAR, CÓDIGO JUAN ANTONIO *******
Label1.Text = "Conectando con el servidor..."
Dim req As HttpRequest
Dim Query As String
Query="SELECT poblacion FROM paises WHERE ID='" & Renglon.Renglon1 & "'"
' req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
req.InitializePost2("http://elandroide.webatu.com/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, poblacion) '''''''' En ResponseSuccess hará el Case de poblacion
End Sub
' Error en la conexión con la Base de datos.
Sub hc_ResponseError (Response As HttpResponse, Reason As String, StatusCode As Int, tarea As Int)
Log("Error: " & Reason & ", StatusCode: " & StatusCode)
If Response <> Null Then
Log(Response.GetString("UTF8"))
Response.Release
End If
ProgressDialogHide
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'''''''''' ESTA ES LA PARTE DEL CODIGO QUE HACE EL BORRADO
Sub Button1_Click
Dim req As HttpRequest
Dim Query As String
Query="DELETE FROM paises WHERE ID='" & borraID & "'"
' req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
req.InitializePost2("http://elandroide.webatu.com/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, 4) ' ------- He cambiado esto, 4 es una tarea que no existe en Select
ListView1.Clear
Buscar_lista_de_paises
Label1.Text=""
Label2.Text=""
End Sub
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'''''''''' ESTA ES LA PARTE DEL CODIGO QUE HACE LA BÜSQUEDA
Sub Button2_Click
Dim req As HttpRequest
Dim Query As String
Dim busca As String
busca = EditText1.Text
Query="SELECT * FROM paises WHERE nombre LIKE '" & busca & "'"
' req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
req.InitializePost2("http://elandroide.webatu.com/paises.php", Query.GetBytes("UTF8"))
hc.Execute(req, buscar)
End Sub
|
Comentarios
Al final del código he añadido la Subrutina del Button2, en donde obtengo el nombre del país que el usuario quiere buscar.
Establezco una llamada de búsqueda:
Query="SELECT * FROM paises WHERE nombre LIKE '" & busca & "'"
El programa va al servidor MySQL.
En este caso he probado el código en un servidor gratuito en Internet llamado 000web.com (Al final de esta página indico cómo me he registrado y creado una base de datos en ese servidor de Internet).
req.InitializePost2("http://elandroide.webatu.com/paises.php", Query.GetBytes("UTF8"))
Lanza llamada al servidor mediante
hc.Execute(req, buscar)
buscar es una variable que utilizaré posteriormente cuando me llegue la respuesta.
Cuando llega la respuesta, el código se dirige a la subrutina:
' Esta es la Respuesta de la orden hc.Execute
Sub hc_ResponseSuccess (Response As HttpResponse, tarea As Int)
La información se obtiene en la variable
res = Response.GetString("UTF8")
Esta información viene en formato JSON (por lo cual necesitamos la librería correspondiente para fácilmente desglosar la información).
El código entra en un Select que tiene tres opciones (paises, poblacion y buscar), cuando enviamos la llamada del hc.Execute digimos que cuando viniera la respuesta tomara en cuenta la opción buscar hc.Execute(req, buscar)
De tal manera que cuando llega la respuesta el código se dirige a la parte
************* BUSCAR, CÓDIGO JUAN ANTONIO *****------
Case buscar
En esa parte desglosa la información obtenida del código JSON
Respuesta del servidor: [{"ID":"GU","nombre":"Guatemala","poblacion":"16000"}]
y presenta el país y su población en los Label1 y Label2.
Al principio del código se le ha asignado a buscar un número de tarea para el funcionamiento del Case
buscar = 3 ' Es la tarea 3 PARA BUSCAR, CÓDIGO JUAN ANTONIO ------
____________________________________________
El programa se podría haber realizado de otra manera.
Hacemos una llamada para obtener todos los paises y su población, como lo hemos hecho para que los paises se inserten en el ListView.
Esa llamada, en donde están todos los paises, se obtiene en la variable res
'res = [{"name":"Argentina","id":"AR"},.... hasta ....,{"name":"Venezuela","id":"VE"}]
Una vez que tenemos todos los paises en la variable res, buscamos la del país requerido.
Es decir, podemos bajar toda la base de datos desde el servidor MySQL a nuestro teléfono Android, y una vez bajada podemos actuar mediante la librería JSON en la variable res que es donde se encuentra bajada toda la base de datos.
___________________________
5.- Hacerlo funcionar en Internet.
Una vez que has montado el paquete WAMP en tu ordenador y has visto funcionar la base de datos en tu red local (LAN), vamos hacerlo funcionar en Internet (WAN), para ello primero consultamos nuestra IP pública entrando en una web como esta...
http://www.vermiip.es/
esa que indica es tu IP pública, es la que debes poner donde antes ponía...
req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
- También tienes que ir al Panel de control y deshabilitar el Firewall para que puedan entrar conexiones (más adelante puedes buscar cómo dejar pasar la conexiones al puerto 80 a través del Firewall sin deshabilitarlo totalmente).
- Por último debes "abrir puerto del router", concretamente debes abrir el puerto 80 del Router. Abrir el puerto 80 significa en este caso, asociar la IP local del ordenador que tiene instalado el WAMP con el puerto 80.
192.168.1.3 ............. 80
- Busca en Internet cómo puedes entrar en la configuración de tu Router (escribiendo en un navegador tu puerta de enlace).
- Consulta cuál es tu nombre y contraseña para entrar en tu Router.
- Mira en qué opción de la configuración de tu Router se establece la IP y su puerto.
La mejor web sobre abrir puertos es ésta, en inglés:
http://portforward.com/english/routers/port_forwarding/routerindex.htm
Una vez que tengas todo esto configurado, se podrá entrar en la base de datos que se encuentra en tu ordenador, a través de WAMP y de nuestra aplicación del móvil.
Incluso si haces una página web llamada index.htm y la guardar en C:\wamp\www podrá ver esa página escribiendo desde cualquier navegador tu IP Pública.
___________________________
6.- Un servidor de Internet gratuito y sin publicidad.
- Otra manera de hacerlo es tener nuestra base de datos y nuestros archivos .php en un servidor web comercial (hosting), en este caso gratuito.
- Recomiendo dos sitios web desde donde podemos obtener un hosting gratuito y sin publicidad:
- byehost.com (Free host): http://byethost.com/free-hosting/news
- webhost.com (Free host): http://www.000webhost.com/
NOTA: en byethost, a pesar de ser un buen servidor gratuito he comprobado que no funciona, así que aconsejo probarlo en:
http://www.000webhost.com/
- Entramos en su web y pulsamos sobre Order now en Free Hosting. Nos registramos indicando nuestro correo donde recibiremos confirmación de la activación.
- Una vez confirmada la cuenta entramos escribiendo nuestra dirección de correos y la contraseña que elegimos al registrarnos.
En mi caso he elegido el subdominio elandroide.webatu.com.
Pulsamos sobre Go to CPanel.
- Mediante el File Manager vamos a subir al servidor nuestro archivo paises.php
- En el directorio public_html es donde debemos subir nuestro archivo paises.php
- Seleccionamos nuestro archivo paises.php y pulsamos sobre la marca verde para subirlo.
- Ahora vamos a crear la base de datos. Pulsamos en MySQL. y creamos nuestra base de datos.
- Mi base de datos se llamará: a9048122_android
en el nombre de usuario he puesto lo mismo: a9048122_android
la contraseña de la base de datos: ********
Pulsamos Create database y nos indicará que...
para ir a la base de datos deberé escribir: msql12.000webhost.com
(en este caso no es localhost, como estamos acostrumbrado poner.)
- Una vez creada la base de datos, volvemos al Panel de Control y pulsamos en phpMyAdmin, desde aquí podemos configurar la base de datos.
- He creado la tabla paises con 3 columnas.
ID, nombre y poblacion
(respeta las mayúsculas y minúsculas, no le pongas acento a poblacion).
Son de tipo varchar y de tamaño 4, 30 y 11 respectivamente, como indica el gráfico.
- Una vez creada Insertamos varios paises...
- Podríamos ir arriba de esta página de este tutorial, copiar el archivo paises.sql e Importarlos a nuestra base de datos, de esta manera no tendremos que copiar los paises.
Cuando Importes el archivo paises.sql le pones el tipo de carácter latin1 (para que salgan acentos y la eñe)
- Modificación de los códigos:
En Basic4Android debemos cambiar:
' req.InitializePost2("http://192.168.1.3/paises.php", Query.GetBytes("UTF8"))
req.InitializePost2("http://elandroide.webatu.com/paises.php", Query.GetBytes("UTF8"))
En paises.php debemos cambiar:
$databasehost = "mysql12.000webhost.com";
$databasename = "a9048122_android";
$databaseusername ="a9048122_android";
$databasepassword = "contraseña";
__________________________________
NOTA:
A veces cuando hacemos funcionar estos tipos de programas de base de datos en un móvil reciente no funciona, una idea para intentar que funcione sería bajar la librería: mysql-connector-java-5.1.22-bin.jar de esta entrada de foro.
Luego crear una carpeta llamada libs en la misma carpeta donde tenemos la aplicación que estamos realizando.
Después vamos a Tools / Configure Paths / Additionals libraries y poner la dirección de la carpeta donde hemos copiado la librería.
___________________________
- SQLite.
En un tutorial posterior he puesto varias aplicaciones basadas en SQLite.
__________________
Imágenes en una base de datos SQLite.
En este caso se ha creado una base de datos que contiene imágenes, esta base de datos no está en Internet ni utiliza MySQL, está en el directorio Files y es de SQLite (pero se podría adaptar a MySQL)
Baja el código Blob1.zip de esta página.