an experimental irc client

ui: log connection errors to the network message view

rockorager.dev b97f0d72 ff49ab89

verified
+36 -8
+36 -8
src/irc.zig
··· 317 317 self.completer_shown = false; 318 318 319 319 if (std.mem.startsWith(u8, local, "/")) { 320 - try self.client.app.handleCommand(.{ .channel = self }, local); 320 + self.client.app.handleCommand(.{ .channel = self }, local) catch { 321 + log.warn("invalid command: {s}", .{input}); 322 + return; 323 + }; 321 324 } else { 322 325 try self.client.print("PRIVMSG {s} :{s}\r\n", .{ self.name, local }); 323 326 } ··· 2687 2690 } 2688 2691 } 2689 2692 2690 - pub fn readThread(self: *Client) !void { 2691 - defer self.status.store(.disconnected, .unordered); 2693 + fn warn(self: *Client, comptime fmt: []const u8, args: anytype) void { 2694 + self.read_buf.appendSlice(":comlink WARN ") catch {}; 2695 + self.read_buf.writer().print(fmt, args) catch {}; 2696 + self.read_buf.appendSlice("\r\n") catch {}; 2697 + } 2698 + 2699 + pub fn readThread(self: *Client) void { 2700 + defer self.status.store(.disconnected, .release); 2701 + 2702 + // We push this off to another function that can enforces it only fails for allocation 2703 + // errors 2704 + self._readThread() catch |err| { 2705 + switch (err) { 2706 + error.OutOfMemory => {}, 2707 + } 2708 + log.err("out of memory", .{}); 2709 + }; 2710 + } 2692 2711 2712 + fn _readThread(self: *Client) Allocator.Error!void { 2693 2713 self.connect() catch |err| { 2694 - log.warn("couldn't connect: {}", .{err}); 2714 + self.warn("* CONNECTION_ERROR :Error while connecting to server: {}", .{err}); 2695 2715 return; 2696 2716 }; 2697 - 2698 2717 try self.queueWrite("CAP LS 302\r\n"); 2699 2718 2700 2719 const cap_names = std.meta.fieldNames(Capabilities); ··· 2717 2736 // WouldBlock means our socket timeout expired 2718 2737 switch (err) { 2719 2738 error.WouldBlock => {}, 2720 - else => return err, 2739 + else => { 2740 + self.warn("* CONNECTION_ERROR :{}", .{err}); 2741 + return; 2742 + }, 2721 2743 } 2722 2744 2723 2745 if (retries == keepalive_retries) { ··· 2727 2749 } 2728 2750 2729 2751 if (retries == 0) { 2730 - try self.configureKeepalive(keepalive_interval); 2752 + self.configureKeepalive(keepalive_interval) catch |err2| { 2753 + self.warn("* INTERNAL_ERROR :Couldn't configure socket: {}", .{err2}); 2754 + return; 2755 + }; 2731 2756 } 2732 2757 retries += 1; 2733 2758 try self.queueWrite("PING comlink\r\n"); ··· 2738 2763 // If we did a connection retry, we reset the state 2739 2764 if (retries > 0) { 2740 2765 retries = 0; 2741 - try self.configureKeepalive(keepalive_idle); 2766 + self.configureKeepalive(keepalive_idle) catch |err2| { 2767 + self.warn("* INTERNAL_ERROR :Couldn't configure socket: {}", .{err2}); 2768 + return; 2769 + }; 2742 2770 } 2743 2771 self.read_buf_mutex.lock(); 2744 2772 defer self.read_buf_mutex.unlock();