User Activity by Xon

User Activity by Xon 2.13.4

No permission to download
You step the IP/port to that dedicated redis instance as shown in that config snippet. Ensure this goes after the normal $config['cache'] bits.

The biggest failure mode is if you make a typo and config.php isn't valid php
 
Hello and thank you for the wonderful add on.

I read but might have missed otherwise I would not take up your time.

Is there a way to limit this to certain forums only?
 
We're noticing the guest counts within a thread and the parent forum being way off; the member count tracking however seems to be probably correct. For guests, the count is reading from 3-6 or so for the past 45 minutes, but if I view the "Current visitors" page filtered to Guests, I just counted 39 guests listed as viewing that thread in the first 5 pages alone, out of 15 pages worth of guests. So the actual count of guests viewing that thread is likely over 100, where this addon is reporting <10. And as mentioned, it's been like that for over 45 minutes, so the 15 minute window shouldn't be an issue. Or at least not where it would account for such a huge discrepancy.

Any idea why that might be happening? We are using Redis as well, for reference.

EDIT:
For reference, this thread with patch notes for a game was linked from Steam and is currently getting a lot of views:
And yet looking through the Guest activity for the forums you can very quickly count higher activity for that thread than what the addon is reporting in the thread:
 
Last edited:
The add-on tracks if a guest views a thread by adding them to a 15 minute bucket grouped by user-id&ip while the members online tracks sessions.

So if the same IP with a guest has multiple sessions it will show up as multiple XF sessions but only count as 1 "user activity" record. This is something of a design limitation that works well enough.
 
The add-on tracks if a guest views a thread by adding them to a 15 minute bucket grouped by user-id&ip while the members online tracks sessions.

So if the same IP with a guest has multiple sessions it will show up as multiple XF sessions but only count as 1 "user activity" record. This is something of a design limitation that works well enough.
That's definitely not working correctly, then. As above, over more than a 45-minute period where there was consistently over 100 guests constantly viewing the thread from completely different IPs, an ever changing list of different guests, the addon reported a number ranging from 3-6 guests. This could be easily confirmed as an admin looking at the guest list, counting the number of guests listed as viewing that specific thread, and seeing all unique IPs on them.

We are behind CloudFlare, which could conceivably cause wrong IPs reported, but we have the IPs automatically updated by Nginx and reported to any downstream software as the user's correct IP, so I don't see how that would be an issue. To XF and everything else, the user's IP is reported.
And as mentioned, in the guest list the list of guest users with all their unique IPs are provided.

Any other ideas why it would be reporting incorrectly?

EDIT:
And checking just now, I come to a count of 20 in the first 5 pages of guests, all on unique IPs, some IPv4 and some IPv6, out of 12 pages of guests total. So probably ~40+ guests. The addon is reporting 8, which is at least higher than it was earlier, but... clearly off.
 
Last edited:
This add-on is relatively simple in how it logs and then displays guest users. For guests, per-ip record is added every view (redis ensures this is unique) and then on display it fetches the records an counts the number without a user-id associated with them.
 
This add-on is relatively simple in how it logs and then displays guest users. For guests, per-ip record is added every view (redis ensures this is unique) and then on display it fetches the records an counts the number without a user-id associated with them.
With it being that simple, it is strange that it is failing, but it is. Inconvenient, but true. A cursory look through our guest list linked above even now can demonstrate that. As an admin I can see the IPs in the guest list as well and confirm they're unique; as a guest or regular user viewing the guest list, you can at least count the guests viewing that thread and quickly reach a much higher number than the addon is indicating viewing the thread.
 
Regarding your comment to my rating, as has already been solidly established, that's not what was happening. Dozens of guests with unique IPs, being replaced over the minutes and hours and days by other guests with unique IPs, consistently high numbers over a few days, but this addon was consistently vastly underreporting them at every given moment. I provided links earlier demonstrating this which you could have followed and observed much of that behavior yourself.

I absolutely appreciate all the work that you do on this and other valuable addons, of which we use several, including a couple of paid addons, but this addon absolutely is flawed in some way in how it tallies up guest viewer counts. Perhaps something else, like caching, or who knows what, is bypassing the part of the code where you count guest views? I don't know, but whatever it is, something is preventing it from correctly counting all of them.
 
The default behavior doesn't track sessions marked as robots (configurable with the "User activity tracks robots" global addon option), and it groups by guest requests by ip. These two factors can vastly reduce how much read traffic the add-on reports, especially if using are using an add-on which adds more robot detection (ie @Sim'sKnown bots)
 
The default behavior doesn't track sessions marked as robots (configurable with the "User activity tracks robots" global addon option), and it groups by guest requests by ip. These two factors can vastly reduce how much read traffic the add-on reports, especially if using are using an add-on which adds more robot detection (ie @Sim'sKnown bots)
Neither of those was the case. Our "Current visitors" list does have guests and robots separated. And as I've mentioned more than once, practically all of the guests listed had different IPs. This addon was not properly counting all of the non-robot guests with unique IPs. Not by a very very large margin.

Anyway, enough said, we're basically going in circles covering the same talking points here.
 
Just to add, out of curiosity I tested a bit further. I stayed logged in through my real IP on my desktop to my forum admin account, and opened a an older forum thread that nobody else was viewing; the addon indicated 1 member viewing, 0 guests, as it should. I then loaded a VPN on my phone and connected it through a different geographic location, and loaded the same forum thread page as a guest. I then did the same on my tablet/laptop, connecting as a guest through another different VPN location and viewing the same thread. On my tablet, it then reported 3 guests (slightly odd, I would have expected it to correctly be 2 at that point), but for my admin account on my desktop it indicated only 1 guest, even after repeated refreshes.
On my tablet, I then cleared site cookies, switched the VPN to a different location, and reloaded the forum page. I repeated that a couple of times. It continued to report 3 guests consistently to my not-logged-in tablet. The guest count went up to 2 as seen by my admin account on my desktop. After repeating that process as quickly as I could on my tablet, clearing site cookies, switching VPN location (and thus IP), and reloading the page, 4-5 times in a row, the count shown to both devices didn't change again. Except the guest count finally dropped back to 1 after a few minutes as reported to my admin account on my desktop, while I continued juggling new guest IP connections. The guest count stayed at 3 on my tablet. I also occasionally refreshed the page on my phone as another guest.

Not sure why I bothered, it was already clear the addon wasn't counting guests correctly, but just in case this further info is helpful in some way...

I did glance through the code for the addon, since I have many years of programming experience at this point, but after skimming through it... I don't really feel like digging through the injections, extensions, and related core XF code to figure out how exactly this addon interfaces with it and try to hunt down the problem. If you don't, I might try to dig further at some point when I have the free time and willpower.
 
Xon updated User Activity by Xon with a new update entry:

2.12.1 - Feature update

  • Add "View user activity counters" permission. Control if the 'x viewing now' counter displays for a given user-group
  • Add "View user names/avatars in activity block" permissions. If false, the phrase svUserActivity_viewing_users_are_empty is displayed if it is not empty.
    This can be styled using the css selector #uaThreadViewContainer .empty-list
  • Add "Report View" and "Reports List" as options for displaying viewer counts
  • Split "Reports viewing...

Read the rest of this update entry...
 
Recently upgraded to the latest version... came in today and found this (3 pages worth) in my server error log

Code:
TypeError: substr(): Argument #1 ($string) must be of type string, array given
src/XF/Repository/SessionActivity.php:216
Generated by: Unknown account
August 30, 2023 at 4:10 PM

Stack trace
#0 src/XF/Repository/SessionActivity.php(216): substr(Array, 0, 25)
#1 src/addons/SV/LimitBots/XF/Repository/SessionActivity.php(30): XF\Repository\SessionActivity->updateSessionActivity(0, '34.168.205.215', 'XFMG\\Pub\\Contro...', 'View', Array, 'valid', Array)
#2 src/XF/Pub/Controller/AbstractController.php(85): SV\LimitBots\XF\Repository\SessionActivity->updateSessionActivity(0, '34.168.205.215', 'XFMG\\Pub\\Contro...', 'View', Array, 'valid', Array)
#3 src/XF/Pub/Controller/AbstractController.php(45): XF\Pub\Controller\AbstractController->updateSessionActivity('View', Object(XF\Mvc\ParameterBag), Object(XF\Mvc\Reply\View))
#4 src/XF/Mvc/Controller.php(360): XF\Pub\Controller\AbstractController->postDispatchType('View', Object(XF\Mvc\ParameterBag), Object(XF\Mvc\Reply\View))
#5 src/XF/Mvc/Dispatcher.php(385): XF\Mvc\Controller->postDispatch('View', Object(XF\Mvc\ParameterBag), Object(XF\Mvc\Reply\View))
#6 src/XF/Mvc/Dispatcher.php(259): XF\Mvc\Dispatcher->dispatchClass('XFMG\\Pub\\Contro...', 'View', Object(XF\Mvc\RouteMatch), Object(Truonglv\Groups\XFMG\Pub\Controller\Media), Object(XF\Mvc\Reply\Reroute))
#7 src/XF/Mvc/Dispatcher.php(115): XF\Mvc\Dispatcher->dispatchFromMatch(Object(XF\Mvc\RouteMatch), Object(Truonglv\Groups\XFMG\Pub\Controller\Media), Object(XF\Mvc\Reply\Reroute))
#8 src/XF/Mvc/Dispatcher.php(57): XF\Mvc\Dispatcher->dispatchLoop(Object(XF\Mvc\RouteMatch))
#9 src/XF/App.php(2487): XF\Mvc\Dispatcher->run()
#10 src/XF.php(524): XF\App->run()
#11 index.php(20): XF::runApp('XF\\Pub\\App')
#12 {main}
Request state
array(4) {
  ["url"] => string(67) "/media/aiimage78_clone_clone-denoise-low-light-3026-x-2191-jpg.141/"
  ["referrer"] => bool(false)
  ["_GET"] => array(1) {
    ["/media/aiimage78_clone_clone-denoise-low-light-3026-x-2191-jpg_141/"] => string(0) ""
  }
  ["_POST"] => array(0) {
  }
}
Code:
TypeError: SV\UserActivity\Repository\UserActivity::flushTrackViewerUsageBuffer(): Argument #2 ($robotKey) must be of type ?string, array given, called in /home/nginx/domains/astrowhat.com/public/src/addons/SV/UserActivity/XF/Repository/SessionActivity.php on line 36
src/addons/SV/UserActivity/Repository/UserActivity.php:758
Generated by: Unknown account
August 30, 2023 at 4:10 PM

Stack trace
#0 src/addons/SV/UserActivity/XF/Repository/SessionActivity.php(36): SV\UserActivity\Repository\UserActivity->flushTrackViewerUsageBuffer('35.199.167.158', Array, Object(SV\ElasticSearchEssentials\XF\Entity\User))
#1 src/addons/SV/LimitBots/XF/Repository/SessionActivity.php(30): SV\UserActivity\XF\Repository\SessionActivity->updateSessionActivity(0, '35.199.167.158', 'XFMG\\Pub\\Contro...', 'View', Array, 'valid', Array)
#2 src/XF/Pub/Controller/AbstractController.php(85): SV\LimitBots\XF\Repository\SessionActivity->updateSessionActivity(0, '35.199.167.158', 'XFMG\\Pub\\Contro...', 'View', Array, 'valid', Array)
#3 src/XF/Pub/Controller/AbstractController.php(45): XF\Pub\Controller\AbstractController->updateSessionActivity('View', Object(XF\Mvc\ParameterBag), Object(XF\Mvc\Reply\View))
#4 src/XF/Mvc/Controller.php(360): XF\Pub\Controller\AbstractController->postDispatchType('View', Object(XF\Mvc\ParameterBag), Object(XF\Mvc\Reply\View))
#5 src/XF/Mvc/Dispatcher.php(385): XF\Mvc\Controller->postDispatch('View', Object(XF\Mvc\ParameterBag), Object(XF\Mvc\Reply\View))
#6 src/XF/Mvc/Dispatcher.php(259): XF\Mvc\Dispatcher->dispatchClass('XFMG\\Pub\\Contro...', 'View', Object(XF\Mvc\RouteMatch), Object(Truonglv\Groups\XFMG\Pub\Controller\Media), Object(XF\Mvc\Reply\Reroute))
#7 src/XF/Mvc/Dispatcher.php(115): XF\Mvc\Dispatcher->dispatchFromMatch(Object(XF\Mvc\RouteMatch), Object(Truonglv\Groups\XFMG\Pub\Controller\Media), Object(XF\Mvc\Reply\Reroute))
#8 src/XF/Mvc/Dispatcher.php(57): XF\Mvc\Dispatcher->dispatchLoop(Object(XF\Mvc\RouteMatch))
#9 src/XF/App.php(2487): XF\Mvc\Dispatcher->run()
#10 src/XF.php(524): XF\App->run()
#11 index.php(20): XF::runApp('XF\\Pub\\App')
#12 {main}
Request state
array(4) {
  ["url"] => string(53) "/media/7200718a-31f9-456c-b0e0-74579eb97bf8-jpeg.136/"
  ["referrer"] => bool(false)
  ["_GET"] => array(1) {
    ["/media/7200718a-31f9-456c-b0e0-74579eb97bf8-jpeg_136/"] => string(0) ""
  }
  ["_POST"] => array(0) {
  }
}

Using REDIS for caching (along with your add-on for it).

Screen Shot 2023-08-30 at 4.17.24 PM.webp

In fact.. for some reason when I disable this, I get other errors... all related to several add-ons from you... next it was the Limit Bots then it was the ES essentials... about to reboot the server after applying some updates to see if that resolves anything.
 
Code:
    ErrorException: Template error: [E_USER_WARNING] Macro public:UA_ViewContainer_macros:viewerCounts is unknown src/XF/Template/Templater.php:660

Stack-Trace

#0 [internal function]: XF\Template\Templater->handleTemplateError(512, '[E_USER_WARNING...', '/homepages/...', 660)
#1 src/XF/Template/Templater.php(660): trigger_error('Macro public:UA...', 512)
#2 src/XF/Template/Templater.php(773): XF\Template\Templater->getTemplateMacro('public', 'UA_ViewContaine...', 'viewerCounts')
#3 internal_data/code_cache/templates/l2/s4/public/thread_list_macros.php(329): XF\Template\Templater->callMacro('UA_ViewContaine...', 'viewerCounts', Array, Array)
#4 src/XF/Template/Templater.php(990): XF\Template\Templater->{closure}(Object(SV\LazyImageLoader\XF\Template\Templater), Array, Object(XF\Template\ExtensionSet))
#5 src/XF/Template/Templater.php(926): XF\Template\Templater->renderExtensionInternal('main_cell', Array, Array, Object(XF\Template\ExtensionSet))
#6 internal_data/code_cache/templates/l2/s4/public/thread_list_macros.php(662): XF\Template\Templater->renderExtension('main_cell', Array, Object(XF\Template\ExtensionSet))
#7 src/XF/Template/Templater.php(827): XF\Template\Templater->{closure}(Object(SV\LazyImageLoader\XF\Template\Templater), Array, Object(XF\Template\ExtensionSet))
#8 internal_data/code_cache/templates/l2/s4/public/whats_new_posts.php(249): XF\Template\Templater->callMacro('thread_list_mac...', 'item', Array, Array)
#9 src/XF/Template/Templater.php(827): XF\Template\Templater->{closure}(Object(SV\LazyImageLoader\XF\Template\Templater), Array, NULL)
#10 internal_data/code_cache/templates/l2/s4/public/whats_new_posts.php(348): XF\Template\Templater->callMacro('whats_new_posts', 'results', Array, Array)
#11 src/XF/Template/Templater.php(1654): XF\Template\Templater->{closure}(Object(SV\LazyImageLoader\XF\Template\Templater), Array, NULL)
#12 src/XF/Template/Template.php(24): XF\Template\Templater->renderTemplate('whats_new_posts', Array)
#13 src/XF/Mvc/Renderer/Html.php(50): XF\Template\Template->render()
#14 src/XF/Mvc/Dispatcher.php(460): XF\Mvc\Renderer\Html->renderView('XF:WhatsNew\\Pos...', 'public:whats_ne...', Array)
#15 src/XF/Mvc/Dispatcher.php(442): XF\Mvc\Dispatcher->renderView(Object(XF\Mvc\Renderer\Html), Object(XF\Mvc\Reply\View))
#16 src/XF/Mvc/Dispatcher.php(402): XF\Mvc\Dispatcher->renderReply(Object(XF\Mvc\Renderer\Html), Object(XF\Mvc\Reply\View))
#17 src/XF/Mvc/Dispatcher.php(60): XF\Mvc\Dispatcher->render(Object(XF\Mvc\Reply\View), 'html')
#18 src/XF/App.php(2487): XF\Mvc\Dispatcher->run()
#19 src/XF.php(524): XF\App->run()
#20 index.php(20): XF::runApp('XF\\Pub\\App')
#21 {main}
 
Top Bottom