2
\$\begingroup\$

I have REST API written on laravel and front end on vue.js. It is a dashboard for an ecommerce store where you can connect to post shipment service API to upload order shipment data and get tracking number (with .png label). So after I receive tracking number label from post service API I need possibility to show it in front end from the REST API response.

I have route on front end shipments/:id/tracking/label which should show some shipment data and tracking label image.

I got 2 solutions for this. Which is better and why?

Send image content as base64 string and shipment data in one backend route GET shipments/{id}/tracking/label

Backend

    public function getTrackingLabel(Shipment $shipment, LabelIsraelPostService $service)
    {
        $data = [
            'label' => $service->getTrackingLabel($shipment->label_path),
            'shipment' => $shipment
        ];

        return response()->json(['shipment' => $data]);
    }

Frontend

    <v-card>
        <v-card-title>
            Order id : {{ shipment.order_id }}
        </v-card-title>

        <v-img
            max-width="700"
            :src="`data:image/png;base64,${shipment.link}`"
        >
        </v-img>
    </v-card>

Use 2 different backend routes GET shipments/{id} for all shipment data and another one for only image GET shipments/{id}/tracking_label which will return image with headers.

Backend

For get all shipment data

    public function show(Shipment $shipment)
    {
        return response()->json(['shipment' => $shipment])
    }

For get shipment tracking label image

    public function getTrackingLabel(Shipment $shipment, LabelIsraelPostService $service)
    {
        return response(Storage::cloud()->get($path))->header('content-type', 'image\png')
    }

Front end

    <v-card>
        <v-card-title>
            Order id : {{ shipment.order_id }}
        </v-card-title>

        <v-img
            max-width="700"
            :src="`${BASE_API_URL}/shipments/${shipment.id}/tracking/label`"//or use axios for this request
        >
        </v-img>
    </v-card>

Which will upload the image in a browser from the API route and send another request to get all shipment data and show it on the front end.

I like solution #2 but if I will have 10 shipments for show tracking number label, I will have 10 api calls for get image for each of them, and also one for get array of shipments data by ids. In solution #1 I can get only one API call for all shipments with data and base64 image for each of them.

What is best practice to send image as the REST API response and show it with JS front end?

\$\endgroup\$
  • \$\begingroup\$ Usually images are their own request anyway, so for me personally, I would just use the images as a separate request. I would however include the url to the image in the data request, rather then trying to construct the url in js, eg, ${shipment.url_label} \$\endgroup\$ – bumperbox Dec 15 '19 at 17:00
  • \$\begingroup\$ @bumperbox thx for you comment, what if i want to do image as private, so for request it i need auth? Currently route for request image is public \$\endgroup\$ – Roman Shevchenko Dec 16 '19 at 13:56
  • \$\begingroup\$ you can add security by returning the image as a response from a laravel controller action, stackoverflow.com/questions/36066144/… \$\endgroup\$ – bumperbox Dec 18 '19 at 16:19
  • \$\begingroup\$ @bumperbox how then i need to show it on vue front, for me i see only one solution - base64 decode from backend response \$\endgroup\$ – Roman Shevchenko Dec 19 '19 at 17:04

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.