A config as infrastructure foundation for your Internal Developer Platform
Project description
Cally
A config as infrastructure foundation for your Internal Developer Platform
Why
To provide a powerful, but consisent configuration, and CLI to common Platform Engineering tasks
Features
- Multi layered configuration provided by Dyanconf
- Built-in testing harness
- Unit testing for your IaC
- Abstraction of the CDK for Terraform
- Build Terraform JSON, for consumption by OpenTofu or Terraform
Concepts
Cally isn't intended to be consumed directly, but rather as a dependency of your internal IDP tool.
Python Packaging
To give a consistent experience across your Developers/Engineers/CI/CD, packaging your tooling, and providers, should be vailable via your internal python registry.
Internal Registry options
This pyproject.toml
example from our minimal example, is enough to produce an empty stack, or run our hello world exampe command.
[build-system]
requires = ["setuptools"]
build-backend = "setuptools.build_meta"
[project]
name = "minimal-idp"
version = "0.1.0"
dependencies = ["cally"]
requires-python = ">=3.8"
authors = [
{name = "Example Org"},
]
description = "Example Cally Extension"
[tool.setuptools.packages.find]
include=["cally.*"]
[project.scripts]
minimal-idp = "cally.cli:cally"
[project.optional-dependencies]
test = [
"black",
"build",
"mypy",
"pytest",
"pytest-black",
"pytest-mypy",
"pytest-ruff<0.3", # 0.3 + 0.3.1 are currently not working
"ruff",
]
[tool.black]
skip-string-normalization = true
[tool.pytest.ini_options]
testpaths = "tests"
addopts = "-p no:cacheprovider --black --mypy --ruff"
filterwarnings = [
"ignore",
"default:::cally.*",
"default:::tests.*"
]
[tool.ruff]
preview = true
[tool.ruff.lint]
select = [
# flake8
"A", "ARG", "B", "BLE", "C4", "PIE", "RET", "SIM", "S",
"F", # pyflakes
"N", # pep8-nameing
"PL", # pylint
"E", # error
"W", # warning
"PTH", # pathlib
"RUF", # ruff
]
Project Structure
Cally relies heavily on Python namespacing, and expects a structure following this convention:
├── cally
│ └── idp
│ ├── commands
│ │ ├── example.py
│ │ └── __init__.py
│ ├── defaults.py
│ ├── __init__.py
│ ├── py.typed
│ ├── resources
│ │ ├── __init__.py
│ │ └── random.py
│ └── stacks
│ ├── __init__.py
│ └── pets.py
├── cally.yaml
├── pyproject.toml
├── README.md
└── tests
├── __init__.py
├── test_cli.py
├── testdata
│ └── random-pets.json
└── test_stacks.py
Configuration
Cally is built on top of Dynaconf, with an opinionated loader. This can of course be overriden, however the default is intended to provide a robust, but flexible interface. By default it will load a cally.yaml
in your current working directory, but is only necessary if you wish to pass configuration to your services.
Service
When configuring a service, you can pass in the service name via --service name
or via the environment variable CALLY_SERVICE
Environment
When configuring a service, you can pass in the service name via --environment name
or via the environment variable CALLY_ENVIRONMENT
Example cally.yaml
This is the expected layout of a cally.yaml
. The layers have a resolution order, from left to right, with the last winning. Objects are combined as per Dynaconf's merging strategy.
defaults:
provider:
random:
alias: foo
development:
provider:
random:
alias: bar
services:
test-service:
provider:
random:
alias: this-wins
stack_type: CallyStack
stack_vars:
example: variable
The output of test service would look like
$ cally config print-service --environment development --service test-service
ENVIRONMENT: development
NAME: test-service
PROVIDER:
random:
alias: this-wins
STACK_TYPE: CallyStack
STACK_VARS:
example: variabl
As a contrived example, this is what a tf print would output
{
"//": {
"metadata": {
"backend": "local",
"stackName": "test-service",
"version": "0.20.5"
},
"outputs": {
}
},
"terraform": {
"backend": {
"local": {
"path": "state/development/test-service"
}
}
}
}
Defaults
The cally loader will attempt to load your projects defaults, from the DEFAULTS
key, from the defaults namespace in your project.
From the earlier example project layout, a defaults.py
with the following contents
DEFAULTS = {
"providers": {
'random': {
'alias': 'minimal'
}
}
}
Would result in the random provider being configured with an alias default of minimal
Notes
This project is still in its early stages, documentation will be the next focal point, along with any bugs/oversights not found during early development.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
File details
Details for the file cally-0.5.0.tar.gz
.
File metadata
- Download URL: cally-0.5.0.tar.gz
- Upload date:
- Size: 30.9 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/5.1.1 CPython/3.12.7
File hashes
Algorithm | Hash digest | |
---|---|---|
SHA256 | d55df7f6b253ccc5a46c818cda66d1d705462c49820409eccb74a6a3d66e2250 |
|
MD5 | f7017a0f27a18c88e39c1dbadaf2f46b |
|
BLAKE2b-256 | 4e0d617805f95a88b91f861374d8ddb2cf3537afa940c6fc2aab8175975b81b7 |
Provenance
The following attestation bundles were made for cally-0.5.0.tar.gz
:
Publisher:
release-cally.yaml
on CallyCo-io/Cally
-
Statement type:
https://in-toto.io/Statement/v1
- Predicate type:
https://docs.pypi.org/attestations/publish/v1
- Subject name:
cally-0.5.0.tar.gz
- Subject digest:
d55df7f6b253ccc5a46c818cda66d1d705462c49820409eccb74a6a3d66e2250
- Sigstore transparency entry: 147172291
- Sigstore integration time:
- Predicate type:
File details
Details for the file cally-0.5.0-py3-none-any.whl
.
File metadata
- Download URL: cally-0.5.0-py3-none-any.whl
- Upload date:
- Size: 33.4 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/5.1.1 CPython/3.12.7
File hashes
Algorithm | Hash digest | |
---|---|---|
SHA256 | afe495bb9503a76a6b58c31f0c563f04f5c6a718875c74e7f32886dfd35b28ad |
|
MD5 | 6a5b46bcca7d93b16953d7604edac48e |
|
BLAKE2b-256 | 002705098aa35364d6a0ac5b02ebfae6448a6e04f992855c3ae914ae963a69a3 |
Provenance
The following attestation bundles were made for cally-0.5.0-py3-none-any.whl
:
Publisher:
release-cally.yaml
on CallyCo-io/Cally
-
Statement type:
https://in-toto.io/Statement/v1
- Predicate type:
https://docs.pypi.org/attestations/publish/v1
- Subject name:
cally-0.5.0-py3-none-any.whl
- Subject digest:
afe495bb9503a76a6b58c31f0c563f04f5c6a718875c74e7f32886dfd35b28ad
- Sigstore transparency entry: 147172293
- Sigstore integration time:
- Predicate type: