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

Math Parser Laravel Package

mossadal/math-parser

Safe PHP math expression parser/evaluator that builds an AST from user formulas. Supports arithmetic, variables, and elementary functions, plus interpreters for evaluation, symbolic differentiation, and LaTeX pretty-printing; customizable lexer/parser with StdMathParser.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Installation:

    composer require mossadal/math-parser
    
  2. Basic Evaluation:

    use MathParser\StdMathParser;
    use MathParser\Interpreting\Evaluator;
    
    $parser = new StdMathParser();
    $ast = $parser->parse('2 + 3 * x');
    $evaluator = new Evaluator();
    $evaluator->setVariables(['x' => 5]);
    $result = $ast->accept($evaluator); // Returns 17
    
  3. First Use Case:

    • Dynamic Calculator: Parse and evaluate user-submitted expressions in a Laravel controller:
      public function calculate(Request $request) {
          $expression = $request->input('expression');
          $variables = $request->input('variables', []);
      
          $parser = new StdMathParser();
          $ast = $parser->parse($expression);
      
          $evaluator = new Evaluator();
          $evaluator->setVariables($variables);
      
          return response()->json(['result' => $ast->accept($evaluator)]);
      }
      

Where to Look First

  • Documentation: GitHub Pages for API reference.
  • Examples: Focus on StdMathParser and Evaluator for 90% of use cases.
  • AST Structure: Inspect $ast object to understand how expressions are parsed (e.g., $ast->toString()).

Implementation Patterns

Core Workflows

  1. Expression Evaluation:

    • Pattern: Parse → Evaluate → Return Result.
      $parser = new StdMathParser();
      $ast = $parser->parse($expression);
      $evaluator = new Evaluator();
      $evaluator->setVariables($variables);
      return $ast->accept($evaluator);
      
    • Laravel Integration: Wrap in a service class (e.g., MathEvaluatorService) with dependency injection.
  2. Symbolic Differentiation:

    • Pattern: Parse → Differentiate → Evaluate Derivative.
      $differentiator = new Differentiator('x');
      $dfAst = $parser->parse('x^2 + sin(y)')->accept($differentiator);
      $result = $dfAst->accept(new Evaluator(['x' => 1, 'y' => 0])); // Returns 2
      
    • Use Case: Optimization algorithms or physics simulations.
  3. LaTeX Output:

    • Pattern: Parse → Generate LaTeX → Render Frontend.
      $latexGenerator = new \MathParser\Interpreting\LatexGenerator();
      $latex = $parser->parse('(a + b)/c')->accept($latexGenerator);
      // Output: \frac{a + b}{c}
      
    • Frontend: Use MathJax in Blade:
      <script>
        MathJax.typeset();
      </script>
      <div>{{ $latex }}</div>
      

Integration Tips

  • Validation:

    • Restrict allowed functions/variables during parser initialization:
      $parser = new StdMathParser([
          'functions' => ['sin', 'cos', 'log'],
          'variables' => ['x', 'y', 'z']
      ]);
      
    • Use Laravel validation for input sanitization:
      $request->validate([
          'expression' => 'required|regex:/^[a-zA-Z0-9+\-*\/^().\s]+$/'
      ]);
      
  • Caching:

    • Cache parsed ASTs for performance:
      $cacheKey = 'math_ast:' . md5($expression);
      $ast = cache()->remember($cacheKey, now()->addHours(1), function() use ($parser, $expression) {
          return $parser->parse($expression);
      });
      
  • Error Handling:

    • Wrap parsing/evaluation in try-catch:
      try {
          $ast = $parser->parse($expression);
          return $ast->accept($evaluator);
      } catch (\MathParser\Exception\ParseException $e) {
          return response()->json(['error' => 'Invalid expression'], 400);
      }
      
  • Custom Functions:

    • Extend the parser to support custom functions:
      $parser = new StdMathParser();
      $parser->addFunction('myFunc', function($args) {
          return array_product($args);
      });
      $ast = $parser->parse('myFunc(2, 3, 4)'); // Returns 24
      

Laravel-Specific Patterns

  • Service Provider:
    public function register() {
        $this->app->singleton(StdMathParser::class, function() {
            return new StdMathParser(['functions' => ['sin', 'cos']]);
        });
    }
    
  • API Resources:
    public function toArray($request) {
        return [
            'result' => $this->evaluator->evaluate($this->expression),
            'latex' => $this->latexGenerator->generate($this->ast),
        ];
    }
    

Gotchas and Tips

Pitfalls

  1. Implicit Multiplication Quirks:

    • 2x is parsed as 2*x, but x^2y is parsed as x^(2*y) (not x^2*y).
    • Fix: Use explicit multiplication (2*x*y) for clarity or enforce rules via validation.
  2. Variable Naming:

    • Only single-letter variables (e.g., x, y) work with implicit multiplication.
    • Fix: Use explicit multiplication or restrict variables to single letters.
  3. Floating-Point Precision:

    • Results may have precision issues (e.g., 0.1 + 0.2 !== 0.3).
    • Fix: Use bcmath or gmp for high-precision needs:
      $evaluator = new Evaluator();
      $evaluator->setPrecision(10); // If supported (check package docs)
      
  4. Security Risks:

    • User input can crash the parser or cause infinite loops.
    • Fix:
      • Whitelist allowed functions/variables.
      • Limit expression complexity (e.g., max AST depth).
      • Use Laravel’s validate to restrict input format.
  5. Memory Usage:

    • Complex expressions (e.g., nested functions) can bloat the AST.
    • Fix: Monitor memory usage and cache parsed ASTs.
  6. LaTeX Generation:

    • Output may not match expectations for complex expressions.
    • Fix: Test LaTeX output early and adjust parser settings if needed.

Debugging Tips

  • Enable Debug Mode:

    \MathParser\StdMathParser::setDebugMode(true);
    
    • Logs detailed parsing errors to help identify syntax issues.
  • Inspect AST:

    $ast->toString(); // Prints the parsed expression tree
    
    • Useful for verifying parsing behavior.
  • Step-by-Step Evaluation:

    • Override Evaluator to log intermediate steps:
      class DebugEvaluator extends Evaluator {
          public function visitBinaryOpNode($node) {
              logger()->debug("Evaluating: {$node->left->toString()} {$node->op} {$node->right->toString()}");
              return parent::visitBinaryOpNode($node);
          }
      }
      

Configuration Quirks

  • Default Functions:

    • The parser includes common functions (sin, cos, log, etc.), but not all are enabled by default.
    • Fix: Explicitly whitelist required functions:
      $parser = new StdMathParser(['functions' => ['sin', 'exp']]);
      
  • Operator Precedence:

    • Follows standard math rules, but implicit multiplication has the same precedence as explicit multiplication.
    • Example: x^2y is parsed as x^(2*y), not (x^2)*y.
  • Variable Scope:

    • Variables are set globally per Evaluator instance.
    • Fix: Create a new Evaluator for each evaluation if variables are scoped:
      $evaluator = new Evaluator(['x' => 1, 'y' => 2]);
      

Extension Points

  1. Custom Lexer/Parser:

    • Extend Lexer or Parser classes to support custom syntax (e.g., custom operators).
    • Example: Add a new operator ^ for exponentiation (already supported, but can be overridden).
  2. Custom Interpreters:

    • Implement Visitor interface to create new interpreters (e.g., for code generation).
    • Example: Generate Python code from AST:
      class PythonCodeGenerator implements Visitor {
          public function visitBinaryOpNode($node) {
              return "({$node->left->accept($this)} {$node->op} {$node->right->accept($this)})
      
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.
terminal42/code-quality-tools
codifyo/ts-generator-bundle
andydefer/laravel-cluster
testo/fiber
mintobit/jobqueue
a4sex/maintenance-bundle
a4sex/entity-date-update
a4sex/client-identifier
a4sex/base-utilites
a4sex/key-value-storage
a4sex/micro-status
chilldev/dependency-injection-extra
datinglibre/datinglibre-app-api
biberltd/corebundle
bricre/symfony-bundle-test
biberltd/logbundle
dominium/http-adapter-bundle
dominium/google-analytics
a4sex/auto-clean-entity
christhompsontldr/laravel-inky