Usage with Laravel


Before we you proceed make sure you have read the documentation for

Generating an API key

To generate an API key, see this section

For new projects

Starter kit

You can either use our Laravel - Tailwind CSS starter kit to get started or create a new project from scratch.

npx @adiranids/garchi-starter-kit -k laravel

From scratch

Create new Laravel app

composer create-project laravel/laravel garchi-app

Creating components

Let's create a simple page with sections (components) HeroContainer and Paragraph

<!-- resources/views/components/garchi/HeroContainer.blade.php -->

@props([
    "title" => "",
    "sub_heading" => "",
    "image" => "",
    "subSections" => []
])

<div {{$attributes->merge([
        'class' => "relative bg-white"
    ])}}>

    <div class="mx-auto max-w-7xl lg:grid lg:grid-cols-12 lg:gap-x-8 lg:px-8">
    
        <div class="px-6 pb-24 pt-10 sm:pb-32 lg:col-span-7 lg:px-0 lg:pb-56 lg:pt-48 xl:col-span-6">
            <div class="mx-auto max-w-2xl lg:mx-0">

                <h1 class="mt-24 text-4xl font-bold tracking-tight text-gray-900 sm:mt-10 sm:text-6xl">
                    {{$title}}
                </h1>
                <p class="mt-6 text-lg leading-8 text-gray-600">
                    {{ $sub_heading }}
                </p>
                <div class="mt-10 flex items-center gap-x-6">
                    <!-- cta button to render component/garchi/LinkButton -->
                    <!-- this way you can render nested components -->

                    @foreach($subSections as $section)
                        <x-garchi.GarchiComponent :section="$section" />
                    @endforeach
                </div>
            </div>
        </div>
        <div class="relative lg:col-span-5 lg:-mr-8 xl:absolute xl:inset-0 xl:left-1/2 xl:mr-0">
            <img class="aspect-[3/2] w-full bg-gray-50 object-cover lg:absolute lg:inset-0 lg:aspect-auto lg:h-full" src="{{ $image }}" alt="image" />
        </div>
    </div>
</div>
<!-- resources/views/components/garchi/Paragraph.blade.php -->

@props([
    'content' => ""
])


<p {{$attributes->merge([
    'class' => "text-gray-800"
])}}>
    {{ $content }}
</p>

Create a GarchiComponent that will render all the components dynamically


<!-- resources/views/components/garchi/GarchiComponent.blade.php -->

@props([
    'section' => []
])



@if(view()->exists('components.garchi.'.$section['name']))
    @include('components.garchi.'.$section['name'],
    [...$section['props'], 'subSections'=> $section['children']])
@endif

In your route.php

If you want to catch all the routes, then add below in your routes/web.php


Route::get('{slug?}', [PageController::class, 'getPage'])->where('slug', '.*');

In your PageController.php

The PageController might look like this:

// App\Http\Controllers\PageController.php

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Illuminate\Support\Facades\Http;

class PageController extends Controller
{
    public function getPage(string $slug = "/")
    {
        $response = Http::withHeaders([
            "Content-Type" => "application/json",
            "Authorization" => "Bearer your_api_key"
        ])->post('https://garchi.co.uk/api/v2/page', [
            "space_uid" => "c7ba17eb-4004-45ef-b5b3-1d557c5c85f4c34f4a69-3d08-444f-86e0-852b",
            "mode" => "draft",
            "slug" => $slug
        ]);
        $page = $response->json();
        return view('page', compact('page'));
    }
}

Finally in your page.blade.php

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    @vite('resources/css/app.css')
    <title>
        {{$page['title']}}
    </title>
</head>

<body>

    <main>
    <!-- Iterate throught each section and pass it to GarchiComponent to render
    them dynamically -->
        @foreach($page['sections'] as $section)
         <x-garchi.GarchiComponent :section="$section" />
        @endforeach
    </main>
    <script src="https://garchi.co.uk/script/index.es.js"></script>
</body>

</html>

If you notice, I have added a script tag. This makes the editor on the dashboard talk with your website so that when you click on a section in the editor on the dashboard, it will show the respective section with the prop value in the sidebar. Without this script, the editor won't be able to talk with your website.

Now this page's content could be edited from the dashboard.

⚠️ You can also add inline CSS styles. You need to add them as a prop value to the section but it won't be responsive.

You can add HTML class attribute as a prop for a section with a value of a base class and combine it with inline CSS. Sky is the limit 🚀