🧭 VOS Coding Style Guard

A set of internal engineering rules for writing clean, scalable, and maintainable Laravel code across all projects.


1. Validation Rules

All request validations must live inside dedicated Form Request or Validation classes β€” never inline inside controllers or services.


2. Controller Design

Controllers must:

Controllers = Validation ➜ Service ➜ Standard Response

All controllers related to the same feature must be in a subfolder named after that feature: app/Http/Controllers/FeatureName/


3. Service Layer Rules

Services handle:

Controllers must only interact with these services.

Services should:


4. Trait Usage

Traits are allowed for reusable helper logic across multiple services or models β€” e.g., logging, formatting, API requests.

Avoid using traits for core business logic β€” use services instead.


5. File Size and Complexity

No file should exceed 200 lines of code. No method should exceed 40 lines. Use early returns instead of deeply nested if statements. Follow the Single Responsibility Principle (SRP).


6. Naming and Folder Structure

Folder structure must reflect logical boundaries:

app/ β”œβ”€β”€ Http/ β”‚ β”œβ”€β”€ Controllers/ β”‚ β”‚ └── FeatureName/ β”‚ └── Requests/ β”œβ”€β”€ Services/ β”œβ”€β”€ Traits/ β”œβ”€β”€ Models/ β”œβ”€β”€ Policies/ β”œβ”€β”€ Helpers/ β”œβ”€β”€ Enums/ └── Support/

Naming conventions:


7. Response Standards

All controllers should return standardized JSON responses via a Response Helper or Trait.

Example:

return $this->success('User created successfully', $user);

8. Exception & Error Handling

All exceptions must be caught and rethrown as custom exceptions with meaningful messages. Configure a global exception handler in app/Exceptions/Handler.php.


9. Logging and Monitoring

Use centralized logging for all critical actions. Avoid using dd() or dump() in production code.


10. Testing Culture

Every Service or Helper should have a corresponding unit or feature test. Use PestPHP for simplicity and consistency. Never deploy untested features to production.


11. Environment and Configuration

All environment-dependent variables must come from .env β€” no hardcoded URLs, API keys, or secrets. Use Laravel’s config/ system for all environment options.


12. Git and Documentation Discipline

Commit messages must be descriptive:

Each new Service or Trait must have a PHPDoc block at the top describing its purpose. Maintain a docs/architecture.md file describing the overall service structure.


13. Dependency Management

Use Dependency Injection wherever possible. Avoid circular dependencies between services. Do not use facades or static calls inside business logic.


14. Code Review Standard

All pull requests must pass:


15. Security

Always use mass assignment protection ($fillable or DTOs). Never trust client input β€” validate everything. Sanitize all external data before persistence.


16. API Response Consistency

All API responses must follow a unified structure across the codebase.

Standard Format

{ "status": "success" | "error", "message": "Human-readable message", "data": {}, "errors": [] }

Example β€” Success

{ "status": "success", "message": "User created successfully", "data": { "id": 12, "name": "John Doe" } }

Example β€” Error

{ "status": "error", "message": "Validation failed", "errors": { "email": ["The email has already been taken."] } }

Implementation

Create a reusable ApiResponseTrait and include it in all controllers:

trait ApiResponseTrait { protected function success($message, $data = [], $code = 200) { return response()->json([ 'status' => 'success', 'message' => $message, 'data' => $data ], $code); } protected function error($message, $errors = [], $code = 400) { return response()->json([ 'status' => 'error', 'message' => $message, 'errors' => $errors ], $code); } }

Usage:

return $this->success('User created successfully', $user);

🧱 Summary β€” The Four Commandments

  1. Validate in dedicated classes.
  2. Keep controllers thin.
  3. Place business logic in services.
  4. Keep files short, clear, and composable.