fixed issue in freeipa-letsencrypt.sh with setting variable defaults
added set-dns-source.sh updated README.md accordingly
This commit is contained in:
153
README.md
153
README.md
@@ -19,73 +19,29 @@ General Public License, see [below](#license)
|
|||||||
Contents
|
Contents
|
||||||
========
|
========
|
||||||
This repository contains the following scripts:
|
This repository contains the following scripts:
|
||||||
* [users2freeipa.py](#users2freeipa)
|
|
||||||
is a migration script to transfer/synchronize LDAP users to/with FreeIPA
|
|
||||||
* [freeipa-dns.py](#freeipadns)
|
* [freeipa-dns.py](#freeipadns)
|
||||||
is a script providing functionality not available in FreeIPA itself to
|
is a script providing functionality not available in FreeIPA itself to
|
||||||
migrate/synchronize and maintain DNS zones in FreeIPA
|
migrate/synchronize and maintain DNS zones in FreeIPA
|
||||||
* [freeipa-letsencrypt.sh](#freeipaletsencrypt)
|
* [freeipa-letsencrypt.sh](#freeipaletsencrypt)
|
||||||
is a script to setup and configure Certbot and FreeIPA to request and renew
|
is a script to setup and configure Certbot and FreeIPA to request and renew
|
||||||
use publicly verifiable Let's Encrypt certificate(s)
|
use publicly verifiable Let's Encrypt certificate(s)
|
||||||
|
* [set-dns-source.sh](#setdnssource)
|
||||||
|
enforce the source address of outgoing DNS messages using firewalld as work
|
||||||
<a name=users2freeipa>users2freeipa.py</a>
|
around for bind-dyndb-ldap plugin not supporting bind's ```notify-source```
|
||||||
---------------------------------------------
|
* [users2freeipa.py](#users2freeipa)
|
||||||
This script uses LDAP to obtain users from a MacOS Server (or other LDAP)
|
is a migration script to transfer/synchronize LDAP users to/with FreeIPA
|
||||||
server and synchronizes the results with the users registered in FreeIPA.
|
|
||||||
Since it synchronizes data it is safe to run multiple times and users can be
|
|
||||||
imported also as stage users initially.
|
|
||||||
|
|
||||||
The intent is to migrate user data and to not drag on a legacy setup. For
|
|
||||||
this reason, the script will create new user and group IDs and not copy homedir
|
|
||||||
and shell information by default. For the IDs, the legacy information can be
|
|
||||||
stored in an FreeIPA ID View so it remains available, other items can be copied
|
|
||||||
over using command line options. Passwords can be copied-over (if available in
|
|
||||||
a usable format), and the script also supports having FreeIPA generate random
|
|
||||||
passwords and store these in a file for further processing/sharing with users.
|
|
||||||
|
|
||||||
Users can be copied from an existing (generic) LDAP database and a MacOS Server
|
|
||||||
OpenDirectory-flavor LDAP server. In this case, additional information (e.g.
|
|
||||||
Apple's generatedUID) will be copied over as well. Please note that this does
|
|
||||||
require customizing the FreeIPA LDAP schema, which the script will check for
|
|
||||||
and can install (option ```-U```). As the setup is modular it should be easy
|
|
||||||
to tweak or add other migrations.
|
|
||||||
|
|
||||||
By default all users will be migrated/synchronized, but it is also possible to
|
|
||||||
limit this to specific user(s) or group(s) or specifically exclude specific
|
|
||||||
users or groups. An example to copy all users in the group ```workgroup```
|
|
||||||
except ```admin``` from an Apple MacOS OpenDirectory server:
|
|
||||||
~~~
|
|
||||||
./users2freeipa.py -v -O -U -c "Legacy LDAP" -g workgroup -x admin -G \
|
|
||||||
-P -p passwords.txt ldap://ldap.mydomain.tld
|
|
||||||
~~~
|
|
||||||
This will also install the OpenDirectory-specific schema customization, create
|
|
||||||
groups and copy group memberships, copy usuable passwords and ensure that all
|
|
||||||
users have a password (storing generated passwords to ```passwords.txt```)
|
|
||||||
|
|
||||||
Please note that migrating existing passwords from LDAP has limitations, see
|
|
||||||
[this](https://www.freeipa.org/page/NIS_accounts_migration_preserving_Passwords)
|
|
||||||
page on migrating NIS passwords and [this](https://pagure.io/freeipa/issue/4732)
|
|
||||||
issue reported with it. Bottom line is that (at this moment) password migration
|
|
||||||
is flawed and always will require manual action from the user. For this reason
|
|
||||||
the better alternative to set a random password and ask the user to reset the
|
|
||||||
password using the FreeIPA portal makes more sense.
|
|
||||||
|
|
||||||
Before running a production user migration, it is important to have FreeIPA
|
|
||||||
setup and configured correctly so that the right defaults are used for new
|
|
||||||
users. Best is to start with a single user and add that as a stage user (please
|
|
||||||
note that this will not yet assign userIDs, group memberships and a password
|
|
||||||
as FreeIPA does not yet support that) and use an ID View to store legacy data.
|
|
||||||
|
|
||||||
For all available command-line options, run ```users2freeipa.py -h```
|
|
||||||
|
|
||||||
|
|
||||||
<a name=freeipadns>freeipa-dns.py</a>
|
<a name=freeipadns>freeipa-dns.py</a>
|
||||||
----------------------------------------------------------------
|
-------------------------------------
|
||||||
This script provides functionality not provided by FreeIPA to migrate and/or
|
This script provides functionality not provided by FreeIPA to migrate and/or
|
||||||
synchronize / maintain DNS data in FreeIPA. Currently the following commands
|
synchronize / maintain DNS data in FreeIPA. Currently the following commands
|
||||||
are implemented:
|
are implemented:
|
||||||
* axfr - import/synchronize a DNS zone in FreeIPA using a zone-xfer.
|
* axfr - synchronize DNS zone(s) using a zone-xfer. Contrary to the suggested
|
||||||
|
[migration approach](https://docs.pagure.org/bind-dyndb-ldap/Migration.html)
|
||||||
|
this uses the FreeIPA API to migrate or synchronize DNS zones with FreeIPA
|
||||||
|
so it can also be used for running things in parallel or gradual migrations.
|
||||||
|
|
||||||
for example, to migrate / synchronize fromain ```domain.tld``` from DNS
|
for example, to migrate / synchronize fromain ```domain.tld``` from DNS
|
||||||
server ```192.168.1.53``` without checking DNS overlap, issue the command:
|
server ```192.168.1.53``` without checking DNS overlap, issue the command:
|
||||||
|
|
||||||
@@ -172,7 +128,7 @@ the available options for each commmand run ```freeipa-dns.py <command> -h```
|
|||||||
|
|
||||||
|
|
||||||
<a name=freeipaletsencrypt>freeipa-letsencrypt.sh</a>
|
<a name=freeipaletsencrypt>freeipa-letsencrypt.sh</a>
|
||||||
----------------------------------------------------------------
|
-----------------------------------------------------
|
||||||
This script will ensure the necessary setup is in place so that Certbot (EFF's
|
This script will ensure the necessary setup is in place so that Certbot (EFF's
|
||||||
certificate request script for Let's Encrypt) will work with FreeIPA for DNS
|
certificate request script for Let's Encrypt) will work with FreeIPA for DNS
|
||||||
challenges and and instructs it to deploy new certificates for FreeIPA's web
|
challenges and and instructs it to deploy new certificates for FreeIPA's web
|
||||||
@@ -202,9 +158,9 @@ by setting one of the following environment variables:
|
|||||||
|
|
||||||
| Variable | Description | Default value |
|
| Variable | Description | Default value |
|
||||||
|-------------|------------------------------------|---------------------------|
|
|-------------|------------------------------------|---------------------------|
|
||||||
| CERTNAME | certificate hostname, | host's canonicalname (*) |
|
| CERTNAME | certificate hostname, | host's canonicalname (1) |
|
||||||
| DNSALTNAMES | certificate DNS names | host's principalnames (*) |
|
| DNSALTNAMES | certificate DNS names | host's principalnames (1) |
|
||||||
| DOMAIN | Let's Encrypt challenge DNS zone | {DNS name's domain} (**) |
|
| DOMAIN | Let's Encrypt challenge DNS zone | {DNS name's domain} (2) |
|
||||||
| EMAIL | administrator's e-mail address | hostmaster@{domain} |
|
| EMAIL | administrator's e-mail address | hostmaster@{domain} |
|
||||||
| HOSTNAME | FreeIPA server's hostname | `hostname --fqdn` |
|
| HOSTNAME | FreeIPA server's hostname | `hostname --fqdn` |
|
||||||
| KEYTAB | Let'sEncrypt service's keytab file | /etc/letsencrypt/keytab |
|
| KEYTAB | Let'sEncrypt service's keytab file | /etc/letsencrypt/keytab |
|
||||||
@@ -214,11 +170,86 @@ by setting one of the following environment variables:
|
|||||||
| SUDO | command to become root (if needed) | sudo |
|
| SUDO | command to become root (if needed) | sudo |
|
||||||
| TMPDIR | Directory for temporary files | /tmp |
|
| TMPDIR | Directory for temporary files | /tmp |
|
||||||
|
|
||||||
(*) obtained from the FreeIPA server record looked up based on ${HOSTNAME}
|
(1) obtained from the FreeIPA server record looked up based on ${HOSTNAME}
|
||||||
(**) this allows to enforce the DNS zone, e.g. host.subdomain in mydomain.tld
|
(2) this allows to enforce the DNS zone, e.g. host.subdomain in mydomain.tld
|
||||||
|
|
||||||
When things change, the script can simply be run again.
|
When things change, the script can simply be run again.
|
||||||
|
|
||||||
|
|
||||||
|
<a name=setdnssource>set-dns-source.sh</a>
|
||||||
|
------------------------------------------
|
||||||
|
FreeIPA's bind-dyndb-ldap plugin does not support bind's ```notify-source```
|
||||||
|
settings and simply uses the main address when sending DNS notifications. This
|
||||||
|
breaks multi-homed setups and, in case of IPv6, even causes bind to send NOTIFY
|
||||||
|
messages from the temporary IPv6 address, causing slave servers to reject them.
|
||||||
|
This script will setup Source NAT in firewalld to enforce the IPv4/IPv6 address
|
||||||
|
of outgoing DNS packets to ensure that DNS NOTIFYs messages will use the correct
|
||||||
|
source IPv4/IPv6 address. The IPv4/IPv6 address(es) to enforce should either be
|
||||||
|
provided in the environment or changed at the top of the script. In case an IPv4
|
||||||
|
address is provided, the script can figure out itself which device to use when
|
||||||
|
running it, if not this should be provided as well. To install run:
|
||||||
|
~~~
|
||||||
|
sudo IPV4ADDR=192.168.0.100 IPV6ADDR=none ./set-dns-source.sh install
|
||||||
|
~~~
|
||||||
|
to remove installed rules, run with the same parameters and parameter 'remove':
|
||||||
|
~~~
|
||||||
|
sudo IPV4ADDR=192.168.0.100 IPV6ADDR=none ./set-dns-source.sh remove
|
||||||
|
~~~
|
||||||
|
and to see custom rules run: ```sudo firewall-cmd --direct --get-all-rules```
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<a name=users2freeipa>users2freeipa.py</a>
|
||||||
|
------------------------------------------
|
||||||
|
This script uses LDAP to obtain users from a MacOS Server (or other LDAP)
|
||||||
|
server and synchronizes the results with the users registered in FreeIPA.
|
||||||
|
Since it synchronizes data it is safe to run multiple times and users can be
|
||||||
|
imported also as stage users initially.
|
||||||
|
|
||||||
|
The intent is to migrate user data and to not drag on a legacy setup. For
|
||||||
|
this reason, the script will create new user and group IDs and not copy homedir
|
||||||
|
and shell information by default. For the IDs, the legacy information can be
|
||||||
|
stored in an FreeIPA ID View so it remains available, other items can be copied
|
||||||
|
over using command line options. Passwords can be copied-over (if available in
|
||||||
|
a usable format), and the script also supports having FreeIPA generate random
|
||||||
|
passwords and store these in a file for further processing/sharing with users.
|
||||||
|
|
||||||
|
Users can be copied from an existing (generic) LDAP database and a MacOS Server
|
||||||
|
OpenDirectory-flavor LDAP server. In this case, additional information (e.g.
|
||||||
|
Apple's generatedUID) will be copied over as well. Please note that this does
|
||||||
|
require customizing the FreeIPA LDAP schema, which the script will check for
|
||||||
|
and can install (option ```-U```). As the setup is modular it should be easy
|
||||||
|
to tweak or add other migrations.
|
||||||
|
|
||||||
|
By default all users will be migrated/synchronized, but it is also possible to
|
||||||
|
limit this to specific user(s) or group(s) or specifically exclude specific
|
||||||
|
users or groups. An example to copy all users in the group ```workgroup```
|
||||||
|
except ```admin``` from an Apple MacOS OpenDirectory server:
|
||||||
|
~~~
|
||||||
|
./users2freeipa.py -v -O -U -c "Legacy LDAP" -g workgroup -x admin -G \
|
||||||
|
-P -p passwords.txt ldap://ldap.mydomain.tld
|
||||||
|
~~~
|
||||||
|
This will also install the OpenDirectory-specific schema customization, create
|
||||||
|
groups and copy group memberships, copy usuable passwords and ensure that all
|
||||||
|
users have a password (storing generated passwords to ```passwords.txt```)
|
||||||
|
|
||||||
|
Please note that migrating existing passwords from LDAP has limitations, see
|
||||||
|
[this](https://www.freeipa.org/page/NIS_accounts_migration_preserving_Passwords)
|
||||||
|
page on migrating NIS passwords and [this](https://pagure.io/freeipa/issue/4732)
|
||||||
|
issue reported with it. Bottom line is that (at this moment) password migration
|
||||||
|
is flawed and always will require manual action from the user. For this reason
|
||||||
|
the better alternative to set a random password and ask the user to reset the
|
||||||
|
password using the FreeIPA portal makes more sense.
|
||||||
|
|
||||||
|
Before running a production user migration, it is important to have FreeIPA
|
||||||
|
setup and configured correctly so that the right defaults are used for new
|
||||||
|
users. Best is to start with a single user and add that as a stage user (please
|
||||||
|
note that this will not yet assign userIDs, group memberships and a password
|
||||||
|
as FreeIPA does not yet support that) and use an ID View to store legacy data.
|
||||||
|
|
||||||
|
For all available command-line options, run ```users2freeipa.py -h```
|
||||||
|
|
||||||
|
|
||||||
<a name="license">License</a>
|
<a name="license">License</a>
|
||||||
-----------------------------
|
-----------------------------
|
||||||
These scripts, documentation & configration examples are free software: you can
|
These scripts, documentation & configration examples are free software: you can
|
||||||
|
|||||||
@@ -36,7 +36,13 @@ else
|
|||||||
fi
|
fi
|
||||||
|
|
||||||
# Set KRB5CCNAME to ensure the current ticket cache will be used
|
# Set KRB5CCNAME to ensure the current ticket cache will be used
|
||||||
KRB5CCNAME=${KRB5CCNAME:-$(klist -l | head -3 | tail -1 | cut -d\ -f2-)}
|
: ${KRB5CCNAME:=$(klist -l | head -3 | tail -1 | cut -d\ -f2-)}
|
||||||
|
|
||||||
|
# Set parameters
|
||||||
|
: ${CERTNAME:=$(ipa host-show $HOSTNAME --raw | fgrep "krbcanonicalname: host/" | cut -d/ -f2 | cut -d@ -f1)}
|
||||||
|
: ${DNSALTNAMES:=$(ipa host-show $HOSTNAME --raw | fgrep "krbprincipalname: host/" | cut -d/ -f2 | cut -d@ -f1 | paste -sd,)}
|
||||||
|
: ${EMAIL:=hostmaster@${HOSTNAME#*.}}
|
||||||
|
: ${SERVICE:=letsencrypt/$(ipa host-show $HOSTNAME --raw | fgrep "krbcanonicalname: host/" | cut -d/ -f2)}
|
||||||
|
|
||||||
# Ensure the user consents with changing his system.
|
# Ensure the user consents with changing his system.
|
||||||
if tty > /dev/null; then
|
if tty > /dev/null; then
|
||||||
@@ -46,12 +52,11 @@ use a Let's Encrypt certificate and will automatically renew that when needed.
|
|||||||
The following changes will be made for this:
|
The following changes will be made for this:
|
||||||
1. Add Let's Encrypt Root and Intermediate CAs as trusted CAs
|
1. Add Let's Encrypt Root and Intermediate CAs as trusted CAs
|
||||||
2. Create DNS Administrator role in FreeIPA that can edit any DNS Record
|
2. Create DNS Administrator role in FreeIPA that can edit any DNS Record
|
||||||
3. Create host service: ${SERVICE:=letsencrypt/$(
|
3. Create host service: $SERVICE
|
||||||
ipa host-show $HOSTNAME --raw | fgrep "krbcanonicalname: host/" | cut -d/ -f2)}
|
|
||||||
4. Allow letsencrypt host service to manage DNS entries
|
4. Allow letsencrypt host service to manage DNS entries
|
||||||
5. Register with Let's encrypt as: ${EMAIL:=hostmaster@${HOSTNAME#*.}}
|
5. Register with Let's encrypt as: $EMAIL
|
||||||
6. Request a Let's Encrypt SSL certificate for: ${CERTNAME:=$(ipa host-show $HOSTNAME --raw | fgrep "krbcanonicalname: host/" | cut -d/ -f2 | cut -d@ -f1)}
|
6. Request a Let's Encrypt SSL certificate for: $CERTNAME
|
||||||
with DNS Alternative names: ${DNSALTNAMES:=$(ipa host-show $HOSTNAME --raw | fgrep "krbprincipalname: host/" | cut -d/ -f2 | cut -d@ -f1 | paste -sd,)}
|
with DNS Alternative names: $DNSALTNAMES
|
||||||
7. install the Let's Encrypt certificate in apache as host SSL certificate,
|
7. install the Let's Encrypt certificate in apache as host SSL certificate,
|
||||||
storing renewal config in: /etc/letsencrypt/renewal/$HOSTNAME.conf
|
storing renewal config in: /etc/letsencrypt/renewal/$HOSTNAME.conf
|
||||||
8. configure the Fedora Certbot renew timer so that certbot is run daily to
|
8. configure the Fedora Certbot renew timer so that certbot is run daily to
|
||||||
@@ -121,7 +126,7 @@ $SUDO systemctl enable --now certbot-renew.timer
|
|||||||
|
|
||||||
cat << EOT
|
cat << EOT
|
||||||
|
|
||||||
FreeIPA was successfully setup to use a Let\'s Encrypt certificate for its web
|
FreeIPA was successfully setup to use a Let's Encrypt certificate for its web
|
||||||
interface. This certificate will be renewed automatically when needed.
|
interface. This certificate will be renewed automatically when needed.
|
||||||
|
|
||||||
EOT
|
EOT
|
||||||
|
|||||||
48
set-dns-source.sh
Executable file
48
set-dns-source.sh
Executable file
@@ -0,0 +1,48 @@
|
|||||||
|
#!/bin/bash -e
|
||||||
|
#
|
||||||
|
# set-dns-source.sh - Setup Source NAT in firewalld for outgoing DNS traffic
|
||||||
|
#
|
||||||
|
# Version 1.0, latest version, documentation and bugtracker available at:
|
||||||
|
# https://gitlab.lindenaar.net/scripts/freeipa
|
||||||
|
#
|
||||||
|
# Copyright (c) 2018 Frederik Lindenaar
|
||||||
|
#
|
||||||
|
# This script is free software: you can redistribute and/or modify it under the
|
||||||
|
# terms of version 3 of the GNU General Public License as published by the Free
|
||||||
|
# Software Foundation, or (at your option) any later version of the license.
|
||||||
|
#
|
||||||
|
# This script is distributed in the hope that it will be useful but WITHOUT ANY
|
||||||
|
# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
|
||||||
|
# A PARTICULAR PURPOSE. See the GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# You should have received a copy of the GNU General Public License along with
|
||||||
|
# this program. If not, visit <http://www.gnu.org/licenses/> to download it.
|
||||||
|
|
||||||
|
case $1 in
|
||||||
|
install) CMD=add
|
||||||
|
;;
|
||||||
|
remove) CMD=remove
|
||||||
|
;;
|
||||||
|
*) echo "usage: $0 <install | remove>"
|
||||||
|
exit 1
|
||||||
|
esac
|
||||||
|
|
||||||
|
IPV4ADDR=${IPV4ADDR:?Please provide an IPv4 address or set to 'none'}
|
||||||
|
IPV6ADDR=${IPV6ADDR:?Please provide an IPv6 address or set to 'none'}
|
||||||
|
|
||||||
|
DEV=${DEV:=$( /usr/sbin/ip route | fgrep ${IPV4ADDR:?No IPv4 address provided, please set device manually} | cut -d\ -f3 )}
|
||||||
|
: ${DEV:?No route found for $IPV4ADDR, please check config or set device manually}
|
||||||
|
|
||||||
|
# inspired by https://blog.sebastien.raveau.name/2009/04/per-process-routing.html
|
||||||
|
# and https://unix.stackexchange.com/questions/389756/how-to-use-snat-with-firewalld-vs-masq
|
||||||
|
|
||||||
|
for PROTO in ipv4 ipv6; do
|
||||||
|
[ "$PROTO" == ipv6 ] && ADDR="$IPV6ADDR" || ADDR="$IPV4ADDR"
|
||||||
|
if [ -n "$ADDR" -a "$ADDR" != none ]; then
|
||||||
|
for MODE in "" --permanent; do
|
||||||
|
firewall-cmd $MODE --direct --$CMD-rule $PROTO mangle OUTPUT 0 -m owner --uid-owner named -j MARK --set-mark 53
|
||||||
|
firewall-cmd $MODE --direct --$CMD-rule $PROTO nat POSTROUTING 0 -o $DEV -m mark --mark 53 -j SNAT --to-source $ADDR
|
||||||
|
done
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
Reference in New Issue
Block a user