熟悉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文档会详细的对其进行解释。 如果我们并不能完全理解上面所编写的代码也不担心,几天后就会变得清晰了。
查看更多关于Symfony学习第三天,深入MVC体系结构的详细内容...