Closed makedir closed 2 days ago
The account switcher does not need an internet connection. The update check, error reporting and optional anonymous stats submission to help me improve the app are the only bits that use the internet.
Any closing related to no internet (blocking, or lack of internet entirely) is a crash and not intentional.
Something that manages your account is high-trust, and hence it needs to be open source. This is incredibly important. You are more than free to view the source code in its entirety, and build from source should you not trust my distributions.
EDIT: I will keep crashes due to no internet in mind for the next update :)
Wrong. I just installed it, and it crashes with no internet connection error when opening and closes after 2 seconds with no user input possible.
That's what I am saying, it's unintentional.
It's attempting to communicate with https://tcno.co/, my blog, and where I run the API for this program (aforementioned stats, updates). This is failing for some reason, however.
I dont want the app to communicate to the internet, no updater, no anonymous stats submission. make options to opt out of that during setup.
Easier said than done. Installers are limited, when you don't create your own from scratch (I do want to avoid this as it's easy to mess something up that deletes more than necessary on uninstall, for example). NSIS is what I use for this project, and being open-source, anyone can help submit changes.
%AppData%\TcNo Account Switcher\WindowSettings.json
<- Open this with a text editor and paste (Delete everything in it first):
{
"CollectStats": false,
"ShareAnonymousStats": false,
"MinimizeOnSwitch": false,
"DiscordRpcEnabled": false,
"DiscordRpcShareTotalSwitches": false
}
This disables stats collection, and Discord RPC for discord integration. It should be able to start up properly without attempting internet access, and hence leading to a crash.
I'll reopen this as it is a bug, and should be patched on the next update.
I'll do further research into adding an option to maybe place the above template in the AppData folder assuming a button is checked? Will have to see.
thank you. you could also just ask first time starting the app to opt out of all internet related connections not during setup.
Should the auto-updater not be functional (this is a default ON for almost every bit of software. Steam, for example, gives you an optional prompt upon finding an update), people will live indefinitely on an old, broken version.
I pushed an update where the auto-updater stopped functioning almost a year ago and there are still thousands of users there, using it daily, without new features and new platforms.
An updater is more than a necessity, especially in sometimes fragile open-source software. Steam, Ubisoft and anyone else is free to change how they store the usernames of the last logged-in account, and assuming it changes, the software breaks inexplicably overnight. Leading to many angry "WHY NO WORKY?!", even with an update prompt that explains things.
EDIT: This software also has its own custom 'updater'. Using git-like partial updates, it doesn't need to download 50MB+ on a minor change, it's only a few KB at a time, sometimes more with major features.
For those working in an air-gapped system, for example, the option to disable internet access is there and should be functional. This is an unexpected crash and one not tested for.
Like I said: make OPT INS/OUTS during first start or setup. never force anything on people. ask during setup via checkbox, if stats are allowed if auto update or "stats" are wanted.
This program looks promising, but unfortunately I won't be installing it... I downloaded a copy of the source code, and went through it. Now, I'm not a professional programmer myself, but I am near the end of getting my bachelors in computer science with specialization in application development, and what bothered me more than anything is that there's analytics-gathering-code literally everywhere. Do users know that their location, country, IP address and who knows what more are being collected by you without user consent? Hearing that this is pushed on the user from the initial release of this app is so wrong.
Moreover, is it just me or is the codebase messy as heck, like really. I mean if you 'only' need to swap out files on the user's system and / or a registry key, why are you using 10 programming languages? And PHP, really?
Also why is the whole codebase so difficult to understand, it actually looks like code obfuscation to me.
Here a screenshot of a sample of code about analytics taken from this file: \other\tcno.co\api\update\index.php
.
Do users know that their location, country, IP address and who knows what more are being collected by you without user consent? Hearing that this is pushed on the user from the initial release of this app is so wrong.
You'd be surprised the reason some issues happen. Some regions had difficulties reaching my website prior to setting up cloudflare. Getting error logs referring to obscure issues all from one country makes finding the cause of the issue easier.
The reason the user's country is collected is for global usage analytics. You can see later in the same PHP file you mentioned that literally ONLY the continent, country and state is collected. The IP address is thrown away, anonymizing the user to just a +1 in the region. In this file as well the only other thing collected is the version they updated from.
This is similar for the other bits of stat collection. See the 'launch counter' stat: How many launches per country /[other](https://github.com/TCNOco/TcNo-Acc-Switcher/tree/master/other)/[tcno.co](https://github.com/TCNOco/TcNo-Acc-Switcher/tree/master/other/tcno.co)/[api](https://github.com/TCNOco/TcNo-Acc-Switcher/tree/master/other/tcno.co/api)/index.php.
Not only is this interesting to see, but it is also useful in further localizing the program and seeing what else is necessary to do with the region in mind. There are an infinite number of websites that could freely collect your IP upon visiting them or even so much as downloading an image from them. Your IP address is given out the moment you use the internet. Hence, the geo data for it is inaccurate on purpose for 99.99% of ISPs, and doing anything like an IP lookup only returns who you're with. This is also useful should a DOS attack or something similar emanate from your IP.
Consider this: Why would I share code relating to the server for my project where I host the updates for download, the latest version counter and more when it has almost nothing to do with code from the application? Trust. Why would I share code that would be otherwise completely inaccessible to users reading through the source code? Trust. Why do I spend money on a digitally signed certificate from a trusted company? It's not cheap and does nothing but helps verify that I released these binaries. Why? Trust.
Moreover, is it just me or is the codebase messy as heck, like really. I mean if you 'only' need to swap out files on the user's system and / or a registry key, why are you using 10 programming languages? And PHP, really?
This is true. But, a my website does not run on C#. PHP is the most common and well-documented web server language. HTML, CSS, SCSS, Javascript are ALL used in the GUI of the application. I think I may have some code on here with regard to my website, I don't remember. NSIS is used for the installer. There are many reasons one language is better than another for specific tasks and purposes.
The core of this application is C#.
Also why is the whole codebase so difficult to understand, it actually looks like code obfuscation to me.
While the code is messy, and spaghetti in locations: it is far from obfuscation. I am not paid in any way to create or update this software, it is entirely a passion project. In fact, it's cost me more money in hosting and digitally sign my releases.
Ultimately there are other projects should you choose not to support mine. This is a passion project and was built because of my love of gaming. There are other closed-source account switchers, should you choose to blindly trust them because you don't know what's happening behind closed doors. This project was made open source for trust. I have no reason to take your accounts, I earn a full-time income from YouTube and voice acting.
It is your choice to use and trust this software. Should you not trust my builds: vet the codebase and build it yourself from the source. Should you not trust me, then there are other account switchers, most of which are nowhere near as open as this.
Replying to @TCNOco's last response. I'm not using the 'Quote reply' feature, as it would make the comment unnecessarily messy.
Thank you for taking the time to respond to my concerns about the analytics-gathering-code and the messy codebase in your program. While I appreciate your explanation of the reasons for collecting user data, I still believe that users should be informed about the collection of their data and be given the option to opt-out of it. Transparency and user privacy should be a top priority, and it's important to ensure that users understand what data is being collected and why.
Regarding the issue that some regions having difficulties reaching your website, could you please clarify why users need to access your website if the app should be able to run fully offline? In your project description (README.md), you mentioned that the app works by exchanging local user files and/or registry keys, which suggests that it should not need an external server to function. I would appreciate any additional information you can provide on this matter.
As for your comment about potentially having some code related to your website in the codebase, could you please explain why this is the case? If the app is designed to work offline and doesn't require an external server, it's unclear why there would be any connection between the app and your website. And if the connection is needed to send analytics, I assume the website is already running somewhere in the cloud? Why then include it's source if it's not related to the core purpose of the application?
Regarding the codebase, I understand that different languages are better suited for specific tasks and purposes, but it's still important to maintain a clean and understandable codebase for easier maintenance and troubleshooting. Messy code can lead to errors and security vulnerabilities, which can ultimately harm the user experience.
However, I appreciate your transparency and openness in making your codebase available for others to review and build from. It's clear that you are passionate about this project and have put a lot of time and effort into it. I also understand that you are not being paid to create or update this software, and that it's entirely a passion project for you.
I also noticed that your "simple" account switching app consists of 6 projects, which seems like a lot for a program that only swaps out files and registry values. Can you explain why the codebase requires 6 projects for this purpose?
For ease and public reference, these are the project names:
And at last, could you explain in more detail how the process of swapping two Epic Games accounts works? If it's not too much to explain, perhaps you could include the steps involved in the swapping process, or message me on Discord or any platform you're most familiar with.
clarify why users need to access your website if the app should be able to run fully offline
Update checks. So users know when to update. Nobody is going to check a GitHub repo that gets updated once every few months at best. Huge issues like the program has had before where it stops working on certain platforms because things change, etc. Almost every program worth updating has a "Check for updates" feature. Some auto-update completely, others offer the ability to update or not.
potentially having some code related to your website in the codebase. Could you please explain why this is the case
Why then include it's source if it's not related to the core purpose of the application?
Transparency. There is literally no need for me to include any code from my web server that is almost completely disconnected from this project and codebase other than providing a version number/date for update checks, etc. Had I not included it, a lot of this thread wouldn't have come to be.,.. What you don't know would likely concern you less. I have nothing to hide and believe in being transparent.
Messy code can lead to errors and security vulnerabilities, which can ultimately harm the user experience.
I'm going to keep it real and tell you I started this project not knowing a line of C#. I came from knowing almost nothing to this. The most experience I had was some HTML/CSS for web coding and some VB.net. This was jumping in the deep end to try something new and more powerful. So, of course, the codebase will be beyond messy. A lot of it was built around bad practices, but that's just the nature of cobbling something together and maintiaining/improving it over the years.
I also noticed that your "simple" account switching app consists of 6 projects
It was simple originally being just a CLI tool. Then it grew to have a user-frieldy GUI, then I jumped in the deep end again and wanted to create something a lot fancier. WPF and normal front end code is less than easy to modify the looks of something. Forget animations. To change the style of a button, if something isn't included in the framework already, you need to REWRITE the component from scratch almost. Incredible waste of time and not customizable at all. So the easiest solution is to do what Discord and other programs already using Electron do, and that's use HTML/CSS/JS. Easy to prototype and work on, improve and even animate. So, I could use something like Electron, but I opted to use WebView2, which is practically just a Chrome browser component to drop into my code. Then a server is needed to serve the front-end GUI (HTML/CSS/JS). But, being a "browser", there is literally nothing I can control on a system. Imagine a website you visit reading your Documents folder as they please, it's completely blocked off in every imaginable way.
So a background processes is needed to handle everything. Yes I could build everything into one, but here's the reasoning:
TcNo Account Switcher - Contains files for creating an MSIX installer and publishing to the MS store. This never finished and is just sitting around unused.
TcNo-Acc-Switcher-Client - The GUI front-end. The WebView2 component and everything ended for showing the front-end. TcNo-Acc-Switcher-Server - The back-end where all the file interactions take place. This also serves code for the Client to handle. These are split up in hopes of making it easier to make the program cross-platform. Swapping out the way things are displayed should be separate from how files are interacted with on the back-end. Want something other than WebView2, or something that works on a different platform? Replace the client and don't worry about changing how the back-end code works.
TcNo-Acc-Switcher-Tray - This handles the tray icon, and needs to be a separate program to keep less loaded in the RAM. This lets the main Client/Server close entirely and keep only a small amount of the PC in use as you game, etc. This also lets you quickly swap accounts without needing to wait for the GUI and the rest to load.
TcNo-Acc-Switcher-Globals - This contains code that is shared between all the different components. Hence "Global". This is a DLL, a Dynamic Link Library, something that contains functions that all of the above use, to simplify maintaining the codebase else as a lot of code would be repeated.
TcNo-Acc-Switcher-Updater - A standalone program that allows maintaining the program. You can't modify a programs .EXE while it's running without some crazy memory hacks, running the program out of memory alone - This is what viruses do. It makes sure every TcNo program is closed, downloads the differences from my website, and then applies them. This way you don't have a 100MB+ complete redownload of the software, instead literally just the few KB changes in text format to be applied to the program. This is similar to how pushing commits to this git repo work: It's just what's different, so you can easily push it forwards.
This also needs to be separate as if I upgrade from .NET Core to .NET 6, as I have, then the program won't open at all, until the new framework is downloaded and installed. This allows me to show a message like "You need to download .NET 6 from here", etc. Otherwise, you wouldn't see anything on a lot of systems, the exe would just flash a window or nothing and close.
This also allows me to let users verify the files of their install, so anything that may be corrupt, half-updated, or missing can be downloaded without needing to redownload everything.
Steam has something similar to this that starts and runs before the actual client opens. It verifies its own files on every launch.
more detail how the process of swapping two Epic Games accounts works
The main platforms are explained here: Platforms, everything else is explained here Everything else.
As epic game just needs files swapped around while it's closed, the majority of what is done is explained in Platforms.json as just normal code. I can't create a write-up for every platform the community or I add, especially because a lot would just be copy-paste and adds nothing.
...
"Epic Games": {
"Identifiers": [ "e", "epg", "epic", "epicgames" ],
"ExeLocationDefault": "C:\\Program Files (x86)\\Epic Games\\Launcher\\Portal\\Binaries\\Win32\\EpicGamesLauncher.exe",
"ExesToEnd": [ "EpicGamesLauncher.exe" ],
"PathListToClear": [ "SAME_AS_LOGIN_FILES" ],
"LoginFiles": {
"%LocalAppData%\\EpicGamesLauncher\\Saved\\Config\\Windows\\GameUserSettings.ini": "GameUserSettings.ini",
"REG:HKCU\\Software\\Epic Games\\Unreal Engine\\Identifiers:AccountId": "UNIQUE_ID"
},
"Extras": {
"CachePaths": [
"%LocalAppData%\\Epic Games\\Epic Online Services\\UI Helper\\Cache\\Cache",
"%LocalAppData%\\Epic Games\\Epic Online Services\\UI Helper\\Cache\\GPUCache",
"%LocalAppData%\\Epic Games\\EOSOverlay\\BrowserCache\\Cache"
],
"BackupFolders": {
"%LocalAppData%\\EpicGamesLauncher\\Saved\\Config\\": "Config"
}
},
"UniqueIdFile": "HKCU\\Software\\Epic Games\\Unreal Engine\\Identifiers:AccountId",
"UniqueIdMethod": "REGKEY"
},
...
ExesToEnd
tells the program what processes to close/kill. Once Epic Games is closed, it will clear the PathListToClear
files, which in this case is the same as the files that are saved and swapped for account switching. Some programs may require more files to be deleted and recreated once a new account is signed into.
"LoginFiles": {
"%LocalAppData%\\EpicGamesLauncher\\Saved\\Config\\Windows\\GameUserSettings.ini": "GameUserSettings.ini",
"REG:HKCU\\Software\\Epic Games\\Unreal Engine\\Identifiers:AccountId": "UNIQUE_ID"
},
One registry key containing the account ID, and the GameUserSettings.ini file is saved to "save" an account. Deleted to sign into a new account, and swapped out to sign into another account.
CachePaths
is an extra feature that you can use to save a little space, and clear out some unnesecary cache files stored on your PC.
BackupFolders
is the folder/s that are backed up when you choose Backup. This way you could hopefully save a few settings for the platform between reinstalls, and new Windows installs, etc.
UniqueIdFile
is how the currently logged in account is identified and highlighted in the program. The program reads the ID of the currently logged in account, and if it is saved, highlights it on the list.
UniqueIdMethod
just lets the program know how to look for the above..
Ultimately it is simple. The way that it is put together is far from optimized, but a ton of work and love has been put into this software.
High trust, high transparency. I truly believe in making it as easy as possible for the community to maintain and improve this, as I have. I still have plans to take this further but life has more than got in the way.
Replying to @TCNOco's last response. I'm not using the 'Quote reply' feature, as it would make the comment unnecessarily messy.
To start off, interestingly enough you omitted my concerns in the first paragraph. I believe that users should be informed about the collection of their data and be given the option to opt-out of it. It's important to prioritize user privacy and ensure that users understand what data is being collected and why. This would help build trust with users and demonstrate a commitment to their privacy. I hope you can understand where I'm coming from on this, and I'd appreciate it if you could address this specific point in your response. Thanks!
Next, the issue about users needing to have access to your website is clear enough to me now, thank you.
Regarding the issue that the codebase 'potentially' contains code related to your website is clear to me as well. However, could you point where the project / code for your website is located exactly? Also, do I understand it correctly that the site the app communicates with, for update-related reasons, is tcno.co? Is it a static or dynamic site. What languages does it use?
Then, to address your response about the messy code. You have to realize that the 'transparency' of this program, doesn't align with your wish for it to be fully transparent. There's so much going on in the app, duplicate code, generic variable / class / … names, etc. that it becomes nearly impossible to be able to 'build the app ourselves'. What's the difference if I install your executable, or build from your source, if the code is extremely hard to read and understand?
As for your comment about the codebase consisting of 6 projects, you said that 'a background process is needed to handle everything'. Do I understand correctly that the project 'TcNo-Acc-Switcher-Server' is the 'background process'?
Then you explain the purpose of each project, thank you for this. Don't you think then that the project 'TcNo Account Switcher', should be removed from the source? There's already so much going on in the code, why add an unnecessary project whose purpose is nothing else than to confuse.
So the server project is responsible for serving the WebView2 component into the client and it's also here where all the swapping of files and registry values happens? Is the port number of this server always the same or is it random at each app start?
As for the updater project, it's definitely an interesting and clever approach to distribute updates for the app, but how does it work really? Is the updated code first available on the GitHub repo under 'releases'?
The use for the other projects is now clear, thank you.
Lastly, I'd like to thank you for you your explanation about the switching process in more detail! I wasn't aware of this repo's Wiki, my bad. I analyzed what you explained and some parts of the Wiki and tried to manually do what's needed to switch 2 Epic Games accounts, and it worked. This is awesome, as I can't find anywhere else on the Internet how this process would look like.
And a last note, can you list some other account switchers you have found? Because I didn't find any other than yours? There's this one, but it's only for Steam: SteamAccountSwitcher.
I still believe that users should be informed about the collection of their data and be given the option to opt-out of it.
Yes. I didn't avoid it as much as I had addressed this previously as:
Easier said than done. Installers are limited, when you don't create your own from scratch (I do want to avoid this as it's easy to mess something up that deletes more than necessary on uninstall, for example). NSIS is what I use for this project, and being open-source, anyone can help submit changes.
But can see where there isn't enough detail. I haven't looked into it, but it should be possible to add an opt-out in the launcher, as mentioned. An example of working around the limited system was a 'default' settings file that could be copied. This is, however, only going to come in the future on the next release.
There is an opt-out built-in to the program, and it has been since the update that introduced these new features:
Regarding the issue that the codebase 'potentially' contains code related to your website is clear to me as well. However, could you point where the project / code for your website is located exactly?
As far as I can remember off the top of my head, it's the files you've already looked at regarding stats collection. That would be pretty much everything in the folder: /other/tcno.co.
update-related reasons, is tcno.co? Is it a static or dynamic site. What languages does it use?
Static for the most part. PHP is used, as shown in the public code, to collect the current version for logging reasons. Notice the version.php
and net_version.php
files. Practically duplicates. The reason being that a lot of old users (thousands) are stuck on an old version where the updater stopped functioning with an update. Without an automatic update check, those users still stuck there today after a year or so will never know there's another update as the actual up-to-date updater program is never downloaded, and the check broken. Besides the point.
https://tcno.co/Projects/AccSwitcher/api is the endpoint for the TcNo Account Switcher API.
The update check can be seen Herre, and manually reached with just the link https://tcno.co/Projects/AccSwitcher/api
Some other links to the code:
There are a large number of reasons to have a good server to handle important requests like the above.
Then, to address your response about the messy code. You have to realize that the 'transparency' of this program, doesn't align with your wish for it to be fully transparent.
I am a fulltime YouTuber, and freelance voice actor. I have not studied, nor a degree in coding in any capacity. This is a hobby, and I am entirely self-taught. Bad practices and all. I would refactor the code base for incredible readability, and more had I had infinite free time and, more importantly, drive. But new features and bug fixes outweigh this in the time that I do have.
'TcNo-Acc-Switcher-Server' is the 'background process'?
Yes, but it can be called by itself for the user to open a browser of their choice and interact with the program as usual. Another reason for the "Client" to be a separate thing. You could even connect to the address it shows via your phone assuming the computers firewall allows.
'TcNo Account Switcher', should be removed from the source?
I do like clean code, but a work-in-progress codebase will usually have things lying around for future work. This is one of those cases. I could keep it in a separate folder on my PC, but it's nice to have a backup online. And hey, maybe someone knows a better way to do something in that code, or wants to complete it fully, they can do that. Some helpful users have helped fix up and add entirely new features with their free time and that's great.
So the server project is responsible for serving the WebView2 component into the client
The "Client" handles this and all other components necessary for the 'browser-like environment'. The server just merely serves up a web page and interacts with the file system upon request.
There are a further 85 commits and TONS of rewriting to try and get this software to use .NET MAUI, to help remove the need for a separate server and client. But this is a far way away. I expended the majority of my drive very close to MAUI's first appearance. It was limited, and missing some niche features important to this project, so hours and hours of head-to-wall thinking I put it aside. This is close to being done, with only a little work left to bring it up-to-par with the main branch. JsToRazor-DI-MAUI.
You can see failed attempts left half-done as JsToRazorTEMP, JsToRazor, JsToRazor-DI, JsToRazor-DI2.
Literally, the entire code base needed refactoring. A complete change in how memory and state are handled.
Is the port number of this server always the same or is it random at each app start?
The port is saved in the users config file.
Should that port be in use (which leads to a crash, or the program being rendered useless) it generates a new port and uses that instead. This is then saved as well.
Launching the Server.exe separately lets Microsoft handle the port in whichever way they do. It stays the same unless taken, similar to my method, as far as I recall.
I analyzed what you explained and some parts of the Wiki and tried to manually do what's needed to switch 2 Epic Games accounts, and it worked. This is awesome, as I can't find anywhere else on the Internet how this process would look like.
That's where the "How does it work? Simple." part of this project comes in. It's an overengineered solution, but works incredibly well for what it is.
And a last note, can you list some other account switchers you have found?
Oh, and
impossible to be able to 'build the app ourselves'
For the most part, you install Visual Studio 2022, open the project, click Build. You won't be able to sign with my code signing cert, for obvious reasons.
Seems really fishy to me. It doesnt work with no internet, why? it even auto closes with an error if there is no internet.