Made my Rust port into a patch that adds the dedicated reaction user.

The rc.d uglyness is now gone, but requires a patch to the Rust code
to set the correct permissions on the socket. Would prefer to have
this patch in upstream first if commited.

The pkg/MESSAGE is updated to notify of the daemon user changes and
point to the very crucial pkg/README for setup.

files/authlog.jsonnet has some new regexes to match that were taken
from the reaction documentation.

Added Lydia as maintainer since I have no objection.

Index: sysutils/reaction/Makefile
===================================================================
RCS file: /cvs/ports/sysutils/reaction/Makefile,v
diff -u -p -r1.3 Makefile
--- sysutils/reaction/Makefile  24 Jun 2026 06:48:50 -0000      1.3
+++ sysutils/reaction/Makefile  30 Jun 2026 21:55:14 -0000
@@ -3,11 +3,14 @@ COMMENT =     scan logs and take action, alt
 V =    v2.5.1
 DISTNAME =     reaction-${V}
 PKGNAME =      ${DISTNAME:S/-v/-/}
+REVISION =     0
 
 SITES =        https://framagit.org/ppom/reaction/-/archive/${V}/
 
 CATEGORIES =   sysutils security
 HOMEPAGE =     https://reaction.ppom.me/
+
+MAINTAINER =           Lydia Sobot <[email protected]>
 
 # AGPL-3.0
 PERMIT_PACKAGE =       yes
Index: infrastructure/db/user.list
===================================================================
RCS file: /cvs/ports/infrastructure/db/user.list,v
diff -u -p -r1.490 user.list
--- infrastructure/db/user.list 6 Jun 2026 10:18:19 -0000       1.490
+++ infrastructure/db/user.list 30 Jun 2026 21:55:14 -0000
@@ -414,3 +414,4 @@ id  user            group           port
 903 _iaxmodem          _iaxmodem       telephony/iaxmodem
 904 _neighbot          _neighbot       net/neighbot
 905 _pgweb             _pgweb          www/pgweb
+906 _reaction          _reaction       sysutils/reaction
Index: sysutils/reaction/files/authlog.jsonnet
===================================================================
RCS file: /cvs/ports/sysutils/reaction/files/authlog.jsonnet,v
diff -u -p -r1.2 authlog.jsonnet
--- sysutils/reaction/files/authlog.jsonnet     24 Jun 2026 06:48:50 -0000      
1.2
+++ sysutils/reaction/files/authlog.jsonnet     30 Jun 2026 21:55:14 -0000
@@ -1,10 +1,10 @@
 local banFor(time) = {
   ban: {
-    cmd: ['pfctl', '-t', 'blocked_ssh', '-T',  'add', '<ip>'],
+    cmd: ['doas', 'pfctl', '-t', 'blocked_ssh', '-T',  'add', '<ip>'],
   },
   unban: {
     after: time,
-    cmd: ['pfctl', '-t', 'blocked_ssh', '-T',  'del', '<ip>'],
+    cmd: ['doas', 'pfctl', '-t', 'blocked_ssh', '-T',  'del', '<ip>'],
   },
 };
 {
@@ -16,7 +16,7 @@ local banFor(time) = {
   start: [
   ],
   stop: [
-    ['pfctl', '-t', 'blocked_ssh', '-T',  'flush'],
+    ['doas', 'pfctl', '-t', 'blocked_ssh', '-T',  'flush'],
   ],
   streams: {
     ssh: {
@@ -28,6 +28,17 @@ local banFor(time) = {
             @'Failed password for invalid user .* from <ip>',
             // Client disconnects during authentication
             @'Disconnected from invalid user .* <ip>',
+            // Other auth failures
+            @'Connection from <ip> port [0-9]*: invalid format',
+            @'Invalid user .* from <ip>',
+            // Optional: Client disconnects during authentication
+            @'Connection (reset|closed) by (authenticating|invalid) user .* 
<ip> port',
+            @'Connection (reset|closed) by <ip> port',
+            @'Disconnected from .* <ip> .*preauth',
+            @'Disconnecting .* <ip> .*preauth',
+            @'Timeout before authentication for <ip>',
+            @'Received disconnect from <ip> .*preauth',
+            @'Unable to negotiate with <ip> .*preauth',
           ],
           retry: 3,
           retryperiod: '6h',
Index: sysutils/reaction/patches/patch-src_daemon_socket_rs
===================================================================
RCS file: sysutils/reaction/patches/patch-src_daemon_socket_rs
diff -N sysutils/reaction/patches/patch-src_daemon_socket_rs
--- /dev/null   1 Jan 1970 00:00:00 -0000
+++ sysutils/reaction/patches/patch-src_daemon_socket_rs        30 Jun 2026 
21:55:14 -0000
@@ -0,0 +1,25 @@
+make the socket owner and group writable
+
+Index: src/daemon/socket.rs
+--- src/daemon/socket.rs.orig  Mon Jun 29 00:19:57 2026
++++ src/daemon/socket.rs       Sun Jun 28 20:29:58 2026
+@@ -2,6 +2,8 @@ use std::{
+     collections::{BTreeMap, HashMap},
+     path::{Path, PathBuf},
+     sync::Arc,
++    fs::Permissions,
++    os::unix::fs::PermissionsExt,
+ };
+ 
+ use futures::{SinkExt, StreamExt};
+@@ -51,7 +53,9 @@ async fn open_socket(path: &Path) -> Result<UnixListen
+         }),
+     }?;
+     // Open socket
+-    err_str!(UnixListener::bind(path))
++    let socket = UnixListener::bind(path);
++    let _ = fs::set_permissions(path, Permissions::from_mode(0o770)).await;
++    err_str!(socket)
+ }
+ 
+ async fn handle_trigger_order(
Index: sysutils/reaction/pkg/MESSAGE
===================================================================
RCS file: /cvs/ports/sysutils/reaction/pkg/MESSAGE,v
diff -u -p -r1.1.1.1 MESSAGE
--- sysutils/reaction/pkg/MESSAGE       11 Sep 2024 11:30:36 -0000      1.1.1.1
+++ sysutils/reaction/pkg/MESSAGE       30 Jun 2026 21:55:14 -0000
@@ -1,6 +1,7 @@
-To block the bots connecting on ssh by default, add the following line early in
-${SYSCONFDIR}/pf.conf:
+reaction now uses a seperate user for running the daemon.
+Please see the package README for setup details.
 
-table <blocked_ssh> persist
+Pre 2.5.1p0 users will want to update the database ownership as
+follows:
+# chown _reaction:_reaction /var/reaction/reaction.db
 
-block return in quick log from <blocked_ssh>
Index: sysutils/reaction/pkg/PLIST
===================================================================
RCS file: /cvs/ports/sysutils/reaction/pkg/PLIST,v
diff -u -p -r1.2 PLIST
--- sysutils/reaction/pkg/PLIST 24 Jun 2026 06:48:50 -0000      1.2
+++ sysutils/reaction/pkg/PLIST 30 Jun 2026 21:55:14 -0000
@@ -1,3 +1,5 @@
+@newgroup _reaction:906
+@newuser _reaction:906:906:default:reaction daemon:/var/reaction:/sbin/nologin
 @rcscript ${RCDIR}/reaction
 @bin bin/reaction
 @bin bin/reaction-plugin-virtual
@@ -13,13 +15,20 @@
 share/bash-completion/
 share/bash-completion/completions/
 share/bash-completion/completions/reaction
+share/doc/pkg-readmes/${PKGSTEM}
 share/examples/reaction/
 share/examples/reaction/README.md
 share/examples/reaction/authlog.jsonnet
 @sample ${SYSCONFDIR}/reaction/authlog.jsonnet
 share/examples/reaction/example.jsonnet
 share/examples/reaction/example.yml
-@sample /var/reaction/
+@mode 750
+@owner _reaction
+@group _reaction
+@sample ${LOCALSTATEDIR}/reaction/
+@mode
+@owner
+@group
 share/fish/
 share/fish/vendor_completions.d/
 share/fish/vendor_completions.d/reaction.fish
Index: sysutils/reaction/pkg/README
===================================================================
RCS file: sysutils/reaction/pkg/README
diff -N sysutils/reaction/pkg/README
--- /dev/null   1 Jan 1970 00:00:00 -0000
+++ sysutils/reaction/pkg/README        30 Jun 2026 21:55:14 -0000
@@ -0,0 +1,54 @@
++-------------------------------------------------------------------------------
+| Running ${PKGSTEM} on OpenBSD
++-------------------------------------------------------------------------------
+
+Access to log files
+==============
+
+You need to give the _reaction user access to the log files in one of the
+following ways.
+
+Adding _reaction to the wheel group
+-------------------
+# usermod -G wheel _reaction
+
+Creating a new group
+-------------------
+# groupadd groupname
+# usermod -G groupname admin
+# usermod -G groupname _reaction
+# chown :groupname /var/log/authlog
+
+Allowing world readable access
+-------------------
+# chmod 644 /var/log/authlog
+
+Each option has its own security considerations.
+
+Choose which best fits your needs.
+
+Access to pfctl
+==============
+
+Add the following to the bottom of your doas.conf(5) file:
+
+    deny _reaction
+    permit nopass keepenv _reaction as root cmd pfctl
+
+This denies the _reaction user any of the earlier privileges and only
+grants access to pfctl.
+
+Reaction and pf configuration
+==============
+
+You can find yml and jsonnet configuration examples at:
+/usr/local/share/examples/reaction/
+
+The example file, authlog.jsonnet, is configured to monitor /var/log/authlog
+and block any repeated attempts at logon through pfctl(8) with the following
+pf.conf(5) configuration:
+
+    table <blocked_ssh> persist
+
+    block return in quick log from <blocked_ssh>
+
Index: sysutils/reaction/pkg/reaction.rc
===================================================================
RCS file: /cvs/ports/sysutils/reaction/pkg/reaction.rc,v
diff -u -p -r1.2 reaction.rc
--- sysutils/reaction/pkg/reaction.rc   24 Jun 2026 06:48:50 -0000      1.2
+++ sysutils/reaction/pkg/reaction.rc   30 Jun 2026 21:55:14 -0000
@@ -4,6 +4,7 @@ daemon="${TRUEPREFIX}/bin/reaction"
 daemon_flags="start -c ${SYSCONFDIR}/reaction/"
 daemon_execdir="${LOCALSTATEDIR}/reaction"
 daemon_logger="daemon.info"
+daemon_user=_reaction
 
 . /etc/rc.d/rc.subr
 
@@ -11,7 +12,7 @@ rc_reload=NO
 rc_bg=YES
 
 rc_pre() {
-       install -d ${LOCALSTATEDIR}/run/reaction
+       install -d -g wheel -m 750 -o _reaction ${LOCALSTATEDIR}/run/reaction
 }
 
 rc_cmd $1

On Wed, 24 Jun 2026 21:02:00 +0200
"Lydia Sobot" <[email protected]> wrote:

> On Wed Jun 24, 2026 at 08:50 CEST, Landry Breuil wrote:
> > fwiw, i've finally been able to test it and replaced my setup, still
> > works fine. welcoming further improvements to run it as a separate
> > unpriviledged user, but that requires:
> > - improving MESSAGE to mention what needs to go in doas.conf
> > - testing in various situations
> Sounds good to me, I'm also looping upstream in to guide development.
> Also, if there are no objections, I am willing to take maintainer.

Reply via email to