Why doesn't `vacuum full` release space immediately? On Postgres 9.5 I had a table that grew to 30GB, but it was ultimately mostly dead rows. After cleaning it up with a vacuum full, postgres reports that the table size is now around 500MB. However, I see no space being released to the OS.

I found PostgreSQL - VACUUM FULL does not free space back to the OS which suggests the WAL files might be the culprit, but these are present on a different disk so it shouldn't affect my actual data disk at all.

I have confirmed that there are no other long running transactions or autovacuum's that might be locking the table.

What can I look at to figure out why my space isn't being released?
I traced this to a long-running autovacuum backend process. Even though the autovacuum was running on another table, it was hanging on to the file descriptors for the old files for the table on which I had just done a full vacuum. It was easy to confirm this with lsof.

Cancelling the autovacuum released the space immediately.