I am confused when it is proper to use an application with multiple entry points, or I guess an application with multiple interconnected modules. I have a network application (Netty) as well as a web application (spring). I can bundle them together, in effect tightly coupling them together, or I can modularize them to operate interdependently of each other while still working together to make the application whole.
Is there any specific reason for making an application a single entity vs multiple entities? Is it "desired" to have a self contained application (eg. One main method)?
First of all, asking about the number of main() methods is a bit misleading. You can have several classes with main() methods in a single JAR file after all.
But the question seems to be more about single application vs. multiple applications, or to be more precise: tiers.
It's important to note that this issue is separate from the question of modularity and multi-threading, all of which can be employed in a single tier application just as easily as in a multi-tier application.
The reasons you'd need a multi-tiered application can vary, but here are a few examples:
It is simply part of the requirements: i.e. a chat software will usually need a server and a client because the requirement is to move data between two computers.
Scaling: you need to spread the work to multiple computers to cope with large amounts of data or requests. (This is a typical use case of message queues for example.)
Separation of concerns: This typically happens in "enterprise" systems, where different functions need to be performed in complete isolation, allowing modules to be replaced/restarted on the go or to scale them separately.
Web applications are supposed to have multiple entries; think of the URL you type that can lead to to a resource. In fact, in many web application architectures, such as JAX-RS, exposing the resource URI is encouraged. Each entity, as small as one java bean, has its own entry point. Not sure if this is what you mean, but that's my opinion.
Related
My employer has currently given me a project that has me scratching my head about synchronization.
I'm going to first talk about the situation I'm in:
I've been asked to create a pdf-report/quotation-tool that takes data (from csv-files; because the actual database the data is on is being used by old IBM software and they for reasons (unknown) don't want any direct access to this database (so instead of making copies of the data to other databases, they apparently found it incredibly fine to just create a folder on the server with loads and loads and loads of CSV-files.)), this piece of software is to load data into the application, query it, transform where needed, do calculations and then return with a pdf-file to the end-user.
The problem here is that getting, querying, and calculating things takes a fair amount of time, the other problem is: they want it to be a WebApp because the business team does not want to install any new software, they're mostly moving towards doing everything online (since the start of the pandemic), it being a WebApp means that every computation has to be done by the WebApp and getting the data likewise.
My question: Is each call to a servlet by a separate user treated as a separate servlet and should I only synchronize the methods on the business logic (getting and using the data); or should I write some code that puts itself in the middle of the servlet, receives a user-id (as reference), that then runs the business-logic in a synchronized-fashion, then receiving data and returning the pdf-file?
(I hope you get the gist of it...)
Everything will run on Apache Tomcat 8 if that helps. Build is Java 11lts.
Sorry, no code yet. But I've made some drawings.
With java web applications, the usual pattern is for the components to not have conversational state (meaning information specific to a specific user's request). If you need to keep state for a user on the server, you can use the http session. With a SPA or Ajax application it's often easier to keep a lot of that kind of state in the browser. The less state you keep on the server the easier things are as your application scales, you don't have to pin sessions to servers (messing up load balancing) or copy lots of session state across a cluster.
For simple (non-reactive) web apps that do blocking i/o, each request-response cycle gets its own dedicated thread from tomcat's pool. That thread delivers the http request to the servlet, handles the business logic and blocks while talking to the database, then carries the http response.
(Reactive webapps are going to be more complex to build, you will need a non-blocking database driver and you will have less choices for databases, so I would steer clear of those, at least for your first web application.)
The threadpool used by tomcat has to protect itself from concurrent access but that doesn't impact your code. Likewise there are 3rd party middletier caching libraries that have to deal with concurrency but you can avoid dealing with it directly. All of your logic is confined to one thread so it doesn't interfere with processing done by other threads unless there are shared mutable data structures. Those data structures would be the part of the application where synchronization might be one of several possible solutions.
Synchronization or other locking schemes are local to one instance of the application. If you want to stand up multiple instances of this application then you need to be aware each one would be locking separately from the others. So for some things it's better to do locking in the database, since that is shared across webapp instances.
If you can make use of a database to store your data, so that you can rely on the database for caching and indexing, then it seems likely your application should be able to avoid having doing a lot of locking.
If you want examples there are a lot of small examples for building web apps using spring at https://spring.io/guides. These are spring boot applications that are self hosted so you can put them together quickly and run them right away.
Going rogue with a database may not be the best course since databases need looking after by DBAs. My advice is put together two project plans, one for using a database, and one for using the flat files. The flat file one will have to allow for addressing issues like handling caching, indexing data, replication of data from the legacy database, and not having standard tools that generate pdfs from sql queries. The alternative plan using a database should have a lot less sorting out of infrastructure and a shorter time til you can get down to cranking out reports.
I have a XML webservice application that consists of several parts. There is a common entry servlet that delegates to different internal webservices based on the request parameters.
Now I wonder which solution might be better:
to have any of those services running within a single application? So, one application serves all?
or split them into microservices, where each servlet app is responsible for only one single purpose/brand?
Example: lets assume we have a common car service that serves content for all cars of a brand. Each of them might have completely different logic.
Some brands might have periodic data imports.
Some brands might get data from additional an external webservice.
Some brands might have a database cache, etc.
/my/rest/car/AUDI/details?id=123
/my/rest/car/BMW/details?id=456
...
Most of those webservices are nearly independent. Though they are currently contained within a single application, as they all serve "car content".
Now I'm rethinking if it could make sense having the common /my/rest/car/{brand} webservice servlet in a main war file. And then create a new war file for each of the brands. Each of them would offer its own XML webservice, and the common servlet would delegate and join them.
Of course, this might result in a bit overhead, as the xml request and response has to be exchanged locally between those services.
But as an advantage, I could more easily maintain and restart each service individually without downtime of the others, and would have less side effects refactoring and extending a part. Eg if there is only one data import change for BWM.
So, what is your experience in splitting large applications like this? One serves all, or single services?
Currently I am working for a company that has 6-7 Java EE projects. They are multi module maven projects that are all fairly large and serve different purposes. As such, their models are very different but for the most part the data is stored in the same database.
The problem, to me, is that since there are a few areas of overlap, they simply inject the existing DAOs all the way up the depedency chain. So I have
A-parent
-A-JPA
-A-DAO
B-Parent
-B-JPA
-B-DAO
-A-JPA
-B-DAO
etc, etc. They are really only using 2 percent of the other projects model and respective DAO.
I am trying to attempt to decouple these dependencies by simply duplicating the entities needed (and only including fields/mappings for the things that are really needed) so that the same EJB isn't deployed 7 times (or more when clustered), but apparently I'm not making a convincing argument. Can anyone help point me to an article with best practices for this situation or help bring up points to explain to him.
TLDR: I want each project to have its own set of entities even if there is a very small bit of overlap to reduce dependencies between projects as well as make it so we aren't deploying the same EJB's 7 times. My boss thinks there is nothing wrong with these being unnecessarily coupled. Am I making a big deal about this for nothing? Thanks!
If it is a single data model that is being maintained for various applications to use, the persistence entities (and even their DAOs) may be seen as the Java API to that database, and I'd put it in a central component. Some organizations may even drive the design from the database upwards, and reverse engineer the persistence entities, in which case they'll be same or similar for different users.
Whether such central component is a library (reused by other components) or an EJB of its own (that's being called by other components) I would let depend on the desired transactional and caching behavior of the application, and how you see responsibilities being organized. On one project we strongly upheld the rule that each piece of data could only be maintained by a single component (a service or an EJB) and others would have to go through that single component.
If it is a common domain model, but every EJB implement its own data storage for that, then the domain model may be shared, and I would not share the persistence entities. Then you get into the discussion of sharing the domain model among different components. The world may be viewed in slightly different ways from within different sub-domains and I feel that you end up designing your domains slightly different across different sub-systems, hence there I would possibly vote against reuse.
Everyone's mileage may vary, and I may see things differently given the actual circumstances of a particular project.
I would like to design an application with a core and multiple modules on top of the core. The core would have the responsibility to receive messages from the network, to parse the incoming messages and to distribute the messages to registered modules.
There are multiple types of messages, some modules may be interested to receive only some of the types. The modules can execute in parallel, or they can execute sequentially (e.g. when modules are interdependent with a well defined order of execution).
Also, it would be great if the modules could be deployed/undeployed even if the core is up.
It is completely new for me, I used to write modular application but with the multiple parts wired statically.
Which direction (i.e. framework, pattern...) should I take for such a design? I don't know if it's relevant to my question but I precise I'll use Java.
Thanks
You has a very good approach at the architecture level. But it will be beneficial only when your application layers/tire will be at separate instance, so that you can shut down one module/server and while other part will still be running. Point is will you run the modules on separate instances?
Secondly, I would like to suggest you to build the application core architecture using Web-Service either REST/SOAP as it will automatic achieve your thought that follows Service Oriented Architecture (SOA). That will be producer - consumer relation and you can run on separate instance. And while deploying/undeploying you can still run the services part to support other client instances.
Using Web service will also provide you a global information exchange system that will likely to communicate with several application views/front end.
I am a S/W developer working on a Java web application.
I have very limited knowledge of Java and want to understand my application architecture from a very high level in simple terms. Being a developer, I do not completely understand the big picture.
Can anyone help me understand this?
Each layer represents a place where some problems are solved is similar way, often using some particular libraries or frameworks. In trying to understand this work your way down through the layers. BUT, note that each layer hides the details underneath, you don't need to understand the details of lower layers in order to understand one layer.
So the Struts piece is dealing with the User-Interface related issues of understanding user requests choosing some business logic to invoke and choosing how to display the results back to the user. It doesn't concern itself with how the business logic works, that's the job of the next layer down.
By Business Logic I mean the Java (or other language) code that expresses the realities of a the customer's business. For example in a retail application we might need to work out discounts for particular volumes of orders. So the UI layer wants to display the price for a customer's order. It doesn't have any discount logic itself, instead it says to the business logic layer "Customer X is order N widgets and M zettuls, when can we supply and how much shall we charge" and the business logic figures out the pricing for this customer, which might depend on all sorts of things such as the status of the customer, the number things we have in stock, the size of the order and so on. The UI just gets an answer £450, to be delivered 16th September, and displays it.
That leads to questions such as "why separate the business logic to its own layer?" There are several possible reasons:
The business logic might be used by some completely different UI as well
It pre-exists, from some older system
Our brains are too small to think about UI and Business Logic at the same time
We have different teams working on UI and BL - different skills are needed
This same way of thinking follows down the layers. Th important thing when thinking about each layer is to try to focus on the role of the layer and treat the other layers as black-boxes. Our brains tend to be too small to think about the whole thing at the same time. I can almost feel myself changing mode as I shift between the layers - take off my UI head, put on my persistence head.
There's plenty of material "out there" about each layer. Suggest you start by reading up about one of them and ask specific questions if you get stuck.
Looks like a standard "enterprisy" application to me.
Interface
This app. is primarily intended to be used via web browsers by humans. This interface or UI layer (in a broad sense) is build using the MVC framework Struts. If you don't know MVC, then it's a good idea to read up on this term.
The app. also exposes web service interface, which is intended to be used by non-humans (other applications or scripts).
So, 2 kinds of interface is provided.
Business logic
Request coming from the 2 interfaces noted above, ultimately talk to the lower half (App. tier) to get some real job done. The actual process (calculating stuff, storing stuff and what not) happens here. Note also that this tier also talks to external systems (via Service Gateway) in order to complete the requests.
The reason they separated the system like this can vary. If it's a very simple, small app. then it doesn't pay off to have these abstractions, so it's probably a quite complex system. Maybe the app. tier is some legacy app. and they wanted to put some better UI on top of it. Maybe the app. tier and the web tier happened to use different technology stack. Or perhaps the app. tier is used by many other external systems. It also makes updating each services/replacing each services etc. easier, so maybe they are anticipating that. Anyways, it looks like a very common SOA type of design.
Not sure what else you might want to know. I see that the designer intends to use distributed cache in both tiers. All in all, it's a very common type of system integration diagram.
App Tier - Where the basic application logic resides (think of a basic console-only program).
Database - MySQL, Oracle... server
DOs - Short for Domain Objects. If anemic usually limited to getters/setters and can be synonymous with Entities (#Entity).
Data Access Objects - Objects using DAO pattern to fetch domain objects from the database. Could be considered equivalent as DAL (Data Access Layer) although this might not fit here. Usually uses a persistence/mapping framework such as Hibernate or iBatis.
Domain Model - Where Domain (domain being what has been studied/analyzed from requirements) Classes are packaged and associated (one-to-one, many-to-one, ...). Sometimes there are even composited in other container classes.
Core Application Services - Groups Services classes which could be equated to the Business Logic Layer (BLL). Biz services handle the Domain Model, Application Services are relative to the Application (methods don't manipulated Domain) and not sure what System Services are supposed to do. I'm also not sure what the distinction between Core and the Application Service block is.
Facade/Interface - This is where all the communication is done with other Tiers. It helps to fully understand interfaces and the Facade pattern.
TOs: Transfer Objects. Related to Domain Objects and used for transferring as the name implies.
Web Tier - All the logic added to make the application accessible from the Web.
Business Delegate: Block using delegation pattern? Here it apparently plays the middle man between Application facade and the Presentation Tier using TOs.
Model: Notion relative to the MVC pattern and variants. With JSF I know that beans are usually linked to JSPs. This model is to be distinguished from the Domain Model. It is created for the purposes of presentation and might contain information that has nothing to do with the data being manipulated in the application tier and is specific to the web tier.
View: Notion relative to the MVC pattern and variants. JSPs represent individual pages and use their own markup.
Session: Look up theory on sessions (necessary as HTTP is stateless).
ApplicationContext: Groups instances/settings that can be pulled into from anywhere. Often associated in the Java world with the Spring framework. To not be confused with UglyGlobalVar/singletons.
Front controller: Could be considered as equivalent to Controller of MVC although the Front Controller pattern appears to be more specific. Servlets are considered as controllers as they handle communication (GET, POST...) and coordinate the model/view. Not familiar with Struts but imagine that the framework implements classes to represent user actions.
Presentation Tier: Simply all of the logic used for outside presentation.
Filters: Can be used to filter requests, for example to redirect a request to a login page.
Feel free to add/correct this description.