JSF sessões

Fiz um chat em jsf assim:
a cada vez que um usuario se loga e manda uma mensagem, esta é adicionada numa tabela dentro de um escopo se sessão, sendo atualizada pelo poll
até ae tudo bem, as 2 sessoes estao recebendo a mensagem e mandando sem problemas
O chat nao tem privado, todas as mensagens sao publicas
Porém acontece o seguinte
Eu me logo
Vc se loga
Eu mando mensagem para todos
Como so tem vc na sala, vc responde
Outra pessoa entra no chat
ela consegue ver todas as mensagens anteriores

Eu queria fazer que nem um bate papo do uol, que a pessoa so ve as mensagens a partir da hora, que ela entrou, entende?
Será que eh um problema de arquitetura?(detalhe: fiz com um bean so de sessao)Uma sessao nao conhece a outra, so conhece essa tabela …

Meu cod ta assim:



    public String login(){
        ExternalContext extCon = FacesContext.getCurrentInstance().getExternalContext();
           HttpSession session = (HttpSession) extCon.getSession(true);
         setCor(getCorEscolhida());
  
            
        session.setAttribute("User", usuario);

     
        session.setAttribute("Cor", getCor());
        mensagens = new ArrayList();
     
        Mensagem msg = new Mensagem();
        SimpleDateFormat sdf = new SimpleDateFormat( "hh:mm:ss" );  
        String hora= sdf.format( new Date() );  
        msg.setHora(hora);
        msg.setMsgGenerica("entrou online");
               msg.setUsuario(usuario);
        msg.setCor(cor);
        getMensagens().add(msg);
        

        return "sala";
    }
    
    public String enviar()
    {
        
       int a=geraCorUsuario();
           int b=geraCorUsuario();
           int c=geraCorUsuario();
    
           ExternalContext extCon = FacesContext.getCurrentInstance().getExternalContext();
              HttpSession session = (HttpSession) extCon.getSession(true);
           String userName = (String) session.getAttribute("User");
           String cor = (String) session.getAttribute("Cor");
        Mensagem msg = new Mensagem();
         SimpleDateFormat sdf = new SimpleDateFormat( "hh:mm:ss" );  
         String hora= sdf.format( new Date() );  
         msg.setHora(hora);
         msg.setMsgGenerica(mensagemrecebida);
                msg.setUsuario(userName);
      msg.setCor(cor);
        getMensagens().add(msg);
     

             return null;
       }

Oi Carla,

cria um atributo de sessão do usuário do site com a data/hora que ele logou.
Como vc tem a data/hora das mensagens enviadas, na hora de vc exibir as mensagens para os usuários vc testa horaMensagem > horaLogin.

Certo!

O problema eh q essa tabela eh unica
Se eu tiver que exibir so as depois que ele logou, ao atualizar, isso vai mudar para todas as sessoes
As mensagens antigas nao vao aparecer pros usuarios antigos, que entraram antes desse usuario

Você poderia colocar um campo timestamp na sua tabela e gravar na sessão do uduário o momento que ele logou. Sendo assim, vc faz a pesquisa na tabela com uma condição que o tempo sempre deve ser maior que o tempo em que o usuário logou. Acho que resolve o seu problema.

Espero não ser tarde

[quote=carlavb]O problema eh q essa tabela eh unica
Se eu tiver que exibir so as depois que ele logou, ao atualizar, isso vai mudar para todas as sessoes
As mensagens antigas nao vao aparecer pros usuarios antigos, que entraram antes desse usuario[/quote]

O que eu quis dizer é o seguinte:

Vamos supor que vc esteja usando um dataTable para exibir mensagens e um outputLabel para exibi-las.
Vc pode fazer com rendered…

<rich:dataTable value="#{bean.listaMensagem}" var="mensagem" > <h:outputLabel rendered="#{bean.mensagem.dataHora > sessionScope.dataHoraLogin}" value="#{bean.mensagem.texto}" > </rich:dataTable>

ou com if

[code]<rich:dataTable value="#{bean.listaMensagem}" var=“mensagem” >
<c:if test="#{bean.mensagem.dataHora > sessionScope.dataHoraLogin}">
<h:outputLabel value="#{bean.mensagem.texto}" >
</c:if>
</rich:dataTable>

[/code]

Mas isso só acontece se ela utilizar ou classes estáticas no servidor, ou configurar o manage-beam com escopo de aplicação.

Com o escopo de sessão, cada usuário terá a sua instância no servidor. Então, se ela colocar a restrição no sql, ela consegue o resultado esperado.

Isso não se faz no JSF, se faz na classe de controle, porque é regra de negócio.

gente, nao adianta, pq a tabela fica a mesma para todas as sessoes, e o escopo eh sessao

 <h:dataTable value="#{salaBean.mensagens}"  var="msg" id="grid2" style="font-family:Trebuchet MS;">
      <%-- 
        oracle-jdev-comment:Faces.RI.DT.Class.Key:entrevista.Mensagem
      --%>
      <h:column>
        <f:facet name="header">
          <h:outputText value=""/>
        </f:facet>
        <h:outputText value="#{msg.hora}" style="font-color:Gray"/>
      </h:column >
      <h:column  >
        <f:facet name="header">
          <h:outputText value="" />
        </f:facet>
    
   
        <h:outputText value="#{msg.usuario}" styleClass="#{msg.cor}"/>
             
     
      </h:column>
      <h:column>
        <f:facet name="header">
          <h:outputText value=""/>
        </f:facet>
        <h:outputText value="#{msg.msgGenerica}"/>
      </h:column>
    </h:dataTable>

[quote=carlavb]gente, nao adianta, pq a tabela fica a mesma para todas as sessoes, e o escopo eh sessao
[/quote]

Joga a tabela para o scopo de aplicação, assim a tabela fica sendo única para todos.

mas eh isso que eu nao quero, que seja unica para todas…
eu quero que eu, que so entrei no chat depois de fulano, so veja as conversar depois da hora que eu loguei…
nao todas…se eu entrei antes de x, e x antes de a, eu vou ver todas as conversas de mesma forma
isso que eu nao quero…
entende?

do jeito que eu to fazendo, todas as sessoes recebem as mensagem sem eu ter que adicionar em todas as sessoes, eu apenas adiciono uma linha de conversa na tabela e todas recebem, graças ao a4j:poll, porem eu queria que as tabelas ainda tievessem essa propriedade sem terem que serem alteradas por completo quando eu quiser mexer na logica de so mostrar X registros na sessao…

Carla, mosta o método sala.

Outra coisa, como você está atualizando a tela?

Outra coisa, se você coloca uma restrição do tipo: hora > xxxx então, para cada usuário, os dados só serão exibido a partir dakela hora.

Agora, tem dois detalhes nesse abordagem:
primeiro, vc tem que usar o formato de data em DD/MM/AAA-HH:MM:SS
segundo, você deve guardar quando o usuário logou. E não pode usar estático. Mas esse é simples, basta criar um bean que guarda o valor. Como o bean será modificado apenas uma vez, enquanto o usuário estiver logado, o bean guarda o momento que ele logou.

Carla,

junte os post’s anteriores e forme a seguinte solução.
Jogue o bean com as conversas para o scopo de aplicação e quando for mostrar as conversas faça o teste da hora da conversa > hora login do usuário, conforme sugestão anterior.

Penso que assim vai funcionar.

Eu ja tinha posto com escopo de aplicação
Como o de aplicação atualiza para todos, e nao por sessao, se eu restringir com o IF, ele vai limitar as conversas para todos, como relatei antes

=/

[quote=carlavb]Eu ja tinha posto com escopo de aplicação
Como o de aplicação atualiza para todos, e nao por sessao, se eu restringir com o IF, ele vai limitar as conversas para todos, como relatei antes

=/[/quote]

Carla, veja bem,

o bean com as conversas vai ficar no escopo de aplicação.
O IF vc vai colocar na página Jsf e não no java. A página Jsf não tem escopo.

Mas da o erro de que ele nao deixa comparar datas com o operador > e sim so com o after()…
como faço para comparar datas com >?

Carla,

veja se vc está fazendo assim:

<c:if test="#{beanSessao.dataLogin > beanAplicacao.mensagem.dataMensagem}" > // exibe a mensagem aqui </c:if>

se o ‘>’ n funcionar tente ‘gt’ (maior que)

#{beanSessao.dataLogin gt beanAplicacao.mensagem.dataMensagem}" 

ah…mt obrigada
vou tentar

olha, tentei dessa forma, e quando outro usuaário de loga, beleza, ele nao ve as mensagens antigas
Porem basta que qualquer um mande outra mensagem, para um, a tabela mostrat tudo de novo
Me parece que o IF do JSTL so testa quando a página é instanciada, e depois não mais
tá ae meu código:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"http://www.w3.org/TR/html4/loose.dtd">
<%@ page contentType="text/html;charset=windows-1252"%>
<%@ taglib uri="http://java.sun.com/jsf/html" prefix="h"%>
<%@ taglib uri="http://java.sun.com/jsf/core" prefix="f"%>
<%@ taglib uri="http://richfaces.org/rich" prefix="rich"%>
<%@ taglib uri="http://richfaces.org/a4j" prefix="a4j"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<f:view>
  <html>
    <head>
      <meta http-equiv="Content-Type"
            content="text/html; charset=windows-1252"/>
      <title>sala</title>
      <style type="text/css" >
      
      .pink{
     color:Purple;
      font-weight:bold;
      }
       .blue{
      color:Blue;
       font-weight:bold;
      }
       .orange{
    color:Orange;
       font-weight:bold;
      }
      
      .green{
     color:Green;
       font-weight:bold;
      }
      
        .maroon{
     color:Maroon;
       font-weight:bold;
      }
      
        .red{
   color:Red;
      font-weight:bold;
      }
      
      </style>
    </head>
    <body>
     <a4j:region>
        <h:form>
            <a4j:poll id="poll2" reRender="grid2"
             />
        </h:form>
    </a4j:region>

    
    
   
    
    <a4j:form id="formChat">
     <div style="overflow: auto;height:300px">
      
        <h:dataTable value="#{salaBean.mensagens}"  var="msg" id="grid2" style="font-family:Trebuchet MS;">
       
            <h:column>
            <f:facet name="header">
              <h:outputText value=""/>
            </f:facet>
                 <c:if test="${msg.data gt chatSessaoBean.dataLogin}" >
            <h:outputText value="#{msg.hora}" style="font-color:Gray"/>
             </c:if>
          </h:column >
          <h:column  >
            <f:facet name="header">
              <h:outputText value="" />
            </f:facet>
         
              <c:if test="${msg.data gt chatSessaoBean.dataLogin}" >
            <h:outputText value="#{msg.usuario}" styleClass="#{msg.cor}"/>
                 
          </c:if>
          </h:column>
          <h:column>
            <f:facet name="header">
              <h:outputText value=""/>
            </f:facet>
                   <c:if test="${msg.data gt chatSessaoBean.dataLogin}" >
            <h:outputText value="#{msg.msgGenerica}"/>
             </c:if>
          </h:column>
              <h:column>
            <f:facet name="header">
              <h:outputText value=""/>
            </f:facet>
                <c:if test="${msg.data gt chatSessaoBean.dataLogin}" >
            <h:outputText value="#{msg.data}"/>
             </c:if>
          </h:column>
         
        </h:dataTable>
             
        
         </div>
        <h:inputText value="#{salaBean.mensagemrecebida}" binding="#{salaBean.d}" id="entradaMsg"/>
        <a4j:commandButton action="#{salaBean.enviar}" reRender="poll2" value="Enviar"/>
    </a4j:form></body>
  </html>
</f:view>








Porque vc está usando o $ no teste e não o #?
Qual versão do Jsf vc está utilizando?

Carla, faça de outra forma

[code] <c:if test="${msg.data gt chatSessaoBean.dataLogin}" >
<h:outputText value="#{msg.hora}" style=“font-color:Gray”/>
</c:if>

///troque o código acima por esse.

<h:outputText value="#{msg.hora}" style=“font-color:Gray” rendered="#{msg.data gt chatSessaoBean.dataLogin}" /> [/code]