skip to Main Content

I have a controller in my API that contains methods that fetches various data from different tables like account statuses, account types, etc and returns it to the API consumer.

use AppModelsAccountStatus;
use AppModelsAccountType;
use AppModelsAlertLevel;

class ClientController extends Controller
{
   public function getAccountStatuses() {
        try {
            $accountStatuses = AccountStatus::all();

            return response()->json([
                'error' => false,
                'message' => 'OK',
                'account_statuses' => $accountStatuses
            ]);
        } catch (Exception $e) {
            return response()->json([
                'error' => true,
                'message' => $e->getMessage() . ' ' . $e->getFile() . ' ' . $e->getLine()
            ], 500);
        }
    }

    public function getAccountTypes() {
        try {
            $accountTypes = AccountType::all();

            return response()->json([
                'error' => false,
                'message' => 'OK',
                'account_types' => $accountTypes
            ]);
        } catch (Exception $e) {
            return response()->json([
                'error' => true,
                'message' => $e->getMessage() . ' ' . $e->getFile() . ' ' . $e->getLine()
            ], 500);
        }
    }

    public function getAlertLevels() {
        try {
            $alertLevels = AlertLevel::all();

            return response()->json([
                'error' => false,
                'message' => 'OK',
                'alert_levels' => $alertLevels
            ]);
        } catch (Exception $e) {
            return response()->json([
                'error' => true,
                'message' => $e->getMessage() . ' ' . $e->getFile() . ' ' . $e->getLine()
            ], 500);
        }
    }
}

How do i prevent myself from repeating these almost identical code?

3

Answers


  1. If you want to do some clean code, you should create a Class which will contain a function to handle your duplicate code:

    class ResponseBuilder
    {
        public function createResponseFromData(string $dataResponseKey, $data) 
        {
            try {
                return response()->json([
                    'error' => false,
                    'message' => 'OK',
                    $dataResponseKey => $data
                ]);
            } catch (Exception $e) {
                return response()->json([
                    'error' => true,
                    'message' => $e->getMessage() . ' ' . $e->getFile() . ' ' . $e->getLine()
                ], 500);
            }
        }
    }
    

    This will respect Single Responsability Principle, and in your Controller, just inject it and use it:

    private ResponseBuilder $responseBuilder;
    
    public function __construct(ResponseBuilder $responseBuilder)
    {
         $this->responseBuilder = $responseBuilder; 
    }
    
    public function getAccountStatuses() 
    {
         $accountStatuses = AccountStatus::all();
    
         return $this->responseBuilder->createResponseFromData('account_statuses', $accountStatuses);
    }
    

    You should declare an Interface (ResponseBuilderInterface) to inject it, this way your Controller won’t be responsible of injection.

    Login or Signup to reply.
  2.    public function getData($model) {
        try {
            $data = $model::all();
    
            return response()->json([
                'error' => false,
                'message' => 'OK',
                'account_statuses' => $data
            ]);
        } catch (Exception $e) {
            return response()->json([
                'error' => true,
                'message' => $e->getMessage() . ' ' . $e->getFile() . ' ' . $e->getLine()
            ], 500);
        }
    }
    
    Login or Signup to reply.
  3. Well, there can be many ways to stop repeating the identical codes. It depends on developer’s skills, knowledge and experience. In my case I create A trait file to handel responses.

    <?php
    
    namespace AppHttpTraits;
    
    trait ResponseHandler {
    public function successResponse($responseKey='data', $data) {
        return response()->json([
            'error' => false,
            'message' => 'OK',
            $responseKey => $data
        ]);
    }
    
    public function errorResponse($errorMessage) {
        return response()->json([
            'error' => true,
            'message' => $errorMessage
        ], 500);
    }}
    

    In Your Clientcontroller.php you can use ResponseHandler.php

    <?php
    
    use AppModelsAccountStatus;
    use AppModelsAccountType;
    use AppModelsAlertLevel;
    use AppHttpTraitsResponseHandler;
    
    class ClientController extends Controller
    {
      use ResponseHandler;
      public function getAccountStatuses()
      {
        try {
          $accountStatuses = AccountStatus::all();
          return $this->successResponse('account_types', $accountStatuses);
        } catch (Exception $e) {
          return $this->errorResponse($e->getMessage() . ' ' . $e->getFile() . ' ' . $e->getLine());
        }
      }
    }
    

    Other ways:

    1. Try Repository patterns
    2. Try Service Repository Pattern (I personally like this pattern)

    You should also try Eloquent: API Resources this can help you to expressively and easily transform your models and model collections into JSON.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search