Web mvc controller - Brutos
The Brutos web MVC is a mvc controller in Java. Designed to reduce the complexity of web development, with configurable mapping, view resolution, ioc interface allowing development independent of the container and as well as support for upload and download files. It can be configured as a front controller or controller.
The great advantage of Brutos web MVC with respect to current web mvc frameworks of the market is the possibility of its business model to be totally independent of the framework.
website: Web mvc - Brutos
download: Browse Web MVC for java Files on SourceForge.net
svn: SourceForge.net Repository - [brutos] Index of /
Re: Web mvc controller - Brutos
Available for download version 2.0 of the Brutos MVC.
Brutos application framework -
Re: Web mvc controller - Brutos
Available for download version 2.0 beta 2 of the Brutos MVC. Also available for download a simple web chat developed with Brutos MVC.
new website: Brutos application framework -
webchat: webchat with Brutos framework
Re: Web mvc controller - Brutos
Quote:
Originally Posted by
urubu
... Designed to reduce the complexity of web development, with configurable mapping, view resolution ...
+ with annotations.
What a nonsense! These are all exactly those items that build the heap of the complexity mentioned.
Compare to HybridJava.
Re: Web mvc controller - Brutos
Are those things trying to compete with Spring MVC? What are its advantages over Spring MVC?
Re: Web mvc controller - Brutos
Quote:
Originally Posted by
nambill
Are those things trying to compete with Spring MVC? What are its advantages over Spring MVC?
I will not make comparisons. Each chooses one that meets your needs and makes you comfortable.
There is no way to show all the features here. The focus of the framework is the C (Controller) of MVC. Most frameworks force you to make adjustments in your controller, eg extending class, forcing the use of specific types of return. One of the proposed framework is to allow the developer to program in a natural way. But what would be natural? Natural would not force the developer to make adjustments in the structure of the class.
The annotations are most commonly used:
@Controller: specifies a controller
@Identify: Used to specify the parameter of an action, property of a "bean", property of a controller and a constructor argument.
@Intercept: specifies an interception
@InterceptedBy: used to intercept a controller.
@ThrowSafe: used to intercept and handle exceptions.
@View: Sets the view of a controller or action.
@Action: specifies a controller action.
All annotations are optional.
Have available the code for a webchat using Brutos + CDI + Tomcat with XML, Annotation and COC.
A controller can be created without the use of any class of framework or even a annotation, but it has to use XML.
eg:
Code :
public class RoomController {
private User currentUser;
private RoomService roomService;
public RoomController(){
}
@Inject
public RoomController(@Named(value="sessionUser") User user){
this.currentUser = user;
}
public RoomService getRoomService() {
return roomService;
}
public void setRoomService(RoomService roomService){
this.roomService = roomService;
}
public void sendMessage(
MessageDTO message) throws UserNotFoundException{
roomService.sendMessage(
message.rebuild(
this.roomService,this.getCurrentUser()));
}
public void putUser(
UserDTO userDTO)
throws UserExistException, MaxUsersException{
if(userDTO == null)
throw new NullPointerException();
if(this.getCurrentUser() != null)
this.getCurrentUser().exitRoom();
User user = userDTO.rebuild();
roomService.putUser(user);
this.setCurrentUser(user);
}
public void removeUser(
User user ) throws UserNotFoundException{
if(user != null)
user.exitRoom();
}
public Serializable getMessage()
throws UserNotFoundException, InterruptedException{
Message msg = roomService.getMessage(this.getCurrentUser());
if( msg != null){
MessageDTO msgDTO = new MessageDTO(msg);
msgDTO.setForMe(
msg.getDest().equals(this.currentUser));
return msgDTO;
}
else
return null;
}
public Serializable getUsers(){
List<User> users = roomService.getUsers();
List<UserDTO> usersDTO = new ArrayList<UserDTO>();
for(User user: users)
usersDTO.add(new UserDTO(user));
return (Serializable)usersDTO;
}
public User getCurrentUser() {
return currentUser;
}
public void setCurrentUser(User currentUser) {
this.currentUser = currentUser;
}
}
The above class is a simple POJO without any adaptations to work with the framework.
In the next example has the same class using CoC without XML.
Code :
@RequestScoped
public class RoomController {
private User currentUser;
private RoomService roomService;
public RoomController(){
}
@Inject
public RoomController(@Named(value="sessionUser") User user){
this.currentUser = user;
}
public void messagePartAction(){
}
public void sendPartAction(){
}
public void loginAction(){
}
public RoomService getRoomService() {
return roomService;
}
public void setRoomService(RoomService roomService){
this.roomService = roomService;
}
public void sendAction(
MessageDTO message) throws UserNotFoundException{
roomService.sendMessage(
message.rebuild(
this.roomService,this.getCurrentUser()));
}
public void enterAction(
UserDTO userDTO)
throws ValidatorException, UserExistException,
MaxUsersException, NullPointerException{
if(userDTO == null)
throw new NullPointerException();
if(this.getCurrentUser() != null)
this.getCurrentUser().exitRoom();
User user = userDTO.rebuild();
roomService.putUser(user);
}
public void exitAction() throws UserNotFoundException{
if(this.currentUser != null)
this.currentUser.exitRoom();
}
@ResultView(rendered=true)
public Serializable messageAction()
throws UserNotFoundException, InterruptedException{
Message msg = roomService.getMessage(this.getCurrentUser());
if( msg != null){
MessageDTO msgDTO = new MessageDTO(msg);
msgDTO.setForMe(
msg.getDest().equals(this.currentUser));
return msgDTO;
}
else
return null;
}
@ResultView(rendered=true)
public Serializable listUsersAction(){
List<User> users = roomService.getUsers();
List<UserDTO> usersDTO = new ArrayList<UserDTO>();
for(User user: users)
usersDTO.add(new UserDTO(user));
return (Serializable)usersDTO;
}
public User getCurrentUser() {
return currentUser;
}
}
Is the same class, but without using XML! Almost was not used annotation. Depending, is not necessary annotation.
If prefer, you can use annotations to do the configuration.
Code :
@RequestScoped
@Controller(id="/Room/{roomID:\\d+}")
@View(id="/layout/login.jsp")
@AbstractActions({
@AbstractAction(id="/messagePart",view="/layout/messages.jsp"),
@AbstractAction(id="/sendPart", view="/layout/send.jsp"),
@AbstractAction(id="/login", view="/layout/login.jsp")
})
public class RoomController {
private User currentUser;
private RoomService roomService;
public RoomController(){
}
@Inject
public RoomController(@Named(value="sessionUser") User user){
this.currentUser = user;
}
public RoomService getRoomService() {
return roomService;
}
@Identify(bean="roomID")
public void setRoomService(RoomService roomService){
this.roomService = roomService;
}
@Action("/send")
public void sendMessage(
@Identify(useMapping=true)
MessageDTO message) throws UserNotFoundException{
roomService.sendMessage(
message.rebuild(
this.roomService,this.getCurrentUser()));
}
@Action("/enter")
@View(id="/layout/room.jsp")
@ThrowSafeList({
@ThrowSafe(target=ValidatorException.class, view="/layout/login.jsp"),
@ThrowSafe(target=UserExistException.class, view="/layout/login.jsp"),
@ThrowSafe(target=MaxUsersException.class, view="/layout/login.jsp"),
@ThrowSafe(target=NullPointerException.class, view="/layout/login.jsp")
})
public void putUser(
@Identify(useMapping=true)
UserDTO userDTO)
throws UserExistException, MaxUsersException{
if(userDTO == null)
throw new NullPointerException();
if(this.getCurrentUser() != null)
this.getCurrentUser().exitRoom();
User user = userDTO.rebuild();
roomService.putUser(user);
}
@Action("/exit")
public void removeUser(
@Identify(bean="user",scope=ScopeType.SESSION)
User user ) throws UserNotFoundException{
if(user != null)
user.exitRoom();
}
@Action("/message")
@ResultView(rendered=true)
public Serializable readMessage()
throws UserNotFoundException, InterruptedException{
Message msg = roomService.getMessage(this.getCurrentUser());
if( msg != null){
MessageDTO msgDTO = new MessageDTO(msg);
msgDTO.setForMe(
msg.getDest().equals(this.currentUser));
return msgDTO;
}
else
return null;
}
@Action("/listUsers")
@ResultView(rendered=true)
public Serializable readUsers(){
List<User> users = roomService.getUsers();
List<UserDTO> usersDTO = new ArrayList<UserDTO>();
for(User user: users)
usersDTO.add(new UserDTO(user));
return (Serializable)usersDTO;
}
public User getCurrentUser() {
return currentUser;
}
public void setCurrentUser(User currentUser) {
this.currentUser = currentUser;
}
}
What is the framework gives the option to do a thing in many different ways.
It also has mapping beans that can be used in the the controller properties, constructor of a bean and parameters of an action.
You can determine the type, name, scope and how value will be processed.
It has native support types: Date, Calendar, Enum, Map, List and Set.
Code :
public class MessageDTO implements Serializable{
private UserDTO origin;
private UserDTO dest;
private String message;
private boolean forMe;
public MessageDTO(){
}
public MessageDTO(Message msg){
this.origin =
msg.getOrigin() == null?
null :
new UserDTO(msg.getOrigin());
this.dest = new UserDTO(msg.getDest());
this.message = msg.getMessage();
}
public UserDTO getOrigin() {
return origin;
}
public void setOrigin(UserDTO origin) {
this.origin = origin;
}
public UserDTO getDest() {
return dest;
}
public void setDest(UserDTO dest) {
this.dest = dest;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public Message rebuild(RoomService roomService, User currentUser)
throws UserNotFoundException{
Message obj = new Message();
obj.setDest(this.dest.rebuild(roomService));
obj.setOrigin(
currentUser == null?
(this.origin != null?
this.origin.rebuild(roomService)
: null) :
currentUser
);
obj.setMessage(this.message);
return obj;
}
public Message rebuild(RoomService roomService) throws UserNotFoundException{
return rebuild(roomService,null);
}
public boolean isForMe() {
return forMe;
}
public void setForMe(boolean forMe) {
this.forMe = forMe;
}
}
Note, the above example is a simple POJO!
Do not want to use XML, no problems!
Code :
@Bean
public class MessageDTO implements Serializable{
private UserDTO origin;
private UserDTO dest;
private String message;
@Transient
private boolean forMe;
@Constructor
public MessageDTO(){
}
public MessageDTO(Message msg){
this.origin =
msg.getOrigin() == null?
null :
new UserDTO(msg.getOrigin());
this.dest = new UserDTO(msg.getDest());
this.message = msg.getMessage();
}
private void validate(){
if(this.dest == null)
throw new ValidatorException("msgError");
if(this.message == null || this.message.length() > 200 ||
!this.message.matches("[^\\<\\>]*"))
throw new ValidatorException("msgError");
}
public UserDTO getOrigin() {
return origin;
}
public void setOrigin(UserDTO origin) {
this.origin = origin;
}
public UserDTO getDest() {
return dest;
}
public void setDest(UserDTO dest) {
this.dest = dest;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public Message rebuild(RoomService roomService, User currentUser)
throws UserNotFoundException{
this.validate();
Message obj = new Message();
obj.setDest(this.dest.rebuild(roomService));
obj.setOrigin(
currentUser == null?
(this.origin != null?
this.origin.rebuild(roomService)
: null) :
currentUser
);
obj.setMessage(this.message);
return obj;
}
public Message rebuild(RoomService roomService) throws UserNotFoundException{
return rebuild(roomService,null);
}
public boolean isForMe() {
return forMe;
}
public void setForMe(boolean forMe) {
this.forMe = forMe;
}
}
Want to abuse the use of annotations.
Code :
@Bean
public class MessageDTO implements Serializable{
@Identify(useMapping=true)
private UserDTO origin;
@Restrictions(
rules={
@Restriction(rule=RestrictionsRules.REQUIRED, value="true")
},
message="msgError"
)
@Identify(useMapping=true)
private UserDTO dest;
@Restrictions(
rules={
@Restriction(rule=RestrictionsRules.MAXLENGTH, value="200"),
@Restriction(rule=RestrictionsRules.MATCHES, value="[^\\<\\>]*")
},
message="msgError"
)
private String message;
@Transient
private boolean forMe;
@Constructor
public MessageDTO(){
}
public MessageDTO(Message msg){
this.origin =
msg.getOrigin() == null?
null :
new UserDTO(msg.getOrigin());
this.dest = new UserDTO(msg.getDest());
this.message = msg.getMessage();
}
public UserDTO getOrigin() {
return origin;
}
public void setOrigin(UserDTO origin) {
this.origin = origin;
}
public UserDTO getDest() {
return dest;
}
public void setDest(UserDTO dest) {
this.dest = dest;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public Message rebuild(RoomService roomService, User currentUser)
throws UserNotFoundException{
Message obj = new Message();
obj.setDest(this.dest.rebuild(roomService));
obj.setOrigin(
currentUser == null?
(this.origin != null?
this.origin.rebuild(roomService)
: null) :
currentUser
);
obj.setMessage(this.message);
return obj;
}
public Message rebuild(RoomService roomService) throws UserNotFoundException{
return rebuild(roomService,null);
}
public boolean isForMe() {
return forMe;
}
public void setForMe(boolean forMe) {
this.forMe = forMe;
}
}
Also the framework has native support for uploading files! Which allows the use of other frameworks, eg Apache FileUpload.
Code :
public class FileController{
private String repositoryPath;
public FileController( String repositoryPath ){
this.repositoryPath = repositoryPath;
}
public void uploadFile( File file ){
...
}
public File download( String fileName ){
File file = new File( repositoryPath + "/" + fileName );
return file;
}
}
View:
Code :
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title></title>
</head>
<body>
<form method="POST" enctype="multipart/form-data" action="/File/uploadFile">
<table width="100%" cellpadding="0" cellspacing="0" >
<tr>
<td width="100%">File:</td>
</tr>
<tr>
<td width="100%"><input type="file"
name="file" size="20"></td>
</tr>
<tr>
<td width="100%"><input type="submit"
name="action" value="upload"></td>
</tr>
</table>
</form>
</body>
</html>
It has many other features and settings that can be made.
I can not put everything here and still has many features yet to be implemented.