External-check and chroot

Hey there,
we use haproxy to do load balancing and health check on our APIs. I’m trying to use the external-check feature on haproxy 1.7 with the chroot option. It won’t work and I don’t know why:

chroot /var/lib/haproxy
user haproxy
group haproxy

backend ABC
option external-check
external-check command /var/lib/haproxy/check.sh

The /var/lib/haproxy directory looks like:

├── bin
│ └── bash
├── check.sh
├── dev
│ └── log
└── text.txt

The check.sh script does something simple like:


echo "Here the args:"
echo $@  >> /text.txt
exit 0

When I take this configuration online haproxy is immediately assuming the APIs are offline.

Any ideas why that is so?

Considering that you are already in chroot (/var/lib/haproxy/), I assume the check command should just be the script:

external-check command /check.sh

Thanks for the message!

Yes, I also thought about that and tried it but the result is the same - haproxy does not execute the script and assumes the API is down.

You are also dropping privileges though.
Does the haproxy user have the executable privilege for the script and /var/lib/haproxy/bin/bash?

What does sudo -u haproxy /var/lib/haproxy/check.sh say?

If the privileges are also ok, you may want to run haproxy through strace.

Or better yet, try chroot --userspec=haproxy:haproxy /var/lib/haproxy /check.sh

I have the same issue. I have the following configuration:

chroot /var/lib/haproxy
user haproxy
group haproxy

backend TCP
mode tcp
option external-check
external-check command /TCPCheck.sh

File TCPCheck.sh is present in /var/lib/haproxy directory.

Running the command
sudo -u haproxy /var/lib/haproxy/TCPCheck.sh is working properly.

What may be the issue?

Do I need to configure external-check path configuration?

Do you have everything you need in chroot?

sudo chroot /var/lib/haproxy

Yes. I have TCPCheck.sh file in /var/lib/haproxy directory as /var/lib/haproxy/TCPCheck.sh

My question was not whether script is in there, but whether everything you need is in there, that probably includes at least bash or sh. That’s why you should actually try it with the commands above.

I have sh on /usr/bin/sh.

Do I need it in /var/lib/haproxy directory?

If yes, I need to provide external-check path ? or can you suggest me any other way?

Test it.

It is impossible for me to know what may or may not be required.

Test it.

I have added all the required libs in my chroot directory.

sudo chroot jail/ /check.sh is running properly. Still I am getting External check error, code: 255

My service is running with chroot /var/lib/haproxy. I have confirmed that using ls -al /proc/pid/root.

Now I have usr/ bin/ lib/ sbin/ lib64/ in chroot.

I have used external-check command /bin/true. Which is also creating error External check error, code: 255.

How can /bin/true returning 255?


I have the same problem and can’t find the correct way to do this.
Did you find a solution to your issue?


I have found the solution for me.

The chroot needs to provide all the libraries your command needs.
For example if you use a shell script you need to have the shell itself and all its libraries.

I’ve used this article : https://www.howtogeek.com/441534/how-to-use-the-chroot-command-on-linux/

Basically, here is what I’ve done :

mkdir -p $chr/{bin,lib,lib64}
list="$(ldd /bin/bash | egrep -o '/lib.*\.[0-9]')"
for i in $list; do cp -v --parents "$i" "${chr}"; done
cp -v /bin/bash $chr

Then you can put your scripts in the bin directory of the chroot.


is it possible to decide which server to forward based on this script execution?
i mean capture this in an ACL and use it for conditional forwarding?

Best Regards,