jSimple-parent (родовой модуль jSimple, конфигурирующий базовые зависимости)
├── aop -- использование cglib для реализации AOP, поддерживающее несколько интерцепторов (не отсортировано)
├── bean -- контейнер beans и сканнер
├── blog -- блог, созданный с помощью AngularJS
├── cache -- простое решение кэширования, включающее память и Memcached
├── config -- все константы конфигурации jSimple
├── data -- простой интерфейс доступа к данным, основанный на dbutils, реализующий простую ORM и поддержку ленивой загрузки
├── exception -- единый набор исключений jSimple
├── hessian -- пример использования Hessian
├── ioc -- внедрение зависимостей, основанное на контейнере beans
├── mvc -- MVC-фреймворк, который работает хорошо
├── utils -- общие библиотеки Java на основе Apache Commons
После клонирования кода используйте команду Maven для установки:
mvn clean install
```### 2. Создание Maven Web проекта
Основная структура директорий Java выглядит следующим образом:
com.sky.jSimple.blog ├── controller/ - контроллеры ├── entity/ - сущности ├── dao/ - доступ к данным ├── service/ - бизнес-логика ├── interceptor/ - интерцепторы
```xml
<dependency>
<groupId>com.sky.jSimple</groupId>
<artifactId>jSimple-mvc</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>
Создайте файл jSimple.xml
в каталоге resources
, содержащий следующее:
<?xml version="1.0" encoding="UTF-8"?>
<jSimple>
<mvc static-suffix=".jpg;.bmp;.jpeg;.png;.gif;.html;.css;.js;.htm;.ttf;.woff;.svg;.swf;.map"
static-expire="3600"/>
<beans scan-package="${scan.package}">
<bean id="dataSource"
class="org.apache.commons.dbcp.BasicDataSource">
<property name="driverClassName" value="com.mysql.jdbc.Driver"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.user}"/>
<property name="password" value="${jdbc.password}"/>
<property name="initialSize" value="10"/>
<property name="maxIdle" value="20"/>
<property name="minIdle" value="5"/>
Далее в web.xml
добавляется один servlet:
<servlet>
<servlet-name>jsimplemvc</servlet-name>
<servlet-class>com.sky.jSimple.mvc.DispatcherServlet</servlet-class>
<init-param>
<param-name>configPath</param-name>
<param-value>/jSimple.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>jsimplemvc</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
@Entity("blog")
public class Blog implements Serializable {
@Id
private long id;
private String title;
private String content;
private Date createdDate;
private Date lastModifiedDate;
private long uid;
private long viewCount;
private String linkName;
private long categoryId;
private String tags;
private int isRecommend;
``````markdown
### 6. Создание DAO
```java
@Bean
public class BlogDao {
@Inject
private JSimpleDataTemplate jSimpleDataTemplate;
public void insert(Blog entity) {
jSimpleDataTemplate.insert(entity);
}
public void update(Blog entity) {
jSimpleDataTemplate.update(entity);
}
public void delete(Long id) {
jSimpleDataTemplate.delete(id, Blog.class);
}
public Blog getById(Long id) {
return jSimpleDataTemplate.getById(Blog.class, id);
}
}
Аннотация @Bean
указывает, что данный класс будет помещён в контейнер бинов. Аннотация @Inject
используется для внедрения зависимостей.
@Bean
public class BlogService implements IBlogService {
@Inject
private BlogDao blogDao;
@Transactional
public void insert(Blog entity) {
blogDao.insert(entity);
}
@Transactional
public void update(Blog entity) {
blogDao.update(entity);
}
public void delete(Long id) {
blogDao.delete(id, Blog.class);
}
public Blog getById(Long id) {
return blogDao.getById(Blog.class, id);
}
}
Аннотация @Transactional
используется для управления транзакциями, внутри которых могут выполняться различные операции с базой данных.
@Bean
public class BlogController extends ControllerBase {
@Inject
private IBlogService blogService;
@HttpPost("/api/blog")
public ActionResult addBlog(Blog blog) {
blog.setCreatedDate(new Date());
blog.setLastModifiedDate(new Date());
blog.setUid(1);
blog.setViewCount(0);
blogService.insert(blog);
return json(blog);
}
}
```Контроллер важен тем, что методы, помеченные аннотацией `@HttpPost`, используются для обработки POST-запросов от клиентской стороны. Аргументы таких методов могут представлять собой объекты, карты или другие типы данных.
Существует четыре маркера: @HttpPost
, @HttpGet
, @HttpPut
, @HttpDelete
.
Отправляемый ActionResult
поддерживает различные типы контента, такие как JSON, HTML, JSP, файлы, Freemarker, Velocity и другие, при этом легко расширяем.
```Например, если мне нужно вернуть капчу, то вот как можно реализовать ActionResult
:
public class ValidateCodeResult extends ActionResult {
@Override
public void executeResult() {
response.setContentType("image/jpeg"); // Устанавливаем тип содержимого, чтобы браузер знал, что это изображение
response.setHeader("Pragma", "No-cache"); // Устанавливаем заголовок ответа, чтобы браузер не кэшировал этот контент
response.setHeader("Cache-Control", "no-cache");
response.setDateHeader("Expires", 0);
// Класс генерации капчи
RandomValidateCode randomValidateCode = new RandomValidateCode();
try {
randomValidateCode.getRandcode(request, response); // Метод вывода изображения
} catch (Exception e) {
throw new JSimpleException(e);
}
}
}
Вызов в контроллере:
@HttpGet("/validateCode")
public ActionResult getValidateCode()
{
return new ValidateCodeResult();
}
Так просто!
Каждый контроллер имеет метод onException
, который по умолчанию возвращает страницу с сообщением об ошибке. Переопределив onException
, можно создать свою логику обработки ошибок.
Например, для AJAX запроса, где требуется отправка JSON вместо страницы с ошибками, код может выглядеть так:
public class AjaxController extends ControllerBase {
public void onException(Throwable e, HttpServletRequest request, HttpServletResponse response) {
try {
Map<String, Object> map = new HashMap<>();
map.put("error", e);
json(map).executeResult(); // Отправка JSON
} catch (JSimpleException e1) {
e1.printStackTrace();
}
}
}
```### 10. Написание промежуточных компонентов
Допустим, мне нужно реализовать промежуточный компонент для перенаправления незарегистрированных пользователей. Код будет таким:
```java
@Order(98)
public class NeedLoginInterceptor extends Interceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
if (!request.getUserPrincipal().getName().equals("anonymousUser")) {
return true;
}
String loginUrl = request.getContextPath() + "/login";
response.sendRedirect(loginUrl);
return false;
}
}
``````markdown
@Override
public ActionResult before(Class<?> cls, Method method, Object[] params) {
if (BlogContext.getUser() == null) {
return new RedirectResult("/user/login?path=" + request.getAttribute("encodeUrl"));
}
return null;
}
@Override
public void after(Class<?> cls, Method method, Object[] params, ActionResult result) {
}
`@Order` annotation specifies the execution order of this interceptor; the higher the value, the earlier it executes. The `getAnnotation()` method shows which annotations are applied to a method.
### Summary
This framework has many drawbacks, but it can be used as an educational material. The example above was taken from a blog created based on this framework—jsimple-blog, thank you for your attention!
## P.S.
I would like to emphasize once again that using someone else's code without permission is inappropriate. I apologize to the author.
Вы можете оставить комментарий после Вход в систему
Неприемлемый контент может быть отображен здесь и не будет показан на странице. Вы можете проверить и изменить его с помощью соответствующей функции редактирования.
Если вы подтверждаете, что содержание не содержит непристойной лексики/перенаправления на рекламу/насилия/вульгарной порнографии/нарушений/пиратства/ложного/незначительного или незаконного контента, связанного с национальными законами и предписаниями, вы можете нажать «Отправить» для подачи апелляции, и мы обработаем ее как можно скорее.
Комментарии ( 0 )