I've created a project with a Spring Initilizr. I'm trying to parse a string into a "code.html" file and recover it with a #GetMapping. Here's the file:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>Code</title>
</head>
<body>
<pre>
<p th:text="${code}">
</pre>
</body>
</html>
And here's the method:
#GetMapping("/code")
public ModelAndView getHTML(HttpServletResponse response) {
response.addHeader("Content-Type", "text/html");
ModelAndView model = new ModelAndView();
model.addObject("code", code.getCode());
model.setViewName("code.html");
return model;
}
(I have a seperate class for the code so code.getCode() just returns a string.)
Unfortunately, http://localhost:8080/code returns an empty screen. What am I doing wrong? Maybe there's an easier way to achieve the task?
i work with springboot and thymeleaft
maybe you need send only the view in the code
like this
#GetMapping("/code")
public ModelAndView getHTML(HttpServletResponse response,Model model) {
model.addAtributte("key", "code");
return new ModelAndView ("templates/code");
}
the model is shipped with the view
in the html try this
<p th:text="${key}">
or you can try the <th:block>
check thymeleaf documentation
Related
i am trying to display a string in springboot web page but it,s not working correctly !
controller
#Controller
public controller {
#RequestMapping("/")
public ModelAndView get(){
ModelAndView model = new ModelAndView("index.html");
String name = "World";
model.addObject("name",name);
return model;
}
}
index.html
<html>
<body>
<h1>Hello <span th:text="${name}"></span></h1>
</body>
</html>
it works like this
#Controller
public controller {
#RequestMapping("/")
public ModelAndView get(){
ModelAndView model = new ModelAndView("index");
String name = "World";
model.addObject("name",name);
return model;
}
}
Test by removing the .html
Also add th="http://www.thymeleaf.org" like below.
<html xmlns:th="http://www.thymeleaf.org">
<h1>Hello th:text="${name}"></h1>
Try removing the span or correctly add the content inside the span.
Thank you
You don't need to change anything in java classes and even you don't need to remove the span in the HTML file. Check with the namespace in the HTML. The following is working without any issue with spring-boot <2.2.9.RELEASE> and using the thymeleaf template engine.
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.servlet.ModelAndView;
#Controller
public class TestController {
#RequestMapping("/")
public ModelAndView get(){
ModelAndView model = new ModelAndView("index.html");
String name = "World";
model.addObject("name",name);
return model;
}
}
index.html
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="utf-8" />
<title>test</title>
</head>
<body>
<h1>
Hello <span th:text="${name}"></span>
</h1>
</body>
</html>
I am using Spring boot and Thymeleaf as a template framework. I set a couple constants on the backend and I need to get data on the frontend via that constants.
I have the backend look like the following:
public class Constant {
public static final String MY_VAR = "test";
}
#Controller
public class MyController {
#GetMapping("/")
public String home(Model model) {
List<String> data = new ArrayList<>();
data.add("item1");
model.addAttribute(Constant.MY_VAR, data);
return "home";
}
}
and on the frontend I want to do like this:
<!DOCTYPE html>
<html lang="en"
xmlns:th="http://www.thymeleaf.org">
<head>
...
</head>
<body>
<div class="container-fluid p-0">
<div th:unless="${not #lists.isEmpty(Constant.MY_VAR)}">
</div>
</div>
</body>
</html>
how can I get access to model data via constant from the backend?
You can use **ModelAndView ** to solve this problem
backend
#GetMapping("/")
public ModelAndView home() {
ModelAndView modelAndView = new ModelAndView();
modelAndView.setViewName("home");
List<String> data = new ArrayList<>();
data.add("item1");
modelAndView.addObject("test", data);
return modelAndView;
}
frontend
<!DOCTYPE html>
<html lang="en"
xmlns:th="http://www.thymeleaf.org">
<head>
...
</head>
<body>
<div class="container-fluid p-0">
<div th:if="${test.size() > 0}">
<li th:each="item:${test}">
<span th:text="${item}"></span>
</li>
</div>
</div>
</body>
</html>
if u want get static attribute in your view。
you can do that
${T(packageName.Constant).MY_VAR}
so u can change your code
${not #lists.isEmpty(Constant.MY_VAR)}
to
${not #lists.isEmpty(#ctx.getVariable(T(packageName.Constant).MY_VAR))}
I am learning Spring Boot now and I wrote a small application. The application has this controller:
#Controller
#RequestMapping("/")
public class ApplicationController {
#RequestMapping(value="/account", method = RequestMethod.POST)
public String getAccountVo(ModelMap model) {
AccountVO vo = new AccountVO();
vo.setAccountNo("0102356");
vo.setAccountHolderName("Dinesh");
model.addAttribute("acc", vo);
return "account";
}
}
... and the page (view) is:
<%# page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Account Details</title>
</head>
<body>
<form>
Account number <input type="text" name="acctNo" value="${acc.getAccountNo()}"><br>
Account Holder Name <input type="text" name="name" value="${acc.getAccountHolderName()}"><br>
</form>
</body>
</html>
When I ran the application, I got HTTP Status 405 with the message Request method 'GET' not supported. But when I changed the method in the #RequestMapping annotation to method=RequestMethod.GET I got my expected page.
Why did this happen?
#RequestMapping(value="/account", method = RequestMethod.POST)
This means that getAccountVo method handler is responsible for POST requests on the /account endpoint. So when you fire a GET request to /account endpoint, since you haven't define any method handler to process that, Spring complains with 405 Method Not Supported.
If your intent is to have a form processing workflow, a typical approach is define two method handlers on the /account endpoint: One for displaying the form and other for processing the submitted form, kinda like this:
#Controller
#RequestMapping("/")
public class ApplicationController {
#RequestMapping(value="/account", method = RequestMethod.GET)
public String displayAccountForm(...) {
// do whatever suits your requirements
return "account";
}
#RequestMapping(value="/account", method = RequestMethod.POST)
public String handleSubmittedForm(...) {
// do whatever suits your requirements
return "successPage";
}
}
I am using Eclipse, Spring MVC, Maven and Tomcat. This index.jsp displays exactly as show below in the web browser. It is not rendering properly.
Any idea what is wrong?
index.jsp
<%# page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Insert title here</title>
</head>
<body>
<h1>Index</h1>
</body>
</html>
#Controller
public class HelloController {
#RequestMapping("/greeting")
public String sayHello() {
System.out.println("Greeting");
return "hello";
}
#RequestMapping("/")
public String index() {
System.out.println("Index page");
return "index";
}
}
A controller has a GET and a POST RequestMethod.However at a quick glance you need to change #RequestMapping("/greeting") to #RequestMapping(value = "/greeting") just for starters. By default your jsp file should be in /src/main/webapp/WEB-INF/views (Spring MVC Starter Project)
When you return a String - Spring MVC will look for a jsp with that .jsp. So in this example you just want to have greeting.jsp
#Controller
public class GreetingController {
/**
* GET
*/
#RequestMapping(value = "/greeting", method = RequestMethod.GET)
public String handleRequest() {
// This will be used when you GET the URL
return "greeting";
}
/**
* POST
*/
#RequestMapping(value = "/greeting", method = RequestMethod.POST)
public String processSubmit(){
// This will be used when you POST to the URL
//TODO Do something here and it will put you right back in your page
return "greeting";
}
}
Go ahead and comment if you have any other questions. Also check my account for my other example Neither BindingResult nor plain target object for bean name available as request attr
Hope this helps. Good Luck!
Just a note Spring has more RequestMethod's but GET and POST are the most used and easiest to understand.
It could be that the only thing you're missing is to
Right click on the jsp page and click RUN AS, then RUN ON SERVER.
My template do not see objects, passed from Spring.
My code:
public class PublicModelAndView extends ModelAndView {
#Autowired
TemplateModulesHandler templateModulesHandler;
public void init() {
setViewName("index");
CSSProcessor cSSProcessor = new CSSProcessor();
cSSProcessor.setSiteRegion("public");
super.addObject("CSSProcessor", cSSProcessor);
JSProcessor jSProcessor = new JSProcessor();
super.addObject("JSProcessor", jSProcessor);
templateModulesHandler.setPublicModelAndView(this);
}
}
Contoller's code:
#SpringBootApplication
#Controller
public class IndexPage {
#Autowired
PublicModelAndView publicModelAndView;
#Autowired
OurServicesBean ourServicesBean;
#Autowired
PortfolioBean portfolioBean;
#RequestMapping(value = "/", method = RequestMethod.GET)
public ModelAndView indexPage() {
publicModelAndView.setTemplate("publicSiteIndexPage");
publicModelAndView.addObject("pageTitle", "TITLE!!!!!!!!!!!!!!");
publicModelAndView.addObject("ourServices", ourServicesBean.getMenu());
publicModelAndView.addObject("portfolioWorkTypes", portfolioBean.getWorkTypes());
publicModelAndView.addObject("portfolioWorks", portfolioBean.getWorks());
return publicModelAndView;
}
}
Main template's code:
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:th="http://www.thymeleaf.org"
>
<head th:include="headerAndFooter/fragments/header :: publicSiteHeader">
<title></title>
</head>
<body>
hello!
</body>
</html>
Fragment's code:
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:th="http://www.thymeleaf.org">
<head th:fragment="publicSiteHeader">
<title>${pageTitle}</title>
<!--[if lte IE 8]>
<script src="<?= SITE_TEMPLATE_PATH ?>/js/html5shiv.js"></script>
<![endif]-->
</head>
<body>
</body>
</html>
As result I do not see value of the object pageTitle, but I see in page output code like
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>${pageTitle}</title>
Why thymeleaf didn't paste value of the pageTitle to between title tag's open and close?
The same code works good with JSP, but do not work with thymeleaf.
Thymeleaf is not JSP, so that's why your template does not work as you expect.
Look here http://www.thymeleaf.org/doc/tutorials/2.1/usingthymeleaf.html#using-texts and use something like:
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:th="http://www.thymeleaf.org">
<title th:text="#{pageTitle}">page title</title>
Edited - my solution is for localised texts which is good practice anyway. if you want to use content of variable than use $.