{"id":31628064,"url":"https://github.com/jirutka/muacme","last_synced_at":"2025-10-06T20:17:32.758Z","repository":{"id":56321005,"uuid":"215892519","full_name":"jirutka/muacme","owner":"jirutka","description":"A convenient wrapper for the ACMEv2 client uacme","archived":false,"fork":false,"pushed_at":"2023-03-10T13:08:38.000Z","size":33,"stargazers_count":8,"open_issues_count":0,"forks_count":2,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-06-08T13:18:51.822Z","etag":null,"topics":["acme-client","letsencrypt","letsencrypt-cli","uacme"],"latest_commit_sha":null,"homepage":"","language":"Shell","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jirutka.png","metadata":{"files":{"readme":"README.adoc","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2019-10-17T21:57:50.000Z","updated_at":"2024-07-02T01:24:31.000Z","dependencies_parsed_at":"2024-06-20T16:39:30.547Z","dependency_job_id":null,"html_url":"https://github.com/jirutka/muacme","commit_stats":null,"previous_names":[],"tags_count":9,"template":false,"template_full_name":null,"purl":"pkg:github/jirutka/muacme","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jirutka%2Fmuacme","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jirutka%2Fmuacme/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jirutka%2Fmuacme/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jirutka%2Fmuacme/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jirutka","download_url":"https://codeload.github.com/jirutka/muacme/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jirutka%2Fmuacme/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":278672041,"owners_count":26025826,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-06T02:00:05.630Z","response_time":65,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["acme-client","letsencrypt","letsencrypt-cli","uacme"],"created_at":"2025-10-06T20:17:31.046Z","updated_at":"2025-10-06T20:17:32.752Z","avatar_url":"https://github.com/jirutka.png","language":"Shell","funding_links":[],"categories":[],"sub_categories":[],"readme":"= μacme\n:toc: macro\n:toc-title:\n// custom\n:proj-name: muacme\n:gh-name: jirutka/{proj-name}\n:version: 0.6.0\n:muacme-conf: link:muacme.conf[/etc/muacme/muacme.conf]\n\nThis a convenient wrapper for the ACMEv2 client https://github.com/ndilieto/uacme[uacme] that provides a ready-to-go solution for a cron-based periodic renewal of an arbitrary number of TLS certificates.\n\n\n[discrete]\n== Table of Contents\n\ntoc::[]\n\n\n== Requirements\n\n* https://github.com/ndilieto/uacme[uacme]\n* http://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html[POSIX-sh] compatible shell with `pipefail` (e.g. Busybox ash, ZSH, bash, …)\n* `grep`, `sed`, `tr`, `xargs` (BSD, Busybox or GNU)\n* `openssl` command (should work with OpenSSL and LibreSSL)\n\nhttpd-challenge-hook.sh:\n\n* `busybox httpd`\n* `start-stop-daemon` from OpenRC\n\nnsupdate-challenge-hook.sh:\n\n* `knsupdate` and `kdig` from Knot DNS tools or `nsupdate` and `dig` from BIND tools\n\nacmedns-challenge-hook.sh:\n\n* `kdig` from Knot DNS tools or `dig` from BIND tools\n* `wget` (tested with Busybox or GNU)\n\n\n== Installation\n\n=== On Alpine Linux\n\nInstall package {proj-name} from the Alpine’s community repository:\n\n[source, sh, subs=\"+attributes\"]\napk add {proj-name}\n# if you wanna use httpd-challenge-hook.sh:\napk add busybox-extras\n# if you wanna use nsupdate-challenge-hook.sh or acmedns-challenge-hook.sh:\napk add knot-utils\n\n\n=== From Tarball\n\n[source, sh, subs=\"+attributes\"]\nwget https://github.com/{gh-name}/archive/v{version}/{proj-name}-{version}.tar.gz\ntar -xzf {proj-name}-{version}.tar.gz\ncd {proj-name}-{version}\nmake install\n\n\n== Usage\n\nSee the help section in link:muacme#L3[muacme] (or run `muacme -h`) and comments in link:muacme.conf[].\n\nNote that you have to create an ACME account first (see https://ndilieto.github.io/uacme/uacme.html#_usage[uacme(1)] for more information):\n\n[source]\nuacme -v -c /etc/ssl/uacme new [EMAIL]\n\n\n== Examples\n\n* Issue a certificate for domain _example.org_ with alternative name _www.example.org_ (and using options specified in the configuration file {muacme-conf}):\n+\n[source, sh]\nmuacme issue example.org www.example.org\n\n* Issue a certificate for each domain listed in the given file (one per line with optional alternative names separated by a space) for which we don’t have one already.\nDomains for which we already have a certificate will be ignored.\n+\n[source,sh]\nmuacme issue -F domains.list\n\n* Renew all certificates that are close to their expiration:\n+\n[source, sh]\nmuacme renew all\n\n* Renew certificate for domain _example.org_ even if it’s too soon:\n+\n[source, sh]\nmuacme renew -f example.org\n\n* A renew hook for reloading nginx on a system using OpenRC:\n+\n[source, sh]\n#!/bin/sh\n/etc/init.d/nginx --ifstarted --quiet reload\n\n* A cron script _/etc/periodic/weekly/muacme-renew-all_:\n+\n[source, sh]\n#!/bin/sh\nexec muacme renew -l all\n\n\n== Challenge Hooks\n\n=== httpd (HTTP-01)\n\nlink:httpd-challenge-hook.sh[] is a hook script for the https://letsencrypt.org/docs/challenge-types/#http-01-challenge[HTTP-01 challenge] that automatically starts https://busybox.net[busybox] httpd server on port 80 to serve the key authorization for the challenge verification and stops it right after it’s done.\n\nThe complete process of renewal looks like this:\n\n. A cron job starts `muacme renew -l all`.\n. `muacme` invokes `uacme` for each certificate found in _/etc/ssl/uacme/_.\n. `uacme` checks the certificate expiration date; if it’s near expiration (parameter `days` in {muacme-conf}), uacme generates a CSR and creates a new order at Let’s Encrypt.\n. `uacme` executes link:httpd-challenge-hook.sh[] script that writes the validation file for Let’s Encrypt into a temporary directory and *starts a webserver* (`busybox httpd`) *on port 80* to serve this file.\n. Let’s Encrypt retrieves the validation file from `++http://\u003cdomain\u003e/.well-known/acme-challenge/\u003ctoken\u003e++`.\n. `uacme` retrieves the issued certificate from Let’s Encrypt.\n. `uacme` executes link:httpd-challenge-hook.sh[] script again to remove the verification file and *stop the webserver*.\n. `uacme` executes your link:renew-hook.sh[] script to reload services etc.\n\n\n=== nsupdate (DNS-01)\n\nlink:nsupdate-challenge-hook.sh[] is a hook script for https://letsencrypt.org/docs/challenge-types/#dns-01-challenge[DNS-01 challenge] that utilizes `knsupdate` (or `nsupdate`) to add/delete `_acme-challenge.\u003cdomain\u003e` TXT record for the requested domain name.\nThis script can be configured using {muacme-conf} or environment variables.\n\nIf you want to use `nsupdate` and `dig` instead of their Knot variants, you have to overwrite options `dns01_nsupdate` and `dns01_dig`.\n\n\n=== acmedns (DNS-01)\n\nlink:acmedns-challenge-hook.sh[] is a hook script for https://letsencrypt.org/docs/challenge-types/#dns-01-challenge[DNS-01 challenge] that calls REST API provided by the https://github.com/joohoi/acme-dns[acme-dns] server to add `_acme-challenge.\u003cdomain\u003e` TXT record for the requested domain name.\nThis script can be configured using {muacme-conf} or environment variables.\n\nBefore you can issue a certificate for a domain, you must do a registration on the acme-dns server and add the obtained subdomain, username and password to `/etc/muacme/acme-dns.keys`.\nThis can be easily done using the provided `muacme-acmedns` script, for example `muacme-acmedns register https://auth.acme-dns.io`.\n\nIf you want to use `dig` instead of its Knot variants, you have to overwrite option `dns01_dig`.\n\n\n== License\n\nThis project is licensed under http://opensource.org/licenses/MIT/[MIT License].\nFor the full text of the license, see the link:LICENSE[LICENSE] file.\n\n\n== See Also\n\n* https://ndilieto.github.io/uacme/[uacme(1)]\n* https://www.knot-dns.cz/docs/3.0/html/man_kdig.html[kdig(1)]\n* https://www.knot-dns.cz/docs/3.0/html/man_knsupdate.html[knsupdate(1)]\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjirutka%2Fmuacme","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjirutka%2Fmuacme","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjirutka%2Fmuacme/lists"}