Skip to content

Instantly share code, notes, and snippets.

View TylerPachal's full-sized avatar

Tyler Pachal TylerPachal

View GitHub Profile
@TylerPachal
TylerPachal / Main.scala
Last active April 19, 2017 19:52
Play! Json validation that considers more than one field
/* This is a small example of how to use Play! Json to validate a JsValue, when you need to consider a combination
* of fields. In this example, I have ContactInfo, where either a phone number or an email address have to provided
* (or both). Each field is represented as a simple String, when in reality you may want to do further validation
* on each field to make sure it is a valid phone number and/or email.
*/
import play.api.libs.json._
object Main {
@TylerPachal
TylerPachal / PossibilityInfinite.scala
Last active June 27, 2017 15:18
An example of how to express (positive) Infinite in JSON using Play!
// This is an example of how to express Infinity in Json using the Play! Scala Json library.
// Infinity cannot be expressed as a Scalar value in Json, so I am using an object to hold it instead.
//
// Example of a finite value:
// {
// "value": 12.009,
// "isInfinite": false
// }
//
// Example of an infinite value:
@TylerPachal
TylerPachal / parser_usage.iex
Last active November 9, 2017 18:54
Example usage of the Parser module, which crashes the parent process when it crashes
# Create a new Parser process
iex(2)> {:ok, pid} = Parser.start_link()
{:ok, #PID<0.118.0>}
# Verify the process is alive
iex(3)> Process.alive?(pid)
true
# Send it a valid message
iex(4)> GenServer.call(pid, "100")
@TylerPachal
TylerPachal / parser.ex
Created November 9, 2017 18:32
A flakey worker that parses all incoming messages as integers
defmodule Parser do
use GenServer
def start_link() do
GenServer.start_link(__MODULE__, :ok, [])
end
def handle_call(message, _from, state) do
i = String.to_integer(message)
{:reply, i, state}
@TylerPachal
TylerPachal / parser_usage_trap.iex
Last active November 9, 2017 18:54
Example usage of the Parser module, with exit trapping so a dying Parser will not kill the parent iex process
# Create a new Parser process
iex(1)> {:ok, pid} = Parser.start_link()
{:ok, #PID<0.112.0>}
# Figure out our iex process' PID
iex(2)> self()
#PID<0.110.0>
# See that our iex process is linked to the Parser process
iex(3)> Process.info(self(), :links)
@TylerPachal
TylerPachal / my_supervisor_draft.ex
Last active November 9, 2017 18:59
First iteration of the example supervisor, with the ability to start child process and list of those processes
## lib/MySupervisor.ex
defmodule MySupervisor do
use GenServer
## API
def start_link(child_spec_list) do
GenServer.start_link(__MODULE__, child_spec_list)
end
def list_processes(pid) do
@TylerPachal
TylerPachal / starting_my_supervisor.iex
Last active November 9, 2017 19:02
Starting up a MySupervisor process and verifying that is has linked to child processes
# Start a supervisor with two child specifications
iex(1)> {:ok, pid} = MySupervisor.start_link([{Parser, :start_link, []}, {Parser, :start_link, []}])
{:ok, #PID<0.123.0>}
# See the two processes that the supervisor started
iex(2)> MySupervisor.list_processes(pid)
%{#PID<0.124.0> => {Parser, :start_link, []},
#PID<0.125.0> => {Parser, :start_link, []}}
# Verify the supervisor has linked to the processes
@TylerPachal
TylerPachal / testing_my_supervisor_draft.iex
Last active November 9, 2017 19:03
Sending messages to a Parser process that is supervised by the first draft of MySupervisor
# Get a reference to one of the Parser process pid
iex(4)> parser_pid = MySupervisor.list_processes(pid) |> Map.keys |> List.first
#PID<0.124.0>
# Send a valid message
iex(5)> GenServer.call(parser_pid, "100")
100
# Send an invalid message
iex(6)> GenServer.call(parser_pid, "tyler")
@TylerPachal
TylerPachal / my_supervisor_new_callback.ex
Created November 9, 2017 18:47
Adding a new callback to the MySupervisor so that it can handle exiting children process
## OTP Callbacks
def handle_info({:EXIT, dead_pid, _reason}, state) do
# Start new process based on dead_pid spec
{new_pid, child_spec} = state
|> Map.get(dead_pid)
|> start_child()
# Remove the dead_pid and insert the new_pid with its spec
new_state = state
@TylerPachal
TylerPachal / testing_my_supervisor.iex
Last active November 9, 2017 19:05
Testing MySupervisor and verifying that it restarts dying children processes
# Start a supervisor with two child specifications
iex(1)> {:ok, pid} = MySupervisor.start_link([{Parser, :start_link, []}, {Parser, :start_link, []}])
{:ok, #PID<0.112.0>}
# See the two processes that the supervisor started
iex(2)> MySupervisor.list_processes(pid)
%{#PID<0.113.0> => {Parser, :start_link, []},
#PID<0.114.0> => {Parser, :start_link, []}}
# Get a reference to one of the Parser process pid