লোডের উপর একটি ল্যারাভেল / স্বতন্ত্র মডেলটিতে একটি কাস্টম বৈশিষ্ট্য যুক্ত করবেন?


219

রেডবিনের $model->open() পদ্ধতিতে কীভাবে এটি অর্জন করা যায় তার অনুরূপ, লোড করা হলে আমি লারাভেল / এলওলিউড মডেলটিতে একটি কাস্টম অ্যাট্রিবিউট / সম্পত্তি যুক্ত করতে সক্ষম হতে চাই ।

উদাহরণস্বরূপ, এই মুহুর্তে, আমার নিয়ামকটিতে আমার রয়েছে:

public function index()
{
    $sessions = EventSession::all();
    foreach ($sessions as $i => $session) {
        $sessions[$i]->available = $session->getAvailability();
    }
    return $sessions;
}

লুপটি বাদ দিতে এবং 'উপলভ্য' বৈশিষ্ট্যটি ইতিমধ্যে সেট এবং পপুলেটেড করতে সক্ষম হওয়াই ভাল লাগবে।

বস্তুটি লোড হওয়ার পরেও এই সম্পত্তিটি সংযুক্ত করতে ডকুমেন্টেশনে বর্ণিত কিছু মডেল ইভেন্টগুলি ব্যবহার করার চেষ্টা করেছি, তবে এখন পর্যন্ত সাফল্য ছাড়াই।

মন্তব্য:

  • অন্তর্নিহিত সারণীতে 'উপলভ্য' কোনও ক্ষেত্র নয়।
  • $sessionsকোনও এপিআই-র অংশ হিসাবে জেএসওএন অবজেক্ট হিসাবে ফিরিয়ে দেওয়া হচ্ছে, এবং সুতরাং $session->available()কোনও টেম্পলেটের মতো কিছু কল করা কোনও বিকল্প নয়

উত্তর:


316

সমস্যাটি এই কারণে ঘটেছিল যে Modelএর toArray()পদ্ধতিটি এমন কোনও প্রবেশকারীকে অগ্রাহ্য করে যা অন্তর্নিহিত সারণীর কোনও কলামের সাথে সরাসরি সম্পর্কিত নয়।

যেমন টেলর ওটওয়েল এখানে উল্লেখ করেছেন , "এটি উদ্দেশ্যমূলক এবং পারফরম্যান্সের কারণে।" তবে এটি অর্জনের একটি সহজ উপায় রয়েছে:

class EventSession extends Eloquent {

    protected $table = 'sessions';
    protected $appends = array('availability');

    public function getAvailabilityAttribute()
    {
        return $this->calculateAvailability();  
    }
}

End সংযোজন সম্পত্তিটিতে তালিকাভুক্ত যে কোনও বৈশিষ্ট্য স্বয়ংক্রিয়ভাবে মডেলের অ্যারে বা জেএসওএন ফর্মের মধ্যে অন্তর্ভুক্ত হবে, যদি আপনি উপযুক্ত প্রবেশাধিকারী যুক্ত হন তবে।

পুরানো উত্তর (লারাভেল সংস্করণ <4.08 এর জন্য):

আমি যে সর্বোত্তম সমাধানটি পেয়েছি তা হ'ল toArray()পদ্ধতিটি ওভাররাইড করা এবং হয় স্পষ্টতাই বৈশিষ্ট্যটি সেট করা:

class Book extends Eloquent {

    protected $table = 'books';

    public function toArray()
    {
        $array = parent::toArray();
        $array['upper'] = $this->upper;
        return $array;
    }

    public function getUpperAttribute()
    {
        return strtoupper($this->title);    
    }

}

বা, আপনার যদি প্রচুর কাস্টম অ্যাকসেসর থাকে তবে সেগুলি সমস্ত লুপ করে এগুলি প্রয়োগ করুন:

class Book extends Eloquent {

    protected $table = 'books';

    public function toArray()
    {
        $array = parent::toArray();
        foreach ($this->getMutatedAttributes() as $key)
        {
            if ( ! array_key_exists($key, $array)) {
                $array[$key] = $this->{$key};   
            }
        }
        return $array;
    }

    public function getUpperAttribute()
    {
        return strtoupper($this->title);    
    }

}

আজকের জন্য সেরা প্রশ্নোত্তর। আমি কীভাবে এটি অর্জন করতে পারি এবং লারাভেল.ওয়েতে কোনও প্রশ্ন পোস্ট করার আগে আমি এটি বিভিন্ন রূপায়ণে কাজ করছি! হ্যাঁ !!!
গায়ান হেওয়া

এবং কিছু উপায়ের জন্য এগুলিকে জোসনে যুক্ত না করার উপায় আছে?
জর্ডি পুইগডেলভোল 21

3
সম্পর্কের মাধ্যমে মডেলটি কল করার সময় এই শুল্ক বৈশিষ্ট্যগুলি উপস্থিত হবে বলে মনে হয় না। (প্রাক্তন: মডেলস \ সংস্থা :: সহ ('লোক'))। কোন ধারণা?
অ্যান্ড্রু

@ জোর্ডিপুইগডেললভোল লারাভেল ৫-এ, আপনি protected $hidden = []বাদ দেওয়া কলাম / এক্সেসর যুক্ত করতে ব্যবহার করতে পারেন ।
জঙ্কিস্তু

124

Laravel বলিয়ে ডক পৃষ্ঠাতে শেষ জিনিস হল:

protected $appends = array('is_admin');

মডেলটিতে নতুন অ্যাকসেসর যুক্ত করতে কোনও স্বয়ংক্রিয়ভাবে ব্যবহারের মতো কোনও অতিরিক্ত কাজ যেমন পরিবর্তনের পদ্ধতিগুলি ছাড়াই করা যেতে পারে ::toArray()

শুধু তৈরি getFooBarAttribute(...)অ্যাকসেসর যোগ foo_barকরার $appendsঅ্যারে।


4
আহ আকর্ষণীয়। আমার প্রশ্ন পোস্ট হওয়ার পরে এই বৈশিষ্ট্যটি লারাভেলের সাথে যুক্ত হয়েছে ( github.com/laravel/framework/commit/… )। V4.08 বা ততোধিক উচ্চতর যে কেউ ব্যবহার করছে তার পক্ষে এটি সঠিক উত্তর।
coatesap অক্টোব

3
আপনি যদি আপনার অ্যাক্সেসরগুলির জন্য সামগ্রী তৈরি করতে সম্পর্ক ব্যবহার করেন তবে এটি আপনার কাছে উপলব্ধ হবে না। এই উদাহরণস্বরূপ, আপনাকে toArrayপদ্ধতিটি ওভাররাইড করার জন্য অবলম্বন করতে হতে পারে ।
জিপিএমক্যাডাম

2
দেখে মনে হচ্ছে আপনি যে ডকুমেন্টেশনটি উল্লেখ করেছেন তা এখানে সরানো হয়েছে: https://laravel.com/docs/5.5/eloquent-seialization
mibbler

40

আপনি যদি আপনার getAvailability()পদ্ধতির নিজের নামটির নামকরণ করেন তবে getAvailableAttribute()একজন অ্যাক্সেসর হয়ে যায় এবং আপনি ->availableসরাসরি আপনার মডেলটি ব্যবহার করে এটি পড়তে সক্ষম হবেন ।

দস্তাবেজ: https://laravel.com/docs/5.4/eloquent-mutators#accessors-and-mutators

সম্পাদনা: যেহেতু আপনার বৈশিষ্ট্যটি "ভার্চুয়াল", তাই এটি আপনার বস্তুর JSON উপস্থাপনায় ডিফল্টরূপে অন্তর্ভুক্ত নয়।

তবে আমি এটি পেয়েছি: কাস্টম মডেল অ্যাকসেসরগুলি প্রক্রিয়া করা হয় না -> টুজসন () কে ফোন করা হলে?

আপনার বৈশিষ্ট্যটিকে অ্যারেতে ফিরে আসতে বাধ্য করতে, এটিকে $ গুণাবলী অ্যারেতে একটি কী হিসাবে যুক্ত করুন।

class User extends Eloquent {
    protected $attributes = array(
        'ZipCode' => '',
    );

    public function getZipCodeAttribute()
    {
        return ....
    }
}

আমি এটি পরীক্ষা করিনি, তবে আপনার বর্তমান সেটআপে চেষ্টা করার জন্য আপনার কাছে বেশ তুচ্ছ হওয়া উচিত।


এটি বস্তুটিতে যতটা ->availableউপলভ্য তা $sessionকার্যকরভাবে কাজ করে তবে $sessionsসরাসরি জেএসএন স্ট্রিংয়ে রূপান্তরিত হয় (এটি একটি এপিআইয়ের অংশ), এটি ব্যবহারের সুযোগ নেই।
coatesap

আমি নিশ্চিত না যে আপনার জিনিসগুলি কীভাবে কাজ করে তা আমি বুঝতে পেরেছি। যদি EventSession::all()কোনও এপিআই থেকে কোনও জেএসএন বস্তু ফেরত দেয়, আপনি সত্যিই লারাভেল মডেলটি ব্যবহার করছেন না, তাই না? দুঃখিত, আপনি কীভাবে আপনার মডেলটি প্রয়োগ করেছিলেন তা নিয়ে আমি বিভ্রান্ত।
আলেকজান্দ্রে ডানাল্ট

ইভেন্টসেশন একটি স্ট্যান্ডার্ড এলওভার্ট অবজেক্ট ( class EventSession extends Eloquent)। ::all()যেমন একটি উদাহরণ। EventSession::find(170071)অন্য হতে হবে। এগুলি সেশনকন্ট্রোলার ( SessionController extends \BaseController) জুড়ে বিভিন্ন পয়েন্টে ডাকা হয় যা '/ সেশন / 170071' এর মতো ইউআরএলগুলির মাধ্যমে কল করা হবে।
coatesap

আমি মনে করি কীটি এলওভার্টের অন্তর্নির্মিত বস্তুতে জেএসএন রূপান্তর ঘটতে পারে যা ঘটে takes এমনকি আপনি যদি public $availableমডেলটির মতো কাস্টম বৈশিষ্ট্য যুক্ত করেন তবে অবজেক্টটি রূপান্তরিত হলে এটি প্রদর্শিত হয় না।
কোটসাপ

3
এই উপলব্ধ অক্টোবর 8th উপর Laravel 4.0.8 মুক্তির সাল থেকে 2013 কর্মকর্তা ডক্স দেখুন: laravel.com/docs/eloquent#converting-to-arrays-or-json (জন্য বর্ণন protected $appends = array('is_admin');)
রোনাল্ড Hulshof

23

আমার কিছু সিমুলার ছিল: আমার মডেলটিতে আমার একটি বৈশিষ্ট্যযুক্ত চিত্র রয়েছে এটি স্টোরেজ ফোল্ডারে ফাইলের অবস্থান ধারণ করে। চিত্রটি অবশ্যই বেস 64 এনকোড করাতে হবে

//Add extra attribute
protected $attributes = ['picture_data'];

//Make it available in the json response
protected $appends = ['picture_data'];

//implement the attribute
public function getPictureDataAttribute()
{
    $file = Storage::get($this->picture);
    $type = Storage::mimeType($this->picture);
    return "data:" . $type . ";base64," . base64_encode($file);
}

1
এটি চিত্র_ডেটা picture বৈশিষ্ট্যগুলি এবং $ সংযোজনগুলিতে চিত্র নয় ডেটা হওয়া উচিত। এবং আপনি $ বৈশিষ্ট্যগুলি পরিবর্তনশীলও এড়িয়ে যেতে পারেন।
মধুশান পেরেরা

16

আপনি setAttributeএকটি কাস্টম বৈশিষ্ট্য যুক্ত করতে মডেলটিতে ফাংশন ব্যবহার করতে পারেন


9

ধরা যাক আপনার ব্যবহারকারীর টেবিলে আপনার প্রথম নাম এবং সর্বশেষ নাম নামের দুটি কলাম রয়েছে এবং আপনি পুরো নামটি পুনরুদ্ধার করতে চান। আপনি নিম্নলিখিত কোড সহ অর্জন করতে পারেন:

class User extends Eloquent {


    public function getFullNameAttribute()
    {
        return $this->first_name.' '.$this->last_name;
    }
}

এখন আপনি পুরো নামটি পেতে পারেন:

$user = User::find(1);
$user->full_name;

7

পদক্ষেপ 1: $appends
দ্বিতীয় ধাপে বৈশিষ্ট্যগুলি সংজ্ঞায়িত করুন : সেই বৈশিষ্ট্যের জন্য অ্যাক্সেসরকে সংজ্ঞায়িত করুন।
উদাহরণ:

<?php
...

class Movie extends Model{

    protected $appends = ['cover'];

    //define accessor
    public function getCoverAttribute()
    {
        return json_decode($this->InJson)->cover;
    }

3

আমার সাবস্ক্রিপশন মডেলটিতে আমার চাঁদাটি বিরতি দেওয়া হয়েছে কিনা তা জানতে হবে। আমি এখানে এটি কিভাবে

public function getIsPausedAttribute() {
    $isPaused = false;
    if (!$this->is_active) {
        $isPaused = true;
    }
}

তারপরে ভিউ টেমপ্লেটে, আমি $subscription->is_pausedফলাফলটি পেতে ব্যবহার করতে পারি।

getIsPausedAttributeএকটি কাস্টম অ্যাট্রিবিউট সেট করতে ফরম্যাট,

এবং is_pausedআপনার দর্শনটিতে বৈশিষ্ট্যটি পেতে বা ব্যবহার করতে ব্যবহার করে uses


2

আমার ক্ষেত্রে, একটি খালি কলাম তৈরি করা এবং এর অ্যাক্সেসরটি সেট করা ভাল কাজ করেছে। আমার অ্যাক্সেসর ডাব কলাম থেকে ব্যবহারকারীর বয়স পূরণ করছে। toArray () ফাংশনটিও কাজ করেছে।

public function getAgeAttribute()
{
  return Carbon::createFromFormat('Y-m-d', $this->attributes['dateofbirth'])->age;
}
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.