Laravel 5의 모든 뷰에 데이터를 전달하는 방법은 무엇입니까?


125

Laravel 5 애플리케이션의 모든 뷰에서 일부 기본 데이터에 액세스하고 싶습니다.

검색을 시도했지만 Laravel 4에 대한 결과 만 찾습니다. 여기에서 '모든 뷰와 데이터 공유'문서를 읽었 지만 어떻게해야할지 이해할 수 없습니다. 다음 코드는 어디에 배치해야합니까?

View::share('data', [1, 2, 3]);

당신의 도움을 주셔서 감사합니다.


이 요구 사항을 관리하려면 시작 코드가 필요합니까?
Safoor Safdar

1
데이터베이스 호출 결과와 함께 서비스 공급자에서 View :: share를 사용하면 db 마이그레이션 새로 고침을 실행하거나 연결할 수없는 db 연결로 황혼을 실행하려고 할 때 응용 프로그램에서 오류가 발생합니다 (긴 이야기, .env.dusk.local은 서비스 제공 업체가 실행 된 후에 만 ​​사용됨). 아래에서 언급했듯이 기본 컨트롤러 또는 미들웨어가 가장 좋습니다.
Andy Lobel

또한 *뷰 컴포저에서 사용할 때 특히 db 쿼리를 사용하는 경우에는 포함 된 모든 하위 뷰, 구성 요소 등에 대해 실행되므로 수백 개의 불필요한 쿼리를 실행할 수 있으므로 가장 좋은 방법은 레이아웃과 같은 기본 뷰를 사용하는 것입니다. 그런 다음 필요에 따라 데이터를 전달합니다.
Andy Lobel

답변:


222

이 목표는 다른 방법을 통해 달성 할 수 있습니다.

1. BaseController 사용

내가 설정하는 방식 BaseController은 라 라벨 자체를 확장 하는 클래스를 만들고 Controller거기에 다양한 글로벌 사물을 설정합니다. 다른 모든 컨트롤러 BaseController는 Laravel의 컨트롤러 가 아닌 확장됩니다 .

class BaseController extends Controller
{
  public function __construct()
  {
    //its just a dummy data object.
    $user = User::all();

    // Sharing is caring
    View::share('user', $user);
  }
}

2. 필터 사용

전체 애플리케이션의 모든 요청에 ​​대한 뷰에 대해 무언가를 설정하려는 사실을 알고 있다면 요청 전에 실행되는 필터를 통해 수행 할 수도 있습니다. 이것이 제가 Laravel에서 User 객체를 처리하는 방법입니다.

App::before(function($request)
{
  // Set up global user object for views
  View::share('user', User::all());
});

또는

자신 만의 필터를 정의 할 수 있습니다.

Route::filter('user-filter', function() {
    View::share('user', User::all());
});

간단한 필터 호출을 통해 호출합니다.

버전 5. *에 따라 업데이트

3. 미들웨어 사용

View::share와 함께 사용middleware

Route::group(['middleware' => 'SomeMiddleware'], function(){
  // routes
});



class SomeMiddleware {
  public function handle($request)
  {
    \View::share('user', auth()->user());
  }
}

4. View Composer 사용

View Composer는 특정 데이터를 다른 방식으로보기에 바인딩하는데도 ​​도움이됩니다. 변수를 특정보기 또는 모든보기에 직접 바인딩 할 수 있습니다. 예를 들어 요구 사항에 따라보기 작성기 파일을 저장할 고유 한 디렉터리를 만들 수 있습니다. 이러한 View Composer 파일은 서비스를 통해보기와 상호 작용을 제공합니다.

View composer 메서드는 다른 방식으로 사용할 수 있습니다. 첫 번째 예제는 다음과 유사합니다.

App\Http\ViewComposers디렉토리를 만들 수 있습니다 .

서비스 제공자

namespace App\Providers;
use Illuminate\Support\ServiceProvider;
class ViewComposerServiceProvider extends ServiceProvider {
    public function boot() {
        view()->composer("ViewName","App\Http\ViewComposers\TestViewComposer");
    }
}

그런 다음 "providers"섹션에서 config / app.php에이 공급자를 추가합니다.

TestViewComposer

namespace App\Http\ViewComposers;

use Illuminate\Contracts\View\View;

class TestViewComposer {

    public function compose(View $view) {
        $view->with('ViewComposerTestVariable', "Calling with View Composer Provider");
    }
}

ViewName.blade.php

Here you are... {{$ViewComposerTestVariable}}

이 방법은 특정보기에만 도움이 될 수 있습니다. 그러나 모든 뷰에 ViewComposer를 트리거하려면이 단일 변경 사항을 ServiceProvider에 적용해야합니다.

namespace App\Providers;
use Illuminate\Support\ServiceProvider;
class ViewComposerServiceProvider extends ServiceProvider {
    public function boot() {
        view()->composer('*',"App\Http\ViewComposers\TestViewComposer");
    }
}

참고

Laravel 문서

추가 설명을 위해 Laracast 에피소드

내 편에서 여전히 불분명 한 것이 있으면 알려주십시오.


귀하의 예에는 register()방법 이 누락되어 있습니다 -선택 사항이 아닙니다
Jonathan

지적 해 주셔서 감사합니다. 그러나 예제에는 처리해야 할 섹션 만 포함되어 있습니다. 보기와 데이터 공유에 대한 관점.
Safoor Safdar

필터는 어디에 두나요? 아마도 가장 정답은 지금 미들웨어 그룹을 사용하는 것은 laravel.com/docs/5.3/middleware#middleware-groups 또는 글로벌 미들웨어
Toskan

7
이것은 좋은 생각이 아닙니다. View composers는 각 개별 뷰에 대해 composer 인스턴스를 생성합니다. 즉, 1000 번의 루프를 실행하면 1000 번의 composer 인스턴스가 생성되고 1000 번의 실행 이벤트가 처리되므로 원하는 것이 아닙니다.
Reza Shadman 2016

4
@RezaShadman이 맞습니다! 나는 이것을 어려운 방법으로 배웠다. 조사를 위해 laravel-debugbar 도구를 설치할 때까지 내 응용 프로그램이 너무 느리게 실행되었습니다. 그런 다음 단일 페이지로드에 대해 약 15 번 실행되는 8 개의 쿼리 모두를 깨달았습니다. 포함 된 각 블레이드 파일에 대해 뷰 작성기가 호출되기 때문입니다. 별표를 사용하는 경우 *입니다. 를 사용하지 않는 경우 *괜찮습니다.
Syclone

66

고유 한 서비스 제공 업체 를 만들거나 ( ViewServiceProvider이름이 일반적 임) 기존 AppServiceProvider.

선택한 공급자에서 부팅 방법에 코드를 입력합니다.

public function boot() {
    view()->share('data', [1, 2, 3]);
}

이렇게하면 $data모든 뷰에서 변수에 액세스 할 수 있습니다.

당신은 오히려 외관 대신 도우미, 변경 사용하려는 경우 view()->에을 View::하지만이하는 것을 잊지 마세요 use View;파일의 상단에.


감사합니다. 부팅 기능이 이런 일을위한 것입니까, 아니면 나만의 서비스 공급자를 만드는 것이 좋습니까?
Ragnarsson

2
공유 할 항목이 하나 또는 두 개만 있으면 넣는 것이 AppServiceProvider좋지만 그 이상을 얻은 경우 새 공급자를 만드는 것을 고려해야합니다.
Marwelln

작동했지만 오늘은 작동하지 않는다는 것을 알았습니다! 사용 composer update도 작동하지 않습니다. 실제로 전혀 발사되지 않습니다 boot(). 두 가지 변수를 공유해야합니다.
itsazzad 2015-06-01

11
마이그레이션을 실행하기 전에 호출되므로 데이터베이스 레코드를 가져 오는 경우에는 작동하지 않습니다. 따라서 기본적으로 데이터베이스 레코드가 존재하기 전에 가져 오려고합니다. 적어도 저에게는 그런 것 같습니다.
lorey

1
불행하게도이 사용자 인증 로그인 :: 사용자 (), Safoor의 # 1 대답은,이 아래 :) 않습니다 공유와 함께 작동하지 않는 것
스탠 스멀 더스

11

나는 이것이 가장 쉬운 것임을 알았다. 새 공급자를 만들고 '*'와일드 카드를 사용하여 모든보기에 연결합니다. 5.3에서도 작동합니다 :-)

<?php

namespace App\Providers;

use Illuminate\Http\Request;
use Illuminate\Support\ServiceProvider;

class ViewServiceProvider extends ServiceProvider
{
    /**
     * Bootstrap the application services.
     * @return void
     */
    public function boot()
    {
        view()->composer('*', function ($view)
        {
            $user = request()->user();

            $view->with('user', $user);
        });
    }

    /**
     * Register the application services.
     *
     * @return void
     */
    public function register()
    {
        //
    }
}

2
당신의 설정 / 응용 프로그램에서 제공의 배열이 공급자 추가 "앱 \ 공급자 \ ViewServiceProvider :: 클래스"
Nadeem0035

8

가장 좋은 방법은 다음을 사용하여 변수를 공유하는 것입니다. View::share('var', $value);

다음을 사용하여 작성하는 데 문제가 있습니다 "*".

다음 접근 방식을 고려하십시오.

<?php
// from AppServiceProvider::boot()
$viewFactory = $this->app->make(Factory::class);

$viewFacrory->compose('*', GlobalComposer::class);

예제 블레이드보기에서 :

  @for($i = 0; $i<1000; $i++)
    @include('some_partial_view_to_display_i', ['toDisplay' => $i])
  @endfor

무슨 일이야?

  • GlobalComposer클래스의 인스턴스가 1,000 사용 시간을 App::make.
  • 이벤트 composing:some_partial_view_to_display_i1000 번 처리 됩니다.
  • 클래스 compose내부 의 함수 GlobalComposer는 1000 번 호출됩니다.

그러나 부분보기 some_partial_view_to_display_i는로 구성된 변수와 관련이 GlobalComposer없지만 렌더링 시간이 크게 늘어납니다.

최선의 접근 방식?

View::share그룹화 된 미들웨어와 함께 사용 .

Route::group(['middleware' => 'WebMiddleware'], function(){
  // Web routes
});

Route::group(['prefix' => 'api'], function (){

});

class WebMiddleware {
  public function handle($request)
  {
    \View::share('user', auth()->user());
  }
}

최신 정보

미들웨어 파이프 라인을 통해 계산되는 것을 사용 하는 경우 적절한 이벤트수신 하거나 파이프 라인의 마지막 하단에 뷰 공유 미들웨어를 배치 할 수 있습니다.


4

문서에서 :

일반적으로 서비스 공급자의 부팅 메서드 내에서 공유 메서드를 호출합니다. AppServiceProvider에 추가하거나이를 수용 할 별도의 서비스 공급자를 생성 할 수 있습니다.

Marwelln에 동의 AppServiceProvider합니다. 부팅 기능에 넣습니다 .

public function boot() {
    View::share('youVarName', [1, 2, 3]);
}

다른 '전역'변수가없는 혼동이나 실수를 피하기 위해 변수에 특정 이름을 사용하는 것이 좋습니다.


3

문서는 https://laravel.com/docs/5.4/views#view-composers를 듣지만 분해하겠습니다.

  1. 디렉토리를 찾아 응용 프로그램 \ 공급자 응용 프로그램의 루트 디렉토리 및 파일 생성 ComposerServiceProvider.php을 복사하고 그것에과 저장 아래의 텍스트 과거.

    <?php
        namespace App\Providers;
        use Illuminate\Support\Facades\View;
        use Illuminate\Support\ServiceProvider;
    
        class ComposerServiceProvider extends ServiceProvider
        {
            /**
            * Register bindings in the container.
            *
            * @return void
            */
        public function boot()
        {
            // Using class based composers...
            View::composer(
                'profile', 'App\Http\ViewComposers\ProfileComposer'
            );
    
            // Using Closure based composers...
            View::composer('dashboard', function ($view) {
                //
            });
        }
    
        /**
        * Register the service provider.
        *
        * @return void
        */
        public function register()
        {
            //
        }
    }
  2. 애플리케이션의 루트에서 Config / app.php를 열고 파일에서 Providers 섹션을 찾은 다음이 'App \ Providers \ ComposerServiceProvider'를 복사 하여 배열에 붙여 넣습니다 .

이를 통해 Composer 서비스 공급자를 만들었습니다. http : // yourdomain / something / profile 과 같이 프로필보기를 사용하여 애플리케이션을 실행 하면 서비스 공급자 ComposerServiceProvider 가 호출되고 App \ Http \ ViewComposers \ ProfileComposer 클래스가 아래 코드로 인해 Composer 메서드를 호출하여 인스턴스화됩니다. 부팅 방법 또는 기능.

 // Using class based composers...
 View::composer(
   'profile', 'App\Http\ViewComposers\ProfileComposer'
 );
  1. 응용 프로그램을 새로 고치면 App \ Http \ ViewComposers \ ProfileComposer 클래스 가 아직 존재하지 않기 때문에 오류가 발생 합니다. 이제 만들어 보겠습니다.

디렉토리 경로 app / Http로 이동하십시오.

  • ViewComposers 라는 디렉터리를 만듭니다.

  • ProfileComposer.php 파일을 만듭니다 .

    class ProfileComposer
    {
        /**
        * The user repository implementation.
        *
        * @var UserRepository
        */
        protected $users;
    
        /**
        * Create a new profile composer.
        *
        * @param  UserRepository  $users
        * @return void
        */
        public function __construct(UserRepository $users)
        {
            // Dependencies automatically resolved by service container...
            $this->users = $users;
        }
    
        /**
        * Bind data to the view.
        *
        * @param  View  $view
        * @return void
        */
        public function compose(View $view)
        {
            $view->with('count', $this->users->count());
        }
    }

이제보기 또는이 경우 Profile.blade.php로 이동하여

{{ $count }}

프로필 페이지의 사용자 수가 표시됩니다.

모든 페이지 변경 횟수를 표시하려면

// Using class based composers...
View::composer(
    'profile', 'App\Http\ViewComposers\ProfileComposer'
);

// Using class based composers...
View::composer(
    '*', 'App\Http\ViewComposers\ProfileComposer'
);

<? php 및 네임 스페이스 App \ Http \ ViewComposers; Illuminate \ Contracts \ View \ View를 사용하십시오. ProfileComposer.php에서 누락되었습니다
Unicco



1

config 폴더 안에 php 파일 이름을 만들 수 있습니다. 예를 들어 "variable.php"에 아래 내용이 있습니다.

<?php

  return [
    'versionNumber' => '122231',
  ];

이제 모든 뷰에서 다음과 같이 사용할 수 있습니다.

config('variable.versionNumber')

정보가 진정으로 글로벌하고 어디서나 액세스 할 수 있기 때문에 어떤 경우에는 이렇게합니다. 이러한 이유로 구성 파일 "global.php"를 호출하고 코드의 다른 모든 부분에서 액세스 할 수있는 모든 항목을 거기에 넣습니다. 유일한 제한은 이것이 정적 데이터에 대한 것이며 캐시됩니다. 지속적으로 데이터를 변경하는 경우 이러한 방식으로 사용해서는 안됩니다.
eResourcesInc

1

1) (app \ Providers \ AppServiceProvider.php)에서

// in boot function
       view()->composer('*', function ($view) {
            $data = User::messages();
            $view->with('var_messages',$data);
        });

2) 사용자 모델에서

  public static function messages(){ // this is just example
        $my_id = auth()->user()->id;
        $data= Message::whereTo($my_id)->whereIs_read('0')->get(); 
        return $data; // return is required
    }

3) 당신의 관점에서

 {{ $var_messages }}


0

두 가지 옵션이 있습니다.

1. App \ Providers \ AppServiceProvider의 부팅 기능을 통해 공유

public function boot() { view()->share('key', 'value'); }

그리고보기 파일에서 $ key 변수에 액세스합니다.

참고 : 여기에서는 현재 세션, 인증, 경로 데이터에 액세스 할 수 없습니다. 이 옵션은 정적 데이터를 공유하려는 경우에만 유용합니다. 현재 사용자, 경로 또는 이로 수행 할 수없는 사용자 지정 세션 변수를 기반으로 일부 데이터를 공유한다고 가정합니다.

  1. 도우미 클래스 사용 응용 프로그램의 어느 위치 에나 도우미 클래스를 만들고 config 폴더의 app.php 파일에있는 Alias ​​배열에 등록합니다.

'aliases' => [ ..., 'Helper' => App\HelperClass\Helper::class, ],

App 폴더 내의 HelperClass 폴더에 Helper.php를 만듭니다.

namespace App\HelperClass;

class Helper
{
    public static function Sample()
    {
        //Your Code Here
    }
}

어디서나 액세스 할 수 있습니다. Helper::Sample()

여기에서 Auth, Route, Session 또는 기타 클래스를 사용하도록 제한되지 않습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.