Domanda

I nostri clienti vorrebbero sapere chi è online e attualmente utilizza l'applicazione personalizzata che abbiamo scritto per loro. Ne ho discusso con loro e questo non deve essere esatto , funzionerà più di un ospite.

Quindi il mio pensiero è un intervallo di tempo di 15 minuti per determinare l'attività dell'utente. Alcune idee che ho per farlo sono le seguenti:

  1. Contrassegna il record utente con la data e l'ora della sua ultima attività ogni volta che fanno qualcosa che colpisce il database o richiede una pagina web ... anche se potrebbe essere piuttosto intensivo per il database.

  2. Invia un " chi è richiesta online " dal nostro software, in cerca di risposte, questo potrebbe essere fatto ad un intervallo programmato, quindi timbrare il record dell'utente con la data e l'ora correnti per ogni risposta che ho ricevuto.

Quali sono i tuoi pensieri? E come gestiresti questa situazione?

Chiarimento

Vorrei usare la stessa architettura sia per Windows che per il Web, se possibile. Ho un unico livello di logica aziendale con cui interagiscono più interfacce utente, potrebbe essere Windows o il Web.

Per Windows intendo client-server.

Chiarimento

Sto usando un'architettura di livello n in modo che i miei oggetti business gestiscano tutte le interazioni con il livello di presentazione. Tale livello di presentazione potrebbe alimentare un'applicazione Windows client, un'applicazione Web, un servizio Web e così via.

Non è un'applicazione ad alto traffico, poiché è stata sviluppata per un nostro cliente, forse al massimo 100 utenti.

È stato utile?

Soluzione

La nostra soluzione è mantenere una "Transazione" tabella (che segue ciò che è stato fatto), oltre alla nostra "Sessione" tabella (che segue chi era qui). Le istruzioni UPDATE, INSERT e DELETE sono tutte gestite tramite una "Transaction" oggetto e ciascuna di queste istruzioni SQL è memorizzata nella " Transaction " tabella una volta eseguita correttamente sul database (a seconda delle tabelle aggiornate: abbiamo la possibilità di seguire alcune tabelle in modo specifico e ignorarne altre). Questa " Transazione " la tabella ha altri campi come transazionetipo (I per INSERISCI, D per ELIMINA, U per AGGIORNAMENTO), transazioneDataTempo, ecc. e una chiave esterna "sessionId", che ci dice infine chi ha inviato l'istruzione. È anche possibile, attraverso alcuni codici, identificare chi ha fatto cosa e quando (Gus ha creato il record lunedì, Tim ha modificato il prezzo unitario martedì, Liz ha aggiunto uno sconto extra giovedì, ecc.)

I vantaggi di questa soluzione sono:

  1. sei in grado di dire " cosa chi e quando " ;, e mostrarlo ai tuoi utenti! (avrai bisogno di un po 'di codice per analizzare le istruzioni SQL)
  2. se i dati vengono replicati e la replica non riesce, è possibile ricostruire il database tramite questa tabella

I contro sono

  1. 100.000 aggiornamenti di dati al mese significano 100.000 record in Tbl_Transaction
  2. Infine, questa tabella tende ad essere il 99% del volume del database

La nostra scelta: tutti i record più vecchi di 90 giorni vengono automaticamente cancellati ogni mattina

Altri suggerimenti

Ho già visto la strategia 1 funzionare prima. Ovviamente il sito era piccolo.

Mi chiedo come fa un sito come StackOverflow?

Devono scegliere come target un evento specifico, dato che ho appena utilizzato il sito, dai un'occhiata al mio profilo e dice ancora qualcosa come visto l'ultima volta 8 minuti fa .

Lascerei semplicemente una tabella dei registri nel db.

UserId int FK
Action char (3) ('in' o 'out')
Time DateTime

Puoi eliminare un nuovo record nella tabella quando qualcuno accede o esce o in alternativa aggiorna l'ultimo record per l'utente.

Se disponi di dati di sessione, utilizzali. La maggior parte dei sistemi di sessione dispone già di timestamp in modo che possano scadere sessioni non utilizzate per x minuti.

Puoi incrementare una variabile globale ogni volta che viene creata una sessione utente e diminuirla quando viene distrutta. In questo modo sempre saprai quanti utenti sono online in un dato momento.

Se si desidera monitorarlo nel tempo, invece, penso che l'inizio della sessione di registrazione e la fine del database siano l'opzione migliore e si calcola l'attività dell'utente dopo il fatto con una semplice query.

[DISCLAIMER 1 --- soluzione Java]

Se a ciascun utente significativo viene assegnata una sessione, è possibile scrivere l'implementazione di SessionListener per tenere traccia di ogni sessione creata e distrutta.

[DISCLAIMER 2 --- Codice non testato o compilato]

public class ActiveSessionsListener implements HttpSessionListener {
    public void sessionCreated(HttpSessionEvent e) {
        ServletContext ctx = e.getSession().getServletContext();
        synchronized (ctx) {
            Integer count = ctx.getAttribute("SESSION_COUNT");
            if (count == null) { count = new Integer(0); }
            ctx.setAttribute("SESSION_COUNT", new Integer(count.intValue() + 1);
        }
    }
    public void sessionDestroyed(HttpSessionEvent e) {
        ... similar for decrement ...    
    }
}

E registralo nel tuo web.xml:

<listener-class>com.acme.ActiveSessionsListener</listener-class>

Spero che questo aiuti.

L'unico problema con una soluzione di applicazione web è che spesso non sai quando qualcuno si disconnette. Ovviamente, se si dispone di un requisito di accesso / autenticazione, è possibile acquisire quando una persona accede e come parte del codice di accesso ai dati, è possibile accedere quando una persona accede al database. Ma dovrai accettare che ci sarà un modo affidabile per catturare quando una persona si disconnette - molti si allontaneranno semplicemente dal sito senza togliere " disconnettiti " azione.

Immagino che l'uso di un trigger sarebbe un'opzione ragionevole che ti impedirebbe di dover fare confusione con eventuali differenze logiche tra il web e l'ambiente non web (o qualsiasi altro ambiente per quella materia). Tuttavia, questo cattura solo le modifiche all'ambiente e non fa nulla quando vengono fatte delle istruzioni selezionate. Questo, tuttavia, può essere superato se tutti i tuoi comandi dalle tue app vengono eseguiti tramite stored procedure.

Con un'app Web, il concetto di " online " è un po 'nebuloso. Il meglio che puoi veramente fare è "fare una richiesta negli ultimi X minuti" o forse "autenticato negli ultimi X minuti".

Scegli un set di eventi (richiesta fatta, aggiornamento eseguito, autenticato, ...) e registrali su una tabella DB.

Registrali in una tabella in un DB separato

Ho lavorato con molti sistemi che hanno utilizzato il primo metodo che hai elencato, con una pianificazione un po 'attenta che può essere fatta in un modo che davvero non ha molto effetto.

Tutto dipende esattamente da quando / come / cosa stai cercando di tracciare. Se devi tenere traccia di più sessioni, in genere vedrò persone che usano un sistema di sessione legato a un account utente, e poi per un tempo trascorso specifico tale sessione viene consegnata morta.

Se stai veramente cercando online, la tua prima opzione è la migliore.

Ho appena implementato un sistema visto per ultimo per il mio sito web. La tua prima opzione è simile, ma aggiorno solo ogni + -5 minuti. Funziona per la mia situazione, ma i siti Web su larga scala potrebbero richiedere qualcosa in più.

<?php
function updateLastSeen($user_ref, $session_id, $db) { /*Parameters: The user's primary key, the user's session id, the connection to the database*/
  $timestamp = date('Y-m-d H:i:s');
  if ($session_id !== '') {
    /*logged in*/
    $sql_check = "SELECT user_id FROM user_last_seen WHERE user_id = ?";
    $stmt_check = $db->prepare($sql_check);
    $stmt_check->bind_param('s', $user_ref);
    $result_check = $stmt_check->execute();
    $stmt_result_check = $stmt_check->get_result();
    if ($stmt_result_check->num_rows > 0) { /*If the user's last seen was previously recorded, update his record*/
      $sql = "UPDATE user_last_seen SET last_seen = ? WHERE user_id = ?"; 
    } else { /*Otherwise, insert a record for him*/
      $sql = "INSERT INTO user_last_seen (last_seen, user_id) VALUES (?,?)";
    }
    $stmt = $db->prepare($sql);
    $stmt->bind_param('ss', $timestamp, $user_ref);
    $result = $stmt->execute();
  }
}
if( !isset(

Ho appena implementato un sistema visto per ultimo per il mio sito web. La tua prima opzione è simile, ma aggiorno solo ogni + -5 minuti. Funziona per la mia situazione, ma i siti Web su larga scala potrebbero richiedere qualcosa in più.

<*>SESSION['lastSeen']) ){ /*User logs into the website or lands on the current page, create a lastSeen variable*/

Ho appena implementato un sistema visto per ultimo per il mio sito web. La tua prima opzione è simile, ma aggiorno solo ogni + -5 minuti. Funziona per la mia situazione, ma i siti Web su larga scala potrebbero richiedere qualcosa in più.

<*>SESSION['lastSeen'] = time(); updateLastSeen($user_ref, $session_id, $db); } else { $last_seen_time_difference = (time() -

Ho appena implementato un sistema visto per ultimo per il mio sito web. La tua prima opzione è simile, ma aggiorno solo ogni + -5 minuti. Funziona per la mia situazione, ma i siti Web su larga scala potrebbero richiedere qualcosa in più.

<*>SESSION['lastSeen']) / 60; if ($last_seen_time_difference > 5) { //if the difference between now and the lastSeen is 5 minutes or more, record his last seen. updateLastSeen($user_ref, $session_id, $db);

Ho appena implementato un sistema visto per ultimo per il mio sito web. La tua prima opzione è simile, ma aggiorno solo ogni + -5 minuti. Funziona per la mia situazione, ma i siti Web su larga scala potrebbero richiedere qualcosa in più.

<*>SESSION['lastSeen'] = time(); /*after updating the database, reset the lastSeen time to now.*/ }/* else { //do nothing. Don't update database if lastSeen is less than 5 minutes ago. This prevents unnecessary database hits. }*/ }
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top