Em um post anterior, apresentei o novo recurso de Grupos nos Servidores WebSocket. Neste post, mostrarei como combinar os Grupos WebSocket com as Conexões de Cliente para identificar e armazenar os dados do usuário em uma conexão de cliente.
A biblioteca sgcWebSockets permite criar seus próprios objetos e vinculá-los a uma classe TsgcWSConnection, para que você possa acessar seu objeto personalizado a qualquer momento quando uma nova mensagem for recebida, quando o cliente se desconectar... Agora você pode combinar a facilidade de uso dos Grupos e dos Objetos Personalizados para criar aplicações avançadas facilmente.
Autenticar Usuários
O servidor será configurado para aceitar apenas conexões de usuários autenticados, portanto, primeiro ative a Autenticação no lado do servidor e depois configure o evento OnAuthentication para autenticar a conexão recebida pelo servidor. Os usuários geralmente são armazenados em um banco de dados; neste exemplo, eles estão codificados diretamente para simplificar.
Server.Authentication.Enabled := True; Server.Authentication.Basic.Enabled := True;
Veja abaixo um exemplo de código: primeiro avalie se o Usuário/Senha são conhecidos; se corretos, crie uma nova instância da classe TsgcUser onde os dados do usuário são armazenados, preencha as propriedades e atribua à propriedade Connection.Data. Desta forma, você pode acessar os dados do usuário quando receber uma mensagem dele, quando se desconectar...
type
TsgcUser = class
private
FAge: Integer;
FDepartment: string;
FPhone: string;
FUsername: string;
public
property Username: string read FUsername write FUsername;
property Department: string read FDepartment write FDepartment;
property Phone: string read FPhone write FPhone;
property Age: Integer read FAge write FAge;
end;
procedure OnServerAuthentication(Connection: TsgcWSConnection; aUser,
aPassword: string; var Authenticated: Boolean);
var
oUser: TsgcUser;
begin
if (aUser = 'user-1') and (aPassword = 'password-1') then
begin
Authenticated := True;
oUser := TsgcUser.Create;
oUser.Username := 'Mark';
oUser.Phone := '+55431588744134';
oUser.Department := 'Sales';
oUser.Age := 22;
Connection.Data := oUser;
end
else
Authenticated := False;
end;
Assim que o usuário é Autenticado, o evento OnConnect será disparado; aqui você pode adicionar o usuário a um Grupo. Nesta demonstração, a propriedade Department do usuário será usada como nome do Grupo. Você pode adicionar uma conexão a mais de 1 grupo, basta chamar o método Groups.Add quantas vezes forem necessárias.
procedure OnServerConnect(Connection: TsgcWSConnection); begin Server.Groups.Add(TsgcUser(Connection.Data).Department, Connection); end;
Quando o cliente se desconecta, a classe de conexão é removida automaticamente da propriedade Groups, portanto, não é necessário remover manualmente, pois isso é feito automaticamente.
Usando Eventos
A propriedade Groups tem 2 eventos para notificar sempre que um usuário foi adicionado a um grupo ou quando foi removido.
OnClientAdded: quando uma nova conexão foi adicionada a um grupo.
OnClientRemoved: quando uma conexão existente foi removida de um grupo.
Você pode configurar esses eventos antes de o Servidor ser iniciado. No exemplo a seguir, enviamos uma mensagem a todos os membros do grupo informando que um novo membro foi adicionado ou que um membro existente se desconectou.
Server.Groups.OnClientAdded := OnClientAddedEvent;
Server.Groups.OnClientRemoved := OnClientRemovedEvent;
procedure OnClientAddedEvent(Sender: TObject; const aGroup:
TsgcWSServerGroupItem; const aConnection: TsgcWSConnection);
var
vMessage: string;
begin
vMessage := TsgcUser(aConnection.Data).Username + ' has logged in.';
aGroup.BroadCast(vMessage);
end;
procedure TForm16.OnClientRemovedEvent(Sender: TObject; const aGroup:
TsgcWSServerGroupItem; const aConnection: TsgcWSConnection);
var
vMessage: string;
begin
vMessage := TsgcUser(aConnection.Data).Username + ' has disconnected.';
aGroup.BroadCast(vMessage);
end;
Enviando Mensagens
Você pode usar os Grupos para transmitir mensagens a grupos específicos, a múltiplos grupos... veja abaixo alguns exemplos.
// All members
Server.Groups.Broadcast('*', 'Hello All Members.');
// Only group "admin"
Server.Groups.Broadcast('admin', 'Hello Admin Members.');
// All sales groups (sales/asi, sales/europe, sales/america...)
Server.Groups.Broadcast('sales/*', 'Hello Sales Members.');
// Only group "accounting" (must exists!!!)
Server.Groups.Group['accounting'].Broadcast('Hello Accounting Members.');
Veja abaixo o código-fonte das aplicações de Servidor e Cliente, bem como os binários compilados para Windows.
