Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Money Laravel Package

moneyphp/money

moneyphp/money is a PHP value-object library for safe money handling without floats. Uses string-based big integers, supports arithmetic, allocation, currencies/ISO repositories, formatting (incl. intl), JSON serialization, and exchange rates. Requires BCMath.

View on GitHub
Deep Wiki
Context7

Technical Evaluation

Architecture Fit

  • Domain-Driven Design (DDD) Alignment: The moneyphp/money package is a near-perfect fit for financial systems, e-commerce, billing, or any domain requiring precise monetary calculations. It enforces Martin Fowler’s Money Pattern, ensuring immutability, type safety, and currency-aware operations—critical for domains where floating-point errors or incorrect currency handling could lead to financial discrepancies.
  • Laravel Ecosystem Synergy: Laravel’s built-in support for eloquent models, queues, and API responses aligns well with this package. For example:
    • Eloquent Attributes: Store Money objects as JSON in database columns (via json type or Money::jsonSerialize()).
    • API Responses: Serialize Money objects directly in JSON APIs (native support via jsonSerialize).
    • Validation: Integrate with Laravel’s validator to enforce monetary constraints (e.g., min:1000 for EUR).
  • Microservices/Monolith Compatibility: The package’s immutable design and currency-aware operations make it ideal for both monolithic Laravel apps and microservices (e.g., a payments service). Its PSR-compliant nature (e.g., jsonSerialize) ensures seamless interoperability with other PHP libraries.

Integration Feasibility

  • Low Friction for Laravel:
    • Composer Integration: Zero-config installation (composer require moneyphp/money).
    • Service Container: Register the package as a Laravel service provider to centralize currency configurations (e.g., ISOCurrencies, CryptoCurrencies).
    • Facade Pattern: Create a Money facade to simplify usage (e.g., Money::EUR(1000)->add($fee)).
  • Database Compatibility:
    • Store Money objects as JSON (PostgreSQL, MySQL 8.0+) or decimal strings (e.g., "1000.00" in a decimal(10,2) column).
    • Use eloquent-cast to automatically convert between Money objects and database values.
  • API/HTTP Layer:
    • Request Validation: Use Laravel’s FormRequest to validate monetary inputs (e.g., rule('amount')->money()).
    • Response Formatting: Format Money objects for APIs using DecimalMoneyFormatter or IntlLocalizedDecimalFormatter.

Technical Risk

Risk Area Mitigation Strategy
BCMath Dependency Ensure PHP’s bcmath extension is enabled (required for high-precision calculations). Fallback to gmp if bcmath is unavailable.
Floating-Point Rejection Enforce string-based arithmetic (e.g., sprintf('%.2f', $float)) to avoid precision loss. Document this requirement in API contracts.
Currency Mismatches Implement runtime checks (e.g., Money::isSameCurrency()) and fail fast with descriptive errors.
Legacy Float Usage Use Teller (v4.2+) for legacy systems requiring float compatibility (deprecated in v4+).
Performance Benchmark critical paths (e.g., Money::add() in bulk operations). Consider caching Currency objects if used frequently.
Testing Complexity Leverage Money\Comparator for unit tests to assert monetary equality without floating-point quirks.

Key Questions for TPM

  1. Currency Scope:
    • Will the system support only ISO currencies (e.g., EUR, USD) or also crypto (e.g., BTC, ETH)? This affects dependency choices (e.g., moneyphp/crypto-currencies).
  2. Precision Requirements:
    • Are subunit-level operations (e.g., cents, satoshis) critical, or can the system tolerate rounding? This impacts calculator selection (bcmath vs. gmp).
  3. Legacy Integration:
    • Are there existing systems using floats for money? If so, plan a migration strategy (e.g., Teller for gradual replacement).
  4. Exchange Rates:
    • Will exchange rates be static (e.g., hardcoded) or dynamic (e.g., fetched from an API)? This determines whether to use FixedExchange or Exchanger.
  5. Database Schema:
    • How will Money objects be persisted? Options:
      • JSON column (flexible, but requires application-layer parsing).
      • Decimal columns (e.g., amount DECIMAL(10,2) + currency VARCHAR(3)).
      • Separate tables (normalized, but complex for joins).
  6. Localization:
    • Are locale-specific formatting (e.g., €1,000.00 vs. 1,000.00€) required? This impacts the choice between DecimalMoneyFormatter and IntlLocalizedDecimalFormatter.
  7. Concurrency:
    • Are there high-contention scenarios (e.g., concurrent Money::allocate())? Consider thread-safe patterns or database-level locks.

Integration Approach

Stack Fit

  • Laravel Core:
    • Eloquent Models: Use accessors/mutators to convert between Money objects and database values.
      // Model: Order.php
      protected $casts = [
          'amount' => Money::class, // Automatically serialize/deserialize
      ];
      
    • Validation: Extend Laravel’s validator with custom rules for monetary values.
      use Illuminate\Validation\Rule;
      
      Rule::macro('money', function ($attribute, $value, $parameters) {
          return Money::parse($value, 'USD')->isValid();
      });
      
    • API Resources: Format Money objects in responses using DecimalMoneyFormatter.
      // App\Http\Resources\OrderResource.php
      public function toArray($request) {
          return [
              'amount' => $this->whenLoaded('amount', fn () =>
                  DecimalMoneyFormatter::format($this->amount)
              ),
          ];
      }
      
  • Queue/Jobs:
    • Serialize Money objects in delayed jobs (e.g., RefundJob) using json_encode().
    • Deserialize in the job handler with Money::parse().
  • Caching:
    • Cache currency repositories (e.g., ISOCurrencies) if loaded frequently.
    • Cache exchange rates (if dynamic) with a TTL (e.g., Cache::remember()).

Migration Path

Phase Action Tools/Libraries
Assessment Audit existing money-handling code for float usage, currency mismatches, and precision issues. PHPStan, Psalm, custom linting rules.
Pilot Replace a non-critical module (e.g., a reporting feature) with Money. Feature flags, Laravel’s config.
Core Integration Migrate Eloquent models, API endpoints, and validation logic. Eloquent casts, API resources.
Legacy Wrap Use Teller to wrap legacy float-based systems until fully migrated. Money\Teller (v4.2+).
Testing Rewrite unit/integration tests to use Money\Comparator for assertions. PHPUnit, Pest.
Performance Benchmark critical paths (e.g., bulk Money::add() operations) and optimize if needed. Laravel Forge, Blackfire.

Compatibility

Component Compatibility Notes
PHP 8.0+ Required (v4.0+). Use v3.x for PHP 7.4–8.0 support.
Laravel 9/10 Full compatibility. Laravel’s type system works seamlessly with Money’s immutable objects.
Databases - PostgreSQL: Use jsonb or decimal columns.
- MySQL 8.0+: Use JSON or DECIMAL columns.
- SQLite: Use JSON or TEXT (store as string, e.g., "1000.00").
Third-Party APIs - Stripe/PayPal: Convert their float-based responses to Money using Money::parse().
- GraphQL: Use Laravel GraphQL to serialize Money objects.
Legacy Systems - Float-based: Use Teller for gradual migration.
- Doctrine ORM: Update entity mappings if using Currency embeddables (note v3.0’s code rename).
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
codraw/entity-migrator
codraw/doctrine-extra
codraw/aws-tool-kit
codraw/validator
codraw/workflow
codraw/open-api
codraw/cron-job
codraw/process
codraw/log
nexmo/api-specification
capell-app/block-library
axium/identity
cetria/laravel-dummy-models
cetria/reflection-helper
agropredict/sso-auth-bundle
evolvestudio/spam-protection
datacore/hub-sdk
develia/commons
cuci/prototurk-sdk
cuci/prototurk-sdk-symfony