Skip to content

Instantly share code, notes, and snippets.

@sergiors
Last active October 13, 2016 12:28
Show Gist options
  • Save sergiors/f3387bbaaed35b10ede81abce0b0e597 to your computer and use it in GitHub Desktop.
Save sergiors/f3387bbaaed35b10ede81abce0b0e597 to your computer and use it in GitHub Desktop.
<?php
declare(strict_types = 1);
function partial(callable $fn, ...$args)
{
$arity = (new \ReflectionFunction($fn))->getNumberOfRequiredParameters();
return isset($args[$arity - 1])
? $fn(...$args)
: function (...$restArgs) use ($fn, $args) {
return partial($fn, ...array_merge($args, $restArgs));
};
}
function pipe(callable ...$callbacks)
{
return function ($payload) use ($callbacks) {
$restArgs = tail(func_get_args());
return array_reduce($callbacks, function ($payload, $callback) use ($restArgs) {
return $callback(...array_merge([$payload], $restArgs));
}, $payload);
};
}
function tail(array $xss)
{
return array_slice($xss, 1);
}
function always($x)
{
return function () use ($x) {
return $x;
};
}
function has(...$args)
{
return partial(function ($x, array $xss) {
return isset($xss[$x]);
})(...$args);
}
function get(...$args)
{
return partial(function (array $xss, $x, $notfound = false) {
return ifElse(has($x), function ($xss) use ($x) {
return $xss[$x];
}, always($notfound))($xss);
})(...$args);
}
function equals(...$args)
{
return partial(function ($x, $y) {
return $x === $y;
})(...$args);
}
function filter(...$args)
{
return partial(function (callable $fn, array $xss, $flag = 0) {
return array_filter($xss, $fn, $flag);
})(...$args);
}
function lt(...$args)
{
return partial(function ($x, $y) {
return $x < $y;
})(...$args);
}
function gt(...$args)
{
return partial(function ($x, $y) {
return $x > $y;
})(...$args);
};
function typeof (...$args)
{
return partial(function ($type, $object) {
return $object instanceof $type;
})(...$args);
}
function ifElse(...$args)
{
return partial(function (callable $pred, callable $success, callable $fail) {
return function ($value) use ($pred, $success, $fail) {
return $pred($value)
? $success($value)
: $fail($value);
};
})(...$args);
}
function head(array $xss)
{
$throw = function () {
throw new \InvalidArgumentException();
};
return ifElse(equals([]), $throw, 'array_values')($xss)[0];
}
interface IdInterface
{
}
interface EmailInterface
{
}
interface UserInterface
{
}
interface OrgInterface
{
public function getName(): string;
}
interface ProfileInterface extends UserInterface
{
public function getId(): IdInterface;
public function getName(): string;
public function getEmail(): EmailInterface;
}
$sergio = new class implements ProfileInterface {
public function getId(): IdInterface {
return new class implements IdInterface {
};
}
public function getName(): string {
return 'Sérgio Rafael Siqueira';
}
public function getEmail(): EmailInterface {
return new class implements EmailInterface {
};
}
};
$tiago = new class implements UserInterface {
};
$inbep = new class implements OrgInterface {
public function getName(): string {
return 'INBEP';
}
};
$filterUser = filter(typeof(UserInterface::class));
$filterOrg = filter(typeof(OrgInterface::class));
var_dump($users = [$sergio, $tiago, $inbep]);
var_dump($justUsers = $filterUser($users));
var_dump(pipe($filterUser, 'head')($users)->getName()); // head($justUsers)->getName();
var_dump(pipe($filterOrg, 'head')($users)->getName());
$logger = new class {
private $level = 400;
public function handle(array $record) {
$pred = function (array $xss) {
return gt(get($xss, 'level', 0), $this->level);
};
return ifElse($pred, always(true), always(false))($record);
}
};
var_dump($logger->handle(['level' => 400]));
var_dump($logger->handle(['level' => 500]));
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment