docs
docs copied to clipboard
Приватные свойства - зачем?
Доброго дня. Т.к. свой новый корпоративный проект я решил сразу начать на yii3, то возник ряд вопросов/непониманий. Относятся они наверно ко всему yii3, но живой кейс возник с виджетом табов, поэтому напишу сюда.
Итак имеем:
- Виджет табов, у которого все свойства приватны и имееют type hint
- Сеттер на каждое свойство (зачем там устанавливается через clone мне тоже непонятно, но опустим)
- В конструкторе виджета генерируется $options['id'] если не установлен
Мой "живой" случай в идеале, но не как сейчас:
$tabs = Tabs::widget();
//Ставим остальные свойства через сеттер
$this->registerJs('Vue.createApp(SourceTabsOptions).mount("#' . $tabs->options['id'] . '");');
Т.е. мне всё-равно какой id сгенерится виджетом, у меня к нему не привязано никаких CSS, ни чего другого. Но сейчас я вынужден каждый раз выдумывать этот самый id элемента, т.к. не могу получить приватный $options
Вопрос - а почему эти свойства не сделать публичными?
- Из-за type hint'ов я не смогу поставить недопустимое значение
- Это избавит от написания кучи однообразных сеттеров, которые по сути делают тоже самое
- При наличие того-же сеттера, приватные свойства не имеют смысла - т.к. я в любой момент могу его изменить через него.
При этом, если допустить ошибку и забыть при конфигурации указать "()" в конце, то yii3 заботливо предлагает добавить "$" в начало, чтобы установить свойство - что опять-же не работает с приватными свойствами. Но как минимум я так полагаю, что задумка такая была, но сейчас я мало где вижу ей применение, т.к. практически всё либо private, либо в лучшем случае protected
Заранее благодарен
For get id
we can make method getId()
public.
Private properties and getter/setters allow easier to make changes in the future, create readonly or writeonly properties, also in most cases getter or setter perform additional actions (for example, in Tabs
setters make clone of widget).
Clone are needed in order for the widgets to be immutable.
For get
id
we can make methodgetId()
public.Private properties and getter/setters allow easier to make changes in the future, create readonly or writeonly properties, also in most cases getter or setter perform additional actions (for example, in
Tabs
setters make clone of widget).Clone are needed in order for the widgets to be immutable.
Делать getId() пабликом бессмысленно - т.к. на каждый вызов он будет генерить новый id за счёт накручивающегося счётчика + у данных виджетов "по хардкору" вписан суффикс (-tabs, -alert и т.д.) который может быть изменён в следующих релизах или вообще исчезнуть.
И перефразирую - readonly свойства нужны, не спорю. НО сейчас получается нет никаких read свойств, никаких геттеров - по сути мы имеем сплошное writeonly, т.е. мы можем установить значение, но не можем обратно получить. А это зачастую нужно и именно после манипуляций с этим свойством самим виджетом.
Ну и ИМХО - иммутабельность иммутабельностью, но может не стоит возводить её в абсолют, особенно там где она не "делает погоды"? Т.е. вот тут я не вижу от этого пользы, т.к. всё что требуется - это отрисовать нужный мне контент, в нужном мне месте в зависимости от виджета, всё. Но вижу вред - вынужден ждать когда будут потрачены человекочасы на написание геттеров к каждому свойству у которого есть сеттер и не факт, что они вообще будут написаны (хотя хватило бы просто сделать часть свойств, которые может установить пользователь публичными)
Т.е. к примеру я в миграциях повсеместно напрямую использую ColumnSchemaBuilder, чтобы дополнить недостающие в MigrationBuilder нативные pgsql типы (point, *range, uuid) и никаких проблем с отсутствием в нём иммутабельности я не обнаружил
In getId()
id generated once (see code) and saved in private property.
If getters real need (has use cases), then we should added their.
In modern IDEs create base setters/getter very simple. For example, in PhpStorm:
Immutable objects making impossible to make certain types of mistakes. When we pass an object to somewhere, we are sure that it will not change.
Виджет табов, у которого все свойства приватны и имееют type hint
что удивительного в доступе к свойствам через сеттер/геттер?
Сеттер на каждое свойство (зачем там устанавливается через clone мне тоже непонятно, но опустим)
почитай о immutable objects
При наличие того-же сеттера, приватные свойства не имеют смысла - т.к. я в любой момент могу его изменить через него.
смысл в том что у тебя нет прямого доступа к свойству, ты вызываешь сеттер для его изменения, данных метод может нормализовывать/форматрировать передаваемое значение что гарантирует корректную запись в свойстве.
Для понимания подобных концепций стоит вначале ознакомится с SOLID