SlideShare a Scribd company logo
Functional Operations
Functional Programming @ Comcast Labs Connect
Susan Potter (@SusanPotter)
2018-03-09 Fri
Functional Operations (Functional Programming at Comcast Labs Connect)
Un-Fun Ops
0
Core InfraEng Problems
1
Core InfraEng Problems
• non-repeatable environments
• unpredictable machine rollback
• out-of-band updating of CI dependencies
• lack of muti-node integration testing
1
Causes
2
Causes
• no single source of truth
• partial definitions yield inconsistencies (over time)
• shared mutable state (file manipulation most Linux/UNIX distros)
2
Nix: Reliable Packaging
Nix: What is it?
3
Nix: What is it?
• "The Purely Functional Package Manager" (https://nixos.org/nix)
3
Nix: What is it?
• "The Purely Functional Package Manager" (https://nixos.org/nix)
• (And lazily evaluated expression language)
3
Nix: Source Example
This Nix lambda denotes the hello package
# Named keyword arguments: all non -optional
{ stdenv , fetchurl , perl }: let
version = "2.10";
in stdenv.mkDerivation {
inherit perl;
name = "hello -${version}";
builder = ./builder.sh;
src = fetchurl {
url = "mirror://gnu/hello/${name}.tar.gz";
sha256 = "0ssi1wpaf7plaswqqjw...l7c9lng89ndq1i";
};
}
4
Nix: Derivation drvPath
Inspecting hello package drvPath
$ nix -repl ’<nixpkgs >’
nix -repl > hello.drvPath
"/nix/store /3mdx...-hello -2.10. drv"
nix -repl > hello.outPath
"/nix/store/kmwd ...-hello -2.10"
nix -repl > :q
$ stat -t /nix/store /3mdx...-hello -2.10. drv
/nix/store /3mdx...-hello -2.10. drv 1219 8 8124 0 0 fe00 13940452 ...
5
Nix: Package outPath
Lazy evaluation means we only build the packages we need
$ stat -t /nix/store/kmwd ...-hello -2.10
stat: cannot stat ’/nix/store/kmwd ...-hello -2.10 ’: No such file or ...
To evaluate or realize the package we nix build
$ nix build nixpkgs.hello
[1 copied (0.2 MiB), 0.0 MiB DL]
Now we can see the hello package outPath in the Nix store
$ stat -t /nix/store/kmwd ...-hello -2.10
/nix/store/kmwd ...-hello -2.10 4096 8 416d 0 0 fe00 14115111 4 0 0 ...
6
Nix: Package outPath
The high-level layout of the hello.outPath
$ tree --du -hugFDL 2 /nix/store/kmwd ...-hello -2.10
/nix/store/ kmwd1hq55akdb9sc7l3finr175dajlby -hello -2.10
|-- [root root 33K Dec 31 1969] bin/
| |-- [root root 29K Dec 31 1969] hello*
|-- [root root 16K Dec 31 1969] share/
|-- [root root 4.0K Dec 31 1969] info/
|-- [root root 4.0K Dec 31 1969] locale/
|-- [root root 4.0K Dec 31 1969] man/
53K used in 5 directories , 1 file
7
Nix: Package in user profile
Since it is built, surely we can run the binary? (No, not yet)
$ hello
The program ’hello ’ is currently not installed. It is provided by ...
To link into the user profile we install ("Look Ma, no hands/sudo")
$ nix -env -iA nixos.hello
installing ’hello -2.10 ’
building ’/nix/store /6 s28kd3hdnv5cpd ...1yi5 -user -environment.drv ’...
created 6852 symlinks in user environment
$ hello -v
hello (GNU Hello) 2.10
8
Nix: Properties
9
Nix: Properties
• Lazily evaluated
• Nix store is immutable!
• nixpkgs is an expression: snapshot of community pkgs plus overlayed packages
9
Nix: Properties
• Lazily evaluated
• Nix store is immutable!
• nixpkgs is an expression: snapshot of community pkgs plus overlayed packages
• When packages sandboxed:
• chroot -ed
• private /proc
• disabled network/IPC/etc
• no env var inheritance
9
Nix: Properties
• Lazily evaluated
• Nix store is immutable!
• nixpkgs is an expression: snapshot of community pkgs plus overlayed packages
• When packages sandboxed:
• chroot -ed
• private /proc
• disabled network/IPC/etc
• no env var inheritance
• Same inputs and src and definition yields same result (outPath and content)
• Different inputs or src or definition yields different result (outPath and/or
content)
• Equational reasoning allows binary substitution
9
Nix Shell: Consistent Envs
nix-shell: Getting started
• CI scripts can use nix-shell as shebang
#!/usr/bin/env nix -shell
#!nix -shell -p python27Full python27Packages .boto3
#!nix -shell -I /path/to/pinned/nixpkgs
#!nix -shell -i python
import boto3
ec2 = boto3.client(’ec2’)
response = ec2. describe_instances ()
print(response)
Note: Approach requires Nix/NixOS installed on builders
10
nix-shell: Running (first time)
$ chmod u+x boto.py
$ ./ boto.py
these paths will be fetched (7.70 MiB download , 45.59 MiB unpacked ):
/nix/store/mj8vmgxff9m ...-python -2.7.14
/nix/store/q6js3yms8xd ...-tix -8.4.3
/nix/store/yqgj43ancc0 ...- python2 .7-boto3 -1.4.8
copying path ’/nix/store/yqg...- python2 .7-boto3 -1.4.8 ’ from ’https :// cache.n
copying path ’/nix/store/q6j...-tix -8.4.3 ’ from ’https :// cache.nixos.org ’...
copying path ’/nix/store/mj8...-python -2.7.14 ’ from ’https :// cache.nixos.org
OUTPUT HERE
11
nix-shell: Running (subsequent times)
$ ./ boto.py
OUTPUT HERE
12
Nix Shell: Recap
• Claim: we can get consistent environment, assuming:
• our core Nix expression pins version of nixpkgs
• devs reload shell at the git revisions to pick up dependency changes
• CI server runs tests using shell.nix referenced by nix-shell at that revision
• infrastructure for all environments is built using pinned Nix expression
• devenv, CI, production-like system builds share the same core expression
13
NixOS
What is NixOS?
• "The Purely Functional Linux Distribution" (https://nixos.org/)
• Provides congruent system-level configuration
• System-level rollbacks
14
NixOS: Example (nginx)
# ./machines/nginx.nix
{ pkgs , ... }:
{ boot.kernelPackages = pkgs.linuxPackages_4_15;
time.timeZone = "UTC";
services.nginx = {
enable = true;
virtualHosts."my.domain.tld" = {
forceSSL = true;
enableACME = true;
locations."/assets".root = "/var/www/assets";
locations."/".proxyPass = "http://backend -lb:3000";
};
};
} 15
NixOS: Example (Scala microservice)
# ./machines/scala -services.nix
{ pkgs , ... }: let
inherit (builtins) listToAttrs map;
inherit (pkgs.myorg) scalaServices mulib;
in {
# Interal custom myorg module; overlayed into pkgs
myorg.defaults.enable = true;
users.extraUsers = map mulib.mkSystemUser scalaServices;
systemd.services = map mulib.mkServiceUnit scalaServices;
}
16
NixOS: Example (memcached)
# ./machines/memcached.nix
{ config , pkgs , ... }:
{
services.memcached.enable = true;
services.memcached.maxConnections = 2048;
services.memcached.maxMemory = 256;
services.memcached.listen =
config.networking.eth1.ipAddress;
}
17
NixOS: Containers (composition)
{ config , pkgs , ... }:
{
containers.cache.config = import ./memcached.nix;
containers.proxy.config = import ./nginx.nix;
containers.services = {
config = import ./scala -services.nix;
bindMounts."/webapp" = {
hostPath = pkgs.myorg.scalaServices.webapp.outPath;
isReadOnly = true;
};
};
}
18
NixOS: Multi-node testing (node setup)
import ./make -test.nix ({ pkgs , lib , ... }:
let
kafkaPackage = pkgs.apacheKafka_1_0;
in {
name = "kafka -1.0";
nodes = {
zookeeper = import ./machines/zookeeper.nix;
kafka = import ./machines/kafka.nix;
};
testScript = import ./tests/kafka.nix {
package = kafkaPackage;
util = pkgs.myorg.testing.util;
};
}) 19
NixOS: Multi-node testing (test script)
{ pkg , kPort ? 9092 , zkPort ? 2181 , topic ? "test" , util }:
let
inherit (util) createTopicCmd producerPipe consumerPipe;
in ’’
startAll;
$zookeeper ->waitForUnit("zookeeper");
$zookeeper ->waitForOpenPort(${zkPort});
$kafka ->waitForUnit("apache -kafka");
$kafka ->waitForOpenPort(${kPort});
$kafka ->waitUntilSucceeds("${createTopicCmd}");
$kafka ->mustSucceed("echo ’test 1’ | ${producerPipe}");
$kafka ->mustSucceed("${consumerPipe} | grep ’test 1 ’");
’’
20
NixOS & nixpkgs: Properties
• modular (See nixpkgs overlays)
• extensible (see nixos modules)
• everything (almost) is a package in the Nix store
• system rollbacks (with system profile snapshots saved as generations)
• builds on purity of Nix packaging
• NO FHS mutation-in-place (links into FHS to immutable Nix store)
21
Reliability
Reliable Software
"Those who want really reliable software will discover that they must find means
of avoiding the majority of bugs to start with, and as a result the programming
process will become cheaper." – EWD
22
Why do properties/laws matter?
23
Why do properties/laws matter?
• Because it allows us humble programmers to:
23
Why do properties/laws matter?
• Because it allows us humble programmers to:
• compose our reasoning
• know what we cannot reason about
• break down big problems into smaller parts
• accomplish the same result with less effort
23
Questions?
@SusanPotter (heckle me, ask me questions)
24

More Related Content

PDF
From Zero to Application Delivery with NixOS
PDF
Dynamo: Not Just For Datastores
PDF
Ricon/West 2013: Adventures with Riak Pipe
PDF
From Zero To Production (NixOS, Erlang) @ Erlang Factory SF 2016
PDF
Hopping in clouds: a tale of migration from one cloud provider to another
PDF
Using ngx_lua in UPYUN
PDF
Lua tech talk
PDF
From Zero to Application Delivery with NixOS
Dynamo: Not Just For Datastores
Ricon/West 2013: Adventures with Riak Pipe
From Zero To Production (NixOS, Erlang) @ Erlang Factory SF 2016
Hopping in clouds: a tale of migration from one cloud provider to another
Using ngx_lua in UPYUN
Lua tech talk

What's hot (20)

PDF
BDD - Buzzword Driven Development - Build the next cool app for fun and for.....
PDF
Testing your infrastructure with litmus
PDF
Roll Your Own API Management Platform with nginx and Lua
PDF
RestMQ - HTTP/Redis based Message Queue
PPTX
The Art of Exploiting Unconventional Use-after-free Bugs in Android Kernel by...
PPTX
Discovering OpenBSD on AWS
PDF
Securing Prometheus exporters using HashiCorp Vault
PDF
Web scale infrastructures with kubernetes and flannel
PDF
Building Distributed System with Celery on Docker Swarm - PyCon JP 2016
PDF
Ansible not only for Dummies
PDF
Redis as a message queue
PDF
Coroutines for Kotlin Multiplatform in Practise
PPTX
[오픈소스컨설팅] Linux Network Troubleshooting
PPTX
Behind modern concurrency primitives
PPTX
All you need to know about the JavaScript event loop
PDF
Devinsampa nginx-scripting
PDF
Puppet and the HashiStack
PDF
Event loop
PDF
Bootstrapping multidc observability stack
BDD - Buzzword Driven Development - Build the next cool app for fun and for.....
Testing your infrastructure with litmus
Roll Your Own API Management Platform with nginx and Lua
RestMQ - HTTP/Redis based Message Queue
The Art of Exploiting Unconventional Use-after-free Bugs in Android Kernel by...
Discovering OpenBSD on AWS
Securing Prometheus exporters using HashiCorp Vault
Web scale infrastructures with kubernetes and flannel
Building Distributed System with Celery on Docker Swarm - PyCon JP 2016
Ansible not only for Dummies
Redis as a message queue
Coroutines for Kotlin Multiplatform in Practise
[오픈소스컨설팅] Linux Network Troubleshooting
Behind modern concurrency primitives
All you need to know about the JavaScript event loop
Devinsampa nginx-scripting
Puppet and the HashiStack
Event loop
Bootstrapping multidc observability stack
Ad

Similar to Functional Operations (Functional Programming at Comcast Labs Connect) (20)

PDF
Mininet Basics
PDF
Dependencies Managers in C/C++. Using stdcpp 2014
PDF
Nix for Python developers
PDF
Puppet at Opera Sofware - PuppetCamp Oslo 2013
PDF
Binary Packaging for HPC with Spack
PDF
Package Management via Spack on SJTU π Supercomputer
PDF
9 steps to install and configure postgre sql from source on linux
PPTX
2012 coscup - Build your PHP application on Heroku
PDF
containerit at useR!2017 conference, Brussels
PDF
[EXTENDED] Ceph, Docker, Heroku Slugs, CoreOS and Deis Overview
PDF
DPDK in Containers Hands-on Lab
PDF
Automating complex infrastructures with Puppet
PDF
Nix: What even is it though?
PDF
Sandboxing WebKitGTK (GUADEC 2019)
ZIP
Embedded Linux Odp
PPTX
Why favour Icinga over Nagios - Rootconf 2015
PDF
Inside Docker for Fedora20/RHEL7
PDF
Automating Mendix application deployments with Nix
PDF
Docker containers : introduction
ODP
LSA2 - 02 Namespaces
Mininet Basics
Dependencies Managers in C/C++. Using stdcpp 2014
Nix for Python developers
Puppet at Opera Sofware - PuppetCamp Oslo 2013
Binary Packaging for HPC with Spack
Package Management via Spack on SJTU π Supercomputer
9 steps to install and configure postgre sql from source on linux
2012 coscup - Build your PHP application on Heroku
containerit at useR!2017 conference, Brussels
[EXTENDED] Ceph, Docker, Heroku Slugs, CoreOS and Deis Overview
DPDK in Containers Hands-on Lab
Automating complex infrastructures with Puppet
Nix: What even is it though?
Sandboxing WebKitGTK (GUADEC 2019)
Embedded Linux Odp
Why favour Icinga over Nagios - Rootconf 2015
Inside Docker for Fedora20/RHEL7
Automating Mendix application deployments with Nix
Docker containers : introduction
LSA2 - 02 Namespaces
Ad

More from Susan Potter (13)

PDF
Thinking in Properties
PDF
Champaign-Urbana Javascript Meetup Talk (Jan 2020)
PDF
From Zero to Haskell: Lessons Learned
PDF
Dynamically scaling a political news and activism hub (up to 5x the traffic i...
PDF
Scalaz By Example (An IO Taster) -- PDXScala Meetup Jan 2014
PDF
Functional Algebra: Monoids Applied
PDF
Why Haskell
PDF
Distributed Developer Workflows using Git
PDF
Link Walking with Riak
PDF
Writing Bullet-Proof Javascript: By Using CoffeeScript
PDF
Twitter4R OAuth
PDF
Deploying distributed software services to the cloud without breaking a sweat
PDF
Designing for Concurrency
Thinking in Properties
Champaign-Urbana Javascript Meetup Talk (Jan 2020)
From Zero to Haskell: Lessons Learned
Dynamically scaling a political news and activism hub (up to 5x the traffic i...
Scalaz By Example (An IO Taster) -- PDXScala Meetup Jan 2014
Functional Algebra: Monoids Applied
Why Haskell
Distributed Developer Workflows using Git
Link Walking with Riak
Writing Bullet-Proof Javascript: By Using CoffeeScript
Twitter4R OAuth
Deploying distributed software services to the cloud without breaking a sweat
Designing for Concurrency

Recently uploaded (20)

PDF
2025 Textile ERP Trends: SAP, Odoo & Oracle
PDF
Navsoft: AI-Powered Business Solutions & Custom Software Development
PDF
Which alternative to Crystal Reports is best for small or large businesses.pdf
PPTX
Agentic AI Use Case- Contract Lifecycle Management (CLM).pptx
PPTX
ManageIQ - Sprint 268 Review - Slide Deck
PDF
How Creative Agencies Leverage Project Management Software.pdf
PPTX
Operating system designcfffgfgggggggvggggggggg
PPTX
CHAPTER 2 - PM Management and IT Context
PDF
Claude Code: Everyone is a 10x Developer - A Comprehensive AI-Powered CLI Tool
PDF
AI in Product Development-omnex systems
PDF
How to Choose the Right IT Partner for Your Business in Malaysia
PDF
Design an Analysis of Algorithms II-SECS-1021-03
PPT
Introduction Database Management System for Course Database
PDF
Internet Downloader Manager (IDM) Crack 6.42 Build 41
PDF
Internet Downloader Manager (IDM) Crack 6.42 Build 42 Updates Latest 2025
PDF
Upgrade and Innovation Strategies for SAP ERP Customers
PDF
Addressing The Cult of Project Management Tools-Why Disconnected Work is Hold...
PDF
Raksha Bandhan Grocery Pricing Trends in India 2025.pdf
PDF
Flood Susceptibility Mapping Using Image-Based 2D-CNN Deep Learnin. Overview ...
PDF
Wondershare Filmora 15 Crack With Activation Key [2025
2025 Textile ERP Trends: SAP, Odoo & Oracle
Navsoft: AI-Powered Business Solutions & Custom Software Development
Which alternative to Crystal Reports is best for small or large businesses.pdf
Agentic AI Use Case- Contract Lifecycle Management (CLM).pptx
ManageIQ - Sprint 268 Review - Slide Deck
How Creative Agencies Leverage Project Management Software.pdf
Operating system designcfffgfgggggggvggggggggg
CHAPTER 2 - PM Management and IT Context
Claude Code: Everyone is a 10x Developer - A Comprehensive AI-Powered CLI Tool
AI in Product Development-omnex systems
How to Choose the Right IT Partner for Your Business in Malaysia
Design an Analysis of Algorithms II-SECS-1021-03
Introduction Database Management System for Course Database
Internet Downloader Manager (IDM) Crack 6.42 Build 41
Internet Downloader Manager (IDM) Crack 6.42 Build 42 Updates Latest 2025
Upgrade and Innovation Strategies for SAP ERP Customers
Addressing The Cult of Project Management Tools-Why Disconnected Work is Hold...
Raksha Bandhan Grocery Pricing Trends in India 2025.pdf
Flood Susceptibility Mapping Using Image-Based 2D-CNN Deep Learnin. Overview ...
Wondershare Filmora 15 Crack With Activation Key [2025

Functional Operations (Functional Programming at Comcast Labs Connect)

  • 1. Functional Operations Functional Programming @ Comcast Labs Connect Susan Potter (@SusanPotter) 2018-03-09 Fri
  • 5. Core InfraEng Problems • non-repeatable environments • unpredictable machine rollback • out-of-band updating of CI dependencies • lack of muti-node integration testing 1
  • 7. Causes • no single source of truth • partial definitions yield inconsistencies (over time) • shared mutable state (file manipulation most Linux/UNIX distros) 2
  • 9. Nix: What is it? 3
  • 10. Nix: What is it? • "The Purely Functional Package Manager" (https://nixos.org/nix) 3
  • 11. Nix: What is it? • "The Purely Functional Package Manager" (https://nixos.org/nix) • (And lazily evaluated expression language) 3
  • 12. Nix: Source Example This Nix lambda denotes the hello package # Named keyword arguments: all non -optional { stdenv , fetchurl , perl }: let version = "2.10"; in stdenv.mkDerivation { inherit perl; name = "hello -${version}"; builder = ./builder.sh; src = fetchurl { url = "mirror://gnu/hello/${name}.tar.gz"; sha256 = "0ssi1wpaf7plaswqqjw...l7c9lng89ndq1i"; }; } 4
  • 13. Nix: Derivation drvPath Inspecting hello package drvPath $ nix -repl ’<nixpkgs >’ nix -repl > hello.drvPath "/nix/store /3mdx...-hello -2.10. drv" nix -repl > hello.outPath "/nix/store/kmwd ...-hello -2.10" nix -repl > :q $ stat -t /nix/store /3mdx...-hello -2.10. drv /nix/store /3mdx...-hello -2.10. drv 1219 8 8124 0 0 fe00 13940452 ... 5
  • 14. Nix: Package outPath Lazy evaluation means we only build the packages we need $ stat -t /nix/store/kmwd ...-hello -2.10 stat: cannot stat ’/nix/store/kmwd ...-hello -2.10 ’: No such file or ... To evaluate or realize the package we nix build $ nix build nixpkgs.hello [1 copied (0.2 MiB), 0.0 MiB DL] Now we can see the hello package outPath in the Nix store $ stat -t /nix/store/kmwd ...-hello -2.10 /nix/store/kmwd ...-hello -2.10 4096 8 416d 0 0 fe00 14115111 4 0 0 ... 6
  • 15. Nix: Package outPath The high-level layout of the hello.outPath $ tree --du -hugFDL 2 /nix/store/kmwd ...-hello -2.10 /nix/store/ kmwd1hq55akdb9sc7l3finr175dajlby -hello -2.10 |-- [root root 33K Dec 31 1969] bin/ | |-- [root root 29K Dec 31 1969] hello* |-- [root root 16K Dec 31 1969] share/ |-- [root root 4.0K Dec 31 1969] info/ |-- [root root 4.0K Dec 31 1969] locale/ |-- [root root 4.0K Dec 31 1969] man/ 53K used in 5 directories , 1 file 7
  • 16. Nix: Package in user profile Since it is built, surely we can run the binary? (No, not yet) $ hello The program ’hello ’ is currently not installed. It is provided by ... To link into the user profile we install ("Look Ma, no hands/sudo") $ nix -env -iA nixos.hello installing ’hello -2.10 ’ building ’/nix/store /6 s28kd3hdnv5cpd ...1yi5 -user -environment.drv ’... created 6852 symlinks in user environment $ hello -v hello (GNU Hello) 2.10 8
  • 18. Nix: Properties • Lazily evaluated • Nix store is immutable! • nixpkgs is an expression: snapshot of community pkgs plus overlayed packages 9
  • 19. Nix: Properties • Lazily evaluated • Nix store is immutable! • nixpkgs is an expression: snapshot of community pkgs plus overlayed packages • When packages sandboxed: • chroot -ed • private /proc • disabled network/IPC/etc • no env var inheritance 9
  • 20. Nix: Properties • Lazily evaluated • Nix store is immutable! • nixpkgs is an expression: snapshot of community pkgs plus overlayed packages • When packages sandboxed: • chroot -ed • private /proc • disabled network/IPC/etc • no env var inheritance • Same inputs and src and definition yields same result (outPath and content) • Different inputs or src or definition yields different result (outPath and/or content) • Equational reasoning allows binary substitution 9
  • 22. nix-shell: Getting started • CI scripts can use nix-shell as shebang #!/usr/bin/env nix -shell #!nix -shell -p python27Full python27Packages .boto3 #!nix -shell -I /path/to/pinned/nixpkgs #!nix -shell -i python import boto3 ec2 = boto3.client(’ec2’) response = ec2. describe_instances () print(response) Note: Approach requires Nix/NixOS installed on builders 10
  • 23. nix-shell: Running (first time) $ chmod u+x boto.py $ ./ boto.py these paths will be fetched (7.70 MiB download , 45.59 MiB unpacked ): /nix/store/mj8vmgxff9m ...-python -2.7.14 /nix/store/q6js3yms8xd ...-tix -8.4.3 /nix/store/yqgj43ancc0 ...- python2 .7-boto3 -1.4.8 copying path ’/nix/store/yqg...- python2 .7-boto3 -1.4.8 ’ from ’https :// cache.n copying path ’/nix/store/q6j...-tix -8.4.3 ’ from ’https :// cache.nixos.org ’... copying path ’/nix/store/mj8...-python -2.7.14 ’ from ’https :// cache.nixos.org OUTPUT HERE 11
  • 24. nix-shell: Running (subsequent times) $ ./ boto.py OUTPUT HERE 12
  • 25. Nix Shell: Recap • Claim: we can get consistent environment, assuming: • our core Nix expression pins version of nixpkgs • devs reload shell at the git revisions to pick up dependency changes • CI server runs tests using shell.nix referenced by nix-shell at that revision • infrastructure for all environments is built using pinned Nix expression • devenv, CI, production-like system builds share the same core expression 13
  • 26. NixOS
  • 27. What is NixOS? • "The Purely Functional Linux Distribution" (https://nixos.org/) • Provides congruent system-level configuration • System-level rollbacks 14
  • 28. NixOS: Example (nginx) # ./machines/nginx.nix { pkgs , ... }: { boot.kernelPackages = pkgs.linuxPackages_4_15; time.timeZone = "UTC"; services.nginx = { enable = true; virtualHosts."my.domain.tld" = { forceSSL = true; enableACME = true; locations."/assets".root = "/var/www/assets"; locations."/".proxyPass = "http://backend -lb:3000"; }; }; } 15
  • 29. NixOS: Example (Scala microservice) # ./machines/scala -services.nix { pkgs , ... }: let inherit (builtins) listToAttrs map; inherit (pkgs.myorg) scalaServices mulib; in { # Interal custom myorg module; overlayed into pkgs myorg.defaults.enable = true; users.extraUsers = map mulib.mkSystemUser scalaServices; systemd.services = map mulib.mkServiceUnit scalaServices; } 16
  • 30. NixOS: Example (memcached) # ./machines/memcached.nix { config , pkgs , ... }: { services.memcached.enable = true; services.memcached.maxConnections = 2048; services.memcached.maxMemory = 256; services.memcached.listen = config.networking.eth1.ipAddress; } 17
  • 31. NixOS: Containers (composition) { config , pkgs , ... }: { containers.cache.config = import ./memcached.nix; containers.proxy.config = import ./nginx.nix; containers.services = { config = import ./scala -services.nix; bindMounts."/webapp" = { hostPath = pkgs.myorg.scalaServices.webapp.outPath; isReadOnly = true; }; }; } 18
  • 32. NixOS: Multi-node testing (node setup) import ./make -test.nix ({ pkgs , lib , ... }: let kafkaPackage = pkgs.apacheKafka_1_0; in { name = "kafka -1.0"; nodes = { zookeeper = import ./machines/zookeeper.nix; kafka = import ./machines/kafka.nix; }; testScript = import ./tests/kafka.nix { package = kafkaPackage; util = pkgs.myorg.testing.util; }; }) 19
  • 33. NixOS: Multi-node testing (test script) { pkg , kPort ? 9092 , zkPort ? 2181 , topic ? "test" , util }: let inherit (util) createTopicCmd producerPipe consumerPipe; in ’’ startAll; $zookeeper ->waitForUnit("zookeeper"); $zookeeper ->waitForOpenPort(${zkPort}); $kafka ->waitForUnit("apache -kafka"); $kafka ->waitForOpenPort(${kPort}); $kafka ->waitUntilSucceeds("${createTopicCmd}"); $kafka ->mustSucceed("echo ’test 1’ | ${producerPipe}"); $kafka ->mustSucceed("${consumerPipe} | grep ’test 1 ’"); ’’ 20
  • 34. NixOS & nixpkgs: Properties • modular (See nixpkgs overlays) • extensible (see nixos modules) • everything (almost) is a package in the Nix store • system rollbacks (with system profile snapshots saved as generations) • builds on purity of Nix packaging • NO FHS mutation-in-place (links into FHS to immutable Nix store) 21
  • 36. Reliable Software "Those who want really reliable software will discover that they must find means of avoiding the majority of bugs to start with, and as a result the programming process will become cheaper." – EWD 22
  • 38. Why do properties/laws matter? • Because it allows us humble programmers to: 23
  • 39. Why do properties/laws matter? • Because it allows us humble programmers to: • compose our reasoning • know what we cannot reason about • break down big problems into smaller parts • accomplish the same result with less effort 23
  • 40. Questions? @SusanPotter (heckle me, ask me questions) 24