-
-
Save foosel/ed46769d86dffeb41774302fc0610f57 to your computer and use it in GitHub Desktop.
OctoPrint devtool fabfile
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from __future__ import print_function, unicode_literals, absolute_import | |
from fabric.api import local, run, sudo, cd, prompt | |
from fabric.utils import abort | |
from fabric.state import env | |
from fabric.contrib import files | |
import datetime | |
import calendar | |
import sys | |
import os | |
import codecs | |
def env_from_yaml(path): | |
import yaml | |
with codecs.open(path, errors="replace") as f: | |
data = yaml.safe_load(f) | |
if not isinstance(data, dict): | |
abort("YAML file at {} doesn't contain a dictionary, can't use that for setting env") | |
for key, value in data.items(): | |
setattr(env, key, value) | |
env_from_yaml("./fabfile.yaml") | |
env.disable_known_hosts = True | |
env.no_keys = True | |
##~~ Patreon ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
def sticker_list(export, output=None): | |
now = datetime.date.today() | |
month = now.month - 1 | |
year = now.year | |
if month == 0: | |
month = 12 | |
year -= 1 | |
if output is None: | |
output = "stickers-{:04d}{:02d}.csv".format(year, month) | |
_, last_day = calendar.monthrange(year, month) | |
command = " ".join(["python patronexport.py", | |
"-i {export}", | |
"-t sticker-recipients.csv", | |
"-r 20", | |
"-r 19.10", | |
"-r 10", | |
"-r 9.35", | |
"--until {year:04d}-{month:02d}-{last_day:02d}", | |
"-m patron-mapping.yaml", | |
"-a patron-additional.yaml", | |
"-o {output}"]) | |
local(command.format(**locals())) | |
def supporter_list(export, output=None): | |
if output is None: | |
output = "../SUPPORTERS.md" | |
command = " ".join(["python patronexport.py", | |
"-i {export}", | |
"-t sponsors-template.md", | |
"-r 20", | |
"-r 19.10", | |
"-m patron-mapping.yaml", | |
"-a patron-additional.yaml", | |
"-o {output}"]) | |
local(command.format(**locals())) | |
##~~ Issues ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
def issue_list_export(output=None): | |
token = env.github_token | |
if output is None: | |
output = "issues.yaml" | |
command = " ".join(["python issuelist.py", | |
"--token {token}", | |
"--user foosel", | |
"--repo OctoPrint", | |
"--output {output}"]) | |
local(command.format(**locals())) | |
def issue_list_process(template=None, input=None, output=None): | |
if template is None: | |
template = "issues-template.csv" | |
if input is None: | |
input = "issues.yaml" | |
if output is None: | |
now = datetime.date.today() | |
output = "issues-{year:04d}{month:02d}{day:02d}.csv".format(year=now.year, month=now.month, day=now.day) | |
command = " ".join(["python issuelist.py", | |
"--input {input}", | |
"--template {template}", | |
"--output {output}"]) | |
local(command.format(**locals())) | |
def issue_list(): | |
issue_list_export() | |
issue_list_process() | |
##~~ Release testing ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
def sync_test_repo(force=False): | |
for branch in ("master", "maintenance", "staging/maintenance", "rc/maintenance", "devel", "rc/devel"): | |
local("git checkout {}".format(branch)) | |
if force: | |
local("git push --force releasetest {}".format(branch)) | |
else: | |
local("git push releasetest {}".format(branch)) | |
def test_rc_devel(tag): | |
tag_push_test_repo("rc/devel", tag) | |
def test_rc_maintenance(tag): | |
tag_push_test_repo("rc/maintenance", tag) | |
def test_stable(tag): | |
test_rc_maintenance(tag) | |
merge_push_test_repo("master", "rc/maintenance") | |
merge_push_test_repo("rc/devel", "rc/maintenance") | |
def tag_push_test_repo(push_branch, tag): | |
local("git checkout {}".format(push_branch)) | |
local("git push releasetest {}".format(push_branch)) | |
local("git tag {}".format(tag)) | |
local("git push --tags releasetest {}".format(tag)) | |
local("git tag -d {}".format(tag)) | |
def merge_tag_push_test_repo(push_branch, merge_branch, tag): | |
local("git checkout {}".format(push_branch)) | |
local("git merge {}".format(merge_branch)) | |
local("git push releasetest {}".format(push_branch)) | |
local("git tag {}".format(tag)) | |
local("git push --tags releasetest {}".format(tag)) | |
local("git tag -d {}".format(tag)) | |
def merge_push_test_repo(push_branch, merge_branch): | |
local("git checkout {}".format(push_branch)) | |
local("git merge {}".format(merge_branch)) | |
local("git push releasetest {}".format(push_branch)) | |
def test_prerelease_patch(tag, branch=b"rc/maintenance"): | |
test_patch(tag, branch, True) | |
def test_release_patch(tag, branch=b"rc/maintenance"): | |
test_patch(tag, branch, False) | |
def test_patch(tag, branch, prerelease): | |
now = datetime.datetime.utcnow().replace(microsecond=0).isoformat(b' ') | |
tag_name = b"{} (release candidate)" if prerelease else b"{} (stable)" | |
tag_name = tag_name.format(tag) | |
release = dict(draft=False, | |
html_url=b"https://github.com/foosel/OctoPrint/releases/tag/{}".format(tag), | |
name=tag_name, | |
prerelease=prerelease, | |
published_at=now, | |
tag_name=tag, | |
target_commitish=branch) | |
import json | |
commands = ['["set", "plugins.github_release_patcher.releases.foosel/OctoPrint", [{}]]'.format(json.dumps(release)), | |
'["set", "plugins.softwareupdate.checks.octoprint.pip", "{}/archive/{{target_version}}.zip"]'.format(env.releasetest_repo)] | |
print("Paste this into the YAML Patcher:") | |
print("--- 8< ---") | |
print("[{}]".format(", ".join(commands))) | |
print("--- 8< ---") | |
##~~ OctoPi ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
def octopi_networkconfig(mountpoint, ssid=None, psk=None): | |
if ssid is None: | |
ssid = env.wifi_ssid | |
if psk is None: | |
psk = env.wifi_psk | |
if sys.platform == "win32": | |
mountpoint += ":" | |
path_old = os.path.join(mountpoint, "octopi-network.txt") | |
if not os.path.exists(path_old): | |
abort("{} does not exist, {} doesn't look like an OctoPi /boot mountpoint".format(path_old, mountpoint)) | |
path_new = os.path.join(mountpoint, "octopi-wpa-supplicant.txt") | |
config_old = """ | |
iface wlan0-octopi inet manual | |
wpa-ssid "{ssid}" | |
wpa-psk "{psk}" | |
""" | |
config_new = """ | |
network={{ | |
ssid="{ssid}" | |
psk="{psk}" | |
}} | |
country=DE | |
ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev | |
update_config=1 | |
""" | |
import codecs | |
with codecs.open(path_old, errors="replace", mode="w") as f: | |
f.write(config_old.format(ssid=ssid, psk=psk)) | |
print("Wrote old network config to {}".format(path_old)) | |
with codecs.open(path_new, errors="replace", mode="w") as f: | |
f.write(config_new.format(ssid=ssid, psk=psk)) | |
print("Wrote new network config to {}".format(path_new)) | |
def octopi_hostname(mountpoint, name): | |
if sys.platform == "win32": | |
mountpoint += ":" | |
path = os.path.join(mountpoint, "octopi-hostname.txt") | |
import codecs | |
with codecs.open(path, errors="replace", mode="w") as f: | |
f.write(name) | |
print("Wrote hostname config to {}".format(path)) | |
def octopi_config(mountpoint, ssid=None, psk=None, name=None): | |
octopi_networkconfig(mountpoint, ssid=ssid, psk=psk) | |
if name is not None: | |
octopi_hostname(mountpoint, name) | |
def octopi_octoservice(command): | |
sudo("service octoprint {}".format(command)) | |
def octopi_standardrepo(): | |
run("cd ~/OctoPrint && git remote set-url origin https://github.com/foosel/OctoPrint") | |
def octopi_releasetestrepo(): | |
run("cd ~/OctoPrint && git remote set-url origin {}".format(env.releasetest_repo)) | |
def octopi_releasetestplugin_yaml_patcher(): | |
octopi_install("https://github.com/OctoPrint/OctoPrint-Yamlpatcher/archive/master.zip") | |
def octopi_releasetestplugin_github_release_patcher(): | |
run("cd ~/.octoprint/plugins && wget -Ogithub_release_patcher.py https://gist.githubusercontent.com/foosel/1e6e9c97acb7c2f36d4510ba69097c4d/raw/32e251e407336b1cd81a9d3942e739f354b2e037/github_release_patcher.py") | |
def octopi_releasetestplugins(): | |
octopi_releasetestplugin_yaml_patcher() | |
octopi_releasetestplugin_github_release_patcher() | |
def octopi_checkout(branch, committish=None): | |
if not files.exists("~/OctoPrint/.git"): | |
abort("No git checkout available") | |
with cd("~/OctoPrint"): | |
run("git fetch") | |
run("git checkout {}".format(branch)) | |
run("git pull") | |
if committish is not None: | |
run("git reset --hard {}".format(committish)) | |
run("~/oprint/bin/python setup.py clean && ~/oprint/bin/python setup.py install") | |
octopi_octoservice("restart") | |
def octopi_install(url): | |
run("~/oprint/bin/pip install {}".format(url)) | |
def octopi_tailoctolog(): | |
run("tail -f ~/.octoprint/logs/octoprint.log") | |
def octopi_test_simplecheckout(branch): | |
octopi_releasetestrepo() | |
octopi_checkout(branch) | |
def octopi_test_simplepip(tag): | |
url = "{}/archive/{}.zip".format(env.release_test_repo, tag) | |
octopi_install(url) | |
def octopi_test_update(tag, branch, prerelease): | |
prompt("Make sure you've done first time setup and updated to desired start version, then continue") | |
if files.exists("~/OctoPrint/.git"): | |
octopi_releasetestrepo() | |
octopi_releasetestplugins() | |
octopi_octoservice("restart") | |
# patch | |
test_patch(tag, branch, prerelease) | |
prompt("Enter above patch in YamlPatcher, then continue") | |
octopi_octoservice("restart") | |
octopi_tailoctolog() | |
def octopi_test_update_devel(tag, branch="rc/devel", prerelease=True): | |
octopi_test_update(tag, branch, prerelease) | |
def octopi_test_update_maintenance(tag, branch="rc/maintenance", prerelease=True): | |
octopi_test_update(tag, branch, prerelease) | |
def octopi_test_update_stable(tag, branch="master", prerelease=False): | |
octopi_test_update(tag, branch, prerelease) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#hosts: | |
# - pi@octopi.local | |
password: raspberry | |
releasetest_repo: https://... | |
patch_pip_url: false | |
wifi_ssid: MySSID | |
wifi_psk: MyPassword | |
github_token: my_token |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment