All Projects → afosto → yaac

afosto / yaac

Licence: other
Yet another ACME client: a decoupled LetsEncrypt client

Programming Languages

PHP
23972 projects - #3 most used programming language

Projects that are alternatives of or similar to yaac

ght-acme.sh
Shell script to sign certificate by the letsencrypt CA
Stars: ✭ 31 (-77.54%)
Mutual labels:  letsencrypt, acme-client, acme-v2
ACMECert
PHP client library for Let's Encrypt (ACME v2 - RFC 8555)
Stars: ✭ 83 (-39.86%)
Mutual labels:  letsencrypt, acme-client, acme-v2
acme-dns-01-cloudflare
Cloudflare DNS for Let's Encrypt / ACME dns-01 challenges with Greenlock.js and ACME.js
Stars: ✭ 13 (-90.58%)
Mutual labels:  letsencrypt, acme-v2
itr-acme-client
ITronic ACME Client Library
Stars: ✭ 21 (-84.78%)
Mutual labels:  letsencrypt, acme-client
Win Acme
A simple ACME client for Windows (for use with Let's Encrypt et al.)
Stars: ✭ 4,305 (+3019.57%)
Mutual labels:  letsencrypt, acme-v2
acme-companion
Automated ACME SSL certificate generation for nginx-proxy
Stars: ✭ 6,434 (+4562.32%)
Mutual labels:  letsencrypt, acme-v2
lua-resty-acme
Automatic Let's Encrypt certificate serving and Lua implementation of ACMEv2 procotol
Stars: ✭ 95 (-31.16%)
Mutual labels:  letsencrypt, acme-v2
certbot-dns-schlundtech
SchlundTech XML Gateway DNS Authenticator plugin for EFF's Certbot
Stars: ✭ 14 (-89.86%)
Mutual labels:  letsencrypt, acme-v2
Certbot
Certbot is EFF's tool to obtain certs from Let's Encrypt and (optionally) auto-enable HTTPS on your server. It can also act as a client for any other CA that uses the ACME protocol.
Stars: ✭ 28,541 (+20581.88%)
Mutual labels:  letsencrypt, acme-client
Docker Letsencrypt Nginx Proxy Companion
Automated ACME SSL certificate generation for nginx-proxy
Stars: ✭ 6,350 (+4501.45%)
Mutual labels:  letsencrypt, acme-v2
kong-plugin-acme
Let's Encrypt and ACMEv2 integration with Kong - this plugin has been moved into https://github.com/Kong/kong, please open issues and PRs in that repo
Stars: ✭ 36 (-73.91%)
Mutual labels:  letsencrypt, acme-v2
letsencrypt-manual-hook
Allows you to use dehydrated (a Let's Encrypt/Acme Client) and DNS challenge response with a DNS provider that requires manual intervention
Stars: ✭ 61 (-55.8%)
Mutual labels:  letsencrypt, acme-client
Acme.sh
A pure Unix shell script implementing ACME client protocol
Stars: ✭ 24,723 (+17815.22%)
Mutual labels:  letsencrypt, acme-client
txacme
Twisted client for the ACME (Automatic Certificate Management Environment) protocol
Stars: ✭ 42 (-69.57%)
Mutual labels:  letsencrypt, acme-v2
LetsEncrypt
C# layer for generation of wildcard Let's Encrypt SSL certificates
Stars: ✭ 67 (-51.45%)
Mutual labels:  letsencrypt, acme-v2
self-hosted-services
A core set of privacy-preserving services that can be easily self-hosted via Docker Compose.
Stars: ✭ 123 (-10.87%)
Mutual labels:  letsencrypt
django-template
The ultimate Django template: production ready Django 3.2 with Docker, HTTPS and CI/CD using Github actions ‎️‍🔥
Stars: ✭ 20 (-85.51%)
Mutual labels:  letsencrypt
Intranet-Lets-Encrypt-Certification
Guide to setting up a Let's Encrypt SSL certificate for a non-public facing server.
Stars: ✭ 27 (-80.43%)
Mutual labels:  letsencrypt
letsencrypt-autorenew-docker
letsencrypt certificate generation and cron enabled autorenewal as a docker image
Stars: ✭ 59 (-57.25%)
Mutual labels:  letsencrypt
mediastack
All in one Docker Compose media server
Stars: ✭ 42 (-69.57%)
Mutual labels:  letsencrypt

yaac - Yet another ACME client

Written in PHP, this client aims to be a simplified and decoupled Let’s Encrypt client, based on ACME V2.

Decoupled from a filesystem or webserver

Instead of, for example writing the certificate to the disk under an nginx configuration, this client just returns the data (the certificate and private key).

Why

Why would I need this package? At Afosto we run our software in a multi-tenant setup, as any other SaaS would do, and therefore we cannot make use of the many clients that are already out there.

Almost all clients are coupled to a type of webserver or a fixed (set of) domain(s). This package can be extremely useful in case you need to dynamically fetch and install certificates.

Requirements

  • PHP7+
  • openssl
  • Flysystem (any adapter would do) - to store the Lets Encrypt account information

Getting started

Getting started is easy. First install the client, then you need to construct a flysystem filesystem, instantiate the client and you can start requesting certificates.

Installation

Installing this package is done easily with composer.

composer require afosto/yaac

Instantiate the client

To start the client you need 3 things; a username for your Let’s Encrypt account, a bootstrapped Flysystem and you need to decide whether you want to issue Fake LE Intermediate X1 (staging: MODE_STAGING) or Let's Encrypt Authority X3 (live: MODE_LIVE, use for production) certificates.

use League\Flysystem\Filesystem;
use League\Flysystem\Adapter\Local;
use Afosto\Acme\Client;
 
//Prepare flysystem
$adapter = new Local('data');
$filesystem = new Filesystem($adapter);
 
//Construct the client
$client = new Client([
    'username' => '[email protected]',
    'fs'       => $filesystem,
    'mode'     => Client::MODE_STAGING,
]);

While you instantiate the client, when needed a new Let’s Encrypt account is created and then agrees to the TOS.

Create an order

To start retrieving certificates, we need to create an order first. This is done as follows:

$order = $client->createOrder(['example.org', 'www.example.org']);

In the example above the primary domain is followed by a secondary domain(s). Make sure that for each domain you are able to prove ownership. As a result the certificate will be valid for all provided domains.

Prove ownership

Before you can obtain a certificate for a given domain you need to prove that you own the given domain(s). We request the authorizations to prove ownership. Obtain the authorizations for order. For each domain supplied in the create order request an authorization is returned.

$authorizations = $client->authorize($order);

You now have an array of Authorization objects. These have the challenges you can use (both DNS and HTTP) to provide proof of ownership.

HTTP validation

HTTP validation (where serve specific content at a specific url on the domain, like: example.org/.well-known/acme-challenge/*) is done as follows:

Use the following example to get the HTTP validation going. First obtain the challenges, the next step is to make the challenges accessible from

foreach ($authorizations as $authorization) {
    $file = $authorization->getFile();
    file_put_contents($file->getFilename(), $file->getContents());   
}

If you need a wildcard certificate, you will need to use DNS validation, see below

DNS validation

You can also use DNS validation - to do this, you will need access to an API of your DNS provider to create TXT records for the target domains.

foreach ($authorizations as $authorization) {
    $txtRecord = $authorization->getTxtRecord();
    
    //To get the name of the TXT record call:
    $txtRecord->getName();

    //To get the value of the TXT record call:
    $txtRecord->getValue();
}

Self test

After exposing the challenges (made accessible through HTTP or DNS) we should perform a self test just to be sure it works before asking Let's Encrypt to validate ownership.

For a HTTP challenge test call:

if (!$client->selfTest($authorization, Client::VALIDATION_HTTP)) {
    throw new \Exception('Could not verify ownership via HTTP');
}

For a DNS test call:

if (!$client->selfTest($authorization, Client::VALIDATION_DNS)) {
    throw new \Exception('Could not verify ownership via DNS');
}
sleep(30); // this further sleep is recommended, depending on your DNS provider, see below

With DNS validation, after the selfTest has confirmed that DNS has been updated, it is recommended you wait some additional time before proceeding, e.g. sleep(30);. This is because Let’s Encrypt will perform multiple viewpoint validation, and your DNS provider may not have completed propagating the changes across their network.

If you proceed too soon, Let's Encrypt will fail to validate.

Request validation

Next step is to request validation of ownership. For each authorization (domain) we ask Let’s Encrypt to verify the challenge.

For HTTP validation:

foreach ($authorizations as $authorization) {
    $client->validate($authorization->getHttpChallenge(), 15);
}

For DNS validation:

foreach ($authorizations as $authorization) {
    $client->validate($authorization->getDnsChallenge(), 15);
}

The code above will first perform a self test and, if successful, will do 15 attempts to ask Let’s Encrypt to validate the challenge (with 1 second intervals) and retrieve an updated status (it might take Let’s Encrypt a few seconds to validate the challenge).

Get the certificate

Now to know if we can request a certificate for the order, test if the order is ready as follows:

if ($client->isReady($order)) {
    //The validation was successful.
}

We now know validation was completed and can obtain the certificate. This is done as follows:

$certificate = $client->getCertificate($order);

We now have the certificate, to store it on the filesystem:

//Store the certificate and private key where you need it
file_put_contents('certificate.cert', $certificate->getCertificate());
file_put_contents('private.key', $certificate->getPrivateKey());

To get a seperate intermediate certificate and domain certificate:

$domainCertificate = $certificate->getCertificate(false);
$intermediateCertificate = $certificate->getIntermediate();

Who is using it?

Are you using this package, would love to know. Please send a PR to enlist your project or company.

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].