Symfony学习第三天,深入MVC体系结构_自学php网
来源:自学PHP网
时间:2014-12-04 22:12 作者:
阅读:次
[导读] 熟悉YAML语法,那么我们需要立即开始,因 为这个教程大量用了YAML语法格式。 好了,现在回到测试数据文件。他定义了对象实体,并以内部名称来标识。这个标签对于链接相关对象而不...
熟悉YAML语法,那么我们需要立即开始,因 为这个教程大量用了YAML语法格式。
好了,现在回到测试数据文件。他定义了对象实体,并以内部名称来标识。这个标签对于链接相关对象而不必定义id是十分有用的。例如,创建的第一个对象为User类,并且标识为fabien。第一个问题标识为q1。这就很容易通过指定一个相关对象标签来创建一个类的对象:
Interest:
i1:
user_id: fabien
question_id: q1
前面所给定的数据文件使用了短YAML语法来描述这些内容。我们可以在Symfony一书的数据文件一章了解到更多的关于数据迁移的内容。
我们并不需要为created_at与updated_at列定义值,因为在默认情况下Symfony知道如何来填充这些域。
创建一个批文件来迁移数据
下一步就是实际的迁移数据库,而我们希望用一个可以在命令进行调用的PHP脚本来完成这些工作--一个批处理。
批处理框架
用下面的内容在askeet/batch/目录下创建一个名为load_data.php的文件:
< ?php
define('SF_ROOT_DIR', realpath(dirname(__FILE__).'/..'));
define('SF_APP', 'frontend');
define('SF_ENVIRONMENT', 'dev');
define('SF_DEBUG', true);
require_once(SF_ROOT_DIR.DIRECTORY_SEPARATOR.'apps'.DIRECTORY_SEPARATOR.SF_APP.DIRECTORY_SEPARATOR.'config'.DIRECTORY_SEPARATOR.'config.php');
// initialize database manager
$databaseManager = new sfDatabaseManager();
$databaseManager->initialize();
?>
这个脚本并没有做任何事情,或者说是几乎没有做任何事情:他定义了一个要进行配置的路径,程序以及环境,装入这个配置,并且初始化数据管理器。但是这已经很多了:这就意味着下面所编写的代码将会利用自动装入的类,自动连接到Propel对象以及Symfony根类。
如果我们已经测试了Symfony的前端控制器(例如askeet/web/index.php),我们就会发现这些代码十分的熟悉。这是因为正如批请求一样,每一个web请求需要访问同样的对象与配置。
数据导入
现在已经准备好了批处理的框架,要在使其来完成一些事情了。批处理需要完成:
1 读取YAML文件
2 创建Propel对象实例
3 在所链接的数据库的数据表中创建相关的记录
这听起来很复杂,但是在Symfony中,由于sfPropelData对象,我们只需要两行代码就可以完成这些工作。在askeet/batch/load_data.php脚本最后的?>前添加下面的代码:
data = new sfPropelData();
$data->loadData(sfConfig::get('sf_data_dir').DIRECTORY_SEPARATOR.'fixtures');
这就完成了。创建了一个sfPropelData对象,并且通知其将指定目录下的所有数据--我们的fixtures目录--装入到databases.yml配置文件中所定义的数据库中。
这里的DIRECTORY_SEPARATOR常量用来兼容Windows与*nix平台。
启动批处理
最后,我们可以检测这些代码是否值得我们这样的论述,在命令行输入下面的命令:
$ cd /home/sfprojects/askeet/batch
$ php load_data.php
通过刷新开发中的主页我们可以检测数据库中的这些修改:
http://askeet/frontend_dev.php
数据已成功装入。
默认情况下,sfPropelData对象会在装入新的数据之前删除我们所有的数据。我们也可以在当前数据之后添加:
$data = new sfPropelData();
$data->setDeleteCurrentData(false);
$data->loadData(sfConfig::get('sf_data_dir').DIRECTORY_SEPARATOR.'fixtures');
在模块中访问数据
当 请求question模块的list动作时所显示的页面是executeList()(可以在askeet/frontend/modules /question/actions/action.class.php动作文件中找到)方法传递到askeet/apps/frontend /modules/question/templates/listSuccess.php模板中的结果。这是基于Symfony一书中控制器一章中所解 释的名字转换。让我们看一下所执行的代码:
actions.class.php:
public function executeList ()
{
$this->questions = QuestionPeer::doSelect(new Criteria());
}
listSuccess.php:
...
< ?php foreach ($questions as $question): ?>
< tr>
<td><?php echo link_to($question->getId(), 'question/show?id='.$question->getId()) ?></td>
<td><?php echo $question->getTitle() ?></td>
<td><?php echo $question->getBody() ?></td>
<td><?php echo $question->getCreatedAt() ?></td>
<td><?php echo $question->getUpdatedAt() ?></td>
</tr>
< ?php endforeach; ?>
一步一步的,其所做的工作如下:
1 动作请求满足一个空标准(criteria)的Question表的记录
2 记录列表放在一个数组中($questions)传递到模板
3 模板在动作所传递过来的问题中循环
4 模板显示记录中每一列的值
->getId(),->getTitle(),->getBody()等方法是在Symfony的propel-build-model命令调用中生成的,用来获取id,title,body等数据域的值。这些是标准的获取 方法,由在域名字前添加get前缀进行格式化,而Propel也提供了标准的设置方法,以set为前缀。Propel文档描述了为每一个类所创建的访问方 法。
而我们也许会感到迷惑的是QuestionPeer::doSelect(new Criteria())调用,他也是一个标准的Propel请求。Propel文档会详细的对其进行解释。
如果我们并不能完全理解上面所编写的代码也不担心,几天后就会变得清晰了。 |
|