Save computed value #1407
-
Hi there, I just found out about the feature, that you can use I also thought of jinja_extensions or tasks but these all get executed after the copier-answers file is generated and therfore I can't somehow save my calculated value |
Beta Was this translation helpful? Give feedback.
Replies: 2 comments 5 replies
-
Sorry, this isn't clear to me. Can you show your |
Beta Was this translation helpful? Give feedback.
-
I found a workaround for my problem: copier.yaml project_type:
type: str
help: "PROJECT TYPE: Choose your project type"
choices:
Python Poetry: python_poetry
Docker image extension (extending a base image with additional features): docker_image_extension
Other: other
schedule:
type: json
help: "SCHEDULE: What is your update schedule?"
default: ["* * * * *"]
docker_username:
type: str
help: "DOCKER: Enter your docker username (leave blank if not used)"
default: schulzbot
docker_token:
when: "{% if docker_username %} true {% endif %}"
type: str
help: "DOCKER: Enter your docker token"
secret: true
placeholder: "dckr_pat_..."
validator: "{% if docker_token == '' %} Docker token can't be empty {% endif %}"
# ----- encryption -----
repo:
when: "{% if docker_token %} true {% endif %}"
type: str
help: "What is the owner and the name of this GitHub repo?"
default: ""
validator: "{% if not repo | regex_search('\\S+\\/\\S+')%} Repo must be of the format <owner>/<name> {% endif %}"
# ----- misc -----
_jinja_extensions:
- jinja2_workarounds.MultiLineInclude
- copier_templates_extensions.TemplateExtensionLoader
- copier/checks.py:Checks
- copier/context_updater.py:ContextUpdater
_exclude:
- "*"
- "!.github"
- "!renovate.json"
_tasks:
- "gh label create renovate -c 19D4A8 -d 'This pr got created by renovate' --force"
- "gh label create major -c 00FFFF -d 'Update of a major dependency' --force"
- "gh label create dev -c FFFFFF -d 'Update of a dev dependency' --force"
- "rm -r copier/ -f"
_answers_file: .copier-answers-renovate-template.yaml copier/context_updater.py from copier_templates_extensions import ContextHook
import subprocess
import json
from urllib.request import urlretrieve
import os
import json
from pathlib import Path
DOCKER_TOKEN_ENCRYPTED_FILE = Path("copier/docker_token_encrypted")
def renovate_encrypt(organization: str, repository: str, secret: str):
data = {
"o": f"{organization}",
"r": f"{repository}",
"v": f"{secret}"
}
urlretrieve("https://app.renovatebot.com/renovate.pgp", "renovate.pgp")
encrypted = subprocess.check_output(
["gpg", "--encrypt", "-a", "--recipient-file", "renovate.pgp"],
text=True,
input=json.dumps(data))
encrypted = encrypted.replace("\n", "")
encrypted = encrypted.removeprefix("-----BEGIN PGP MESSAGE-----")
encrypted = encrypted.removesuffix("-----END PGP MESSAGE-----")
os.remove("renovate.pgp")
return encrypted
class ContextUpdater(ContextHook):
update = False
def hook(self, context: dict):
organization, repository = context.get("repo").split("/")
docker_token = context["docker_token"]
if DOCKER_TOKEN_ENCRYPTED_FILE.exists():
with DOCKER_TOKEN_ENCRYPTED_FILE.open() as f:
docker_token_encrypted = f.read()
else:
docker_token_encrypted = ""
if context.get("docker_token_encrypted") and context.get("_copier_answers").get("docker_token_encrypted"):
return
if docker_token and not docker_token_encrypted:
docker_token_encrypted = renovate_encrypt(organization, repository, docker_token)
context["docker_token_encrypted"] = docker_token_encrypted
DOCKER_TOKEN_ENCRYPTED_FILE.parent.mkdir(parents=True, exist_ok=True)
with DOCKER_TOKEN_ENCRYPTED_FILE.open("w") as f:
f.write(docker_token_encrypted)
elif context.get("docker_token_encrypted") and not docker_token_encrypted:
docker_token_encrypted = context.get("docker_token_encrypted")
context["docker_token_encrypted"] = docker_token_encrypted
context["_copier_answers"]["docker_token_encrypted"] = docker_token_encrypted In the context updater I do the encrypting and what I found out is that you can add data to context._copier_answers, which will put the encrypted token in the answers file. This will then be available in the context on the next update. One problem is, that the context updater will get called multiple times. For that I will save the encrypted value in a file while rendering and cleaning it up with a task afterwards. That way I only generate the encrypted value only once. Maybe this discussion is also a bit related to #695 and I could use the solution there in my code or other way around. |
Beta Was this translation helpful? Give feedback.
I found a workaround for my problem:
copier.yaml