Spring State Machine
FOSSA Live Project Report latest report ( license checks)
FOSSA ran license checks across 77 dependencies
Requirements are:
PeopleFlow is a global HR platform enabling companies to hire & onboard their employees internationally, at the push of a button. It is our mission to create opportunities for anyone to work from anywhere. As work is becoming even more global and remote, there has never been a bigger chance to build a truly global HR-tech company.
As a part of our backend engineering team, you will be responsible for building our core platform including an employees management system.
The employees on this system are assigned to different states, Initially when an employee is added it will be assigned "ADDED" state automatically .
The other states (State machine) for A given Employee are:
- ADDED
- IN-CHECK
- APPROVED
- ACTIVE
Our backend stack is:
- Java 11
- Spring Framework
- Kafka
First Part:
Your task is to build Restful API doing the following:
-
An Endpoint to support adding an employee with very basic employee details including (name, contract information, age, you can decide.) With initial state "ADDED" which indicates that the employee isn't active yet.
-
Another endpoint to change the state of a given employee to "In-CHECK" or any of the states defined above in the state machine
Please provide a solution with the above features with the following consideration.
- Being simply executable with the least effort Ideally using Docker and docker-compose or any similar approach.
- For state machine could be as simple as of using ENUM or by using https://projects.spring.io/spring-statemachine/
- Please provide testing for your solution.
- Providing an API Contract e.g. OPENAPI spec. is a big plus
Second Part (Optional but a plus):
Being concerned about developing high quality, resilient software, giving the fact, that you will be participating, mentoring other engineers in the coding review process.
- Suggest what will be your silver bullet, concerns while you're reviewing this part of the software that you need to make sure is being there.
- What the production-readiness criteria that you consider for this solution
Absolute minimum is being there:
- Source code,
- Tests code,
- Maven,CI\CD, Docker etc scripts.
Nevertheless
Production-readiness criteria list is not so short. Below is the Production-readiness criteria list but it is not complete and could be updated.
- Correctly implemented business requirement (or fix reported\discovered issue) ( User Acceptance that system meets all required needs, Passed all quality tests related to functionality requirements.)
- Use best practice in implementing solution (appropriate patterns etc)
- Comply Project coding standarts (naming convention\formatting style\documentation(comments))
- Comply Project logging & monitoring standarts ( Kibana, DataDog, Relic etc.)
- Pass automatic CI review (Travis CI etc).
- Covered by tests according Project policy.
- Pass automated tests.
- Pass team member code review.
- Pass vulnerability security review & testing (Veracode, Codacy, Sonarqube) (Security Review includes completed and mitigated Vulnerability Scans and if required Penetration tests)
- Injection
- XML Injection (aka Blind XPath Injection)
- ‘NoSQL injection’
- ‘SQL Injection’
- Broken authentication
- Sensitive data exposure
- Cross-site scripting (XSS)
- Insecure deserialization.
- Pass dependencies vulnerabilities check (not used components with known vulnerabilities)
- Validate Docs\Readme etc documentation related to this solution is up to date
- Check that Production environments properly configured and tested
- Check that Hardware/software requirements documented
- Check that Problem resolution process (troubleshooting) in place
- Privacy & Regulatory data have been identified and system complies with privacy and regulatory requirements.
- Problem resolution process (troubleshooting) in place
- Check that Synthetic transactions/smoke tests complete
Third Part (Optional but a plus):
Another Team in the company is building another service, This service will be used to provide some statistics of the employees, this could be used to list the number of employees per country, other types of statistics which is very vague at the moment.
- Please think of a solution without any further implementation that could be able to integrate on top of your service, including the integration pattern will be used, the database storage etc.
A high-level architecture diagram is sufficient to present this.
his is a very broad question so here are a few of the more useful Design Patterns, you may need to use one or more of these depending on what you are trying to do:
Adapter - If you want to wrap the 3rd party API with an interface that fits better into the rest of your system.
A Must for Vendor & Service Integrations
the adapter pattern is used to implement a light wrapper around third-party APIs, one that is contextually
relevant for your codebase, and can withstand upstream changes or wholesale replacements of the vendor API
without impacting the rest of your application.
Facade - If you want to simplify interacting with the 3rd party library by going through some kind of helper class.
Bridge - Define a new intermediate interface between your code and the 3rd party library.
This is most useful if the 3rd party library is subject to future changes, any changes will only affect
the one class that communicates with this 3rd party library leaving the rest of your system unaffected.
The Bridge Pattern is also useful if you need to switch to a different but similar 3rd party library;
again making you only change one class.
Using API gateway in design microservices architecture
When working with REST APIs we must remember to consider security from the start.
OAuth 2.0 authentication can be used to verify linked services to run API requests. Using OAuth2 to access the 3rd party API
OAuth2 flow: The initial request
The following image shows the OAuth2 flow when you access the SSM API for the first time

OAuth2 flow: Subsequent requests
On subsequent requests, you do not need to exchange your credentials for a token. Instead, you can just include the access token you already have, as long as it hasn't expired yet:

OAuth2 flow: When your access token expires
When an access token expires (after fe 12 hours), you can use the refresh token to get a new access token

The application is written for Java 11 and uses an in-memory H2 database, so doesn't require any additional actions to start, except building a jar and execution of the command to start. Also used default port 8080
How to run with Java 11:
mvn clean install
java -jar target/ssm-0.0.1-SNAPSHOT.jarHow to run with Docker:
mvn clean install
docker build --build-arg=target/ssm-0.0.1-SNAPSHOT.jar -t ssm-0.0.1-SNAPSHOT .
docker run -p 8080:8080 ssm-0.0.1-SNAPSHOT

