• Save
Curso Symfony - Clase 3
Upcoming SlideShare
Loading in...5
×
 

Curso Symfony - Clase 3

on

  • 9,570 views

Presentación de la tercera clase de un curso sobre el framework Symfony

Presentación de la tercera clase de un curso sobre el framework Symfony
--
Slides used in the third class of a symfony framework training.

Statistics

Views

Total Views
9,570
Views on SlideShare
9,021
Embed Views
549

Actions

Likes
13
Downloads
0
Comments
0

6 Embeds 549

http://www.symfony.es 499
http://www.slideshare.net 40
http://static.slideshare.net 3
http://www.sfexception.com 3
http://symfony.es 3
http://feeds2.feedburner.com 1

Accessibility

Categories

Upload Details

Uploaded via as Adobe PDF

Usage Rights

CC Attribution-NonCommercial-ShareAlike LicenseCC Attribution-NonCommercial-ShareAlike LicenseCC Attribution-NonCommercial-ShareAlike License

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

Curso Symfony - Clase 3 Curso Symfony - Clase 3 Presentation Transcript

  • Frameworks de desarrollo Symfony Clase 3 Javier Eguíluz javier.eguiluz@gmail.com
  • Esta obra dispone de una licencia de tipo Creative Commons Reconocimiento‐No comercial‐ Compartir  bajo la misma licencia 3.0  Se prohíbe explícitamente el uso de este material en  actividades de formación comerciales http://creativecommons.org/licenses/by‐nc‐sa/3.0/es/
  • This work is licensed under a Creative Commons Attribution‐Noncommercial‐Share Alike 3.0  The use of these slides in commercial courses or trainings is explicitly prohibited http://creativecommons.org/licenses/by‐nc‐sa/3.0/es/
  • Capítulo 12 El generador de  la parte de  administración
  • Creando la aplicación  backend
  • backend/ config/ $ symfony lib/ generate:app ‐‐escaping‐strategy=on modules/ ‐‐csrf‐secret=UniqueSecret1 backend templates/
  • Controladores frontales frontend_dev.php frontend |  desarrollo index.php frontend |  producción backend_dev.php backend |  desarrollo backend.php backend |  producción
  • propel:data‐load JobeetJob::save() apps/frontend/config/app.yml app.yml backend/ config/app.yml
  • Los módulos de la  aplicación backend
  • $ symfony propel:generate‐admin backend JobeetJob ‐‐module=job backend/modules/job actions/ config/ lib/ templates/
  • apps/backend/config/routing.yml jobeet_job: class: sfPropelRouteCollection options: model:                JobeetJob module:               job prefix_path:          job column:               id with_wildcard_routes: true
  • El aspecto de la  aplicación backend
  • http://jobeet.localhost/backend_dev.php/job • Listado con paginación,  ordenación y filtrado • Crear, modificar y borrar  objetos • Borrar varios objetos a la  vez • Formularios con validación • Mensajes flash para  feedback • ...y mucho más
  • La cache de Symfony
  • apps/backend/modules/job/actions/actions.class.php require_once dirname(__FILE__).'/../lib/jobGeneratorConfiguration.class.php'; require_once dirname(__FILE__).'/../lib/jobGeneratorHelper.class.php'; class jobActions extends autoJobActions { } cache/backend/dev/modules/autoJob/actions/actions.class.php class autoJobActions extends sfActions { public function preExecute() { $this‐>configuration = new jobGeneratorConfiguration(); ... apps/backend/modules/job/config/generator.yml
  • apps/backend/modules/job/config/generator.yml generator: class: sfPropelGenerator param: model_class:           JobeetJob theme:                 admin non_verbose_templates: true with_show:             false singular:              ~ plural:                ~ route_prefix:          jobeet_job with_propel_route:     1 config: actions: ~ fields:  ~ list:    ~ filter:  ~ form:    ~ edit:    ~ new:     ~
  • Configuración del  título
  • apps/backend/modules/category/config/generator.yml config: actions: ~ fields:  ~ list:     title: Gestión de categorías filter:  ~ form:    ~ edit: title: Editando la categoría quot;%%name%%quot; new: title: Nueva categoría
  • Configuración de los  campos
  • apps/backend/modules/job/config/generator.yml config: fields: is_activated: { label: Activated?, help: Whether the user  has activated the job, or not } is_public:    { label: Public? } config: list: fields: is_public:    { label: quot;Public? (label for the list)quot; }
  • fields filter list form new edit
  • Configuración de la  página list
  • apps/backend/modules/category/config/generator.yml config: list: title:   Category Management display: [=name, slug] enlace
  • apps/backend/modules/job/config/generator.yml config: list: title:   Job Management display: [company, position, location, url, is_activated, email] layout:  stacked params:  | %%jobeet_category%% %%is_activated%% <small>%%category_id%%</small> ‐ %%company%% (<em>%%email%%</em>) is looking for a %%=position%% (%%location%%)
  • apps/backend/modules/job/config/generator.yml config: list: sort: [expires_at, desc] max_per_page: 10
  • apps/backend/modules/category/config/generator.yml config: list: batch_actions: {}
  • apps/backend/modules/job/config/generator.yml config: list: batch_actions: _delete:    ~ extend:     ~ apps/backend/modules/job/actions/actions.class.php class jobActions extends autoJobActions { public function executeBatchExtend(sfWebRequest $request) { $ids = $request‐>getParameter('ids'); $jobs = JobeetJobPeer::retrieveByPks($ids); foreach ($jobs as $job) { $job‐>extend(true); } ... } }
  • apps/backend/modules/category/config/generator.yml config: list: object_actions: {} apps/backend/modules/job/config/generator.yml config: list: object_actions: extend:     ~ _edit:      ~ _delete:    ~
  • apps/backend/modules/job/config/generator.yml config: list: actions: deleteNeverActivated: { label: Borrar ofertas inactivas } apps/backend/modules/job/actions/actions.class.php class jobActions extends autoJobActions { public function executeListDeleteNeverActivated(sfWebRequest $request) { $nb = JobeetJobPeer::cleanup(60); ... $this‐>redirect('@jobeet_job'); }
  • apps/backend/modules/job/config/generator.yml config: list: peer_method: doSelectJoinJobeetCategory
  • Configuración de la  página de  formularios
  • apps/backend/modules/job/config/generator.yml config: form: display: Content: [category_id, type, company, logo, url, position, location, description, how_to_apply,  is_public, email] Admin:   [_generated_token, is_activated,  expires_at] apps/backend/modules/job/templates/_generated_token.php <div class=quot;sf_admin_form_rowquot;> <label>Token</label> <?php echo $form‐>getObject()‐>getToken() ?> </div>
  • BaseJobeetJobForm JobeetJobForm BackendJobeetJobForm
  • lib/form/BackendJobeetJobForm.php $this‐>widgetSchema['logo'] = new sfWidgetFormInputFileEditable(array( 'label' => 'Company logo', 'file_src' => '/uploads/jobs/'.$this‐>getObject()‐>getLogo(), 'is_image' => true, 'edit_mode' => !$this‐>isNew(), 'template' => '<div>%file%<br />%input%<br />%delete% %delete_label%</div>',  )); 
  • Configuración de los  filtros
  • $ ./symfony propel:build‐filters $ ./symfony propel:build‐all
  • $ ./symfony propel:build‐filters JobeetCategoryFormFilter JobeetJobFormFilter JobeetAffiliateFormFilter lib/filter/
  • apps/backend/modules/category/config/generator.yml config: filter: class: false apps/backend/modules/job/config/generator.yml filter: display: [category_id, company, position,  description, is_activated, is_public, email, expires_at]
  • Modificando las  acciones
  • executeIndex() getFilters() listexecuteFilter() setFilters() executeNew() getPager() executeCreate() getPage() executeEdit() setPage() executeUpdate() buildCriteria() executeDelete() addSortCriteria() executeBatch() getSort() executeBatchDelete() setSort() processForm()
  • Personalizando las  plantillas
  • _assets.php _list_field_boolean.php _filters.php _list_footer.php _filters_field.php _list_header.php _flashes.php _list_td_actions.php _form.php _list_td_batch_actions.php _form_actions.php _list_td_stacked.php _form_field.php _list_td_tabular.php _form_fieldset.php _list_th_stacked.php _form_footer.php _list_th_tabular.php _form_header.php _pagination.php _list.php editSuccess.php _list_actions.php indexSuccess.php _list_batch_actions.php newSuccess.php
  • Capítulo 13 El usuario
  • sfUser
  • Mensajes flash
  • Mensaje temporal que se almacena en la sesión  del usuario y que se borra automáticamente  después de la siguiente petición
  • apps/frontend/modules/job/actions/actions.class.php public function executeExtend(sfWebRequest $request) { ... $this‐>getUser()‐>setFlash( 'notice', 'La oferta se ha actualizado' ); ... } apps/frontend/templates/layout.php <?php if ($sf_user‐>hasFlash('notice')): ?> <div class=quot;flash_noticequot;> <?php echo $sf_user‐>getFlash('notice') ?> </div> <?php endif; ?>
  • Atributos del usuario
  • quot;para facilitar la navegación por las ofertas  de trabajo, en el menú se muestran los  enlaces a las tres últimas ofertas de trabajo  vistas por el usuarioquot;
  • apps/frontend/modules/job/actions/actions.class.php class jobActions extends sfActions { public function executeShow(sfWebRequest $request) { $this‐>job = $this‐>getRoute()‐>getObject(); // obtener las ofertas del historial $jobs = $this‐>getUser()‐>getAttribute( 'historial', array() ); // añadir la oferta al historial array_unshift($jobs, $this‐>job‐>getId()); // guardar de nuevo el historial $this‐>getUser()‐>setAttribute('historial', $jobs); } // ... }
  • apps/frontend/modules/job/actions/actions.class.php class jobActions extends sfActions { public function executeShow(sfWebRequest $request) { $this‐>job = $this‐>getRoute()‐>getObject(); $this‐>getUser()‐>addJobToHistory($this‐>job); } // ... } apps/frontend/lib/myUser.class.php class myUser extends sfBasicSecurityUser { public function addJobToHistory(JobeetJob $job) { ... } $sf_user }
  • La seguridad de la  aplicación
  • apps/backend/config/security.yml default: is_secure: on
  • apps/backend/config/settings.yml all: .actions: login_module: default login_action: login if (!$this‐>getUser()‐>isAuthenticated()) { $this‐>getUser()‐>setAuthenticated(true); }
  • Plugins
  • http://www.symfony‐project.org/plugins
  • sfGuardPlugin
  • $ ./symfony plugin:install sfGuardPlugin $ apt‐get install php‐pear $ pear channel‐discover pear.symfony‐project.com
  • La seguridad de la  aplicación backend
  • $ ./symfony propel:build‐all ‐‐no‐confirmation $ ./symfony cc apps/backend/lib/myUser.class.php class myUser extends sfGuardSecurityUser { } apps/backend/config/settings.yml all: .settings: enabled_modules: [default, sfGuardAuth] # ... .actions: login_module: sfGuardAuth login_action: signin
  • $ ./symfony guard:create‐user usuario contrasena $ ./symfony guard:promote usuario
  • $ ./symfony list guard
  • apps/backend/templates/layout.php <?php if ($sf_user‐>isAuthenticated()): ?> <div id=quot;menuquot;> <ul> <li> <?php echo link_to('Jobs', '@jobeet_job') ?> </li> <li> <?php echo link_to('Categories', '@jobeet_category') ?> </li> <li> <?php echo link_to('Logout', '@sf_guard_signout') ?> </li>  </ul> </div> $ ./symfony app:routes <?php endif; ?> 
  • apps/backend/config/settings.yml all: .settings: enabled_modules: [default, sfGuardAuth, sfGuardUser] apps/backend/templates/layout.php <li> <?php echo link_to('Users', '@sf_guard_user') ?> </li>
  • Probando los  usuarios
  • test/functional/frontend/jobActionsTest.php $browser‐> info('4 ‐ User job history')‐> loadData()‐> restart()‐> info(' 4.1 ‐ When the user access a job, it is added to its history')‐> get('/')‐> click('Web Developer', array(), array('position' => 1))‐> get('/')‐> with('user')‐>begin()‐> isAttribute('job_history', array($browser‐>getMostRecentProgrammingJob()‐>getId()))‐> end()‐> info(' 4.2 ‐ A job is not added twice in the history')‐> click('Web Developer', array(), array('position' => 1))‐> get('/')‐> with('user')‐>begin()‐> isAttribute('job_history', array($browser‐>getMostRecentProgrammingJob()‐>getId()))‐> end() ; 
  • Capítulo 14 El día de  descanso
  • CC by‐nc‐sa StockVault
  • Capítulo 15 Canales Atom
  • Formatos
  • plantilla1 petición plantilla2 plantilla3
  • $request‐>setRequestFormat('xml'); txt xml js rdf css atom json
  • http://jobeet.localhost/frontend_dev.php/job http://jobeet.localhost/frontend_dev.php/job.html
  • Canales Atom
  • apps/frontend/modules/job/templates/indexSuccess.atom.php <?xml version=quot;1.0quot; encoding=quot;utf‐8quot;?> <feed xmlns=quot;http://www.w3.org/2005/Atomquot;> <title>Jobeet</title> <subtitle>Latest Jobs</subtitle> <link href=quot;quot; rel=quot;selfquot;/> <link href=quot;quot;/> <updated></updated> <author><name>Jobeet</name></author> <id>Unique Id</id> <entry> <title>Job title</title> <link href=quot;quot; /> <id>Unique id</id> <updated></updated> <summary>Job description</summary> <author><name>Company</name></author> </entry> </feed>
  • indexSuccess.php indexSuccess.html.php indexSuccess.php return sfView::SUCCESS indexError.php return sfView::ERROR indexHola.php return quot;Holaquot; indexPlantilla.php return quot;Plantillaquot;
  • apps/frontend/templates/layout.php <li class=quot;feedquot;> <a href=quot;<?php echo url_for('@job?sf_format=atom') ?>quot;> Full feed </a> </li> application/atom+xml; charset=utf‐8 has_layout: off <link rel=quot;alternatequot; type=quot;application/atom+xmlquot; title=quot;Latest Jobsquot; href=quot;<?php echo url_for('@job?sf_format=atom', true) ?>quot;  />
  • apps/frontend/modules/job/templates/indexSuccess.atom.php <title>Jobeet</title> <subtitle>Latest Jobs</subtitle> <link href=quot;<?php echo url_for('@job?sf_format=atom', true) ?>quot; rel=quot;selfquot;/> <link href=quot;<?php echo url_for('@homepage', true) ?>quot;/> <updated><?php echo gmstrftime('%Y‐%m‐%dT%H:%M:%SZ',  JobeetJobPeer::getLatestPost()‐>getCreatedAt('U')) ?></updated> <author> <name>Jobeet</name> </author> <id><?php echo sha1(url_for('@job?sf_format=atom', true)) ?></id>
  • apps/frontend/modules/job/templates/indexSuccess.atom.php <?php use_helper('Text') ?> <?php foreach ($categories as $category): ?> <?php foreach ($category‐>getActiveJobs( as $job): ?> sfConfig::get('app_max_jobs_on_homepage')) <entry> <title> <?php echo $job‐>getPosition() ?> (<?php echo $job‐>getLocation() ?>) </title> <link href=quot;<?php echo url_for('job_show_user', $job, true) ?>quot; /> <id><?php echo sha1($job‐>getId()) ?></id> ...
  • apps/frontend/config/routing.yml category: url:     /category/:slug.:sf_format class:   sfPropelRoute param:   { module: category, action: show, sf_format: html } options: { model: JobeetCategory, type: object } requirements: sf_format: (?:html|atom) apps/frontend/modules/job/templates/indexSuccess.php <div class=quot;feedquot;> <a href=quot;<?php echo url_for('category', array('sf_subject'  => $category, 'sf_format' => 'atom')) ?>quot;>Feed</a> </div>  apps/frontend/modules/job/templates/showSuccess.php <div class=quot;feedquot;> <a href=quot;<?php echo url_for('category', array('sf_subject'  => $category, 'sf_format' => 'atom')) ?>quot;>Feed</a> </div> 
  • apps/frontend/modules/job/templates/_list.atom.php <?php use_helper('Text') ?> <?php foreach ($jobs as $job): ?> <entry> <title><?php echo $job‐>getPosition() ?> (<?php echo $job‐ >getLocation() ?>)</title> <link href=quot;<?php echo url_for('job_show_user', $job,  true) ?>quot; /> <id><?php echo sha1($job‐>getId()) ?></id> ... apps/frontend/modules/job/templates/indexSuccess.atom.php <?php foreach ($categories as $category): ?> <?php include_partial( 'job/list', array('jobs' => $category‐>getActiveJobs(sfConfig::get('app_max_jobs_on_homepage')) )) ?> <?php endforeach; ?>