Documentation for irc-hybrid-client
F.A.Q.
Why did you write this program?
What difficult challenges did you face?
Are multiple users supported?
Are multiple IRC networks supported?
Are concurrent connections supported?
Are there any tracking beacons in the code?
Does the program use cookies?
What data is stored locally in the IRC users's web browser?
What data is stored in the remote instance of a irc-hybrid-client web server?
What are "IRC Cache Reload" messages?

Q: Why did you write this program?

A: That's a good question. There are already many excellent IRC clients to choose from. WeeChat is my favorite. Why write my own? Actually, I ran across a youtube video where a simple telnet client was easily able to emulate an IRC client. I became interested and I started to explore using my own telnet program while reading the RFC-2812 client protocol. I soon found telnet very repetitious, so I opened nodejs and with a little Googling, I had a TCP socket connecting to IRC. Soon I was using javascript to exchange IRC messages with the IRC server. It was really fun and I learned a lot.

As a second inspiration, I have tried several options to use IRC on my iPhone. I really didn't like any of them. Given the Covid-19 pandemic lock-down, I've been primarily stuck at home with nothing to do. Over the period of about a month, this slowly evolved into an IRC client. I started to use it as my regular IRC smartphone client. This started the endless process of adjusting IRC client user interface to adapt to smartphone capabilities. I guess I'm still in the process of finding a better UI.

Q: What difficult challenges did you face?

A: I found it challenging to work with sockets. I used the npm package "ws" as a websocket server for the browser connection, and nodejs API net.Socket or tls.TLSSocket to connect to IRC. Addressing tasks like wrapping the websocket in TLS, security authorization of the browser's websocket connection, detecting disconnects, and dealing with legacy disconnected sockets was an interesting learning experience.

I also found it tricky to encode and decode buffers of multi-byte international characters where a string byte length is different from the string character length. Then, from a stream/message standpoint, multiple messages from the server can concatenate into a single socket data packet, or one individual IRC message can split between two different data packets, requiring re-assembly into a single string.

Q: Are multiple users supported?

A: No. This operates as a single user personal server. One person per webserver instance.

Q: Are multiple IRC networks supported?

A: No. The application is limited to one IRC network connection at a time. You can sign out of IRC and switch between different IRC networks using different configurations in the IRC server list.

However, a single user can be present on multiple IRC network by running multiple instances of the irc-hybrid-client program concurrently. Each web server is required listen on a different port number. This would provide a different browser bookmark URL (host:port) for each instance. Therefore different IRC networks could be attended in different browser tabs. Refer to the Login Config section to properly set "instanceNumber" to manage unique cookies when running multiple irc-hybrid-client instances.

Q: Are concurrent connections supported?

A: Yes. A desktop, tablet, and smartphone can be open at the same time. Each device will remain in sync, showing the same content in all devices concurrently.

Q: Are there any tracking beacons in the code?

A: No.

Q: Does the program use cookies?

A: Yes. Web browser HTTP requests are authorized using session cookies for purposes of access control. This is disclosed on the login form. No additional persistent identifiers are used.

Q: What data is stored locally in the IRC users's web browser?

A: The web page uses the web browsers window.localStorage API. The browser localStorage is cleared when the "Web Logout" button is activated. The browser localStorage is cleared when the web login userid number does not match the previous userid number. The localStorage data will otherwise persist indefinitely. Local storage should not be preserved when a browser is in incognito mode.

1) Web userid - The web userid and timestamp are saved to localStorage. The userid is an integer number starting at 1 that is assigned in the .env file, environment variables, or credentials.js file. The userid number is used to delete localStorage when a change in userid is detected. The string value of the username is not saved.

2) IRC channel audio beep - A string value for the IRC channel name and a boolean flag for enable audio beep for an IRC channel are saved to localStorage when the checkboxes are selected. The data is used to select previous checkbox state when reloading the page. The default audio beep configuration used as checkbox preset when creating new channel panels is also saved to localStorage in a different record limited to boolean flags and timestamp.

3) Private message audio beep - A boolean flag used to enable audio beep when new private message windows are created. The data is used to select previous checkbox state when reloading the page.

4) Enable auto-open of channel panels - A boolean flag used to enable auto-open of channel panels for channel messages, mode changes, and when a new nickname enters. The data is used to select previous checkbox state when reloading the page.

5) Color Theme - A string value of "light" or "dark" is saved to the localStorage property colorTheme.

6) Persisted Websocket State - Two boolean flags are stored to indicate if the websocket should automatically connect on the next page load or reload. By default, the websocket will reconnect automatically if the record is not present. This is referred to as Standby state.

7) Saved Example IRC Command - In the show-raw panel used to display raw IRC server message, there is an input field used to submit example IRC server messages to the remote IRC command parser. Should an error occur when the browser receives a message from the IRC server, the problematic message can be copy/paste from the raw message log and debugged while observing the browser console. There is an option to save the example string to localStorage so that debugging can be repeated as code is modified. No data is saved to localStorage unless buttons on the show-raw panel are manually activated by the user.

Q: What data is stored in the remote instance of a irc-hybrid-client web server?

A: The web server fulfills 2 roles, an IRC client and a web server. Therefore the web server may contain both web server related data and IRC client related data.

It should be noted that irc-hybrid-client is a server based application that was developed in a Linux server environment. Ideally, irc-hybrid-client should be implemented as a single user IRC client running in a linux server controlled by the same person. This could be a home server or a dedicated cloud based virtual private server. If this application is run as a shell account in a multi-user environment, Linux server administrators with root access would potentially have permissions allowing administrators to read all server files, including configuration files for this application.

The configuration files are not encrypted.

1) Web server configuration files include data used to control access to the web server including credentials used for cookie digital signatures and cookie names.

2) Optionally, the web server may be configured to use Redis as a database to persist user login state across web server shutdown and restart. In this case, configuration files may include data used to connect irc-hybrid-client to the Redis server. The Redis database itself would include the session store as extracted from the express-session module. Basically this includes server side data needed to authorize HTTP web requests based on user login state. A Redis server installation is independent of irc-hybrid-client instance. In the case of a multi-user system or cases where other users may have access to the Redis database contents, it is recommended to disable Redis by setting 'SESSION_ENABLE_REDIS=false'. The default session store (Memorystore) is RAM based and does not save any session related data to file. However, without Redis, the web browser would be logged out each time the server is shutdown and restarted.

3) When configured for local password authentication, configuration will include the username and bcrypt hashed password that would be entered by the user for the web browser to login to the web server.

4) When configured for remote password authentication, configuration will include the web server's client id, client secret and other data used to obtain and validate an OAuth 2.0 access token.

5) Optionally, irc-hybrid-client may be configured to use a remote socks5 proxy to establish a proxy network connection to an IRC server. In this case, configuration files may include data used to connect irc-hybrid-client to a remote socks5 proxy server.

6) The IRC server configuration file 'servers.json' includes data used by irc-hybrid-client to connect to various different IRC networks. This may include IRC server password, IRC server SASL username/password, and NickServ services IDENTIFY command. This configuration is not encrypted and stored in plain text in the servers.json file.

7) Optionally, irc-hybrid-client may be configured to save IRC message to an IRC log file. If enabled, logging will include both incoming and outgoing IRC server messages in raw format. This was intended primarily for use in debugging the program. The logging software includes a limited password filter to redact passwords from common commands, such as 'OPER' and NickServ IDENTIFY commands. The filter may be reviewed in file 'server/irc/irc-client-write.mjs'. The filter was primarily developed using DALnet. When users send passwords through IRC, they should review the 'logs/irc.log' to better understand the limitations of password filtering.

8) The web server includes an internal IRC message cache used to keep the IRC windows in the web browser synchronized with the backend IRC client. Refreshing the web page will pull content from the message cache. The message cache is RAM based. Optionally, the server may be configured to persist the message cache across web server restarts. If the optional setting 'IRC_PERSIST_MESSAGE_CACHE=true', upon server shutdown, the IRC message cache will be saved to a temporary file in the /logs/ folder. The contents of this temporary file are cleared after the server is restarted. The IRC message cache does not include password filtering.

Q: What are "IRC Cache Reload" messages?

A: The "--- IRC Cache Reload messages ---" are intended to distinguish between live IRC messages, displayed real time, and cached messages.

Due to various technical reasons, occasionally it is necessary to clear the text content of a specific panel, re-parse the RFC-2812 server messages, and regenerate the text content of the panel. Examples are reloading the browser page, reconnecting to IRC, kick and re-join a channel, mobile device power save mode turns off radio to save battery. Refreshing panels from the message cache is a global action, clearing and refreshing all panels.