Skip to content

Commit

Permalink
♻️ Change makefile commands and update repository readme
Browse files Browse the repository at this point in the history
  • Loading branch information
jasonBirchall committed Jun 25, 2024
1 parent e6b1460 commit 3367021
Show file tree
Hide file tree
Showing 2 changed files with 196 additions and 91 deletions.
164 changes: 90 additions & 74 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,81 +1,97 @@
include defensive-domains/domains.mk

test: defensive-domains-validate defensive-domains-noop
.PHONY: test

all:
.PHONY: all
EDITOR ?= vim
CONFIG_FILE ?= config.yaml
ZONES_DIR ?= hostedzones

# Check for AWS credentials
AWS_ACCESS_KEY_ID ?= $(shell aws configure get aws_access_key_id)
AWS_SECRET_ACCESS_KEY ?= $(shell aws configure get aws_secret_access_key)

# Export AWS credentials
export AWS_ACCESS_KEY_ID
export AWS_SECRET_ACCESS_KEY

# Function to check if AWS credentials are set
define check_aws_creds
@if [ -z "$(AWS_ACCESS_KEY_ID)" ] || [ -z "$(AWS_SECRET_ACCESS_KEY)" ]; then \
echo "AWS credentials are not set. Please set AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY."; \
exit 1; \
fi
endef

.PHONY: help install edit-zone validate-zones sync-dry-run sync-apply list-zones dump-zone compare-zone clean

help:
@echo "Available commands:"
@echo " make help - Show this help message"
@echo " make install - Set up the Python environment"
@echo " make edit-zone zone=<zone> - Edit a hosted zone file"
@echo " make validate-zones - Validate all zone files"
@echo " make sync-dry-run - Perform a dry-run sync for all zones"
@echo " make sync-apply - Apply changes to all zones"
@echo " make list-zones - List all zones"
@echo " make dump-zone zone=<zone> - Dump the current live configuration for a zone"
@echo " make compare-zone zone=<zone> - Compare a zone file with its live configuration"
@echo " make clean - Clean up generated files"

install:
python3 -m venv venv
. venv/bin/activate
python3 -m pip install --upgrade pip
. venv/bin/activate && \
python3 -m pip install --upgrade pip && \
python3 -m pip install -r requirements.txt
.PHONY: install


# Defensive domain actions
# These all take the $DEFENSIVE_DOMAINS "array" (actually a
# whitespace-separated list of domains) and use Make's pattern
# substitution (https://www.gnu.org/software/make/manual/make.html#Text-Functions)
# to expand them into a list of config file paths.
#
# These config files are then prerequisites to be generated using the
# rules in "Defensive domain config", below

defensive-domains-validate: defensive-domains/config.yaml \
$(DEFENSIVE_DOMAINS:%=defensive-domains/config/%.yaml)
octodns-validate --config-file=$<
.PHONY: defensive-domains-validate

defensive-domains-noop: defensive-domains/config.yaml \
$(DEFENSIVE_DOMAINS:%=defensive-domains/config/%.yaml) \
defensive-domains-validate
octodns-sync --config-file=$<
.PHONY: defensive-domains-noop

defensive-domains-apply: defensive-domains/config.yaml \
$(DEFENSIVE_DOMAINS:%=defensive-domains/config/%.yaml) \
defensive-domains-validate
octodns-sync --config-file=$< --doit
.PHONY: defensive-domains-apply

defensive-domains-get-live-config: \
$(DEFENSIVE_DOMAINS:%=defensive-domains/live/%.yaml)
.PHONY: get-live-defensive-domain-config


# Defensive domain config
# defensive-domains/config/%.yaml and defensive-domains/live/%.yaml are
# Make pattern rules (https://www.gnu.org/software/make/manual/make.html#Pattern-Rules)
# meaning that they match any file path that fits that format (where % is
# a wildcard).
#
# We then use the $(<F) (first prerequisite's filename), $@ (target file),
# $(@D) (target file's directory) and $* (match stem) automatic variables
# (https://www.gnu.org/software/make/manual/make.html#Automatic-Variables)
# to generate only the required configs.

defensive-domains/config.yaml: defensive-domains/config.tmpl.yaml defensive-domains/domains.mk
@cat $< > $@
@echo " $(DEFENSIVE_DOMAINS:%=%.:\n sources:\n - config\n targets:\n - route53\n )" >> $@

defensive-domains/config/%.yaml: defensive-domains/dns.tmpl.yaml
@mkdir -p defensive-domains/config/
@ln -s ../$(<F) $@

defensive-domains/live/%.yaml: defensive-domains/config.yaml
octodns-dump \
--config-file=$< \
--output-dir=$(@D) \
$*. route53


# Cleanup
edit-zone:
@if [ -z "$(zone)" ]; then \
echo "Please specify a zone to edit. Usage: make edit-zone zone=example.com"; \
exit 1; \
fi
@if [ ! -f "$(ZONES_DIR)/$(zone).yaml" ]; then \
echo "Zone file for $(zone) not found. Creating a new file."; \
touch "$(ZONES_DIR)/$(zone).yaml"; \
fi
$(EDITOR) "$(ZONES_DIR)/$(zone).yaml"

validate-zones:
$(call check_aws_creds)
octodns-validate --config-file=$(CONFIG_FILE)

sync-dry-run:
$(call check_aws_creds)
octodns-sync --config-file=$(CONFIG_FILE)

sync-apply:
$(call check_aws_creds)
octodns-sync --config-file=$(CONFIG_FILE) --doit

list-zones:
@ls -1 $(ZONES_DIR)/*.yaml | sed 's/.*\///' | sed 's/\.yaml//'

dump-zone:
$(call check_aws_creds)
@if [ -z "$(zone)" ]; then \
echo "Please specify a zone to dump. Usage: make dump-zone zone=example.com"; \
exit 1; \
fi
octodns-dump --config-file=$(CONFIG_FILE) --output-dir=tmp $(zone). route53

compare-zone:
$(call check_aws_creds)
@if [ -z "$(zone)" ]; then \
echo "Please specify a zone to compare. Usage: make compare-zone zone=example.com"; \
exit 1; \
fi
@if [ ! -f "$(ZONES_DIR)/$(zone).yaml" ]; then \
echo "Zone file for $(zone) not found."; \
exit 1; \
fi
octodns-dump --config-file=$(CONFIG_FILE) --output-dir=tmp $(zone). route53
@echo "Differences between local and live configuration:"
@diff -u $(ZONES_DIR)/$(zone).yaml tmp/$(zone).yaml || true
@rm -f tmp/$(zone).yaml

clean:
@rm -rf \
defensive-domains/config.yaml \
defensive-domains/config/ \
defensive-domains/live/
.PHONY: clean
@rm -rf venv tmp
@find . -type f -name "*.pyc" -delete
@find . -type d -name "__pycache__" -delete

# Set help as the default target
.DEFAULT_GOAL := help
123 changes: 106 additions & 17 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# &#127760; MoJ DNS Management

[![repo standards badge](https://img.shields.io/endpoint?labelColor=231f20&color=005ea5&style=for-the-badge&label=MoJ%20Compliant&url=https%3A%2F%2Foperations-engineering-reports.cloud-platform.service.justice.gov.uk%2Fapi%2Fv2%2Fcompliant-repository%2Fdns&logo=data:image/png;base64,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)](https://operations-engineering-reports-prod.cloud-platform.service.justice.gov.uk/public-report/dns)
[![repo standards badge](https://img.shields.io/endpoint?labelColor=231f20&color=005ea5&style=for-the-badge&label=MoJ%20Compliant&url=https%3A%2F%2Foperations-engineering-reports.cloud-platform.service.justice.gov.uk%2Fapi%2Fv2%2Fcompliant-repository%2Fdns&logo=data:image/png;base64,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)](https://operations-engineering-reports-prod.cloud-platform.service.justice.gov.uk/public-report/dns)

This repository manages DNS records for the Ministry of Justice using [octoDNS](https://github.com/octodns/octodns). It provides a streamlined, code-based approach to DNS management, ensuring consistency and enabling version control for our DNS records.

Expand Down Expand Up @@ -30,11 +30,53 @@ This repository manages DNS records for the Ministry of Justice using [octoDNS](

## Making Changes

1. Clone this repository.
2. Create a new branch for your changes.
3. Edit the appropriate zone file in the `hostedzones/` directory.
4. Ensure changes are made in alphabetical order within the file.
5. Commit your changes and create a Pull Request.
1. Clone this repository:
```bash
git clone https://github.com/your-org/dns.git
cd dns
```

2. Install dependencies:
```bash
make install
```

3. Create a new branch for your changes:
```bash
git checkout -b your-branch-name
```

4. Edit the appropriate zone file:
```bash
make edit-zone zone=example.com
```
This will open the zone file in your default editor. If the file doesn't exist, it will be created.

5. Ensure changes are made in alphabetical order within the file.

6. Validate your changes:
```bash
make validate-zones
```

7. Perform a dry-run to see what changes would be made:
```bash
make sync-dry-run
```

8. If you want to compare your local changes with the live configuration:
```bash
make compare-zone zone=example.com
```

9. Commit your changes and create a Pull Request:
```bash
git add .
git commit -m "Your descriptive commit message"
git push origin your-branch-name
```

10. Create a Pull Request on GitHub.

Example of adding a new A record to `example.com.yaml`:

Expand All @@ -57,6 +99,16 @@ www:
value: example.com.
```
## Viewing Current Configuration
To view the current live configuration for a zone:
```bash
make dump-zone zone=example.com
```

This will dump the current Route53 configuration for `example.com` to a file in the `tmp/` directory.

## Configuration

The `config.yaml` file is set up dynamically to encompass all hosted zones in the mojdsd AWS account. We use the `lenient` option due to historical non-uniform record creation.
Expand All @@ -72,25 +124,62 @@ The AWS IAM user required for this DNS management system is not created or manag

This approach centralises our IAM user management and ensures that the DNS management system uses credentials that are consistently managed alongside our other operational resources.

## Requirements to Run Locally

- Python 3.x
- AWS IAM user with appropriate Route53 permissions

:warning: **Caution:** We strongly recommend you don't run `octodns-sync --doit` locally. Instead, use the CI/CD pipeline to apply changes.
## Makefile Commands

To install dependencies:
This repository includes a Makefile to simplify common operations. You can use the following commands:

```bash
pip install -r requirements.txt
make # Show help message with available commands
make help # Same as above, shows help message
make install # Set up the Python environment
make edit-zone zone=<zone> # Edit a hosted zone file
make validate-zones # Validate all zone files
make sync-dry-run # Perform a dry-run sync for all zones
make sync-apply # Apply changes to all zones
make list-zones # List all zones
make dump-zone zone=<zone> # Dump the current live configuration for a zone
make compare-zone zone=<zone> # Compare a zone file with its live configuration
make clean # Clean up generated files
```

And then run the following command to preview changes:
To see a full list of available commands and their descriptions, simply run `make` or `make help`.

## AWS Credentials

This project requires AWS credentials to interact with Route53. The Makefile will attempt to use AWS credentials from the following sources, in order:

1. Environment variables (`AWS_ACCESS_KEY_ID` and `AWS_SECRET_ACCESS_KEY`)
2. AWS CLI configuration

If neither of these sources provides valid credentials, commands that require AWS access will fail with an error message.

To set your AWS credentials, you can either:

1. Export them as environment variables:
```
export AWS_ACCESS_KEY_ID=your_access_key_id
export AWS_SECRET_ACCESS_KEY=your_secret_access_key
```

2. Configure them using the AWS CLI:
```
aws configure
```

Ensure your AWS credentials have the necessary permissions to manage Route53 hosted zones.

## Applying Changes

:warning: **Caution:** We strongly recommend you don't apply changes locally. Instead, use the CI/CD pipeline to apply changes.

If you need to apply changes locally (which should be done with extreme caution), you can use:

```bash
octodns-sync --config-file=./config.yaml
make sync-apply
```

This will apply all pending changes to Route53. Always perform a `make sync-dry-run` first to review the changes that will be made.

## License

This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.

0 comments on commit 3367021

Please sign in to comment.