PHP
雑記
mvc

MVCのモデルの誤解を解くためにフレームワークを例に挙げようとしたら誤解してもしゃーないなって思った

More than 1 year has passed since last update.

モデル?はいはいわかってますよ。

DBを操作するためのクラス(ActiveRecordとか)だけじゃなくてそれ以外もビジネスロジックならモデル行きでしょ?

一番使うのはDBだし?説明簡単だし?それだけだと思いこんじゃうのも仕方ないけど、まあちゃんと解説読んでみてよ。

自分が使っているフレームワークのドキュメントとかわかりやすいんじゃない?

って思ってたけど調べたらうーん…

「(フレームワーク) モデル」などで検索

引用記事です


Zend1

明確なモデルの説明は無し?

モデルとデータベーステーブルの作成

https://framework.zend.com/manual/1.11/ja/learning.quickstart.create-model.html

create-model.html

「DBを扱うモデル」の作り方の説明のみ。

タイトルからもモデルとデータベースが強く紐付いていると受け取れる。


Laravel

Laravelはmodelと決別したがってたかなーという記憶がありましたが

ディレクトリ構造 5.3 Laravel


modelsディレクトリはどこにある?

Laravelを学習し始めるとき、多くの開発者はmodelsディレクトリが存在しないことに戸惑います。しかし、意図的にこのディレクトリを用意していません。多くの別々の人達にとって、その意味合いは様々なため、"models"という言葉の定義は曖昧であることに私達は気づきました。ある開発者たちはすべてのビジネスロジックを総称してアプリケーションの「モデル」と呼び、一方で別の人達はリレーショナルデータベースに関連するクラスを「モデル」として参照しています。

このため、私達はEloquentモデルをデフォルトではappディレクトリ下へ設置することを選択し、開発者自分が選んだどこか別の場所へ設置してもらうことにしました。


Eloquent:利用の開始 5.3 Laravel


Eloquent ORMはLaravelに含まれている、美しくシンプルなアクティブレコードによるデーター操作の実装です。それぞれのデータベーステーブルは関連する「モデル」と結びついています。モデルによりテーブル中のデータをクエリできますし、さらに新しいレコードを追加することもできます。


モデル=リレーショナルデータベースに関連するクラスのみという考え方を間違いではなく許容しつつLaravelとしての正解は出さない方向性。

ただ、ディレクトリ構造のページはあまり参照されないでしょうし、Eloquentのページの書き方からしてモデル=Eloquentと覚えてしまうのもありうるなーと。


CakePHP2

モデル CakePHP


モデル

モデルはアプリケーションのビジネスレイヤーを担当するクラスです。 すなわち、業務ドメインにおけるデータやその妥当性、トランザクションや 情報ワークフローの過程で発生する全てのことがらを管理する役割を負うということです。

モデルクラスは通常はデータを表すもので、 CakePHP のアプリケーションではデータアクセスに使われます。 具体的に言うと、モデルはデータベースのテーブルを表しますが、それに限らず ファイルや外部ウェブサービス、iCal のイベントや CSV ファイルの行など、 データを扱うあらゆるものに使われます。


前半はやや難解に色々なものがモデルだと。後半はモデル=DB?

「具体的」より「具体例」とかのほうが?

続いては「ただしDB以外にもCSVなどのデータ型にも対応できる」と読めるかもしれません。(外部ウェブサービスやイベントをどう読み取るか?)

PHPとは別のデータファイル形式の読み書きをするものがモデルだと誤解しなければいいのですが。

その直後に


モデルを理解する

Model はデータモデルを表します。オブジェクト指向プログラミングにおいて、 データモデルは自動車や人、家といった「もの」を表現するオブジェクトです。


とフォローはあるのですが、すぐDBのクエリの話に戻りますね。

MVC(Model-View-Controller)を理解する


モデル(Model)層¶

モデル層はビジネスロジックを実装するアプリケーションの部品を表します。これはデータの検索、アプリケーションに意味のある形への変換、また処理、検証(validating)、関連(associating)、そしてデータを扱うことに関する様々なタスクに責任をもつことを意味します。

一見して、モデルオブジェクトはアプリケーションに使用しているであろうデータベースとやりとりする最初の層と見ることができるでしょう。 しかし、一般的にこれはアプリケーションを実装するものの主要な概念を表します


こっちはいいんじゃないでしょうか。

変換・検証までモデルの責務だと言ってくれていますし。

データベースとのやり取りに終始しないと言及。

3の日本語訳ドキュメントになるとそれらしいページは消えてるんですよね。


FuelPHP

Model-View-Controller - 概要 - FuelPHP ドキュメント


モデル

モデルクラスは APPPATH/classes/model に配置します。

データを取得/処理/削除する必要がある時は必ず、モデルで行うべきです。 モデルは、ある種のデータの表現であり、データを変更するメソッドがあります。例: コントローラに SQL クエリを置くべきではありません。SQL クエリはモデルに置き、コントローラはクエリを実行するときにモデルを呼び出します。 こうすると、データベースが変更になった場合、コントローラを変更する必要はなく、 データベースを扱うモデルのみ変更すればよいです。


データを取得/処理/削除するもの=モデル。

間違ってはいないんでしょうね?


モデルは、ある種のデータの表現であり、データを変更するメソッドがあります。


はいいと思うんですけど、直後の例で「データ」というなんかふにゃっと抽象化されたものから「データ=DB,SQL」といったものに固定化されないか。

モデル - 概要 - FuelPHP ドキュメント


モデルとは?

データを取得し、操作し、あるいはそれを消去したい場合、その処理は常にモデルによって行われるべきです。モデルは、ある種のデータ表現であり、 データを変化させるメソッドを持ちます。たとえば。コントローラには SQL クエリを一切記述せず、モデル側にそれを記述し、コントローラではモデルが実行したクエリを呼び出す、 というような処理が出来ます。この方法によって、データベースを変更した時もコントローラを書き換える必要はなく、データベースに影響を及ぼすモデルのみを書き換えるだけですむのです。

どのようにモデルを使うか?

Fuel において、モデルの本質は単なる クラス です。他のものと同様なのです。つまりライブラリ以外のなにものでもありません。 ただし Model_ プレフィックスが付いているので、他のクラスと見分けを付けることが容易になります。モデルを有効に使うためには、他のクラスを必要とするでしょう。

モデルを書く

モデルは、どのようなかたちのデータストレージに対しても使うことができますが、ここでは SQL での利用に焦点を当てましょう。というのも、 それが最もよく使われているものだからです。ほとんど常だと思いますが、作られるモデルには少なくとも CRUD メソッド: create, read, update, delete (あるいはそれらのバリエーション) の 4 つが全て含まれているはずです。Fuel においては、 モデルは、デフォルトでは何も継承する必要がありません。 もちろん、自分なりのベースモデルを作ることや Fuel の Orm パッケージ を使うことも出来ます。


「モデルの本質は単なる クラス」とはいうものの、データストレージへの対応のみを説き、とくにSQLの利用が最もよく使われていると断言。


CodeIgniter

モデル — CodeIgniter 3.2.0-dev ドキュメント


モデルとは何ですか?

モデルとは PHP クラスであり、データベースの情報とともに動作するように設計されるものです。 たとえば、 CodeIgniter でブログを管理するとしましょう。 モデルクラスはブログのデータを挿入、更新、 および取得するための関数を含むモデルクラスが必要でしょう。 これはこのようなモデルクラスの例です:


データベースと強く紐付いている解説。


データベースの情報とともに


とあるのでモデルとDBは不可分と取れるでしょう。


Yii

参考資料で賞賛されていたYiiドキュメント

基本: モデル | The Definitive Guide to Yii | Yii PHP Framework


モデル

モデルは CModel または CModel を継承したクラスのインスタンスです。 モデルはデータや関連するビジネスルールを保持するために使用されます。

モデルは単一のデータオブジェクトを表します。 それは、データベーステーブルの行であったり、または、ユーザ入力フィールドを持った HTML フォームであったりします。 データオブジェクトのそれぞれのフィールドは、モデルの属性として表されます。 そして、属性はラベルを持ち、一連のルールに対する正当性を検証することができます。

Yii はフォームモデルとアクティブレコードの 2 種類のモデルを実装しています。 両方とも同じベースクラス CModel を継承しています。

モデルを定義するときのベストプラクティスについては、 MVC のベストプラクティス の モデルの章を参照して下さい。


中々いいんじゃないですか?

強引に見れば、モデルとはアクティブレコードとフォームモデルの2種類という誤解も出そうですけど、他のものよりは誤解が少なそうな書き方に見えます。


モデルは単一のデータオブジェクトを表します。


を外さなければいいですよね。冒頭にあるのがいいと思った。

基本: MVC のベストプラクティス | The Definitive Guide to Yii | Yii PHP Framework



  1. モデル ¶

モデル は、ウェブアプリケーションの基礎になるデータ構造を表します。例えば、LoginForm モデルは、アプリケーションのフロントエンドとバックエンドの両方で使われるでしょう。News モデルは、アプリケーションのコンソールコマンド、ウェブ API、フロントエンド、バックエンドで使われるでしょう。従って、


  • モデルは特定のデータを表現するプロパティを持たなければなりません。


  • モデルは、モデルが表しているデータが設計の要求を満たすことを保証するために、ビジネスロジック (例えば、検証ルール) を持たなければなりません。


  • モデルはデータを操作するためのコードを持つことが出来ます。例えば、SearchForm モデルは、検索入力データを表現する他に、実際の検索を実装するために search メソッドを持つことが出来ます。



「ウェブアプリケーションの基礎になるデータ構造」はモデルと言ってますから、DBより範囲は広いですよね。

ビジネスロジックを持たなければならないと強制している点もいいと思う。


Mithrilf.js

はじめよう - Mithrilf


モデル

Mithrilでは基本的に、アプリケーションは名前空間の中に作り、コンポーネントをその中に格納していきます。コンポーネントは見ることが可能な「ページ」もしくはページの一部を表す、単なる構造体です。アプリケーションはModel、Controller、Viewの大きく3つのレイヤーにきれいに分割することができます。

モデルの実体は再利用可能なため、コンポーネントの外で定義されることが多いです

昔ながらのMVCパターンの定義によると、モデルレイヤはデータの保持、状態の管理、ビジネスロジックについての責務を負っています。


コンポーネントが絡んでよくわからなくなる。

というかビューモデル使ってるんでMVVMですよね?

よそでMVVMとして紹介されてますし。

JSの今風なFWは全部MVVMとかMVW?じゃないかしらん。


Ruby on Rails

Active Record Basics — Ruby on Rails Guides


1 What is Active Record?

Active Record is the M in MVC - the model - which is the layer of the system responsible for representing business data and logic. Active Record facilitates the creation and use of business objects whose data requires persistent storage to a database. It is an implementation of the Active Record pattern which itself is a description of an Object Relational Mapping system.


Active Record is the M in MVC

言い切った。間違いではないんですけど…

Active Record の基礎 | Rails ガイド


Active Recordとは、MVCで言うところのM、つまりモデルに相当するものであり、ビジネスデータとビジネスロジックを表すシステムの階層です。Active Recordは、データベースに恒久的に保存される必要のあるビジネスオブジェクトの作成と利用を円滑に行なえるようにします。Active Recordは、ORM (オブジェクトリレーショナルマッピング) システムに記述されている「Active Recordパターン」を実装したものであり、同じ名前が付けられています。


モデル(model) - - Railsドキュメント


モデルとは

データベースの情報を操作する仕組み


Railと言えばActive Record(個人の感想です)。

Active Recordを全面に押し出すプッシュっぷりの影響?

rails generate model hogeがこれだけでActive Recordとして動くんだからさもありなん。


感想(自由記述)

自分なら勘違いする。というかしてました。

モデルって、継承を使わないプレーンなクラスで表現することもあるはずで、

じゃあフレームワークでモデルを紹介しようとするとフレームワークが提供しているORマッパー的なDB操作するモデルの話に終始してしまうのかな、という印象。

事実、利用(作成)頻度が一番高いものはSQLを使うDBのモデルなんでしょうけど。

明言はしていないものの例題ではDBばかり使われているので、自然に頭の中でイコールがついていく。

他のモデルの作り方がサンプルとしてないから、作らない。作れない。作れないと思い込む。

初心者ってMVCを自作するわけもなく、「MVCとは」からがっつり学ぶことは少なくて、フレームワークから入って、フレームワークが使っているMVCという概念をフレームワークから学んでいくんじゃないかなあと想像する。

だからフレームワークのドキュメントとかジェネレーターによる自動生成に強く影響を受けるんじゃないかなあ。

と、PHPerのMVCの一体どこが間違っていたのか - MugeSoの日記を読んで確証バイアスしつつ。

あと、JSはガラッと雰囲気が変わって合っているかわからない。

MVC限定で話をするムリさ。

「hogehoge(Active Record, Eloquent)はモデルです」と言われた時、「モデルとはhogehogeだ」と理解する人は居そう。自分はする。

「hogehogeはモデルの形式のひとつです」程度なら…?

でも海外でもありそうな誤解ですし。

「AはBです」という日本語がもうわけがわからないよ。

包含関係を書いておいてくれればいいのだろうか?

DB操作のためのクラス ⊆ モデル ?

自分自身、まだDB以外のモデルってなんだろって状態なんですが、実際難し

いです。

MにもCにも入れられないビジネスロジックはライブラリやサービスという名前で押し付ける。とか。

Laravelの結論がある種の進退窮まった1現状の最適解なのかもしれないです。

けど、使う側は困らない?

あとわりと「自分はMVCフレームワークです」って公言しているフレームワークを探すことが難しかった。

StrutsはMVCとMVC2?があって避けた。

言行不一致ならみなさん行に従いません?

法令遵守と言いながら「流れに従う」という謎理論で制限速度オーバーしたり?するらしい。

wikiなどの定義ではビジネスロジックを書くと見かけても、実際の実装のフレームワーク側を見るとモデルはDBばっかり扱ってたら現実はそういうものかと納得するとかないかな。ないか。

結論としてはフレームワークのドキュメントを見せるならYiiかな。

ネットで調べるならあっちこっち引っ掻き回してこういった現状を色々調べたり。

正しそうな解説は本当にいっぱいあるんだけど、いっぱいあるぐらい間違いやすいってことだから、半端者が半端な紹介や説明は迂闊にできないなあ。

そもそもMVCの説明をフレームワークのドキュメントでしようとすることが間違い

PHPやっている限りはMVC2(モデル2)をMVCと言って「そういうものだから」で済ますと思いますし、スタートからややこしくなりそう。


"絶対にわかるMVC"との一致はありません。



参考

+有名どころのQiita・ブログ記事いろいろ






  1. 両方の価値観が受け入れられた?