1
0
mirror of https://github.com/laurivosandi/certidude synced 2024-12-22 16:25:17 +00:00

Merge branch 'master' of github.com:laurivosandi/certidude

This commit is contained in:
Lauri Võsandi 2017-01-26 21:59:37 +00:00
commit 5d5a24096c
3 changed files with 112 additions and 55 deletions

View File

@ -17,9 +17,10 @@ eventually support PKCS#11 and in far future WebCrypto.
.. figure:: doc/usecase-diagram.png
Certidude is mainly designed for VPN gateway operators to make
desktop/laptop VPN setup as easy as possible.
User certificate management eg. for HTTPS is also made reasonably simple.
Certidude is mainly designed for StrongSwan and OpenVPN gateway operators to make
VPN client setup on laptops, desktops and mobile devices as painless as possible.
Certidude can also be used to manage HTTPS client certificates for
eg. maintaining an extra layer of protection for intranet websites.
For a full-blown CA you might want to take a look at
`EJBCA <http://www.ejbca.org/features.html>`_ or
`OpenCA <https://pki.openca.org/>`_.
@ -105,18 +106,29 @@ TODO
Install
-------
To install Certidude server:
To install Certidude server you need certain system libraries in addition to
regular Python dependencies.
System dependencies for Ubuntu 16.04:
.. code:: bash
apt-get install -y python python-pip python-dev cython \
apt install -y python python-pip python-dev cython \
python-cffi python-configparser \
python-pysqlite2 python-mysql.connector python-ldap \
build-essential libffi-dev libssl-dev libkrb5-dev \
ldap-utils krb5-user \
libsasl2-modules-gssapi-mit \
libsasl2-dev libldap2-dev
pip install simplepam pykerberos certidude
System dependencies for Fedora 24+:
.. code:: bash
yum install redhat-rpm-config python-devel openssl-devel openldap-devel
At the moment package at PyPI is rather outdated.
Please proceed down to Development section to install Certidude from source.
Setting up authority
@ -139,15 +151,6 @@ If necessary tweak machine's fully qualified hostname in ``/etc/hosts``:
127.0.0.1 localhost
127.0.1.1 ca.example.com ca
Then proceed to install `nchan <https://nchan.slact.net/>`_:
.. code:: bash
wget https://nchan.slact.net/download/nginx-common.deb \
https://nchan.slact.net/download/nginx-extras.deb
dpkg -i nginx-common.deb nginx-extras.deb
apt-get -f install
Certidude can set up certificate authority relatively easily.
Following will set up certificate authority in ``/var/lib/certidude/hostname.domain.tld``,
configure systemd service for your platform,
@ -166,27 +169,27 @@ and start the services:
systemctl restart certidude
Certificate management
----------------------
Setting up PAM authentication
-----------------------------
Use following command to request a certificate on a machine:
Following assumes the OS user accounts are used to authenticate users.
This means users can be easily managed with OS tools such as ``adduser``, ``usermod``, ``userdel`` etc.
.. code::
Make sure you insert `AllowUsers administrator-account-username`
to SSH server configuration if you have SSH server installed on the machine
to prevent regular users from accessing the command line of certidude.
Note that in future we're planning to add command-line interaction
in which case SSH access makes sense.
certidude setup client ca.example.com
If you're planning to use PAM for authentication you need to install corresponding
Python modules:
Use following to list signing requests, certificates and revoked certificates on server:
.. code:: bash
.. code::
certidude list
Use web interface or following to sign a certificate on server:
.. code::
certidude sign client-hostname-or-common-name
pip install simplepam
The default configuration generated by ``certidude setup`` should make use of the
PAM.
Setting up Active Directory authentication
------------------------------------------
@ -199,6 +202,7 @@ Install dependencies:
.. code:: bash
apt-get install samba-common-bin krb5-user ldap-utils
pip install pykerberos
Reset Samba client configuration in ``/etc/samba/smb.conf``, adjust
workgroup and realm accordingly:
@ -274,33 +278,58 @@ Common pitfalls:
the CA machine to domain, eg when you're running CA behind SSL terminating web server:
Bad credentials: Unspecified GSS failure. Minor code may provide more information (851968)
Automating certificate setup
----------------------------
Ubuntu 14.04 based desktops come with NetworkManager installed.
Create ``/etc/NetworkManager/dispatcher.d/certidude`` with following content:
Setting up services
-------------------
Set up services as usual (OpenVPN, Strongswan, etc), when setting up certificates
generate signing request with TLS server flag set.
Paste signing request into the Certidude web interface and hit the submit button.
Since signing requests with custom flags are not allowed to be signed
from the interface due to security concerns, sign the certificate at Certidude command line:
.. code:: bash
#!/bin/sh -e
# Set up certificates for IPSec connection
certidude sign gateway.example.com
case "$2" in
up)
LANG=C.UTF-8 /usr/local/bin/certidude request spawn -k
;;
esac
Download signed certificate from the web interface or ``wget`` it into the service machine.
Fetch also CA certificate and finish configuring the service.
Finally make it executable:
Setting up clients
------------------
This example works for Ubuntu 16.04 desktop with corresponding plugins installed
for NetworkManager.
Configure Certidude client in ``/etc/certidude/client.conf``:
.. code:: ini
[ca.example.com]
insecure = true
trigger = interface up
Configure services in ``/etc/certidude/services.conf``:
.. code:: bash
chmod +x /etc/NetworkManager/dispatcher.d/certidude
[gateway.example.com]
authority = ca.example.com
service = network-manager/openvpn
remote = gateway.example.com
Whenever a wired or wireless connection is brought up,
the dispatcher invokes ``certidude`` in order to generate RSA keys,
submit CSR, fetch signed certificate,
create NetworkManager configuration for the VPN connection.
To request certificate:
.. code:: bash
certidude request
The keys, signing requests, certificates and CRL-s are placed under
/var/lib/certidude/ca.example.com/
The VPN connection should immideately become available under network connections.
Development
@ -323,7 +352,7 @@ To generate templates:
.. code:: bash
apt-get install npm nodejs
apt install npm nodejs
sudo ln -s nodejs /usr/bin/node # Fix 'env node' on Ubuntu 14.04
npm install -g nunjucks@2.5.2
nunjucks-precompile --include "\\.html$" --include "\\.svg$" certidude/static/ > certidude/static/js/templates.js
@ -340,3 +369,30 @@ To install the package from the source:
.. code:: bash
python setup.py install --single-version-externally-managed --root /
To uninstall:
pip uninstall certidude
Certificate attributes
----------------------
Certificates have a lot of fields that can be filled in.
In any case country, state, locality, organization, organizational unit are not filled in
as this information will already exist in AD and duplicating it in the certificate management
doesn't make sense. Additionally the information will get out of sync if
attributes are changed in AD but certificates won't be updated.
If machine is enrolled, eg by running certidude request:
* If Kerberos credentials are presented machine is automatically enrolled
* Common name is set to short hostname/machine name in AD
* E-mail is not filled in (maybe we can fill in something from AD?)
* Given name and surname are not filled in
If user enrolls, eg by clicking generate bundle button in the web interface:
* Common name is either set to username or username@device-identifier depending on the 'user certificate enrollment' setting
* Given name and surname are filled in based on LDAP attributes of the user
* E-mail not filled in (should it be filled in? Can we even send mail to user if it's in external domain?)

View File

@ -1,7 +1,6 @@
import click
import falcon
import kerberos # If this fails pip install kerberos
import logging
import os
import re
@ -13,6 +12,7 @@ from certidude import config, const
logger = logging.getLogger("api")
if "kerberos" in config.AUTHENTICATION_BACKENDS:
import kerberos # If this fails pip install kerberos
ktname = os.getenv("KRB5_KTNAME")
if not ktname:
@ -186,7 +186,7 @@ def authenticate(optional=False):
if not simplepam.authenticate(user, passwd, "sshd"):
logger.critical(u"Basic authentication failed for user %s from %s",
repr(user), req.context.get("remote_addr"))
raise falcon.HTTPForbidden("Forbidden", "Invalid password")
raise falcon.HTTPUnauthorized("Forbidden", "Invalid password", ("Basic",))
req.context["user"] = User.objects.get(user)
return func(resource, req, resp, *args, **kwargs)

View File

@ -239,7 +239,7 @@ def certidude_request(fork):
nm_config.set("vpn", "connection-type", "tls")
nm_config.set("vpn", "comp-lzo", "yes")
nm_config.set("vpn", "cert-pass-flags", "0")
nm_config.set("vpn", "tap-dev", "yes")
nm_config.set("vpn", "tap-dev", "no")
nm_config.set("vpn", "remote-cert-tls", "server") # Assert TLS Server flag of X.509 certificate
nm_config.set("vpn", "remote", service_config.get(endpoint, "remote"))
nm_config.set("vpn", "key", endpoint_key_path)
@ -1174,10 +1174,11 @@ def certidude_serve(port, listen):
from certidude import config
# Fetch UID, GID of certidude user
import pwd
_, _, uid, gid, gecos, root, shell = pwd.getpwnam("certidude")
restricted_groups = []
restricted_groups.append(gid)
if os.getuid() == 0:
import pwd
_, _, uid, gid, gecos, root, shell = pwd.getpwnam("certidude")
restricted_groups = []
restricted_groups.append(gid)
"""
Spawn signer process