web-dev-qa-db-fra.com

Thymeleaf construire URL avec variable

J'ai le code suivant qui définit une variable dans mon contrôleur:

model.set("type", type);

Dans la vue thymeleaf, je souhaite construire un formulaire avec l’action url:

/mycontroller/{type}

Des idées comment y parvenir? J'ai lu la documentation de thymeleaf sans succès.

47
Chris

Comme user482745 le suggère dans les commentaires (maintenant supprimé), la concaténation de chaînes que j'avais précédemment suggérée

<form th:action="@{/mycontroller/} + ${type}">

échouera dans certains contextes Web.

Thymeleaf utilise LinkExpression qui résout l'expression @{..}. En interne, cela utilise HttpServletResponse#encodeURL(String) . Ses états javadoc

Pour un suivi de session robuste, toutes les URL émises par un servlet doivent être exécuter cette méthode. Sinon, la réécriture d'URL ne peut pas être utilisée avec les navigateurs qui ne supportent pas les cookies.

Dans les applications Web où le suivi de session est effectué via l'URL, cette partie sera ajoutée à la chaîne émise pour @{..} avant l'ajout du ${..}. Tu ne veux pas de ça.

Utilisez plutôt les variables de chemin comme suggéré dans la documentation

Vous pouvez également inclure des paramètres sous la forme de variables de chemin de la même façon que les paramètres normaux, mais en spécifiant un espace réservé à l'intérieur le chemin de votre URL:

<a th:href="@{/order/{id}/details(id=3,action='show_all')}">

Donc, votre exemple ressemblerait à

<form th:action="@{/mycontroller/{path}(path=${type})}"> //adding ending curly brace
85
Sotirios Delimanolis

Si vous ne souhaitez pas utiliser la concaténation de chaînes ( proposée par Sotirios ), vous pouvez utiliser le prétraitement expression dans le lien URL :

<form th:action="@{/mycontroller/__${type}__}">
32
lu_ko

Vous devez concaténer la chaîne dans @ {}.

<form th:action="@{'/mycontroller/' + ${type}}">

@ {} est utilisé pour la réécriture d'URL. Une partie de la réécriture d'URL consiste à garder une trace de la session. Première fois qu'une URL de demande d'utilisateur est utilisée, le serveur d'applications ajoute à l'URL ;jsessionid=somehexvalue et génère un cookie avec jsessionid. Lorsque le client envoie un cookie lors de la prochaine requête, le serveur sait que le client prend en charge les cookies. Si le serveur sait que le client prend en charge les cookies, il ne conservera pas addind jsessionid dans l'URL.

Ma méthode préférée est la substitution littérale avec la syntaxe de pipeline (|).

<form th:action="@{|/mycontroller/${type}|}">

La syntaxe de la variable de chemin Thymeleaf est 

<form th:action="@{/mycontroller/{pathParam}(pathParam=${type}}">

Référence: Syntaxe d'URL standard Thymeleaf

13
user482745
Exception evaluating SpringEL expression: "businessId" (login:50)

J'ai le même problème et résoudre via une concaturation de chaîne comme ci-dessous.

LoginController.Java

@RequestMapping(value = "/login/{businessId}", method = RequestMethod.GET)
    public ModelAndView get(HttpServletRequest request, @PathVariable String businessId) {
        ModelAndView modelAndView = new ModelAndView("login");
        modelAndView.addObject("businessId", businessId);
        return modelAndView;
    }

login.html 

            <form role="form" th:action="@{/login} + '/'+ ${businessId}" th:method="post">
                            <fieldset>
                                <div class="form-group">
                                    <input class="form-control" placeholder="E-mail" name="userName"
                                        type="email"></input>
                                </div>
                                <div class="form-group">
                                    <input class="form-control" placeholder="Password"
                                        name="password" type="password" value=""></input>
                                </div>
                                <div class="checkbox">
                                    <label> <input name="remember" type="checkbox"
                                        value="Remember Me"></input>Remember Me
                                    </label>
                                </div>
                                <!-- Change this to a button or input when using this as a form -->
                                <button id="login" class="btn btn-lg btn-success btn-block" type="submit">Login</button>
                            </fieldset>
            </form>
0
erhun