跟踪用户最近活动的策略

时间:2022-11-10 13:00:56

Our customer would like to know who is online and currently using the custom application we wrote for them. I discussed it with them and this does not need to be exact, more of a guestimate will work.

我们的客户想知道谁是在线的,并且正在使用我们为他们编写的自定义应用程序。我和他们讨论过了,这个不需要精确,更多的猜测是有用的。

So my thought is a 15 minute time interval to determine user activity. Some ideas I have for doing this are as follows:

我的想法是用15分钟的时间间隔来确定用户活动。我的一些想法如下:

  1. Stamp their user record with a date and time of their last activity every time they do something that hits the database, or requests a web page ... this though could be quite database intensive.

    在用户记录上加上他们最近一次活动的日期和时间,每次他们做了什么事情去访问数据库,或者请求一个web页面……不过,这可能需要大量的数据库。

  2. Send out a "who is online request" from our software, looking for responses, this could be done at a scheduled interval, and then stamp the user record with the current date and time for each response I received.

    从我们的软件发送一个“who is online request”,寻找响应,这可以在预定的时间间隔内完成,然后在用户记录上加上我收到的每个响应的当前日期和时间。

What are your thoughts? And how would you handle this situation?

你的想法是什么?你将如何处理这种情况?

Clarification

澄清

I would like to use the same architecture for both Windows or the Web if possible. I have a single business logic layer that multiple user interfaces interact with, could be Windows or the Web.

如果可能的话,我希望在Windows和Web上使用相同的体系结构。我有一个业务逻辑层,多个用户界面可以与之交互,可以是Windows或Web。

By Windows I would mean client-server.

在Windows中,我指的是客户端-服务器。

Clarification

澄清

I am using an n-tier architecture so my business objects handle all the interaction with the presentation layer. That presentation layer could be feeding a client-server Windows application, Web application, Web Service and so on.

我使用的是n层架构,因此我的业务对象处理所有与表示层的交互。该表示层可以提供客户机-服务器窗口应用程序、Web应用程序、Web服务等。

It is not a high traffic application, as it was developed for a customer of ours, maybe 100 users at most.

它不是一个高流量的应用程序,因为它是为我们的客户开发的,最多可能有100个用户。

11 个解决方案

#1


4  

Our solution is to maintain a "Transaction" table (which follows what was done), in addition to our "Session" table (which follows who was here). UPDATE, INSERT and DELETE instructions are all managed through a "Transaction" object and each of these SQL instruction is stored in the "Transaction" table once it has been successfully executed on the database (depending on tables updated: we have the possibility to specifically follow some tables and ignore others). This "Transaction" table has other fields such as transactiontType (I for INSERT, D for DELETE, U for UPDATE), transactionDateTime, etc, and a foreign key "sessionId", telling us finally who sent the instruction. It is even possible, through some code, to identify who did what and when (Gus created the record on monday, Tim changed the Unit Price on tuesday, Liz added an extra discount on thursday, etc).

我们的解决方案是维护一个“事务”表(后面跟着所做的),以及我们的“会话”表(后面跟着这里的人)。更新、插入和删除指令都是通过一个“事务”对象进行管理的,一旦这些SQL指令在数据库上成功执行,它们就会被存储在“事务”表中(这取决于更新的表:我们有可能专门跟踪某些表,而忽略其他表)。这个“事务”表有其他字段,如transactiontType (I for INSERT, D for DELETE, U for UPDATE)、transactionDateTime等,以及一个外键“sessionId”,告诉我们最终是谁发送了指令。甚至可以通过一些代码来确定谁做了什么,什么时候做了(Gus在周一创造了这个记录,Tim在周二改变了单价,Liz在周四增加了额外的折扣等等)。

Pros for this solution are:

这种解决方案的优点是:

  1. you're able to tell "what who and when", and to show it to your users! (you'll need some code to analyse SQL statements)
  2. 你能说出“什么人和什么时候”,并显示给你的用户!(需要一些代码来分析SQL语句)
  3. if your data is replicated, and replication fails, you can rebuild your database through this table
  4. 如果数据被复制,并且复制失败,您可以通过这个表重新构建数据库

Cons are

缺点是

  1. 100 000 data updates per month mean 100 000 records in Tbl_Transaction
  2. 每个月10万个数据更新意味着Tbl_Transaction中的10万个记录
  3. Finally, this table tends to be 99% of your database volume
  4. 最后,这个表通常占数据库容量的99%

Our choice: all records older than 90 days are automatically deleted every morning

我们的选择:所有超过90天的记录每天早上都会自动删除

#2


1  

I've seen strategy 1 work before. Of course the site was a small one.

我以前见过策略1。当然,这个网站很小。

#3


0  

I'd just drop a log record table in the db.

我将在db中删除一个日志记录表。

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

UserId int FK动作char(3) ('in'或'out') Time DateTime

You can drop a new record in the table when somebody logs in or out or alternatively update the last record for the user.

当有人登录或退出时,您可以在表中删除一条新记录,或者为用户更新最后一条记录。

#4


0  

If you have session data just use that. Most session systems already have timestamps so they can expire sessions not used for x minutes.

如果你有会话数据,就用它。大多数会话系统都已经有了时间戳,因此它们可以使没有使用x分钟的会话过期。

#5


0  

You can increment a global variable everytime a user session is created, and decrement it when it is destroyed. This way you will always know how many users are online at any given moment.

您可以在每次创建用户会话时递增一个全局变量,并在销毁时递减它。这样你就能随时知道有多少用户在线。

If you want to monitor it over time, on the other hand, I think logging session start and end to the database is the best option, and you calculate user activity after the fact with a simple query.

如果您希望随时间监视它,另一方面,我认为记录会话开始和结束到数据库是最好的选择,您可以使用一个简单的查询来计算用户活动。

#6


0  

[DISCLAIMER 1 --- Java solution]

[免责声明1——Java解决方案]

If each meaningful user is given a Session, then you could write your own SessionListener implementation to track each session that has been created and destroyed.

如果给每个有意义的用户一个会话,那么您可以编写自己的SessionListener实现来跟踪创建和销毁的每个会话。

[DISCLAIMER 2 --- Code not tested or compiled]

[免责声明2——未测试或编译的代码]

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 ...    
    }
}

And register this in your web.xml:

并在您的web.xml中注册:

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

Hope this helps.

希望这个有帮助。

#7


0  

The only problem with a web application solution is you often don't know when someone signs out. Obviously, if you have a login / authentication requirement, you can capture when a person signs on, and as part of your data access code, you can log when a person hits the database. But you will have to accept that there will be on reliable way of capturing when a person logs off - many will just move away from the site without taking the "log off" action.

web应用程序解决方案的唯一问题是,您常常不知道什么时候有人退出。显然,如果您有登录/身份验证需求,您可以在用户登录时进行捕获,作为数据访问代码的一部分,您可以在用户登录数据库时进行日志记录。但你必须承认,当一个人注销时,会有可靠的方法来捕获——许多人会离开网站,而不采取“注销”行动。

#8


0  

I would imagine that using a trigger would be a reasonable option that would preclude you from having to mess with any logic differences between the web and the non-web environment (or any other environment for that matter). However, this only captures changes to the environment and doesn't do anything when select statements are made. This, however, can be overcome if all your commands from your apps are run through stored procedures.

我认为使用触发器是一种合理的选择,可以避免您在web和非web环境(或任何其他环境)之间的逻辑差异造成混乱。但是,这只捕获对环境的更改,并且在执行select语句时不做任何操作。但是,如果应用程序中的所有命令都通过存储过程运行,就可以克服这个问题。

#9


0  

I wonder how a site like * does it?

我想知道像*这样的网站是怎么做到的?

They must target a specific event, as I just tooled around the site, take a look at my profile, and still says something like last seen 8 minutes ago.

他们必须针对一个特定的事件,就像我刚刚在这个网站上使用工具一样,查看一下我的个人资料,仍然会说一些8分钟前最后一次看到的话。

#10


0  

With a web app, the concept of "online" is a little nebulous. The best you can really do is "made a request in the last X minutes" or maybe "authenticated in the last X minutes".

使用web应用程序,“在线”的概念有点模糊。你能做的最好的事情是“在最后X分钟提出请求”或者“在最后X分钟通过验证”。

Choose a set of events (made request, performed update, authenticated, ...), and log them to a DB table.

选择一组事件(发出请求、执行更新、验证、…),并将它们记录到DB表中。

Log them to a table in a separate DB

将它们记录到一个单独的DB中的表中

#11


0  

I have worked with many systems that have utilized the first method you listed, with a little careful planning it can be done in a manner that really doesn't have much of an effect.

我曾与许多系统合作过,它们使用了您列出的第一个方法,只要稍加仔细规划,就可以以一种实际上没有多大效果的方式来完成。

It all depends on exactly when/how/what you are trying to track. If you need to track multiple sessions I'll typically see people that use a session system tied to a user account, and then by a specific elapsed time that session is consiered dead.

这完全取决于你想要跟踪的时间/方式/内容。如果需要跟踪多个会话,我通常会看到使用与用户帐户绑定的会话系统的人,然后在特定的运行时间内会话被认为是无效的。

If you are truly looking for currently online, your first option is the best.

如果你真的在网上寻找,你的第一个选择是最好的。

#1


4  

Our solution is to maintain a "Transaction" table (which follows what was done), in addition to our "Session" table (which follows who was here). UPDATE, INSERT and DELETE instructions are all managed through a "Transaction" object and each of these SQL instruction is stored in the "Transaction" table once it has been successfully executed on the database (depending on tables updated: we have the possibility to specifically follow some tables and ignore others). This "Transaction" table has other fields such as transactiontType (I for INSERT, D for DELETE, U for UPDATE), transactionDateTime, etc, and a foreign key "sessionId", telling us finally who sent the instruction. It is even possible, through some code, to identify who did what and when (Gus created the record on monday, Tim changed the Unit Price on tuesday, Liz added an extra discount on thursday, etc).

我们的解决方案是维护一个“事务”表(后面跟着所做的),以及我们的“会话”表(后面跟着这里的人)。更新、插入和删除指令都是通过一个“事务”对象进行管理的,一旦这些SQL指令在数据库上成功执行,它们就会被存储在“事务”表中(这取决于更新的表:我们有可能专门跟踪某些表,而忽略其他表)。这个“事务”表有其他字段,如transactiontType (I for INSERT, D for DELETE, U for UPDATE)、transactionDateTime等,以及一个外键“sessionId”,告诉我们最终是谁发送了指令。甚至可以通过一些代码来确定谁做了什么,什么时候做了(Gus在周一创造了这个记录,Tim在周二改变了单价,Liz在周四增加了额外的折扣等等)。

Pros for this solution are:

这种解决方案的优点是:

  1. you're able to tell "what who and when", and to show it to your users! (you'll need some code to analyse SQL statements)
  2. 你能说出“什么人和什么时候”,并显示给你的用户!(需要一些代码来分析SQL语句)
  3. if your data is replicated, and replication fails, you can rebuild your database through this table
  4. 如果数据被复制,并且复制失败,您可以通过这个表重新构建数据库

Cons are

缺点是

  1. 100 000 data updates per month mean 100 000 records in Tbl_Transaction
  2. 每个月10万个数据更新意味着Tbl_Transaction中的10万个记录
  3. Finally, this table tends to be 99% of your database volume
  4. 最后,这个表通常占数据库容量的99%

Our choice: all records older than 90 days are automatically deleted every morning

我们的选择:所有超过90天的记录每天早上都会自动删除

#2


1  

I've seen strategy 1 work before. Of course the site was a small one.

我以前见过策略1。当然,这个网站很小。

#3


0  

I'd just drop a log record table in the db.

我将在db中删除一个日志记录表。

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

UserId int FK动作char(3) ('in'或'out') Time DateTime

You can drop a new record in the table when somebody logs in or out or alternatively update the last record for the user.

当有人登录或退出时,您可以在表中删除一条新记录,或者为用户更新最后一条记录。

#4


0  

If you have session data just use that. Most session systems already have timestamps so they can expire sessions not used for x minutes.

如果你有会话数据,就用它。大多数会话系统都已经有了时间戳,因此它们可以使没有使用x分钟的会话过期。

#5


0  

You can increment a global variable everytime a user session is created, and decrement it when it is destroyed. This way you will always know how many users are online at any given moment.

您可以在每次创建用户会话时递增一个全局变量,并在销毁时递减它。这样你就能随时知道有多少用户在线。

If you want to monitor it over time, on the other hand, I think logging session start and end to the database is the best option, and you calculate user activity after the fact with a simple query.

如果您希望随时间监视它,另一方面,我认为记录会话开始和结束到数据库是最好的选择,您可以使用一个简单的查询来计算用户活动。

#6


0  

[DISCLAIMER 1 --- Java solution]

[免责声明1——Java解决方案]

If each meaningful user is given a Session, then you could write your own SessionListener implementation to track each session that has been created and destroyed.

如果给每个有意义的用户一个会话,那么您可以编写自己的SessionListener实现来跟踪创建和销毁的每个会话。

[DISCLAIMER 2 --- Code not tested or compiled]

[免责声明2——未测试或编译的代码]

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 ...    
    }
}

And register this in your web.xml:

并在您的web.xml中注册:

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

Hope this helps.

希望这个有帮助。

#7


0  

The only problem with a web application solution is you often don't know when someone signs out. Obviously, if you have a login / authentication requirement, you can capture when a person signs on, and as part of your data access code, you can log when a person hits the database. But you will have to accept that there will be on reliable way of capturing when a person logs off - many will just move away from the site without taking the "log off" action.

web应用程序解决方案的唯一问题是,您常常不知道什么时候有人退出。显然,如果您有登录/身份验证需求,您可以在用户登录时进行捕获,作为数据访问代码的一部分,您可以在用户登录数据库时进行日志记录。但你必须承认,当一个人注销时,会有可靠的方法来捕获——许多人会离开网站,而不采取“注销”行动。

#8


0  

I would imagine that using a trigger would be a reasonable option that would preclude you from having to mess with any logic differences between the web and the non-web environment (or any other environment for that matter). However, this only captures changes to the environment and doesn't do anything when select statements are made. This, however, can be overcome if all your commands from your apps are run through stored procedures.

我认为使用触发器是一种合理的选择,可以避免您在web和非web环境(或任何其他环境)之间的逻辑差异造成混乱。但是,这只捕获对环境的更改,并且在执行select语句时不做任何操作。但是,如果应用程序中的所有命令都通过存储过程运行,就可以克服这个问题。

#9


0  

I wonder how a site like * does it?

我想知道像*这样的网站是怎么做到的?

They must target a specific event, as I just tooled around the site, take a look at my profile, and still says something like last seen 8 minutes ago.

他们必须针对一个特定的事件,就像我刚刚在这个网站上使用工具一样,查看一下我的个人资料,仍然会说一些8分钟前最后一次看到的话。

#10


0  

With a web app, the concept of "online" is a little nebulous. The best you can really do is "made a request in the last X minutes" or maybe "authenticated in the last X minutes".

使用web应用程序,“在线”的概念有点模糊。你能做的最好的事情是“在最后X分钟提出请求”或者“在最后X分钟通过验证”。

Choose a set of events (made request, performed update, authenticated, ...), and log them to a DB table.

选择一组事件(发出请求、执行更新、验证、…),并将它们记录到DB表中。

Log them to a table in a separate DB

将它们记录到一个单独的DB中的表中

#11


0  

I have worked with many systems that have utilized the first method you listed, with a little careful planning it can be done in a manner that really doesn't have much of an effect.

我曾与许多系统合作过,它们使用了您列出的第一个方法,只要稍加仔细规划,就可以以一种实际上没有多大效果的方式来完成。

It all depends on exactly when/how/what you are trying to track. If you need to track multiple sessions I'll typically see people that use a session system tied to a user account, and then by a specific elapsed time that session is consiered dead.

这完全取决于你想要跟踪的时间/方式/内容。如果需要跟踪多个会话,我通常会看到使用与用户帐户绑定的会话系统的人,然后在特定的运行时间内会话被认为是无效的。

If you are truly looking for currently online, your first option is the best.

如果你真的在网上寻找,你的第一个选择是最好的。