Merge pull request #6549 from RosettaCommons/interactive/petrides/mac_build_fix
[Foldit] Update to XCode Project to Work with More Recent Apple Clang Versions
Merge pull request #6547 from RosettaCommons/interactive/petrides/fix_rephase_for_tracks
[Foldit] Fix Crash For Set Track in Density Refinement Puzzles
Merge pull request #6545 from RosettaCommons/roccomoretti/fix_autoupload
[Foldit] Address race condition in auto solution upload.
We're currently getting disk usage errors with the auto solution upload. It looks like the cause is a race condition where the main thread is adding to the same data structure that the solution thread is uploading from, which results in fresh solutions being immediately uploaded, rather than waiting for the next upload window.
We can move the to-upload data to a local data structure to avoid the race condition. (We just need to make sure to copy the not-yet-uploaded data back if we encounter a server error.)
Merge pull request #6543 from RosettaCommons/interactive/petrides/trim_untrim_lua_tweak
[Foldit] Fix Method Used to Error on Bad Conditions for Trim and Untrim in Lua
Merge pull request #6539 from RosettaCommons/roccomoretti/solutions_dialog
[Foldit] Add download dialog for solution list.
Player are complaining about not being able to fetch the list of shared solutions. This converts the solution list fetching to be behind the recently added Downloader dialog popup.
Merge pull request #6537 from RosettaCommons/roccmoretti/network_popup
[Foldit] Add loading/progress dialog popup for puzzle and solution loading
Automated timeouts seem to be an issue for some players. Instead of playing guess-and-check with the timeout thresholds (which were getting to be long from a UI perspective anyway), create a dialog box which allows users to cancel the download if the server is stalled.
The central clock is animated, to allow players to see that the Foldit client hasn't frozen. The clock will bounce left and right as data is received from the server, which allows players to know if something is happening, or if the server might be stuck. The cancel button will cancel the data transfer, returning the user to what they were doing before.
Puzzle download, solution download and solution upload (the actions which we have players complaining about devprev on) have been converted to use the new popup dialog.
Since the user has control over transfer cancellation, if we have a progress callback (i.e. we have a dialog box up), we don't have a timeout -- Foldit will sit at the dialog box until the transfer succeeds, gets a failure code from the server, or the user presses cancel.
One of the complications is that we can't be holding the GUI mutex while we're waiting for the download to complete. This would keep the dialog box from displaying and updating. The big complication here is that GUI button response callbacks have the GUI mutex held early on in the response chain. So we need to break out the download management into a separate thread.
We also need to update the Curl library calls to use a slightly different interface, to allow us to poll for cancellation during the transfer. (Otherwise the download will block until some sort of transfer happens.)
There's also some code to make server thread error handling more robust, as well as soft crash timeouts in automated solution uploading (so we can monitor for issues).
Merge pull request #6533 from RosettaCommons/roccmoretti/server_unavailable
[Foldit] Add timeout for server communication
We're running into a situation where the Foldit server is nominally "up" (so you don't get a full out connection error), but is taking forever to respond. The curl library has a timeout option, so we can recognize we're not getting a response back in a reasonable amount of time, and then raise an error appropriately.
I double checked, and it looks like everything communicating with the server should be properly wrapped to catch the exception -- whether it behaves reasonably when the server connection goes away is another question.
I tested it with the local server, and things seem to work decently when the connection goes away. (It also works with the login on the main server -- we wait for 5 seconds and then report the appropriate connection error.)
Merge pull request #6532 from RosettaCommons/roccomoretti/queue_play_events
[Foldit] Convert play event logging to use a deferred queue
Previously, the play event logging uploaded to the server directly each time it was called. This PR changes it such that the data gets uploaded to the server at the same time the game scores and the cached solutions get uploaded, hopefully reducing lag due to server communication. (The deferred uploads happen in a separate thread.)
I've also changed things around such that the server mutex isn't held throughout the upload process, which should hopefully reduce client freezing due to mutex contention. (e.g. if the main thread wants to post a queued server upload while the periodic upload is happening.)
Merge pull request #6502 from RosettaCommons/roccomoretti/interactive_telemetry
[Foldit] Re-enable event logging
With the switch to the new server, the event logging framework was disabled. This makes it hard to get statistics for player behavior, limiting how much info we can pull out for onboarding analysis. It looks like the data storage facilities are functional server-side, we just need to update the client to actually use the new approach.
This PR updates the old logging facility to fit into the new framework. I've also cleaned up some of the old logging events which we probably don't need to keep track of (should be easy enough to re-enable), and I've also added logging of tool interactions -- every ~15min or so (or when they exit a puzzle) the count of each move type is uploaded, split by script vs. manual usage. Most actions should be already logged, but there's facilities for adding additional actions to monitor.
Note that this needs manual server-side intervention to work. There's a GameplayEvents table which needs to be populated with the contents of standalone::application::GameplayEvent, such that the numbers in the enum match up with the ID in the database table. This can/should be done manually, and can be done any time prior to this code being released. (But should be done before the code goes into devprev.)
Merge pull request #6521 from RosettaCommons/roccomoretti/tag_solutions
[Foldit] Upload snapshots of tagged solutions
Currently, every five minutes the Foldit client uploads the top scoring solution it saw in the last five minutes. This is broken out by puzzle id, but on certain puzzles it would be nice to be able to get finer-grained results. For example, on ligand design puzzles, it might be nice to have results for the top scoring structure per ligand identity, rather than for as the puzzle as a whole. (Such that you can get more diverse design approaches.) This is particularly true for the ligand puzzles which are more docking puzzle: we want results for all structures, not just the top scoring ones.
This PR adds an option to the puzzle_setup file. "post_solution_tag" -- this allows the puzzle creator to specify additional characteristics of the solution result to tag/separate them out. Currently the two options are "Smiles" (splitting the results by the chemical identity of the designable ligand) and "Sequence" (splitting the results by the [protein] sequence of the structure). The default behavior is set to "None", which results in the current one-per-puzzle behavior.
Additionally, I discovered that we're not pushing the results (including scores) to the server on client shutdown. It theoretically should be done in the Server destructor, but that's apparently not getting called, possibly due to details of how std::exit() works with destructors. I've also added facilities to GameApplication::handle_exit() to make sure that the pending solutions and scores are properly flushed on client closing.
Merge pull request #6525 from RosettaCommons/roccomoretti/auto_ss_load
[Foldit] Autogenerate secondary structures if puzzle inputs are missing them
I'm tired of having to load a new pdb in with secret keys, running DSSP, then saving it again in order to get decent default secondary structure display with the protein.
This PR makes it such that if the puzzle input PDB doesn't contain the secondary structure information block, it will automatically run DSSP on the structure and use that instead.
You should still be able to get a non-DSSP secondary structure annotation by manually providing the secondary structure block. But if you forget, you'll get the DSSP based one. (Which is probably what you want, if you didn't think to explicitly specify what it was.)
Merge pull request #6522 from RosettaCommons/roccomoretti/interactive_qtn
[Foldit] Add ability to suppress Quest to the Native popup.
If you include a guide structure in the puzzle, you automatically get a "This protein's structure is known. See if you can match it!" popup.
There's the possibility you may want to include a guide structure without having that popup. (e.g. to provide a reference backbone in case you don't want to move too far.)
This commit adds a puzzle_setup option "quest_to_native" which can be set false to turn off the popup. The default if the option isn't given is true, so existing puzzles should work as they have. Intro/Education/Dojo puzzles should also be unaffected.