Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
The cobbler's children have no shoes, or buildi...
Search
Sponsored
·
Your Podcast. Everywhere. Effortlessly.
Share. Educate. Inspire. Entertain. You do you. We'll handle the rest.
→
Alex Gaynor
May 30, 2016
Programming
1
280
The cobbler's children have no shoes, or building better tools for ourselves
As delivered at PyCon 2016 in Portland, OR.
Alex Gaynor
May 30, 2016
Tweet
Share
More Decks by Alex Gaynor
See All by Alex Gaynor
Quantifying Memory Unsafety and Reactions to It
alex
0
120
Learning from Failure: Post-mortems
alex
2
300
Techniques for Debugging Hard Problems
alex
1
620
Building Communities with Code Review
alex
4
320
Documenting Domain Specific Knowledge
alex
1
410
Pickles are for Delis, not for Software
alex
0
480
Code Review in Open Source Software
alex
4
790
Why Ruby isn't slow
alex
10
3.8k
PyPy + Swift
alex
2
550
Other Decks in Programming
See All in Programming
AI 駆動開発ライフサイクル(AI-DLC):ソフトウェアエンジニアリングの再構築 / AI-DLC Introduction
kanamasa
11
6.1k
Unicodeどうしてる? PHPから見たUnicode対応と他言語での対応についてのお伺い
youkidearitai
PRO
1
1k
CSC307 Lecture 03
javiergs
PRO
1
480
IFSによる形状設計/デモシーンの魅力 @ 慶應大学SFC
gam0022
1
280
大規模Cloud Native環境におけるFalcoの運用
owlinux1000
0
260
Oxlintはいいぞ
yug1224
5
1.2k
そのAIレビュー、レビューしてますか? / Are you reviewing those AI reviews?
rkaga
6
4.4k
AI前提で考えるiOSアプリのモダナイズ設計
yuukiw00w
0
220
16年目のピクシブ百科事典を支える最新の技術基盤 / The Modern Tech Stack Powering Pixiv Encyclopedia in its 16th Year
ahuglajbclajep
5
940
インターン生でもAuth0で認証基盤刷新が出来るのか
taku271
0
190
公共交通オープンデータ × モバイルUX 複雑な運行情報を 『直感』に変換する技術
tinykitten
PRO
0
200
開発者から情シスまで - 多様なユーザー層に届けるAPI提供戦略 / Postman API Night Okinawa 2026 Winter
tasshi
0
180
Featured
See All Featured
ReactJS: Keep Simple. Everything can be a component!
pedronauck
666
130k
The Mindset for Success: Future Career Progression
greggifford
PRO
0
230
VelocityConf: Rendering Performance Case Studies
addyosmani
333
24k
No one is an island. Learnings from fostering a developers community.
thoeni
21
3.6k
Designing Dashboards & Data Visualisations in Web Apps
destraynor
231
54k
Beyond borders and beyond the search box: How to win the global "messy middle" with AI-driven SEO
davidcarrasco
1
45
The Curse of the Amulet
leimatthew05
1
7.9k
Building a Modern Day E-commerce SEO Strategy
aleyda
45
8.6k
Easily Structure & Communicate Ideas using Wireframe
afnizarnur
194
17k
Measuring Dark Social's Impact On Conversion and Attribution
stephenakadiri
1
110
Marketing Yourself as an Engineer | Alaka | Gurzu
gurzu
0
120
Ruling the World: When Life Gets Gamed
codingconduct
0
130
Transcript
The cobbler's children have no shoes, or building better tools
for ourselves Alex Gaynor - PyCon 2016
About me • Director of the Python Software Foundation •
Open source contributor • Django, PyPy, CPython, pyca/cryptography, etc. • Washington, D.C. resident • Bagel and deli enthusiast • US Digital Service employee
A short history of tools
$ git init
None
Code review
Deployment automation
Emerging trends
CI for PRs
Linting (flake8, bandit, flake8-import-order, etc.)
Coverage Tracking
livegrep.com
github.com/facebook/mention-bot
Workflow
Build more tailored tools
Automation > Process
APIs!
Issues • Create an issue • Add/remove labels • Add
a comment • Assign to someone
Pull requests • Send a PR • Assign a PR
• Add/remove labels • Leave a code review • Add a commit status
Examples
$ pip install github3.py
import github3 gh_client = github3.login( os.environ["GITHUB_USERNAME"], os.environ["GITHUB_PASSWORD"], )
repo = gh_client.repository("django", "django")
HTTPS certificate expiration
def get_expiration_date(host): ssl_context = ssl.create_default_context() with closing(socket.socket(socket.AF_INET, socket.SOCK_STREAM)) as sock:
sock = ssl_context.wrap_socket(sock, server_hostname=host) sock.connect((host, 443)) expiration = ssl.cert_time_to_seconds(sock.getpeercert()["notAfter"]) return datetime.datetime.fromtimestamp(expiration)
while True: for host in MY_DOMAINS: expiration = get_expiration_date(host) if
expiration - datetime.datetime.now() < CUTOFF: file_an_issue(gh_client, host, expiration) time.sleep(3600)
def file_an_issue(gh_client, host, expiration): gh_client.create_issue( "django", "django", "Cert expiring soon:
{}".format(host), "The cert for `{}` expires on {}, get a new one!".format( host, expiration ), "alex", labels=["ssl-cert"] )
Auto-labeling
Web hooks
def github_webhook(request): event = request.headers.get("X-Github-Event") if event != "pull_request": return
Response(status=200) body = json.load(request.stream) if body.get("action") not in {"opened", "reopened", "synchronize"}: return Response(status=200)
issue = repo.issue(body["number"]) pr = repo.pull_request(issue.number) changed_files = (f.filename for
f in pr.iter_files()) if "django/utils/crypto.py" in changed_files: issue.add_labels("security")
Other ideas
requirements.txt bumper
UI change reviewer
Github Web hook UI Reviewer Comment Screenshots
Approval process commit status
Thanks! Questions? https://github.com/alex https://speakerdeck.com/alex