【Laravel】模型封装属性基础

文章目录

概要

随着项目规模的扩大,模型中的属性和方法可能会变得越来越复杂,这会使得代码的维护变得更加困难。为了提高代码的可维护性和可扩展性,我们可以通过封装模型属性来简化这些操作。本文将探讨如何封装 Laravel 模型中的属性,如何将属性封装成方法,并提供一种清晰、结构化的方式来管理模型的属性

什么是封装模型属性?

封装模型属性是将模型的属性(字段)通过方法进行封装,而不是直接访问属性本身。通过这种方式,可以集中处理一些常见的逻辑,比如格式化、转换、验证等,避免将这些操作散布在代码的各个地方。

例如,假设我们有一个 Goods 模型,模型中有一个 price 属性。我们可以封装这个属性,通过方法来自动处理转换,例如将价格从数据库存储的整数(分)转换为浮动数值(元),或反之。

使用访问器和修改器封装属性

Laravel 的 Eloquent 提供了访问器(Accessor)和修改器(Mutator)来帮助我们封装属性。访问器和修改器是通过特定的方法名称约定来定义的,分别用于获取和设置模型的属性值。

模型实现

php 复制代码
namespace App\Models;

use App\Services\Goods\Contracts\GoodsEntity;

class Goods extends BaseModel implements GoodsEntity
{
 	use \App\Models\Traits\GoodsEntity;
}

对应的访问器和修改器接口

php 复制代码
namespace App\Services\Goods\Contracts;

use App\Services\Goods\Contracts\Accessors\GoodsAccessor;
use App\Services\Goods\Contracts\Mutators\GoodsMutator;

interface GoodsEntity extends GoodsAccessor, GoodsMutator
{

}

访问器(Accessor)

访问器用于获取属性值时进行处理,通常用于格式化、转换或者添加前后缀等操作。通过定义一个访问器方法,你可以自动在访问属性时进行转换或计算。

访问器接口

php 复制代码
namespace App\Services\Goods\Contracts\Accessors;

interface GoodsAccessor
{

    /**
     * 获取商品品牌Id
     * @return string
     */
    public function getBrandId(): int;

    /**
     * 获取商品名称
     * @return array
     */
    public function getGoodsName(): string;

    /**
     * 获取商品副标题
     * @return string
     */
    public function getGoodsSubname(): string;

    /**
     * 获取商品编号
     * @return float
     */
    public function getGoodsNo(): string;

    /**
     * 获取价格
     * @return float
     */
    public function getGoodsPrice(): float;

    /**
     * 获取商品市场价格
     * @return float
     */
    public function getGoodsMarketPrice() : float;

    /**
     * 获取商品库存
     * @return int
     */
    public function getGoodsStock() : int;

    /**
     * 获取商品销量
     * @return int
     */
    public function getGoodsSale() : int;

}

访问器实现

php 复制代码
namespace App\Models\Traits\Accessors;

trait GoodsAccessor
{
    /**
     * 获取商品品牌Id
     * @return string
     */
    public function getBrandId(): int
    {
        return $this->attributes['brand_id'];
    }

    /**
     * 获取商品名称
     * @return array
     */
    public function getGoodsName(): string
    {
        return $this->attributes['goods_name'];
    }

    /**
     * 获取商品副标题
     * @return string
     */
    public function getGoodsSubname(): string
    {
        return $this->attributes['goods_subname'];
    }

    /**
     * 获取商品编号
     * @return float
     */
    public function getGoodsNo(): string
    {
        return $this->attributes['goods_no'];
    }

    /**
     * 获取价格
     * @return float
     */
    public function getGoodsPrice(): float
    {
        return $this->attributes['goods_price'];
    }

    /**
     * 获取商品市场价格
     * @return float
     */
    public function getGoodsMarketPrice() : float
    {
        return $this->attributes['goods_market_price'];
    }

    /**
     * 获取商品库存
     * @return int
     */
    public function getGoodsStock() : int
    {
        return $this->attributes['goods_stock'];
    }

    /**
     * 获取商品销量
     * @return int
     */
    public function getGoodsSale() : int
    {
        return $this->attributes['goods_sale'];
    }
}

修改器(Mutator)

修改器用于设置属性值时进行处理,通常用于数据的格式化、转换或者加密等操作。通过定义一个修改器方法,你可以在给属性赋值时进行转换。

修改器接口

php 复制代码
namespace App\Services\Goods\Contracts\Mutators;

interface GoodsMutator
{

    /**
     * 设置品牌id
     * @param int $brandId
     * @return $this
     */
    public function setBrandId(int $brandId);

    /**
     * 设置商品名称
     * @param string $name
     * @return $this
     */
    public function setGoodsName(string $name);

    /**
     * 设置商品副名称
     * @param string $goodsSubname
     * @return $this
     */
    public function setGoodsSubname(string $goodsSubname);

    /**
     * 设置商品编号
     * @param string $goodsNo
     * @return $this
     */
    public function setGoodsNo(string $goodsNo);

    /**
     * 设置价格
     * @param float $price
     * @return $this
     */
    public function setGoodsPrice(float $price);

    /**
     * 设置商品市场价格
     * @param float $price
     * @return $this
     */
    public function setGoodsMarketPrice(float $price);

    /**
     * 设置商品库存
     * @param int $stock
     * @return $this
     */
    public function setGoodsStock(int $stock);

    /**
     * 设置商品销量
     * @param int $sale
     * @return $this
     */
    public function setGoodsSale(int $sale);
}

修改器实现

php 复制代码
namespace App\Models\Traits\Mutators;

trait GoodsMutator
{

    /**
     * 设置品牌id
     * @param int $brandId
     * @return $this
     */
    public function setBrandId(int $brandId)
    {
        $this->attributes['brand_id'] = $brandId;
        return $this;
    }

    /**
     * 设置商品名称
     * @param string $name
     * @return $this
     */
    public function setGoodsName(string $name)
    {
        $this->attributes['goods_name'] = $name;
        return $this;
    }

    /**
     * 设置商品副名称
     * @param string $goodsSubname
     * @return $this
     */
    public function setGoodsSubname(string $goodsSubname)
    {
        $this->attributes['goods_subname'] = $goodsSubname;
        return $this;
    }

    /**
     * 设置商品编号
     * @param string $goodsNo
     * @return $this
     */
    public function setGoodsNo(string $goodsNo)
    {
        $this->attributes['goods_no'] = $goodsNo;
        return $this;
    }

    /**
     * 设置价格
     * @param float $price
     * @return $this
     */
    public function setGoodsPrice(float $price)
    {
        $this->attributes['goods_price'] = $price;
        return $this;
    }

    /**
     * 设置商品市场价格
     * @param float $price
     * @return $this
     */
    public function setGoodsMarketPrice(float $price)
    {
        $this->attributes['goods_market_price'] = $price;
        return $this;
    }

    /**
     * 设置商品库存
     * @param int $stock
     * @return $this
     */
    public function setGoodsStock(int $stock)
    {
        $this->attributes['goods_stock'] = $stock;
        return $this;
    }

    /**
     * 设置商品销量
     * @param int $sale
     * @return $this
     */
    public function setGoodsSale(int $sale)
    {
        $this->attributes['goods_sale'] = $sale;
        return $this;
    }
}

测试业务实现

控制器代码

php 复制代码
namespace App\Http\Controllers\Learn;

use App\Http\Controllers\Controller;
use App\Http\Resources\Goods\GoodsResource;
use App\Models\Goods;
use Illuminate\Http\Request;

class GoodsController extends Controller
{
    public function getEntityList()
    {
        $list = Goods::query()->get();
        return GoodsResource::collection($list);
    }
}

将模型或集合转换为 JSON

php 复制代码
namespace App\Http\Resources\Goods;

use Illuminate\Http\Resources\Json\JsonResource;

class GoodsResource extends JsonResource
{

    /**
     * Transform the resource into an array.
     *
     * @param \Illuminate\Http\Request $request
     * @return array
     */
    public function toArray($request)
    {
        $item = $this->resource;
        return [
            'brand_id'           => $item->getBrandId(),
            'goods_name'   => $item->getGoodsName(),
            'goods_subname'   => $item->getGoodsSubname(),
            'goods_no'      => $item->getGoodsNo(),
            'goods_price'        => $item->getGoodsPrice(),
            'goods_market_price'   => $item->getGoodsMarketPrice(),
            'goods_stock' => $item->getGoodsStock(),
            'goods_sale'           => $item->getGoodsSale(),
        ];
    }
}

运行结果

通过访问接口验证实现效果:

http://xxx.test/api/Learn/goods/getEntityList

结果:

json 复制代码
{
    "data": [
        {
            "brand_id": 1,
            "goods_name": "温热温热",
            "goods_subname": "额我认为耳闻",
            "goods_no": "",
            "goods_price": 34,
            "goods_market_price": 34,
            "goods_stock": 44,
            "goods_sale": 3
        },
        {
            "brand_id": 0,
            "goods_name": "额温热玩儿",
            "goods_subname": "而扼腕容器",
            "goods_no": "",
            "goods_price": 33.4,
            "goods_market_price": 44,
            "goods_stock": 33,
            "goods_sale": 4
        },
        {
            "brand_id": 1,
            "goods_name": "空调开空调开",
            "goods_subname": "的方式地方的说法",
            "goods_no": "",
            "goods_price": 33,
            "goods_market_price": 44,
            "goods_stock": 2232,
            "goods_sale": 0
        }
    ]
}

小结

封装模型属性是提高 Laravel 应用可维护性和可扩展性的一种有效方法。通过使用 Eloquent 提供的访问器、修改器和自定义方法,我们可以将常见的属性转换、计算或格式化逻辑集中管理,避免将业务逻辑散布在控制器和视图中。这样不仅能够提升代码的可读性,也能确保数据处理的一致性。

在实际开发中,可以根据项目的需求灵活选择封装的方式,确保代码的高效和可维护性。

相关推荐
约定Da于配置1 小时前
uniapp封装websocket
前端·javascript·vue.js·websocket·网络协议·学习·uni-app
山楂树の1 小时前
xr-frame 模型摆放与手势控制,支持缩放旋转
前端·xr·图形渲染
LBJ辉2 小时前
1. 小众但非常实用的 CSS 属性
前端·css
milk_yan2 小时前
Docker集成onlyoffice实现预览功能
前端·笔记·docker
村口蹲点的阿三4 小时前
Spark SQL 中对 Map 类型的操作函数
javascript·数据库·hive·sql·spark
m0_748255024 小时前
头歌答案--爬虫实战
java·前端·爬虫
noravinsc5 小时前
python md5加密
前端·javascript·python
ac-er88885 小时前
Yii框架优化Web应用程序性能
开发语言·前端·php
cafehaus5 小时前
抛弃node和vscode,如何用记事本开发出一个完整的vue前端项目
前端·vue.js·vscode
HoneyMoose6 小时前
可以自己部署的微博 Mastodon
前端