2010-07-19 3 views
7

Je cours Symfony 1.3.6 sur Ubuntu 10.0.4 LTS.Utilisation des routes pour générer des URL dans une tâche Symfony

J'ai écrit une tâche Symfony qui génère un rapport contenant des liens (URL).

Voici un extrait de la méthode execute() dans ma classe de tâche:

protected function execute($arguments = array(), $options = array()) 
    { 
    //create a context 
    sfContext::createInstance($this->configuration); 
    sfContext::getInstance()->getConfiguration()->loadHelpers(array('Url', 'Asset', 'Tag')); 

    ... 
    $url = url_for("@foobar?cow=marymoo&id=42"); 

    // Line 1 
    echo '<a href="'.$url.'">This is a test</a>'; 

    // Line 2 
    echo link_to('This is a test', $url); 
    } 

Le nom de l'itinéraire est défini comme suit:

foobar: 
    url: /some/fancy/path/:cow/:id/hello.html 
    param: { module: mymodule, action: myaction } 

Lorsque cela est exécuté, le lien généré est:

Ligne 1 produit cette sortie:

./symfony/symfony/some/fancy/path/marymoo/42/hello.html

au lieu de l'attendre:

/some/fancy/path/marymoo/42/hello.html

Ligne 2 génère une erreur:

Unable to find a matching route to generate url for params "array ( 'action' => 'symfony', 'module' => '.',)".

Encore une fois, l'URL attendue est:

/some/fancy/path/marymoo/42/hello.html

Comment puis-je résoudre ce?

Répondre

17

Pour générer une URL dans une tâche:

protected function execute($arguments = array(), $options = array()) 
{ 
    $routing = $this->getRouting(); 
    $url = $routing->generate('route_name', $parameters); 
} 

Nous ajoutons une méthode pour générer le routage afin que l'URL de la production est toujours utilisé:

/** 
    * Gets routing with the host url set to the url of the production server 
    * @return sfPatternRouting 
    */ 
    protected function getProductionRouting() 
    { 
    $routing = $this->getRouting(); 
    $routingOptions = $routing->getOptions(); 
    $routingOptions['context']['host'] = 'www.example.com'; 
    $routing->initialize($this->dispatcher, $routing->getCache(), $routingOptions); 
    return $routing; 
    } 
+0

+1 pour l'extrait sympa et succinct qui me montre comment résoudre ce problème. Je vais légèrement modifier le code pour convenir à ce que je fais, le tester, si ça marche, j'accepterai cette réponse. – morpheous

+0

Ça marche! Merci à vous, merci, merci! :) – morpheous

+0

Où devrais-je mettre cet extrait?Je ne peux pas appeler $ this-> getRouting() à partir d'une tâche:/ – JavierIEH

1

J'ai eu le même problème et trouvé l'extrait de code suivant: http://snippets.symfony-project.org/snippet/378

La solution est assez similaire, mais elle étend la ProjectConfiguration. L'avantage de cette approche est qu'elle fonctionne de manière transparente aussi bien dans les modules.

3

Je vous veux d'utiliser les aides standards (comme url_for) pour générer url, peut-être ce code pourrait vous aider:

protected function execute($arguments = array(), $options = array()) 
    { 
    // initialize the database connection 
... 
$context = sfContext::createInstance($this->configuration); 

$routing = $context->getRouting(); 
$_options = $routing->getOptions(); 
$_options['context']['prefix'] = "";// "/frontend_dev.php" for dev; or "" for prod 
$_options['context']['host'] = sfConfig::get('app_url_base'); 
$routing->initialize($this->dispatcher, $routing->getCache(),$_options); 
$context->getConfiguration()->loadHelpers('Partial'); 
$context->set('routing',$routing);  
//$_SERVER['HTTP_HOST'] = sfConfig::get('app_url_base'); // ---> I don't remember why I have this on my code, shouldn't be necessary 
... 

Ensuite, vous pouvez utiliser url_for fonction partout avec le paramètre absolu = true fonctionne magiquement.

Bien sûr, vous devez ajouter un * url_base * définition dans votre app.yml (ou vous pouvez peut-être laisser harcoded)

+2

merci beaucoup, cela a fonctionné pour moi. petit commentaire: '$ options' est utilisé pour les options de la ligne de commande de la tâche, donc un nom différent pour la variable évite les problèmes. – Tapper

+0

Mis à jour. Merci. – glerendegui

0

Vous pouvez modifier les options de demande par défaut pour les commandes (sfTask) dans le script de configuration du projet

class ProjectConfiguration extends sfProjectConfiguration { 

    public function setup() { 
     ... 
     $this->dispatcher->connect('command.pre_command', array('TaskWebRequest', 'patchConfig')); 
    } 

} 

class TaskWebRequest extends sfWebRequest { 

    public function __construct(sfEventDispatcher $dispatcher, $parameters = array(), $attributes = array(), $options = array()) 
    { 
     $options['no_script_name'] = true; 
     $options['relative_url_root'] = ''; 
     parent::__construct($dispatcher, $parameters, $attributes, $options); 
    } 

    public static function patchConfig(sfEvent $event) { 
     sfConfig::set('sf_factory_request', 'TaskWebRequest'); 
    } 

} 
Questions connexes