PHP code example of brimmar / phpresult

1. Go to this page and download the library: Download brimmar/phpresult library. Choose the download type require.

2. Extract the ZIP file and open the index.php.

3. Add this code to the index.php.
    
        
<?php
require_once('vendor/autoload.php');

/* Start to develop here. Best regards https://php-download.com/ */

    

brimmar / phpresult example snippets




namespace Brimmar\PhpResult\Interfaces;

/**
 * @template T
 * @template E
 */
interface Result
{
    // ... (methods will be documented below)
}


use Brimmar\PhpResult\Ok;
use Brimmar\PhpResult\Err;
use Brimmar\PhpResult\Interfaces\Result;

class UserRegistration
{
    private $db;
    private $emailService;

    public function __construct(Database $db, EmailService $emailService)
    {
        $this->db = $db;
        $this->emailService = $emailService;
    }

    public function registerUser(string $username, string $email, string $password): Result
    {
        return $this->validateInput($username, $email, $password)
            ->andThen(fn() => $this->checkUserExists($username, $email))
            ->andThen(fn() => $this->hashPassword($password))
            ->andThen(fn($hashedPassword) => $this->saveUser($username, $email, $hashedPassword))
            ->andThen(fn($userId) => $this->sendWelcomeEmail($userId, $email));
    }

    private function validateInput(string $username, string $email, string $password): Result
    {
        if (strlen($username) < 3) {
            return new Err("Username must be at least 3 characters long");
        }
        if (!filter_var($email, FILTER_VALIDATE_EMAIL)) {
            return new Err("Invalid email address");
        }
        if (strlen($password) < 8) {
            return new Err("Password must be at least 8 characters long");
        }
        return new Ok(null);
    }

    private function checkUserExists(string $username, string $email): Result
    {
        $exists = $this->db->query("SELECT id FROM users WHERE username = ? OR email = ?", [$username, $email])->fetchColumn();
        return $exists ? new Err("Username or email already exists") : new Ok(null);
    }

    private function hashPassword(string $password): Result
    {
        $hashedPassword = password_hash($password, PASSWORD_DEFAULT);
        return $hashedPassword ? new Ok($hashedPassword) : new Err("Failed to hash password");
    }

    private function saveUser(string $username, string $email, string $hashedPassword): Result
    {
        $userId = $this->db->insert("INSERT INTO users (username, email, password) VALUES (?, ?, ?)", [$username, $email, $hashedPassword]);
        return $userId ? new Ok($userId) : new Err("Failed to save user to database");
    }

    private function sendWelcomeEmail(int $userId, string $email): Result
    {
        $sent = $this->emailService->send($email, "Welcome to our service!", "Thank you for registering...");
        return $sent ? new Ok($userId) : new Err("Failed to send welcome email");
    }
}

$registration = new UserRegistration($db, $emailService);
$result = $registration->registerUser("johndoe", "[email protected]", "password123")->match(
    Ok: fn($value) => echo "User registered successfully with ID: $value",
    Err: fn($error) => echo "Registration failed: $error",
);


use Brimmar\PhpResult\Ok;
use Brimmar\PhpResult\Err;
use Brimmar\PhpResult\Interfaces\Result;

class WeatherApiClient
{
    private $httpClient;
    private $cache;
    private $rateLimiter;
    private $apiKey;

    public function __construct(HttpClient $httpClient, CacheInterface $cache, RateLimiter $rateLimiter, string $apiKey)
    {
        $this->httpClient = $httpClient;
        $this->cache = $cache;
        $this->rateLimiter = $rateLimiter;
        $this->apiKey = $apiKey;
    }

    public function getWeatherForecast(string $city): Result
    {
        return $this->checkRateLimit()
            ->andThen(fn() => $this->getCachedForecast($city))
            ->orElse(fn() => $this->fetchForecastFromApi($city))
            ->andThen(fn($forecast) => $this->cacheForecast($city, $forecast));
    }

    private function checkRateLimit(): Result
    {
        return $this->rateLimiter->isAllowed('weather_api')
            ? new Ok(null)
            : new Err("Rate limit exceeded. Please try again later.");
    }

    private function getCachedForecast(string $city): Result
    {
        $cachedForecast = $this->cache->get("weather_forecast:$city");
        return $cachedForecast ? new Ok($cachedForecast) : new Err("Cache miss");
    }

    private function fetchForecastFromApi(string $city): Result
    {
        try {
            $response = $this->httpClient->get("https://api.weather.com/forecast", [
                'query' => ['city' => $city, 'apikey' => $this->apiKey]
            ]);

            if ($response->getStatusCode() !== 200) {
                return new Err("API request failed with status code: " . $response->getStatusCode());
            }

            $forecast = json_decode($response->getBody(), true);
            return new Ok($forecast);
        } catch (\Exception $e) {
            return new Err("Failed to fetch forecast: " . $e->getMessage());
        }
    }

    private function cacheForecast(string $city, array $forecast): Result
    {
        $cached = $this->cache->set("weather_forecast:$city", $forecast, 3600); // Cache for 1 hour
        return $cached ? new Ok($forecast) : new Err("Failed to cache forecast");
    }
}

$weatherClient = new WeatherApiClient($httpClient, $cache, $rateLimiter, 'your-api-key');
$result = $weatherClient->getWeatherForecast("New York")->match(
    Ok: fn($value) => echo "Weather forecast for New York: $value['summary']",
    Err: fn($error) => echo "Failed to get weather forecast: $error",
);;


use Brimmar\PhpResult\Ok;
use Brimmar\PhpResult\Err;
use Brimmar\PhpResult\Interfaces\Result;

class ConfigManager
{
    private $configs = [];

    public function getConfig(string $key): Result
    {
        return $this->getFromEnvironment($key)
            ->or($this->getFromFile($key))
            ->orElse(fn() => $this->getDefaultConfig($key));
    }

    private function getFromEnvironment(string $key): Result
    {
        $value = getenv($key);
        return $value !== false ? new Ok($value) : new Err("Not found in environment");
    }

    private function getFromFile(string $key): Result
    {
        return isset($this->configs[$key])
            ? new Ok($this->configs[$key])
            : new Err("Not found in config file");
    }

    private function getDefaultConfig(string $key): Result
    {
        $defaults = ['timeout' => 30, 'retries' => 3];
        return isset($defaults[$key])
            ? new Ok($defaults[$key])
            : new Err("No default value for $key");
    }

    public function setConfig(string $key, $value): void
    {
        $this->configs[$key] = $value;
    }
}

$manager = new ConfigManager();
$manager->setConfig('database_url', 'mysql://localhost/mydb');

$dbConfig = $manager->getConfig('database_url')
    ->map(fn($url) => parse_url($url))
    ->isOkAnd(fn($parsed) => isset($parsed['scheme'], $parsed['host'], $parsed['path']));

if ($dbConfig) {
    echo "Valid database configuration found";
} else {
    echo "Invalid or missing database configuration";
}

$timeout = $manager->getConfig('timeout')
    ->expect("Timeout configuration is 


use Brimmar\PhpResult\Ok;
use Brimmar\PhpResult\Err;
use Brimmar\PhpResult\Interfaces\Result;
use Brimmar\PhpOption\Some;
use Brimmar\PhpOption\None;
use Brimmar\PhpOption\Interfaces\Option;

class UserService
{
    private $users = [];

    public function findUser(int $id): Option
    {
        return isset($this->users[$id]) ? new Some($this->users[$id]) : new None();
    }

    public function updateUser(int $id, array $data): Result
    {
        return $this->findUser($id)
            ->ok()
            ->mapErr(fn() => "User not found")
            ->andThen(fn($user) => $this->validateUserData($data))
            ->map(fn($validData) => array_merge($this->users[$id], $validData))
            ->inspect(fn($updatedUser) => $this->users[$id] = $updatedUser);
    }

    private function validateUserData(array $data): Result
    {
        $errors = array_filter([
            'name' => strlen($data['name'] ?? '') < 2 ? 'Name too short' : null,
            'email' => filter_var($data['email'] ?? '', FILTER_VALIDATE_EMAIL) ? null : 'Invalid email',
        ]);

        return empty($errors) ? new Ok($data) : new Err($errors);
    }

    public function getUserStats(): array
    {
        return array_map(
            fn($user) => $this->calculateUserScore($user)->unwrapOr(0),
            $this->users
        );
    }

    private function calculateUserScore(array $user): Option
    {
        return isset($user['activities'])
            ? new Some(array_sum($user['activities']))
            : new None();
    }
}

$service = new UserService();

// Simulate adding a user
$service->users[1] = ['name' => 'Alice', 'email' => '[email protected]'];

$updateResult = $service->updateUser(1, ['name' => 'Alicia'])
    ->transpose();

$name = $updateResult
    ->iter()
    ->current()['name'] ?? 'Unknown';

echo "Updated name: $name";

$stats = $service->getUserStats();
echo "User stats: " . implode(', ', $stats);

$result = new Ok(42);
echo $result->isOk(); // Output: true

$result = new Err("error");
echo $result->isOk(); // Output: false

$result = new Ok(42);
echo $result->isOkAnd(fn($value) => $value > 40); // Output: true
echo $result->isOkAnd(fn($value) => $value < 40); // Output: false

$result = new Err("error");
echo $result->isOkAnd(fn($value) => true); // Output: false

$result = new Ok(42);
echo $result->isErr(); // Output: false

$result = new Err("error");
echo $result->isErr(); // Output: true

$result = new Err("error");
echo $result->isErrAnd(fn($error) => $error === "error"); // Output: true
echo $result->isErrAnd(fn($error) => $error === "other"); // Output: false

$result = new Ok(42);
echo $result->isErrAnd(fn($error) => true); // Output: false

$result = new Ok(42);
$option = $result->ok('\Brimmar\PhpOption\Some');
echo $option->unwrap(); // Output: 42

$result = new Err("error");
$option = $result->ok('\Brimmar\PhpOption\None');
echo $option->isNone(); // Output: true

$result = new Ok(42);
$option = $result->err('\Brimmar\PhpOption\None');
echo $option->isNone(); // Output: true

$result = new Err("error");
$option = $result->err('\Brimmar\PhpOption\Some');
echo $option->unwrap(); // Output: "error"

$result = new Ok(42);
echo $result->unwrap(); // Output: 42

$result = new Err("error");
$result->unwrap(); // Throws RuntimeException

$result = new Ok(42);
echo $result->expect("Failed to get value"); // Output: 42

$result = new Err("error");
$result->expect("Failed to get value"); // Throws RuntimeException with message "Failed to get value: error"

$result = new Err("error");
echo $result->expectErr("Failed to get error"); // Output: "error"

$result = new Ok(42);
$result->expectErr("Failed to get error"); // Throws RuntimeException with message "Failed to get error: 42"

$result = new Ok(new Ok(42));
$flattened = $result->flatten();
echo $flattened->unwrap(); // Output: 42

$result = new Ok(new Err("inner error"));
$flattened = $result->flatten();
echo $flattened->unwrapErr(); // Output: "inner error"

$result = new Err("outer error");
$flattened = $result->flatten();
echo $flattened->unwrapErr(); // Output: "outer error"

$result = new Err("error");
echo $result->intoErr(); // Output: "error"

$result = new Ok(42);
$result->intoErr(); // Throws RuntimeException

$result = new Ok(42);
echo $result->intoOk(); // Output: 42

$result = new Err("error");
$result->intoOk(); // Throws RuntimeException

$result = new Ok(42);
foreach ($result->iter() as $value) {
    echo $value; // Output: 42
}

$result = new Err("error");
foreach ($result->iter() as $value) {
    echo "This won't be executed";
}

$result = new Ok(42);
echo $result->unwrapOr(0); // Output: 42

$result = new Err("error");
echo $result->unwrapOr(0); // Output: 0

$result = new Ok(42);
echo $result->unwrapOrElse(fn() => 0); // Output: 42

$result = new Err("error");
echo $result->unwrapOrElse(fn($error) => strlen($error)); // Output: 5

$result = new Ok(42);
$mapped = $result->map(fn($value) => $value * 2);
echo $mapped->unwrap(); // Output: 84

$result = new Err("error");
$mapped = $result->map(fn($value) => $value * 2);
echo $mapped->unwrapErr(); // Output: "error"

$result = new Err("error");
$mapped = $result->mapErr(fn($error) => strtoupper($error));
echo $mapped->unwrapErr(); // Output: "ERROR"

$result = new Ok(42);
$mapped = $result->mapErr(fn($error) => strtoupper($error));
echo $mapped->unwrap(); // Output: 42

$result = new Ok(42);
echo $result->mapOr(0, fn($value) => $value * 2); // Output: 84

$result = new Err("error");
echo $result->mapOr(0, fn($value) => $value * 2); // Output: 0

$result = new Ok(42);
echo $result->mapOrElse(
    fn($error) => strlen($error),
    fn($value) => $value * 2
); // Output: 84

$result = new Err("error");
echo $result->mapOrElse(
    fn($error) => strlen($error),
    fn($value) => $value * 2
); // Output: 5

$result = new Ok(42);
$result->inspect(function($value) {
    echo "Got value: $value";
}); // Output: Got value: 42

$result = new Err("error");
$result->inspect(function($value) {
    echo "This won't be executed";
});

$result = new Err("error");
$result->inspectErr(function($error) {
    echo "Got error: $error";
}); // Output: Got error: error

$result = new Ok(42);
$result->inspectErr(function($error) {
    echo "This won't be executed";
});

$result1 = new Ok(42);
$result2 = new Ok(10);
$combined = $result1->and($result2);
echo $combined->unwrap(); // Output: 10

$result1 = new Err("error");
$result2 = new Ok(10);
$combined = $result1->and($result2);
echo $combined->unwrapErr(); // Output: "error"

$result = new Ok(42);
$chained = $result->andThen(fn($value) => new Ok($value * 2));
echo $chained->unwrap(); // Output: 84

$result = new Err("error");
$chained = $result->andThen(fn($value) => new Ok($value * 2));
echo $chained->unwrapErr(); // Output: "error"

$result1 = new Ok(42);
$result2 = new Ok(10);
$combined = $result1->or($result2);
echo $combined->unwrap(); // Output: 42

$result1 = new Err("error1");
$result2 = new Ok(10);
$combined = $result1->or($result2);
echo $combined->unwrap(); // Output: 10

$result = new Ok(42);
$chained = $result->orElse(fn($error) => new Ok($error . " handled"));
echo $chained->unwrap(); // Output: 42

$result = new Err("error");
$chained = $result->orElse(fn($error) => new Ok($error . " handled"));
echo $chained->unwrap(); // Output: "error handled"

$result = new Ok(new Some(42));
$transposed = $result->transpose('\Brimmar\PhpOption\None', '\Brimmar\PhpOption\Some');
echo $transposed->unwrap()->unwrap(); // Output: 42

$result = new Ok(new None());
$transposed = $result->transpose('\Brimmar\PhpOption\None', '\Brimmar\PhpOption\Some');
echo $transposed->isNone(); // Output: true

$result = new Err("error");
$transposed = $result->transpose('\Brimmar\PhpOption\None', '\Brimmar\PhpOption\Some');
echo $transposed->unwrap()->unwrapErr(); // Output: "error"

$result = new Ok(42);
$value = $result->match(
    Ok: fn($value) => "Success: $value",
    Err: fn($error) => "Error: $error"
);
echo $value; // Output: "Success: 42"

$result = new Err("error");
$value = $result->match(
    Ok: fn($value) => "Success: $value",
    Err: fn($error) => "Error: $error"
);
echo $value; // Output: "Error: error"