<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Lipido&#039;s Lab &#187; Informática</title>
	<atom:link href="https://www.sing-group.org/~lipido/blog/category/informatica/feed/" rel="self" type="application/rss+xml" />
	<link>https://www.sing-group.org/~lipido/blog</link>
	<description>Web 2.0: &#34;nobody even knows what it means&#34;, Tim Berners</description>
	<lastBuildDate>Wed, 01 Apr 2020 07:57:31 +0000</lastBuildDate>
	<language>es-ES</language>
		<sy:updatePeriod>hourly</sy:updatePeriod>
		<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.8</generator>
	<item>
		<title>Create a SSH gateway for Git SSH backends</title>
		<link>https://www.sing-group.org/~lipido/blog/2016/12/03/create-a-ssh-gateway-for-git-ssh-backends/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2016/12/03/create-a-ssh-gateway-for-git-ssh-backends/#comments</comments>
		<pubDate>Sat, 03 Dec 2016 11:58:03 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>
		<category><![CDATA[git]]></category>
		<category><![CDATA[gitlab]]></category>
		<category><![CDATA[proxy]]></category>
		<category><![CDATA[ssh]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/?p=279</guid>
		<description><![CDATA[This post shows how to connect to a Gitlab (or any Git SSH server) private server via SSH through a front-end public server you own. [CLIENT] --&#62; [FRONT-END SSH-SERVER] --&#62; [BACK-END GIT SSH-SERVER] On Git back-end server Create the keys for your users as usual (in this example, we assume Gitlab, so the web interface [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>This post shows how to connect to a Gitlab (or any Git SSH server) private server via SSH through a front-end public server you own.</p>
<p><code>[CLIENT] --&gt; [FRONT-END SSH-SERVER] --&gt; [BACK-END GIT SSH-SERVER]</code></p>
<h2>On Git back-end server</h2>
<p>Create the keys for your users as usual (in this example, we assume Gitlab, so the web interface is enough)</p>
<p>Go to the file /var/opt/gitlab/.ssh/authorized_keys and copy all entries. An example of the contents of this file with two users could be:<br />
<code><br />
command="/opt/gitlab/embedded/service/gitlab-shell/bin/gitlab-shell key-1",no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-pty ssh-rsa AAAAB3Nz...rbR6L75887 user1@gmail.com<br />
command="/opt/gitlab/embedded/service/gitlab-shell/bin/gitlab-shell key-2",no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-pty ssh-rsa AAAAB3NzaC1...hVE/141 user2@hotmail.com<br />
</code></p>
<h2>On front-end (intermediate) server</h2>
<p>Create the user git, and create and edit the .ssh/authorized_keys file.<br />
<code>sudo adduser git<br />
su git<br />
mkdir .ssh<br />
touch ./ssh/authorized_keys &amp;&amp; chmod 700 .ssh/authorized_keys<br />
</code></p>
<p>Paste the contents of the file, but by replacing the &#8220;command&#8221; in each entry with this content:</p>
<p><code>command="ssh git@backend-server $SSH_ORIGINAL_COMMAND" ssh-rsa AAAAB3Nz...rbR6L75887 user1@gmail.com<br />
command="ssh git@backend-server $SSH_ORIGINAL_COMMAND" ssh-rsa AAAAB3NzaC1...hVE/141 user2@hotmail.com<br />
</code></p>
<h2>On client machine</h2>
<p>Create or edit your .ssh/config file by adding the following entry:<br />
<code>host frontend-server-name.com<br />
hostname frontend-server-name.com<br />
user git<br />
identityfile /home/user1/.ssh/id_rsa<br />
ForwardAgent yes<br />
</code><br />
The important element here is <b>ForwardAgent</b> which allows the intermediate server to use our key when login via ssh to the backend server. You may need to add the key explicity to the SSH agent via:</p>
<p><code>ssh-add <code>/home/user1/.ssh/id_rsa</code><br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2016/12/03/create-a-ssh-gateway-for-git-ssh-backends/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Interfaces de usuario HTML/CSS/Javascript ¿nuevo estándar?</title>
		<link>https://www.sing-group.org/~lipido/blog/2013/05/07/interfaces-de-usuario-htmlcssjavascript-nuevo-estandar/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2013/05/07/interfaces-de-usuario-htmlcssjavascript-nuevo-estandar/#comments</comments>
		<pubDate>Tue, 07 May 2013 08:36:34 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>
		<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/?p=159</guid>
		<description><![CDATA[En los últimos años la interfaces de usuario para aplicaciones web &#8220;ricas&#8221;, implementadas con el estándar HTML/CSS/Javascript, han experimentado grandes avances, en detrimento de las tecnologías basadas en plugins, como Flash o los Applets Java. Comenzando, por ejemplo, por el componente Canvas de HTML5, que permite el dibujado 2D a bajo nivel con Javascript, posibilitando la creación de casi cualquier componente [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>En los últimos años la interfaces de usuario<b> para aplicaciones web</b><strong> &#8220;ricas&#8221;,</strong> implementadas con el estándar HTML/CSS/Javascript, han experimentado grandes avances, en detrimento de las tecnologías basadas en plugins, como <a href="http://en.wikipedia.org/wiki/Adobe_Flash">Flash</a> o los <a href="http://en.wikipedia.org/wiki/Java_applet">Applets Java</a>. Comenzando, por ejemplo, por el componente <a href="http://en.wikipedia.org/wiki/Canvas_element">Canvas</a> de <a href="http://en.wikipedia.org/wiki/HTML5">HTML5</a>, que permite el dibujado 2D a bajo nivel con Javascript, posibilitando la creación de casi cualquier componente de interfaz de usuario sobre el navegador web sin necesidad de plugins. Continuando por la proliferación de potentes frameworks Javascript para <strong>animaciones</strong> (<a href="http://jquery.com/">JQuery</a>, <a href="http://mootools.net/">Mootools</a>, <a href="http://script.aculo.us/">Script.aculo.us</a>, etc.), <strong>widgets avanzados</strong> (<a href="http://jqueryui.com/">JQuery UI</a>, <a href="http://jquerymobile.com/">JQuery Mobile</a>) o, incluso, <strong>lógica y <a href="http://weblogs.asp.net/dwahlin/archive/2012/07/08/javascript-data-binding-frameworks.aspx">data-binding</a></strong> (<a href="http://d3js.org/">d3.js</a>, <a href="http://backbonejs.org/">backbone.js</a>, <a href="http://angularjs.org/">AngularJS</a>, etc.), a los cuales se unen <strong>nuevos lenguajes</strong> de todavía más alto nivel como <a href="http://coffeescript.org/">Coffeescript</a>, <a href="http://www.dartlang.org/">Dart</a> o <a href="http://lesscss.org/">LESS</a> (para CSS). Todo ello conforma uno de los ecosistemas de tecnologías más activo actualmente, clave para los diseñadores de interfaces de usuario de las aplicaciones web más impactantes. Pero <i>¿hay vida más allá <span style="text-decoration: underline;">de la propia web</span> para HTML/CSS/Javascript?</i> La respuesta es sí.</p>
<p>El primer sector fuera de la Web, es el sector de las interfaces de usuario para<b> dispositivos móviles.</b> El hecho de que los <i>Smartphone, </i>que presentan grandes capacidades a nivel nativo (como localización GPS, cámara de fotos/vídeo, acelerómetro, etc.), se comercialicen sobre tres plataformas muy distintas (<a href="http://en.wikipedia.org/wiki/Android_(operating_system)">Android</a>, <a href="http://en.wikipedia.org/wiki/IOS">iOS</a>, <a href="http://en.wikipedia.org/wiki/BlackBerry_OS">BlackBerry OS</a> y <a href="http://en.wikipedia.org/wiki/Windows_Phone">Windows Phone</a>), unido a la necesidad de publicar aplicaciones en las &#8220;app store&#8221; rápidamente, ha llevado consigo que se busquen soluciones &#8220;<a href="http://en.wikipedia.org/wiki/Write_once,_run_anywhere">programa una vez, ejecuta en cualquier parte</a>&#8221; (a costa de sacrificar rendimiento). Aquí también se ha abierto camino HTML/CSS/Javascript (p. ej: <a href="http://jquerymobile.com/">JQuery Mobile</a>/<a href="http://phonegap.com/">PhoneGap</a>). <i>¿Cómo funcionan en general?</i> Básicamente la idea de esta solución consiste en que la API de la plataforma (móvil en este caso) proporcione:</p>
<ol>
<li>Un motor de renderizado HTML/CSS/Javascript (es decir, un navegador incrustable), que se suele conocer normalmente desde la API nativa como &#8220;WebView&#8221; (frecuentemente está implementado con <a href="http://www.webkit.org/">WebKit</a>).</li>
<li>Una función para &#8220;inyectar&#8221; objetos nativos y hacerlos visibles como objetos Javascript bajo el nombre de una variable. De esta forma las llamadas desde Javascript al objeto inyectado en Javascript serán atendidas realmente por el objeto nativo.</li>
<li>Una función para ejecutar código Javascript arbitrario (en forma de cadena de texto, al estilo de la propia <i>eval()</i> de Javascript). De esta forma se pueden llamar a funciones Javascript desde el código nativo.</li>
</ol>
<p>Un ejemplo paradigmático que explota esta vía es <a href="http://phonegap.com/">PhoneGap</a>, que amplía la API de Javascript para dar una <b>capa de abstracción multiplataforma</b> sobre las capacidades de los smartphone.</p>
<p>Finalmente, en el campo de las interfaces de usuario para<b> aplicaciones de escritorio</b>, siguen surgiendo y mejorándose <a href="https://en.wikipedia.org/wiki/List_of_widget_toolkits">multitud de toolkits gráficos</a> para los diferentes lenguajes de programación, muchos de ellos multi-plataforma, o para al menos Windows/Linux/OSX (como <a href="http://en.wikipedia.org/wiki/Swing_(Java)">Swing</a>, <a href="http://www.oracle.com/technetwork/java/javafx/overview/index.html">JavaFX</a>, <a href="http://www.gtk.org/">GTK+</a>, <a href="http://qt-project.org/">Qt</a>, <a href="http://www.wxwidgets.org/">WxWidgets</a>, etc.). Aunque existen aplicaciones que implementan la interfaz de usuario basada en HTML/CSS/Javascript, su uso es menor. En todo caso es posible hacerlo, y en esta entrada se pondran ejemplos de ello (en concreto en Java con el WebView de JavaFX y en C++ con el WebView de Qt).</p>
<h3>Ventajas y desventajas</h3>
<p>Plantearse la implementación de la interfaz de usuario de un proyecto software empleando HTML/CSS/Javascript, presenta las siguientes ventajas:</p>
<ul>
<li><strong>Evita conocer un toolkit gráfico propio</strong> del lenguaje de programación sobre el que se vaya a desarrollar el proyecto. La curva de aprendizaje de los toolkits gráficos suele ser elevada, sobre todo si se quiere sacar el máximo provecho.</li>
<li>Facilita la <strong>separación de interfaz de usuario de capas inferiores</strong> (lógica y acceso a datos), pudiendo asignar las diferentes partes a programadores especializados en cada parte.</li>
<li>Facilita la <b>reutilización</b> de la interfaz de usuario, sobre todo en distintas plataformas móviles.</li>
<li>Facilita <b>encontrar programadores </b>especialistas. La estandarización de estos lenguajes y la proliferación de la Web como plataforma para aplicaciones facilita que exista un gran número de profesionales estén familiarizados con estas tecnologías.</li>
</ul>
<p>Como desventajas, se podrían destacar:</p>
<ul>
<li>Rendimiento. El hecho de que la interfaz de usuario esté implementada con lenguajes de tan alto nivel e interpretados hace que el rendimiento sea inferior a toolkits más cercanos al lenguaje de programación nativo.</li>
<li>Aspecto &#8220;alien&#8221;. Las aplicaciones hechas con estas tecnologías difícilmente se adaptan a las guías de estilo de los sistemas operativos.</li>
<li>Dificultad o imposibilidad de implementar interfaces avanzadas (por ejemplo 3D). Aunque cada vez esto queda restringido a menos casos. Basta con citar que se implementan <a href="http://www.ibm.com/developerworks/web/library/wa-build2dphysicsengine/">motores videojuegos directamente con Canvas</a> (p. ej: <a href="https://code.google.com/p/playn/">PlayN de Google</a>).</li>
<li>Demasiados lenguajes de programación para back-end y front-end (que ya de por sí son tres: HTML/CSS/Javascript).</li>
</ul>
<h3>Un ejemplo práctico</h3>
<p>Vamos a implementar un ejemplo sencillo tratando de <strong>reutilizar una misma interfaz </strong>(front-end) HTML/CSS/Javascript con diferentes implementaciones del back-end (una mini-lógica). La idea es que se podría cambiar el back-end sin tocar ninguna línea del front-end.</p>
<p>Por otra parte, y aplicando el <strong>principio de diseño <a href="http://en.wikipedia.org/wiki/SOLID_(object-oriented_design)">SOLID</a></strong> de la <a href="http://en.wikipedia.org/wiki/Dependency_inversion_principle">inversión de dependencias</a>, separaremos front-end de back-end mediante una abstracción, que actuará a modo de contrato y que deberá ser llamada por el front-end e implementada por los diferentes back-ends.</p>
<pre class="brush: jscript; title: ; notranslate">//interfaz back-end
/* suma dos numeros (dos primeros parámetros). El resultado se
pasará como parámetro a la función de callback proporcionada
desde el front-end */
sum = function (int, int, callback )
/* obtiene un listado de nombres de frutas que, una vez &quot;calculado&quot;,
será pasado como parámetro a la función de callback proporcionada
desde el front-end */
fruits = function ( callback )
</pre>
<p>La arquitectura se resume en la siguiente imagen:<br />
<a href="/~lipido/blog/wp-content/uploads/2013/05/webview-architecture.png"><img class="aligncenter size-medium wp-image-256" alt="webview-architecture" src="/~lipido/blog/wp-content/uploads/2013/05/webview-architecture-300x221.png" width="300" height="221" /></a></p>
<p>Antes de continuar una pregunta: <em>¿Por qué no devolver el resultado como valor de retorno de las funciones?</em> Se puede hacer sin problema, pero este diseño facilita que se puedan hacer llamadas asíncronas. Imaginemos que fruits() tarda cierto tiempo en calcularse, por lo que el back-end lanza un hilo de cálculo en segundo plano para no bloquear la interacción con el usuario, o que se conecta asíncronamente a un servidor remoto. Este diseño permite que cuando termine el proceso en segundo plano, éste llame de vuelta al front-end y le pase los resultados.</p>
<h4>El front-end</h4>
<pre>
El front-end consiste en un fichero HTML, que emplea una hoja de estilos CSS pequeña, junto con un Javascript sencillo a modo de controlador (<strong>controller.js</strong>).
<strong>index.html</strong>
<pre class="brush: xml; highlight: [12,13,14,15]; title: ; notranslate">
&lt;html&gt;
	&lt;head&gt;
		&lt;link rel=&quot;stylesheet&quot; href=&quot;style.css&quot; /&gt;
		&lt;script type=&quot;text/javascript&quot; src=&quot;jquery-1.9.1.min.js&quot;&gt;&lt;/script&gt;

		&lt;!--
		BACKEND CONFIGURATION
		You can also use the same backend file (e.g.: backend.js)
		and replace its real contents in order to avoid modifying
		index.html to change the backend implementation
		--&gt;
		&lt;script type=&quot;text/javascript&quot; src=&quot;backend-local-java.js&quot;&gt;&lt;/script&gt;
		&lt;!--&lt;script type=&quot;text/javascript&quot; src=&quot;backend-local-cpp.js&quot;&gt;&lt;/script&gt;--&gt;
		&lt;!--&lt;script type=&quot;text/javascript&quot; src=&quot;backend-remote-server.js&quot;&gt;&lt;/script&gt;--&gt;
		&lt;!--&lt;script type=&quot;text/javascript&quot; src=&quot;backend-local-js.js&quot;&gt;&lt;/script&gt;--&gt;

		&lt;script type=&quot;text/javascript&quot; src=&quot;controller.js&quot;&gt;&lt;/script&gt;
	&lt;head&gt;

	&lt;body&gt;

		&lt;div id=&quot;fruits&quot;&gt;
			&lt;h1&gt;Fruits&lt;/h1&gt;
			&lt;ul id=&quot;fruitslist&quot;&gt;&lt;/ul&gt;
		&lt;/div&gt;

		&lt;div id=&quot;calculator&quot;&gt;
			&lt;h1&gt;Calculator&lt;/h1&gt;			

			&lt;label&gt;A:&lt;/label&gt;
			&lt;input id=&quot;aValue&quot; type=&quot;text&quot;/&gt;

			&lt;label&gt;B:&lt;/label&gt;
			&lt;input id=&quot;bValue&quot; type=&quot;text&quot;/&gt;

			&lt;input id=&quot;calculatebutton&quot; type=&quot;button&quot; value=&quot;calc&quot;/&gt;

			&lt;div id=&quot;result&quot;&gt;Result: &lt;span id=&quot;resultvalue&quot;&gt;&lt;/span&gt;
			&lt;/div&gt;

		&lt;/div&gt;
	&lt;/body&gt;
&lt;/html&gt;
</pre>
<p>Las líneas que aparecen señaladas, muestran los diferentes back-end que se han implementado. La idea es que en un software real sólo habría una de esas cuatro líneas.</p>
<p>El controlador en Javascript (<strong>controller.js</strong>) se encarga de atender a los eventos de usuario, llamar al back-end a través de la interfaz abstracta (líneas resaltadas) y actualizar la interfaz de usuario con los resultados (modificando el HTML con JQuery).</p>
<pre class="brush: jscript; highlight: [5,6,7,8,9,30,31,32]; title: ; notranslate">
//FRUITS CONTROLLER
function loaded(){
	// call the back-end and provide
	// a callback function to draw the results
	backend.fruits(function(data){
		for(var fruit in data){
			$(&quot;#fruitslist&quot;).append(&quot;&lt;li&gt;&quot;+data[fruit]+&quot;&lt;/li&gt;&quot;);
		}
	});

};
$(document).ready(function(){
		// It seems that the backend object is not yet available on the
		// body onload() or $(document).ready(). It seems that timers
		// are started after the backend is injected.
		setTimeout(loaded, 10);
});

//CALCULATOR CONTROLLER
//connect the 'calc' button listener
$(document).ready(function(){

		$(&quot;#calculatebutton&quot;).click(function(){
			var a = parseInt($(&quot;#aValue&quot;).val());
			var b = parseInt($(&quot;#bValue&quot;).val());

			// call the back-end and provide a callback
			// function to draw results
			backend.sum(a, b, function(result) {
				$('#resultvalue').html(result);
			});

		});
	}
);
</pre>
<h4>Los diferentes back-end</h4>
<pre>
Ahora se muestran los diferentes back-end: Java, C++, Servidor HTTP remoto (ej. PHP) y Javascript</pre>
<h5>backend Java con WebView JavaFX</h5>
<pre>
Comenzamos por el fichero javascript que se debe incluir en el HTML para conectar el backend: <strong>backend-local-java.js</strong>
<pre class="brush: jscript; title: ; notranslate">
// nothing to do. The &quot;backend&quot; variable will be
// injected from the backend itself
</pre>
<p>Como se puede observar, no es necesario hacer nada, ya que la instanciación de la variable backend se hará en Java y desde allí se inyectará para que esté disponible en el código Javascript.</p>
<p>Veamos ahora la implementación en Java del back-end.</p>
<pre class="brush: java; title: ; notranslate">
package es.uvigo.ei.sing.webviewdemo.backend;

import javafx.application.Platform;
import javafx.scene.web.WebEngine;
import es.uvigo.ei.sing.javafx.webview.JavascriptBridge;

public class BackendImpl extends JavascriptBridge {

	public BackendImpl(final WebEngine engine, String varname) {
		super(engine, varname);
	}

	public void fruits(final String callbackfunction){
		new Thread(){
			public void run() {
				try {
					Thread.sleep(1000);
					Platform.runLater(new Runnable(){
						@Override
						public void run() {
							call(callbackfunction,
									new String[]{
									&quot;apple&quot;,
									&quot;orange&quot;,
									&quot;banana&quot;});
						}
					});
				} catch (InterruptedException e) {	}
			}
		}.start();
	}

	public void sum(int a, int b,
			final String callbackfunction){
		call(callbackfunction, a+b);
	}
}
</pre>
<p>La clase hereda de una clase de utilidad que hemos creado para facilitar dos cuestiones comunes:</p>
<ul>
<li>Reconectar el objeto de nuevo al contexto Javascript, ya que las variables se borran cuando se cambia de URL.</li>
<li>Implementar un método call() para realizar los callback de vuelta hacia el front-end.</li>
</ul>
<pre class="brush: java; highlight: [49,60]; title: ; notranslate">
package es.uvigo.ei.sing.javafx.webview;

import java.util.LinkedList;

import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.concurrent.Worker.State;
import javafx.scene.web.WebEngine;
import netscape.javascript.JSObject;

/**
 * A bridge intended to be a superclass of Java objects
 * connected to the Javascript engine It is specifically
 * designed to implement Java utility objects as a set of
 * methods receiving a javascript callback function to be
 * called-back with results. This is useful to make
 * asynchronous designs from the Web UI tier to the bussiness
 * logic tier.
 *
 * @author lipido
 */
public class JavascriptBridge {

	protected WebEngine webEngine;
	private String varname;
	private InternalChangeListener changeListener;

	protected JavascriptBridge(WebEngine engine,
			final String varname){

		this.webEngine = engine;
		this.varname = varname;

		//Listen to state changes and reconnect to web engine
		this.changeListener = new InternalChangeListener();
		webEngine.getLoadWorker().stateProperty().
			addListener(changeListener);
	}

	private class InternalChangeListener implements
					ChangeListener&lt;State&gt;{

		public void changed(ObservableValue&lt;? extends State&gt; ov,
				State oldState, State newState) {

			if(newState == State.SUCCEEDED){
				//reconnect the backend
				connectToWebEngine();
			}
		}
		private void connectToWebEngine() {
			JSObject window = (JSObject)
				webEngine.executeScript(&quot;window&quot;);

			window.setMember(varname, JavascriptBridge.this);
		}
	};

	protected void call(String callback, Object argument) {
		webEngine.executeScript(&quot;___toEval = &quot;+callback);
		JSObject res = null;
		JSObject window = (JSObject)
				webEngine.executeScript(&quot;window&quot;);

		if (argument instanceof String){
			//it can parse as a json object
			try{
				res = (JSObject) webEngine.executeScript(
						&quot;eval(&quot;+argument.toString()+&quot;)&quot;
				);
				window.call(&quot;___toEval&quot;, res);
			}catch(Exception e){
				// it is not parseable to a json object,
				// so let the API to create the javascript
				// object
				window.call(&quot;___toEval&quot;, argument);
			}
		}else{
			// it is not a json object, so let the
			// API to create the javascript object
			window.call(&quot;___toEval&quot;, argument);
		}
	}
}
</pre>
<p>Finalmente, una clase con el método de entrada <em>main</em> donde se crea el WebView de JavaFX, se le conecta una instancia de BackendImpl y se carga el index.html</p>
<pre class="brush: java; title: ; notranslate">
package es.uvigo.ei.sing.webviewdemo;

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.layout.Region;
import javafx.scene.web.WebView;
import javafx.stage.Stage;
import es.uvigo.ei.sing.webviewdemo.backend.BackendImpl;

public class WebViewDemoJavaBackend extends Application {

	@Override
	public void start(Stage primaryStage) {

		// create the JavaFX webview
		final WebView webView = new WebView();
		primaryStage.setScene(new Scene(new Region(){
			{
				getChildren().add(webView);
			}

		}, 340, 380));
		primaryStage.setTitle(&quot;WebView with Java backend&quot;);

		// connect the backend to the webview
		new BackendImpl(webView.getEngine(), &quot;backend&quot;);

		// load index.html
		webView.getEngine().load(
				getClass().getResource(&quot;/index.html&quot;).
				toExternalForm());

		primaryStage.show();
	}

	public static void main(String[] args) {
		launch(args);
	}
}
</pre>
<p>El resultado final es el siguiente:<br />
<a href="/~lipido/blog/wp-content/uploads/2013/05/webview-java.png"><img class="aligncenter size-medium wp-image-232" alt="webview-java" src="/~lipido/blog/wp-content/uploads/2013/05/webview-java-258x300.png" width="258" height="300" /></a></p>
<h5>Backend C++ con Webview Qt</h5>
<p>Al igual que en el caso de Java, el fichero de backend javascript (<strong>backend-local-cpp.js</strong>) no contiene nada, puesto el objeto backend se inyectará desde el código C++ al arrancar el WebView.</p>
<pre class="brush: jscript; title: ; notranslate">
// nothing to do. The &quot;backend&quot; variable will be
// injected from the backend itself
</pre>
<p>Continuamos por la implementación del Backend, con dos ficheros <strong>backend.h</strong> y <strong>backend.cpp</strong>, que constituyen la implementación de las funciones sum y fruits en C++, haciendo un callback hacia Javascript.<br />
<strong>backend.h</strong></p>
<pre class="brush: cpp; title: ; notranslate">
#ifndef BACKEND_H
#define BACKEND_H
#include &lt;qobject.h&gt;
#include &lt;QWebFrame&gt;
#include &lt;QString&gt;

class Backend : public QObject
{
    Q_OBJECT

private:
    QString toFruits, varname;

    QWebFrame * webview; //the engine
    void call(QString callback, QString data);

public:
    Backend(QWebFrame * webview, QString varname);

public slots:
    void sum(int a, int b, QString callback);
    void fruits(QString callback);

private slots:
    void connectToWebEngine();
    void doFruits();
};

#endif // BACKEND_H

</pre>
<p><strong>backend.cpp</strong></p>
<pre class="brush: cpp; title: ; notranslate">
#include &quot;backend.h&quot;
#include &lt;QThread&gt;

Backend::Backend(QWebFrame * webframe, QString varname)
{
    this-&gt;varname = varname;
    this-&gt;webview = webframe;
    connect(webframe, SIGNAL(javaScriptWindowObjectCleared()),
            SLOT(connectToWebEngine()));
}
void Backend::connectToWebEngine(){
    this-&gt;webview-&gt;addToJavaScriptWindowObject(this-&gt;varname, this);
}
void Backend::sum(int a, int b, QString callback){
    this-&gt;call(callback, QString::number(a+b));
}

void Backend::fruits(QString callback2){
    //we will run this inside a background thread
    QThread * thread = new QThread();
    this-&gt;toFruits = callback2;
    connect(thread, SIGNAL(started()), this, SLOT(doFruits()));
    thread-&gt;start();
}

void Backend::doFruits(){
    QThread::sleep(2);
    this-&gt;call(this-&gt;toFruits,
                   QString(&quot;['orange','apple','banana']&quot;));
}

void Backend::call(QString call, QString data){
    this-&gt;webview-&gt;evaluateJavaScript(&quot;__toEval = &quot;+call);
    QString s(&quot;__toEval(&quot;+data+&quot;)&quot;);
    this-&gt;webview-&gt;evaluateJavaScript(s);
}
</pre>
<p>Al igual que en el caso de Java, es necesario reconectar el objeto C++ al WebView cada vez que se borran las variables Javascript. En este caso, no hemos creado una superclase con este comportamiento.<br />
Finalmente, el fichero con el punto de entrada <em>main</em> donde se crea una ventana Html5ApplicationViewer, creada automáticamente con el asistente de <a href="http://qt.digia.com/Product/Developer-Tools/">Qt Creator</a> cuando se crea un proyecto HTML 5.<br />
<strong>main.cpp</strong></p>
<pre class="brush: cpp; title: ; notranslate">
#include &lt;QApplication&gt;
#include &lt;QWebFrame&gt;
#include &quot;html5applicationviewer.h&quot;
#include &quot;backend.h&quot;

int main(int argc, char *argv[])
{
    QApplication app(argc, argv);

    Html5ApplicationViewer window;
    window.setOrientation(
                Html5ApplicationViewer::ScreenOrientationAuto);

    window.loadFile(QLatin1String(&quot;html/index.html&quot;));
    window.resize(340, 380);
    window.setWindowTitle(&quot;Qt WebView with C++ Backend&quot;);
    window.showExpanded();

    new Backend(window.webFrame, &quot;backend&quot;);
    return app.exec();
}

</pre>
<p>El resultado final es el siguiente:<br />
<a href="/~lipido/blog/wp-content/uploads/2013/05/webview-cpp.png"><img class="aligncenter size-medium wp-image-231" alt="webview-cpp" src="/~lipido/blog/wp-content/uploads/2013/05/webview-cpp-258x300.png" width="258" height="300" /></a></p>
<h5>Backend remoto HTTP (servidor en PHP)</h5>
<p>Este ejemplo refleja un diseño más clásico. El WebView que es, en realidad, el navegador del usuario que se conecta con un servidor mediante AJAX para invocar las funciones sum y fruits. Aunque no tiene nada especial, se incluye aquí para demostrar que es un back-end a mayores del mismo front-end que permanece intacto.<br />
En primer lugar, el fichero Javascript <strong>backend-remote-server.js</strong> que, esta vez sí, tiene contenido. Su misión es servir de intermediario para la comunicación HTTP con el back-end que se encuentra en un servidor remoto. Dicha comunicación se implementa con JQuery empleando la técnica AJAX.<br />
<strong>backend-remote-server.js</strong></p>
<pre class="brush: jscript; title: ; notranslate">
// server implementation of backend
backend = {

		sum: function(a, b, callback){
			jQuery.ajax({
				url: &quot;http://localhost/sum.php?a=&quot;+a+&quot;&amp;b=&quot;+b,
				success: function(data){ callback(data); }
			});
		},
		fruits: function(callback){
			jQuery.ajax({
				url: &quot;http://localhost/fruits.php&quot;,
				success: function(data){ callback(eval(data)); }
			});
		}
	};
</pre>
<p>El servidor en PHP implementa cada una de las funciones del back-end en un fichero PHP sencillo. Habitualmente lo que se encuentra en el servidor es un framework MVC con facilidades para servir peticiones al estilo API REST. Pero por sencillez se deja así.<br />
<strong>sum.php</strong></p>
<pre class="brush: php; title: ; notranslate">
&lt;?
echo $_GET[&quot;a&quot;] + $_GET[&quot;b&quot;];
?&gt;
</pre>
<p><strong>fruits.php</strong></p>
<pre class="brush: php; title: ; notranslate">
&lt;?
echo &quot;['banana', 'orange']&quot;;
?&gt;
</pre>
<h5>Back-end en Javascript</h5>
<p>En este último ejemplo, el WebView vuelve a ser el navegador Implementar el Back-end en Javascript puede ser interesante, sobre todo en dos casos:</p>
<ol>
<li>Implementación de un prototipo del backend (<a href="http://en.wikipedia.org/wiki/Mock_object">mock</a>). De esta forma, el diseñador de la interfaz puede simular las respuestas del back-end sin tenerlo disponible todavía.</li>
<li>Conseguir que la aplicación sea totalmente portable, sin emplear ningún lenguaje de programación nativo. Sin embargo, si se desea acceder a funciones de más bajo nivel, sería necesario algo estilo PhoneGap (para funciones de smartphones) o conectar al lenguaje nativo como se ha visto en los ejemplos anteriores.</li>
</ol>
<p>A continuación, se incluye la implementación del back-end en Javascript: fichero backend-local-js.js</p>
<pre class="brush: jscript; title: ; notranslate">
// local javascript implementation of backend
backend = {

		sum: function(a, b, callback){
			return callback(a + b);
		},
		fruits: function(callback){
			return callback(['orange', 'strawberry']);
		}

	};

</pre>
<p>El resultado final es el siguiente:<br />
<a href="/~lipido/blog/wp-content/uploads/2013/05/webview-chrome.png"><img class="aligncenter size-medium wp-image-230" alt="webview-chrome" src="/~lipido/blog/wp-content/uploads/2013/05/webview-chrome-279x300.png" width="279" height="300" /></a></p>
<h3>Resumen</h3>
<p>El conjunto de estándares más empleados en el desarrollo de las interfaces de usuario Web, formadas principalmente por HTML/CSS/Javascript está experimentando en los últimos años grandes avances. Tanto es así que se han exportado al desarrollo de aplicaciones en otros contextos, concretamente móviles y escritorio. Este post trata de demostrar que es posible, y relativamente sencillo, crear la interfaz de usuario de una aplicación de escritorio mediante estas tecnologías. Además, separando la lógica de negocio (back-end) de la interfaz de usuario (front-end) se pueden incluir verdaderos especialistas en la Web en proyectos de aplicaciones de escritorio.</p>
<h3>Código fuente</h3>
<p>Finalmente adjunto el código fuente.</p>
<ul>
<li>Proyecto en Java (proyecto Maven2): <a href="/~lipido/blog/wp-content/uploads/2013/05/webview-java.zip">webview-java.zip</a></li>
<li>Proyecto Qt (proyecto QtCreator): <a href="/~lipido/blog/wp-content/uploads/2013/05/webview-cpp-qtcreatorproject.zip">webview-cpp-qtcreatorproject.zip</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2013/05/07/interfaces-de-usuario-htmlcssjavascript-nuevo-estandar/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Grabar Spotify en Ubuntu 9.10 con PulseAudio y Audacity</title>
		<link>https://www.sing-group.org/~lipido/blog/2010/01/20/grabar-spotify-en-ubuntu-910-con-pulseaudio-y-audacity/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2010/01/20/grabar-spotify-en-ubuntu-910-con-pulseaudio-y-audacity/#comments</comments>
		<pubDate>Wed, 20 Jan 2010 00:52:19 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2010/01/20/grabar-spotify-en-ubuntu-910-con-pulseaudio-y-audacity/</guid>
		<description><![CDATA[Tras varios intentos, hoy he conseguido hacer funcionar la grabación de la mezcla stereo en Ubuntu 9.10. Traduzco el tutorial que me ha funcionado (fuente: https://wiki.ubuntu.com/PulseAudio). Ojo 1. Mi Ubuntu lo tengo en Inglés, por lo que he hecho traducciones al castellano al vuelo y puede que tengas que echarle imaginación. Ojo 2. Este método [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>Tras varios intentos, hoy he conseguido hacer funcionar la grabación de la mezcla stereo en Ubuntu 9.10. Traduzco el tutorial que me ha funcionado (fuente: <a href="https://wiki.ubuntu.com/PulseAudio">https://wiki.ubuntu.com/PulseAudio</a>). </p>
<p>Ojo 1. Mi Ubuntu lo tengo en Inglés, por lo que he hecho traducciones al castellano al vuelo y puede que tengas que echarle imaginación.</p>
<p>Ojo 2. Este método no separa y nombra las canciones automáticamente. De hecho lo único que explico es cómo hacer que Audacity grabe lo que se oye por los altavoces en un equipo con Ubuntu. Nada más.</p>
<p><b>Requisitos:</b></p>
<ul>
<li>Ubuntu 9.04+. Probado en 9.04 por la fuente original y en 9.10 por mí.</li>
<li>Audacity, disponible en los repositorios de Ubuntu.</li>
</ul>
<p><b>Método:</b></p>
<ol>
<li>
Pon a sonar Spotify.
</li>
<li>
Abre &#8220;Aplicaciones -> Sonido y Vídeo -> Control de volumen PulseAudio&#8221;.  Busca en la solapa de &#8220;Dispositivos de salida&#8221; la aplicación quieres grabar, en este caso Spotify, y selecciona como su dispositivo de salida tus altavoces preferidos (eg: &#8220;auriculares USB&#8221;, si no se encuentra ya seleccionado). No cierres el control de volumen PulseAudio.
</li>
<li>
Abre Audacity y selecciona &#8220;Edición -> Preferencias&#8221;. En la sección de &#8220;Grabación&#8221;, desmarca las dos casillas bajo &#8220;Reproducción a través&#8221;. Bajo &#8220;Dispositivos&#8221; selecciona &#8220;pulse&#8221; tanto para &#8220;Reproducción&#8221; como &#8220;Grabación&#8221;. Canales deja 2 (Stereo). Pulsa OK para guardar. Cierra y abre Audacity otra vez.</li>
<li>
En Audacity, haz clic en el icono de Grabación y que comience a grabar. Grabará un silencio. No te preocupes.
</li>
<li>
Vuelve al control de volumen de PulseAudio y selecciona la solapa de Grabación. Allí deberá estar Audacity como programa que se encuentra grabando. Cambia su dispositivo de donde graba a &#8220;Monitor de auriculares USB&#8221;.</li>
<li>
Pon la canción de interés al principio en Spotify.
</li>
<li>Volviendo a Audacity, verás que está grabando sonido en vez de silencio. Cuando termine lo que quieres grabar, puedes seleccionar y suprimir el silencio inicial o cosas que no interesen (lo que se grabó antes de poner de nuevo la canción al principio). Finalmente puedes exportar la grabación a MP3, por ejemplo.</li>
</ol>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2010/01/20/grabar-spotify-en-ubuntu-910-con-pulseaudio-y-audacity/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>The Google Similarity Distance</title>
		<link>https://www.sing-group.org/~lipido/blog/2009/08/18/the-google-similarity-distance/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2009/08/18/the-google-similarity-distance/#comments</comments>
		<pubDate>Tue, 18 Aug 2009 14:10:10 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2009/08/18/the-google-similarity-distance/</guid>
		<description><![CDATA[Leyendo un artículo me encuentro una referencia a un interesante trabajo: &#8220;The Google Similarity Distance&#8221;, de Cilibrasi y Vitanyi publicado en IEEE Trans. on Knowledge and Data Engineering. Los autores presentan una nueva medida de similitud semántica entre dos palabras, es decir, cuánto se parecen o en qué medida están relacionados dos términos. Las medidas [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>Leyendo un artículo me encuentro una referencia a un interesante trabajo: &#8220;The Google Similarity Distance&#8221;, de Cilibrasi y Vitanyi publicado en IEEE Trans. on Knowledge and Data Engineering.</p>
<p>Los autores presentan una nueva medida de <strong>similitud semántica</strong> entre dos palabras, es decir, cuánto se parecen o en qué medida están relacionados dos términos. Las medidas de distancia entre elementos de muy diversa índole se emplean asiduamente en técnicas de minería de datos que basan sus operaciones a partir de una distancia conocida entre las instancias tratadas, como puede ser el clustering (agrupamiento de instancias similares) o la clasificación basada en la proximidad de ejemplares conocidos (como <a href="http://en.wikipedia.org/wiki/K-nearest_neighbor_algorithm">KNN</a>).</p>
<p>La novedad de este trabajo es que se <strong>propone el uso de Google para calcular la similitud o relación entre dos palabras dadas</strong>, defendiéndose que la Web es el mayor recurso de información existente, donde está representado en gran medida el conocimiento humano de forma actualizada. De forma muy resumida, proponen la siguiente fórmula para calcular la similitud entre dos palabras x,y (NGD=<i>Normalized Google Distance</i>):<br />
<img id="image124" src="http://sing.ei.uvigo.es/%7Elipido/blog/wp-content/uploads/2009/08/formula.png" alt="formula NGD" /><br />
Donde f(x) y f(y) son el número de páginas devueltas por Google buscando el término x e y, respectivamente. f(x,y) denota el número de páginas devueltas por Google donde aparecen ambas palabras. N es un factor de normalización que suele representar la totalidad de páginas web indexadas por Google. Los autores en sus pruebas manejaron valores entre 8·10<sup>9</sup> y 9·10<sup>9</sup>, aunque dicen que los resultados suelen ser insensibles a este valor, siempre que sea razonable. El valor de la fórmula toma valor 0 para palabras totalmente similares y tiende a infinito para palabras no relacionadas.</p>
<p>En el trabajo se pueden ver ejemplos muy ilustrativos de la aplicabilidad de la medida. Uno de ellos, demuestra la capacidad de diccionario &#8220;enciclopédico&#8221; que aporta Google, ya que es capaz de calcular similitudes entre términos más allá de los de un diccionario convencional. Así pues, ejecutan un agrupamiento jerárquico sobre los títulos de obras de diversos autores y, gracias a la similitud calculada que tiende a acercar títulos de un mismo autor (por aparecer juntos en páginas donde se habla de la obra de un autor), el algoritmo crea efectivamente grupos con obras de un mismo autor.</p>
<p>Dejo aquí el artículo completo en <a id="p122" href="http://sing.ei.uvigo.es/%7Elipido/blog/wp-content/uploads/2009/08/tkde06.pdf" title="The Google Similarity Distance (texto completo)">PDF</a>.</p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2009/08/18/the-google-similarity-distance/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Habilitar suavizado &#8216;ClearType&#8217; en Wine</title>
		<link>https://www.sing-group.org/~lipido/blog/2009/06/04/habilitar-suavizado-cleartype-en-wine/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2009/06/04/habilitar-suavizado-cleartype-en-wine/#comments</comments>
		<pubDate>Thu, 04 Jun 2009 09:04:52 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2009/06/04/habilitar-suavizado-cleartype-en-wine/</guid>
		<description><![CDATA[Desde wine 1.1.12 ya es posible habilitar el suavizado de fuentes, lo cual deja un aspecto muy agradable en las fuentes, sobre todo para los monitores TFT. Para habilitarlo, es necesario editar el registro: [HKEY_CURRENT_USER\Control Panel\Desktop] "FontSmoothing"="2" "FontSmoothingType"=dword:00000002 "FontSmoothingGamma"=dword:00000578 "FontSmoothingOrientation"=dword:00000001 Sin embargo, aquí me he encontrado un script que lo hace por nosotros, preguntando el [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>Desde wine 1.1.12 ya es posible habilitar el suavizado de fuentes, lo cual deja un aspecto muy agradable en las fuentes, sobre todo para los monitores TFT.</p>
<p>Para habilitarlo, es necesario editar el registro:<br />
<code>[HKEY_CURRENT_USER\Control Panel\Desktop]<br />
"FontSmoothing"="2"<br />
"FontSmoothingType"=dword:00000002<br />
"FontSmoothingGamma"=dword:00000578<br />
"FontSmoothingOrientation"=dword:00000001</code></p>
<p>Sin embargo, aquí me he encontrado un script que lo hace por nosotros, preguntando el tipo de suavizado que queremos (el cleartype es el &#8216;subpixel smoothing&#8217;)</p>
<p>Script:</p>
<p><code>wget http://files.polosatus.ru/winefontssmoothing_en.sh<br />
bash winefontssmoothing_en.sh</code></p>
<p>Fuente: <a href="http://wine-reviews.net/wine-reviews/tips-n-tricks/how-to-enable-font-anti-aliasing-in-wine.html">http://wine-reviews.net/wine-reviews/tips-n-tricks/how-to-enable-font-anti-aliasing-in-wine.html</a></p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2009/06/04/habilitar-suavizado-cleartype-en-wine/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Top-10 de los algoritmos en Data Mining</title>
		<link>https://www.sing-group.org/~lipido/blog/2009/03/11/top-10-de-los-algoritmos-en-data-mining/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2009/03/11/top-10-de-los-algoritmos-en-data-mining/#comments</comments>
		<pubDate>Tue, 10 Mar 2009 23:32:18 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2009/03/11/top-10-de-los-algoritmos-en-data-mining/</guid>
		<description><![CDATA[Un reciente trabajo publicado a finales del 2007 realiza un estudio de cuáles han sido los 10 algoritmos de Data Mining más exitosos. Según cuentan sus autores, entre los que se encuentran Ross Quinlan -creador de los míticos árboles de decisión ID3 y C4.5- la decisión se llevó a cabo según la opinión de los [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>Un <a href="http://portal.acm.org/citation.cfm?id=1327436">reciente trabajo</a> publicado a finales del 2007 realiza un estudio de cuáles han sido los 10 algoritmos de <a href="http://en.wikipedia.org/wiki/Data_mining">Data Mining</a> más exitosos. Según cuentan sus autores, entre los que se encuentran Ross Quinlan -creador de los míticos árboles de decisión ID3 y C4.5- la decisión se llevó a cabo según la opinión de los autores de los artículos premiados y los comités científicos de las conferencias más prestigiosas en Data Mining (IEEE ICDM y KDD), junto con el número de referencias al algoritmo en Google Scholar (mínimo 50).</p>
<p>Y los premiados son&#8230;</p>
<p><strong>1. C4.5 (1993)</strong><br />
Quinlan, J. R. 1993. C4.5: Programs for Machine Learning. Morgan Kaufmann Publishers Inc.<br />
Google Scholar Count in October 2006: 6907</p>
<p><strong>2. K-Means (1967)</strong><br />
MacQueen, J. B., Some methods for classification and analysis of multivariate observations, in Proc. 5th Berkeley Symp. Mathematical Statistics and Probability, 1967, pp. 281-297.<br />
Google Scholar Count in October 2006: 1579</p>
<p><strong>3. SVM (1995)</strong><br />
Vapnik, V. N. 1995. The Nature of Statistical Learning Theory. Springer-Verlag New York, Inc.<br />
Google Scholar Count in October 2006: 6441</p>
<p><strong>4. Apriori (1994)</strong><br />
Rakesh Agrawal and Ramakrishnan Srikant. Fast Algorithms for Mining Association Rules. In Proc. of the 20th Int&#8217;l Conference on Very Large Databases (VLDB &#8217;94), Santiago, Chile, September 1994.<br />
Google Scholar Count in October 2006: 3639</p>
<p><strong>5. EM (2000)</strong><br />
McLachlan, G. and Peel, D. (2000). Finite Mixture Models. J. Wiley, New York.<br />
Google Scholar Count in October 2006: 848</p>
<p><strong>6. PageRank (1998)</strong><br />
Brin, S. and Page, L. 1998. The anatomy of a large-scale hypertextual Web search engine. In Proceedings of the Seventh international Conference on World Wide Web (WWW-7) (Brisbane, Australia). P. H. Enslow and A. Ellis, Eds. Elsevier Science Publishers B. V., Amsterdam, The Netherlands, 107-117.<br />
Google Shcolar Count: 2558</p>
<p><strong>7. AdaBoost (1997)</strong><br />
Freund, Y. and Schapire, R. E. 1997. A decision-theoretic generalization of on-line learning and an application to boosting. J. Comput. Syst. Sci. 55, 1 (Aug. 1997), 119-139.<br />
Google Scholar Count in October 2006: 1576</p>
<p><strong>8. K Nearest Neighbours (1996)</strong><br />
Hastie, T. and Tibshirani, R. 1996. Discriminant Adaptive Nearest Neighbor Classification. IEEE Trans. Pattern Anal. Mach. Intell. (TPAMI). 18, 6 (Jun. 1996), 607-616.<br />
Google SCholar Count: 183</p>
<p><strong>9. Naive Bayes (??)</strong><br />
Hand, D.J., Yu, K., 2001. Idiot&#8217;s Bayes: Not So Stupid After All? Internat. Statist. Rev. 69, 385-398.<br />
Google Scholar Count in October 2006: 51</p>
<p><strong>10. CART (1984)</strong><br />
L. Breiman, J. Friedman, R. Olshen, and C. Stone. Classification and Regression Trees. Wadsworth, Belmont, CA, 1984.<br />
Google Scholar Count in October 2006: 6078</p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2009/03/11/top-10-de-los-algoritmos-en-data-mining/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Proposiciones de Ley en el Congreso, una fuente RSS</title>
		<link>https://www.sing-group.org/~lipido/blog/2009/02/17/proposiciones-de-ley-en-el-congreso-una-fuente-rss/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2009/02/17/proposiciones-de-ley-en-el-congreso-una-fuente-rss/#comments</comments>
		<pubDate>Tue, 17 Feb 2009 20:21:55 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>
		<category><![CDATA[Política]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2009/02/17/proposiciones-de-ley-en-el-congreso-una-fuente-rss/</guid>
		<description><![CDATA[En la página web del Congreso de los Diputados hay mucha información disponible sobre la vida en la Cámara Baja. Desde que el PP presentó a principios de Febrero una Proposición de Ley para la creación del Consejo de Colegios de Ingenieros en Informática, he estado siguiendo dicha página, esperando a que apareciese en su [&#8230;]]]></description>
				<content:encoded><![CDATA[<p><center><img id="image113" src="http://sing.ei.uvigo.es/%7Elipido/blog/wp-content/uploads/2009/02/rss.jpg" alt="RSS Logo" /><img id="image112" src="http://sing.ei.uvigo.es/%7Elipido/blog/wp-content/uploads/2009/02/congresologo.gif" alt="Congreso Logo" /></center><br />
En la <a href="http://www.congreso.es">página web del Congreso de los Diputados</a> hay mucha información disponible sobre la vida en la Cámara Baja. Desde que el PP <a href="http://www.cpeig.org/portal/node/618">presentó a principios de Febrero una Proposición de Ley para la creación del Consejo de Colegios de Ingenieros en Informática</a>, he estado siguiendo dicha página, esperando a que apareciese en su <a href="http://www.congreso.es/portal/page/portal/Congreso/Congreso/Iniciativas?_piref73_2148295_73_1335437_1335437.next_page=/wc/servidorCGI&#038;CMD=VERLST&#038;BASE=IWI9&#038;FMT=INITXLBA.fmt&#038;NUM1=&#038;DES1=&#038;DOCS=1-25&#038;DOCORDER=FIFO&#038;OPDEF=Y&#038;QUERY=(proposicion+adj2+ley).tipo.+no+%40fcie+no+concluido.fase.">listado de PLs</a> la susodicha propuesta popular. Sin embargo, todavía no ha aparecido y ya comienza a ser tedioso conectarse todos los días.</p>
<p>La <a href="http://en.wikipedia.org/wiki/RSS_(file_format)">tecnología RSS</a>, entre otras cosas, nos evita el tener que acceder periódicamente con nuestro navegador a los portales favoritos en busca de nuevos cambios. Hoy por hoy, el RSS está prácticamente implantado allí donde tiene sentido; ya son pocas las excepciones, entre ellas, la del Congreso.</p>
<p>Es por ello, por lo que me hice un pequeño programa en mi servidor (utilizando una herramienta ultra-secreta, que espero algún día vea la luz, :-P), que hace de puente entre nuestro lector RSS favorito y el listado de PLs del congreso. Así que preparad vuestros lectores para seguir la vida política <strong>real</strong>:</p>
<p>URL del servidor RSS: <a href="http://sing.ei.uvigo.es:8080/aautomator/index.jsp?file=PL.xml&#038;silent=true&#038;ctype=text/xml">http://sing.ei.uvigo.es:8080/aautomator/index.jsp?file=PL.xml&#038;silent=true&#038;ctype=text/xml</a></p>
<p>Por cierto, con esto me he enterado de una interesantísima propuesta realizada por el grupo ERC-IU-ICV, relativa al <a href="http://www.congreso.es/portal/page/portal/Congreso/Congreso/Iniciativas?_piref73_2148295_73_1335437_1335437.next_page=/wc/servidorCGI&#038;CMD=VERLST&#038;BASE=IWI9&#038;PIECE=IWA9&#038;FMT=INITXD1S.fmt&#038;FORM1=INITXLBA.fmt&#038;DOCS=6-6&#038;QUERY=(proposicion+adj2+ley).tipo.+no+%40fcie+no+concluido.fase.">acceso a la vivienda</a>, como derecho Constitucional. Si tengo tiempo, le dedicaré unos post a seguirla.</p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2009/02/17/proposiciones-de-ley-en-el-congreso-una-fuente-rss/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Las Ingenierías Técnicas en Informática constituyen profesiones reguladas, según catedrático de Derecho</title>
		<link>https://www.sing-group.org/~lipido/blog/2009/02/05/las-ingenierias-tecnicas-en-informatica-constituyen-profesiones-reguladas-segun-catedratico-de-derecho/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2009/02/05/las-ingenierias-tecnicas-en-informatica-constituyen-profesiones-reguladas-segun-catedratico-de-derecho/#comments</comments>
		<pubDate>Thu, 05 Feb 2009 22:38:08 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>
		<category><![CDATA[Política]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2009/02/05/las-ingenierias-tecnicas-en-informatica-constituyen-profesiones-reguladas-segun-catedratico-de-derecho/</guid>
		<description><![CDATA[Un informe encargado por la CODDI a José María Baño León, Catedrático de Derecho, arroja unas conclusiones clarificadoras acerca de la regulación de las Ingenierías Técnicas en Informática. Las preguntas formuladas por la CODDI a J.M Baño versaban acerca de si las Ingenierías (Técnicas) Informáticas están al amparo de la ya famosa Ley 12/1986. El [&#8230;]]]></description>
				<content:encoded><![CDATA[<p>Un informe encargado por la CODDI a José María Baño León, Catedrático de Derecho, arroja unas conclusiones clarificadoras acerca de la regulación de las Ingenierías Técnicas en Informática.</p>
<p>Las preguntas formuladas por la CODDI a J.M Baño versaban acerca de si las Ingenierías (Técnicas) Informáticas están al amparo de la ya famosa Ley 12/1986.</p>
<p>El dictamen dice que en la Ley 12/1986 se hace referencia al concepto de &#8220;especialidades técnicas&#8221;, las cuales se encuentran en un listado <strong>no cerrado</strong> en el Decreto 148/1969 que, por razones obvias, no contemplaba Ingeniería Informática. Sin embargo, la Ley 12/1986 prevee la modificación de dicho listado, incluso de forma <strong>automática</strong>, mediante la creación de nuevos títulos por parte del Gobierno, cosa que sí se ha hecho a posteriori con las leyes 1460/1990 y 1461/1990, donde se crean los dos títulos de Ingeniería Técnica en Informática (de Gestión y Sistemas). Por lo cual, estas Ingenierías Técnicas sí están al amparo de la Ley 12/1986.</p>
<p>Pero remitiéndome a las conclusiones textuales tenemos los siguientes párrafos. La primera conclusión da la respuesta en general:</p>
<blockquote><p>PRIMERA. Los títulos universitarios oficiales de Ingeniería Técnica en Informática de Gestión e Ingeniería Técnica en Informática de Sistemas quedan sometidos al régimen jurídico previsto en la Ley 12/1986, de 1 de abril y constituyen, por tanto, <strong>profesiones reguladas</strong></p></blockquote>
<p>A continuación se recalca el carácter no cerrado ni basado en criterios técnicos del listado que aparece en la Ley 148/1969 a la cual se refiere la Ley 12/1986.</p>
<blockquote><p>SEGUNDA. El hecho de que los títulos de Ingeniería Técnica en Informática no estén incluidos en el listado de especialidades de Decreto 148/1969 no tiene relevancia jurídica, pues tal relación no tiene caracter cerrado en el sentido de la Ley 12/1986 ni obedece a ningún criterio técnico</p></blockquote>
<p>Sobre la <strong>actualización automática</strong> se dice:</p>
<blockquote><p>TERCERA. El Gobierno está facultado para modificar las especialidades amaparadas por la Ley 12/1986 mediante la actualización del listado recogido en el Decreto 148/1969 <strong>a través del reconocimiento de nuevos títulos universitarios</strong>, siempre que se den las circunstancias a que se refiere la Disposición Final Primera, apartado dos, de la citada Ley 12/1986</p></blockquote>
<p>A raíz de la conclusión TERCERA, se sacan las dos siguientes donde primero se menciona la creación de nuevos títulos y, después, que además cumplen los requisitos.</p>
<blockquote><p>CUARTA. Con la aprobación de los Reales Decretos 1460/1990 y 1461/1990, de 26 de octubre, el Gobierno actualizó el referido catálogo de especialidades y las titulaciones de Ingeniería Técnica en Informática de Gestión e Ingeniería Técnica en Informática de Sistemas <strong>quedaron automáticamente incluídas</strong>, desde ese momento, en el régimen jurídico de la Ley 12/1986.</p></blockquote>
<blockquote><p>QUINTA. En el caso de los títulos de Ingeniería Técnica en Informática de Gestión e Ingeniería Técnica en Informática de Sistemas se cumplen estrictamente, además, los requisitos exigidos en la Disposición Final Primera de la Ley 12/1986, pues el Gobierno siguió el procedimiento previsto en esa norma (establecimiento en un título universitario oficial), existía una patente demanda social y las actividades reguladas son suficientemente caraterizadas como para justificar el ámbito de protección que garantiza la Ley 12/1986.</p></blockquote>
<p>Finalmente, se concluye que por el R.D. 1393/2007, el Ministerio de Ciencia e Innovación debe crear las fichas para los nuevos Grados en Informática, ya que debe ser así para las profesiones reguladas, donde, según el dictamen, se encuentra la Ingeniería Técnica en Informática: </p>
<blockquote><p>SEXTA. Por todas las razones expuestas, el Ministerio de Ciencia e Innovación debe establecer los requisitos a los que deberán adecuarse los planes de estudios que presenten las Universidades para su verificación por el Consejo de Universidades conducentes a la obtención de los títulos de Grado que habiliten para el ejercicio de la profesión de Ingeniero Técnico en Informática, en las dos especialidades mencionadas y en las mismas condiciones que el resto de ingenierías, de modo que la tenencia del título sea requisito para ejercer la actividad propia de estos titulados.</p></blockquote>
<p>Para finalizar, y fuera del apartado de conclusiones del dictamen, me gustaría extraer un párrafo que ahonda en la idea de que es absurdo aferrarse a los viejos listados y de que nuestra profesión merece más que nadie ser regulada.</p>
<blockquote><p>Y el mejor ejemplo lo tenemos quizás en las ingenierías técnicas en informática que nos ocupan en este dictamen, que no existían en 1969 y que hoy día justifican indiscutiblemente, por su relevancia, reconocer una profesión regulada más que cualquier otra ingeniería técnica</p></blockquote>
<p>Enlace a noticia original: <a href="http://www.hispalive.es/2009/02/05/%c2%bfingenieria-informatica-%c2%bfregulacion-de-la-profesion/">http://www.hispalive.es/2009/02/05/%c2%bfingenieria-informatica-%c2%bfregulacion-de-la-profesion/</a><br />
Enlace al <a href="http://www.hispalive.es/wp-content/uploads/2009/02/dictamen-1.pdf">Dictamen</a></p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2009/02/05/las-ingenierias-tecnicas-en-informatica-constituyen-profesiones-reguladas-segun-catedratico-de-derecho/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Profesiones Reguladas en Europa, Informática vs Telecomunicaciones</title>
		<link>https://www.sing-group.org/~lipido/blog/2009/02/02/profesiones-reguladas-en-europa-informatica-vs-telecomunicaciones/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2009/02/02/profesiones-reguladas-en-europa-informatica-vs-telecomunicaciones/#comments</comments>
		<pubDate>Mon, 02 Feb 2009 08:50:55 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/2009/02/02/profesiones-reguladas-en-europa-informatica-vs-telecomunicaciones/</guid>
		<description><![CDATA[La &#34;Base de datos Europea de profesiones reguladas&#34;, es una buena fuente de información para saber qué profesiones están reguladas en los países europeos. http://ec.europa.eu/internal_market/qua &#8230; me.welcome La verdad es que es un punto de referencia muy bueno, ya que es una base de datos on-line con nombres normalizados de profesiones y no un montón [&#8230;]]]></description>
				<content:encoded><![CDATA[<p><a href="http://ec.europa.eu/internal_market/qualifications/regprof/index.cfm?fuseaction=home.welcome" target="_blank"><img id="image105" src="http://sing.ei.uvigo.es/%7Elipido/blog/wp-content/uploads/2009/02/eurodb.png" alt="Regulated Professions Database" /></a><br />
La <span style="font-weight: bold">&quot;Base de datos Europea de profesiones reguladas&quot;</span>, es una buena fuente de información para saber qué profesiones están reguladas en los países europeos.</p>
<p><!-- m --><a class="postlink" href="http://ec.europa.eu/internal_market/qualifications/regprof/index.cfm?fuseaction=home.welcome">http://ec.europa.eu/internal_market/qua &#8230; me.welcome</a><!-- m --></p>
<p>La verdad es que es un punto de referencia muy bueno, ya que es una base de datos on-line con nombres normalizados de profesiones y no un montón de documentos legislativos.</p>
<p>Me he dedicado a ver si aparecía <span style="font-weight: bold">Ingeniería Informática</span> y he encontrado 2 profesiones afines:</p>
<p><span style="font-weight: bold">Information systems engineer</span>.<br />Enlace: <!-- m --><a class="postlink" href="http://ec.europa.eu/internal_market/qualifications/regprof/index.cfm?fuseaction=profession.regProfs&amp;profId=6365">http://ec.europa.eu/internal_market/qua &#8230; rofId=6365</a><!-- m --><br />Regulada en:
<ul>
<li>Reino Unido, bajo el nombre de &quot;Chartered IT professional&quot;</li>
<li>Grecia, bajo el nombre de &quot;Michanikós ilektronikón ipologistón ke pliroforikís&quot;</li>
</ul>
<p><span style="font-weight: bold">Information systems practitioner</span>. Aquí por cierto es donde algunos países denominan &quot;Ingeniero&quot;.<br />Enlace: <!-- m --><a class="postlink" href="http://ec.europa.eu/internal_market/qualifications/regprof/index.cfm?fuseaction=profession.regProfs&amp;profId=6120">http://ec.europa.eu/internal_market/qua &#8230; rofId=6120</a><!-- m --><br />Regulada en:
<ul>
<li>Reino Unido, bajo el nombre de &quot;Chartered IT professional&quot;</li>
<li>Grecia, bajo el nombre de &quot;Michanikós ilektronikón ipologistón ke pliroforikís&quot;</li>
<li>Italia, bajo el nombre de &quot;Ingegnere dell&#8217;informazione&quot;</li>
<li>Italia, bajo el nombre de &quot;Ingegnere dell&#8217;informazione iunior&quot;</li>
<li>Liechtenstein, bajo el nombre de &quot;Informatiker&quot;</li>
<li><span style="font-weight: bold">Portugal, bajo el nombre de &quot;Engenheiro informático&quot;</span></li>
</ul>
<p>&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;-<br />Como vemos, existir, existimos. Ahora veamos qué pasa con, <span style="font-weight: bold">Ingeniero en Telecomunicación</span>. Encontramos 2 similares:<br /><span style="font-weight: bold">Electronic telecommunications engineer</span><br />Enlace: <!-- m --><a class="postlink" href="http://ec.europa.eu/internal_market/qualifications/regprof/index.cfm?fuseaction=profession.regProfs&amp;profId=6360">http://ec.europa.eu/internal_market/qua &#8230; rofId=6360</a><!-- m -->
<ul>
<li>Grecia, bajo el nombre de: &quot;Ilektronikós michanikós ke michanikós ipologistón&quot;</li>
<li>Portugal, bajo el nombre de &quot;Engenheiro técnico de electrónica e telecomunicações&quot;</li>
<li><span style="font-weight: bold">España, bajo el nombre de &quot;Ingeniero técnico de telecomunicación&quot;</span></li>
</ul>
<p><span style="font-weight: bold">Telecommunications engineer</span><br />Enlace: <!-- m --><a class="postlink" href="http://ec.europa.eu/internal_market/qualifications/regprof/index.cfm?fuseaction=profession.regProfs&amp;profId=6350">http://ec.europa.eu/internal_market/qua &#8230; rofId=6350</a><!-- m --><br />Regulada en:
<ul>
<li>Grecia, bajo el nombre de &quot;Michanikós ilektronikón ipologistón, tilepikinonión ke diktíon&quot;</li>
<li><span style="font-weight: bold">España, bajo el nombre de &quot;Ingeniero de telecomunicación&quot;</span></li>
</ul>
<p>&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;-</p>
<p>¿Conclusiones? Muchas, podemos comenzar a debatir, yo voy dejando alguna:
<ul>
<li>Las profesiones reguladas <span style="font-weight: bold">es algo normal</span> en los países. Si véis las listas de cada país, son más de 150 las profesiones reguladas en cada uno.</li>
<li>La regulación de Telecomunicaciones se queda en Portugal, Grecia y España, sin embargo, <span style="font-weight: bold">Portugal y Grecia además de Telecomunicaciones también tiene regulada Informática</span>.</li>
<li>Informática (Information systems engineer/practitioner) se extiende como profesión regulada por los países donde está Teleco, como Portugal y Grecia, <span style="font-weight: bold">pero además, por Reino Unido, Italia y Liechtenstein.</span></li>
<li> En los países donde se regula teleco, excepto en España, <span style="font-weight: bold">también se regula informática</span>. En los países donde se regula informática, no siempre existe Teleco.  <img src="./images/smilies/icon_rolleyes.gif" alt=":roll:" title="Rolling Eyes" /> </li>
<li> Francia? Alemania? niegan todo conocimiento sobre Teleco e Informática&#8230;., pero sí tienen reguladas una pila de profesiones.</li>
</ul>
<p>En fin, recomiendo darse una vueltecilla por la esta base de datos.<br />Ánimo a todos los que luchamos por la regulación de nuestra profesión.</p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2009/02/02/profesiones-reguladas-en-europa-informatica-vs-telecomunicaciones/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Otro manifiesto informático</title>
		<link>https://www.sing-group.org/~lipido/blog/2008/11/09/otro-manifiesto-informatico/</link>
		<comments>https://www.sing-group.org/~lipido/blog/2008/11/09/otro-manifiesto-informatico/#comments</comments>
		<pubDate>Sun, 09 Nov 2008 13:11:38 +0000</pubDate>
		<dc:creator><![CDATA[lipido]]></dc:creator>
				<category><![CDATA[Informática]]></category>

		<guid isPermaLink="false">http://sing.ei.uvigo.es/~lipido/blog/index.php/2008/11/09/otro-manifiesto-informatico/</guid>
		<description><![CDATA[]]></description>
				<content:encoded><![CDATA[<p><object width="425" height="344"><param name="movie" value="http://www.youtube.com/v/k4ULNPyW2gM&#038;hl=es&#038;fs=1"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="always"></param><embed src="http://www.youtube.com/v/k4ULNPyW2gM&#038;hl=es&#038;fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"></embed></object></p>
]]></content:encoded>
			<wfw:commentRss>https://www.sing-group.org/~lipido/blog/2008/11/09/otro-manifiesto-informatico/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
