JSF 2.2 Como obter FacesContext fora do Bean

Bom gente, já revirei o que eu pude com o Google e não achei uma resposta que pudesse me ajudar, vou tentar descrever o melhor possível a situação.

eu tenho um ManagedBean, esse aqui

import javax.faces.bean.ManagedBean;
import javax.faces.bean.SessionScoped;

@ManagedBean(name="usuario")
@SessionScoped
public class InfoUsu {
	
	private int logou;
	
	public InfoUsu(){
		System.out.println("Bean");// isso é só para eu saber quando o bean for iniciado.
	}

	public final int getLogou() {
		return logou;
	}

	public final void setLogou(int logou) {
		this.logou = logou;
	}
	
	

}

ele é simples, mas pra esse teste um valor é o suficiente, e ele é iniciado pelo index na tag bory,

<h:body onload="#{usuario}">

e tenho uma outra classe que trata as requisições RestFul (estou estudando AngularJS no momento)

import java.util.ArrayList;
import java.util.List;

import javax.ws.rs.Consumes;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;


@Path("/logiinn")
public class Angu {
	
	@GET
	@Path("/pegarai")
	@Produces(MediaType.APPLICATION_JSON)
	public List<Objeto> Retorna(){	
		List<Objeto> lista = new ArrayList<Objeto>();
		lista.add(new Objeto(1,"leandro"));
		lista.add(new Objeto(2,"leandr"));
		lista.add(new Objeto(3,"leanro"));
		lista.add(new Objeto(4,"lendro"));
		lista.add(new Objeto(5,"eandro"));
		lista.add(new Objeto(6,"lndro"));
		lista.add(new Objeto(7,"leano"));
		lista.add(new Objeto(8,"landr"));
		lista.add(new Objeto(9,"eadr"));
		return lista;
	}
	
	@POST
	@Consumes(MediaType.APPLICATION_JSON)
	@Produces(MediaType.TEXT_PLAIN)
	public String Login(LogJson log){
		Logando lo = new Logando();//classe que testa se usuário e senha estão corretos
		boolean logo = lo.loga(log.getUsuario(), log.getSenha());// se o login estiver correto ele devolve true
		if(logo == true){ 
			
			//AQUI é onde deveria chamar a sessão do Bean
			
			return "1";
		}else{
			return "0";
		}
		
	}

}

eu quero, que quando eu mande a partir da pagina uma requisição @POST usando o AngularJS, eu consiga obter a sessão do Bean para que eu possa mudar o valor do int que tem nele, assim quando o usuário for acessar uma outra pagina o filtro que também é uma classe possa acessar o Bean e saber se esse usuário fez ou não o login de acesso.

encontrei varias formas de se pegar essa sessão, mas todas elas como um primeiro passo manda obter o FacesContext, e é isso que eu não consigo, sempre que uso o código,
[/code]
FacesContext facesContext = FacesContext.getCurrentInstance();

[code]
eu recebo null como resposta, e por isso o resto do código não funciona sempre estoura um erro.

alguém sabe como obter o FacesContext a partir de qualquer outro classe? e eu realmente preciso pegar essa sessão do bean para poder mexer nos valores dele?

qualquer coisa que não tenho ficado muito bem claro, me fale que eu tentarei esplicamelhor.

Obrigado a todos pela atenção.

1 curtida

Tenta da uma olhadinha no Doc
https://docs.oracle.com/cd/E17802_01/j2ee/javaee/javaserverfaces/2.0/docs/api/javax/faces/context/FacesContext.html

Ja tentou fazer um filtro? Nele vc so precisaria recuperar a sessão ou o mapa de parâmetros do request. Fazer o tratamento que deseja e seguir com a requisição. Sem a necessidade de chamar o facescontext.

//o urlPatterns indica que de paginas para frente tem que estar logado
@WebFilter(filterName = "FiltroLogin", urlPatterns = "/paginas/*")
public class FiltroLogin implements Filter {

    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        System.out.println("Passei no filtro de login");

        HttpSession sessao = ((HttpServletRequest) request).getSession();
        LoginController controller = (LoginController) sessao.getAttribute("loginController");
        String contextPath = ((HttpServletRequest) request).getContextPath();

        if (controller == null || !controller.isLogado()) {
            sessao.setAttribute("mensagem", "Você precisa estar logado para acessar a aplicação");
            ((HttpServletResponse) response).sendRedirect(contextPath + "/login.faces");
        } else {
            chain.doFilter(request, response);
        }
    }

    @Override
    public void destroy() {
    }

}

engano

antes de mais nada queria pedir perdão por trazer esse tópico das profundezas do limbo, mas é que es estava sem internet nesses últimos tempos então desculpe.

alexafe eu tentei usar o Doc, mas não sei se é burrice minha ou se não tem mesmo, mas o fato que que eu não encontrei uma solução por lá.

thimor eu já tinha tentado usar isso antes de postar aqui, mas, quando coloquei o filtro na mesma classe onde fica as anotações do RestFul a filtro parou de funcionar, então eu tentei por o filtro um passo antes, se a URL for LocalHost:3030/projeto/filtro/rest/log eu coloquei o filtro para trabalhar no /filtro e não funcionou, depois de quebrar bastante a cabeça descobre que não da para pegar o facescontext a partir do filter, e parece que nem de qualquer lugar, ainda continuo procurando uma solução quando achar uma porto aqui.

Bom pessoal acho que encontrei uma solução, pode não ser uma boa solução mas é uma solução, até o momento eu estava tentando pegar o context de qualquer lugar coisa que não dar certo, então o jeito é disponibiliza-lo num lugar “publico”, o que eu fiz, dentro do Bean criei um método que pega o facescontext e manda para um outra classe que vai armazenar esse context em um MAP e o segredo é marcar esse MAP como ‘static’, assim, não importa quantas vezes o Bean ou uma outra classe(eu acho) crie um novo objeto dessa classe os valores desse MAP vão esta lá, claro tenho que dar um jeito de gerenciar esse MAP Agora, mas para o proposta desse tópico, creio que esta resolvido.

valeu galera e espero que esse tópico possa ajudar mais alguem no futuro.

Cada requisição possui uma instancia diferente do facesContext que carrega todos os dados daquele momento da requisição. Vc usou um padrão singleton (static) provendo o mesmo facesContext pra tudo. Com certeza logo vc notará os problemas com mais usuários acessando com concorrencia.