Olá. Estou desenvolvendo uma aplicação que disponibilizará acesso a clientes J2ME. O servidor dessa aplicação usa o framework Spring Security para autenticação e gerenciamento de sessão dos usuários. Porém, só estou conseguindo logar na aplicação utilizando uma página HTML e fazendo uma requisição via POST. Eu acredito que o processo seja o mesmo, tanto numa página HTML como enviando uma requisição através do cliente J2ME. Logo, suspeito que estou fazendo algo errado na aplicação móvel.
Eu não pretendo utilizar cookies, por isso desabilitei no navegador. Deste modo o spring já fornece o jsessionid na própria URL. Apenas pra elucidar, no servidor eu configurei para que uma servlet seja processada quando o usuário não estiver logado e essa servlet apenas exibe “Acesso Negado”. Logo, toda vez que eu acesso algum serviço da minha aplicação e não estou logado sou redirecionado para um link como esse e recebo “Acesso Negado”:
http://localhost:porta/aplicacao/login;jsessionid=42093420934023
Lógico que a jsessionid é sempre diferente. Pra realizar o teste no navegador, utilizo a seguinte página (configuro com a jsession id obtida anteriormente):
<html>
<head>
<title>Teste de acesso ao servidor</title>
</head>
<body>
<form action="http://localhost:8084/Server/j_spring_security_check;jsessionid=42093420934023" method="POST">
Nome: <input type="text" name="j_username"><br/>
Senha: <input type="password" name="j_password"><br/>
<input type="submit" value="Go!">
</form>
</body>
</html>
Após isto, eu sou redirecionado para a página em que tentei acessar inicialmente, porém agora logado e com um novo jsessionid. A partir deste novo jsessionid eu consigo, normalmente, acessar todos os outros serviços da aplicação.
O problema é que na aplicação J2ME, após eu “realizar login” (acho que isso não está acontecendo), minha aplicação continua indo pra servlet que retorna “Acesso Negado”, ou seja, como se não tivesse logado. Meio que no desespero, criei essa classe que faz tudo sequencialmente, apenas pra fazer funcionar esse caso hipotético. Lógico que não é a que irei usar na aplicação, mas para os testes ela já é suficiente:
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package net.unesc.kiron;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import javax.microedition.io.Connector;
import javax.microedition.io.HttpConnection;
/**
* Classe simples para testar conexao j2me
*
* @author wagner
*/
public class ConexaoServidorXML implements Runnable {
private String urlServer = "http://localhost:8084/Server/";
private String urlLogin = "j_spring_security_check";
private HttpConnection connection = null;
private String urlCorrente = null;
private String urlInicial = null;
private String username, password;
/* A URL inicial não é inteira, apenas especifica qual serviço vou usar. */
public ConexaoServidorXML(String urlInicial, String username, String password) {
this.urlInicial = urlInicial;
this.username = username;
this.password = password;
}
/* Realiza conexao */
public void run() {
try {
String dados = "j_username=" + username + "&j_password=" + password;
connection = (HttpConnection) Connector.open(urlServer + urlInicial);
System.out.println(urlServer + urlInicial);
connection.setRequestMethod(HttpConnection.POST);
connection.setRequestProperty("If-Modified-Since", "28 Jul 2008 11:51:00 GMT");
connection.setRequestProperty("User-Agent", "Profile/MIDP-2.0 Configuration/CLDC-1.1");
connection.setRequestProperty("Content-Language", "pt-BR");
connection.setRequestProperty("Custom-Property", "MyCustomProperty/1.0; AnotherProperty/debug_0.1");
connection.setRequestProperty("Content-Length", Integer.toString(dados.getBytes().length));
if (connection.getResponseCode() == 302) {
System.out.println("Arrumar url pra logar");
/* Recebendo jsessionid */
String jsessionid = getJSessionId(connection.getHeaderField("Location"));
connection.close();
connection = (HttpConnection) Connector.open(urlServer + urlLogin + ';' + jsessionid);
connection.setRequestMethod(HttpConnection.POST);
OutputStream output = connection.openOutputStream();
output.write(dados.getBytes());
output.flush();
output.close();
if (connection.getResponseCode() == 302) {
//Nova URL. Aqui ja deveria estar rebendo a URL com o jsessionid logado e acessar os servicos anteriores
String new_uri = connection.getHeaderField("Location");
System.out.println(new_uri);
connection.close();
connection = (HttpConnection) Connector.open(new_uri);
connection.setRequestMethod(HttpConnection.POST);
System.out.println("Iniciar leitura");
InputStream input = connection.openInputStream();
StringBuffer buf = new StringBuffer();
int c;
while ((c = input.read()) != -1) {
buf.append((char) c);
}
System.out.println(buf.toString());
input.close();
}
}
} catch (IOException ex) {
ex.printStackTrace();
} finally {
try {
connection.close();
} catch (IOException ex) {
ex.printStackTrace();
}
}
}
public String getJSessionId(String str) {
for (int i = 0; i < str.length(); ++i) {
if (str.charAt(i) == ';') {
return str.substring(i + 1);
}
}
return null;
}
}
O problema é que só recebo “Acesso Negado”. Estou realizando algum procedimento errado para enviar os parâmetros j_username e j_password? Esses redirecionamentos (usando a resposta 302 do servidor http) estão corretos? Alguém tem idéia do que possa estar acontecendo?
Obrigado pela atenção!