Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
58 commits
Select commit Hold shift + click to select a range
d016235
Add Sequence model
aaabAlhosni May 24, 2026
0886278
Add Service class
aaabAlhosni May 24, 2026
3343438
Implement add sequence
aaabAlhosni May 24, 2026
7f3017a
Implement get sequences
aaabAlhosni May 24, 2026
625b4c5
Add Controller scaffold
aaabAlhosni May 24, 2026
24aa566
Wire POST endpoint
aaabAlhosni May 24, 2026
9309ab5
Wire GET endpoint
aaabAlhosni May 24, 2026
a02912a
Add version backlog
aaabAlhosni May 24, 2026
22819e5
Update README docs
aaabAlhosni May 24, 2026
8bca8a1
Configure application
aaabAlhosni May 24, 2026
26a8381
Fix Service annotation conflict
aaabAlhosni May 24, 2026
7bc74cf
Rename sequence to input, add validation
aaabAlhosni May 24, 2026
e86de4e
Add class comments, update README
aaabAlhosni May 24, 2026
caa3c25
Add output field, hide raw input from response
aaabAlhosni May 24, 2026
7252cd0
Reject inputs starting with underscore
aaabAlhosni May 24, 2026
f9fd210
Add sequenceLogicAlgorithm method stub
aaabAlhosni May 24, 2026
768ba5c
Implement length-encoded parser logic
aaabAlhosni May 24, 2026
07f6559
Wire algorithm, update error message
aaabAlhosni May 24, 2026
c302778
Update version backlog to 0.2
aaabAlhosni May 24, 2026
7b682b4
Update README API reference and architecture
aaabAlhosni May 24, 2026
f5392cf
Move Sequence to Module package
aaabAlhosni May 24, 2026
9a0670e
Add update sequence method
aaabAlhosni May 24, 2026
0fbe366
Add PUT endpoint
aaabAlhosni May 24, 2026
6643ed4
Add delete sequence method
aaabAlhosni May 24, 2026
e4cf6dd
Add DELETE endpoint
aaabAlhosni May 24, 2026
9fd9acd
Update version backlog
aaabAlhosni May 24, 2026
69d79c6
Update README docs
aaabAlhosni May 24, 2026
fe82437
DELETE enqiry message modifyed.
aaabAlhosni May 24, 2026
d7e1da7
Add JPA and Oracle dependencies
aaabAlhosni May 24, 2026
ba308bb
Add Oracle datasource config
aaabAlhosni May 24, 2026
2e75b16
Add JPA entity annotations
aaabAlhosni May 24, 2026
8edf2f7
Add Repository interface
aaabAlhosni May 24, 2026
a61c779
Add Sequence_DATABASE scaffold
aaabAlhosni May 24, 2026
27501c4
Implement persist and retrieve
aaabAlhosni May 24, 2026
b2e1bb7
Implement retrieve by id
aaabAlhosni May 24, 2026
7d89df1
Implement update method
aaabAlhosni May 24, 2026
8b77ff3
Implement remove method
aaabAlhosni May 24, 2026
485b0bb
Add JPA layer comments to Service
aaabAlhosni May 24, 2026
86de428
Update version backlog
aaabAlhosni May 24, 2026
f6b9f3b
Update README docs
aaabAlhosni May 24, 2026
0c1745a
Randomise placeholder credentials in application.yaml
aaabAlhosni May 24, 2026
aefeaef
Enable JPA auto-configuration
aaabAlhosni May 24, 2026
ddde1b6
Set ddl-auto to update and enable SQL logging
aaabAlhosni May 24, 2026
f15a47b
Simplify Sequence_DATABASE error handling
aaabAlhosni May 24, 2026
0518827
Wire Oracle DB persistence into Service
aaabAlhosni May 24, 2026
069107a
Update version backlog for 0.5
aaabAlhosni May 24, 2026
8158f68
Update datasource placeholders to match example values
aaabAlhosni May 24, 2026
cede6b6
Extract JPA entity to DATABASE, strip Sequence annotations
aaabAlhosni May 24, 2026
7847d4d
Update stack to use DATABASE entity throughout
aaabAlhosni May 24, 2026
f8d9260
Update version backlog for 0.6
aaabAlhosni May 24, 2026
e11348c
Update datasource placeholders to match example values
aaabAlhosni May 25, 2026
0a2612a
Remove Sequence class comment
aaabAlhosni May 25, 2026
ebf3927
Polish comments across all source files
aaabAlhosni May 25, 2026
1163424
Reorganize OOP classes: promote Sequence as the main entity, remove D…
aaabAlhosni May 25, 2026
687a5d8
Update README: reflect Oracle persistence, remove submission instruct…
aaabAlhosni May 25, 2026
08cf0f8
Update README: add JAR run instructions for Windows and Linux
aaabAlhosni May 25, 2026
bab2079
Bump version to 1.0 in pom.xml and version.txt
aaabAlhosni May 25, 2026
7765c85
final product
aaabAlhosni May 25, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
370 changes: 309 additions & 61 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,61 +1,309 @@
## Submission Instructions

To submit your Oracle JAVA Spring Boot Maven project as a solution, please follow these steps:

### Step 1: Install git on your PC
- Install "git" as shown in this tutorial: [How to install git](https://youtu.be/iYkLrXobBbA?si=_l0haibv_X9NpIjJ)
- Open command prompt and run
```bash
git version
```
- If you see the version, then git is successfully installed.

### Step 2: Fork the Repository
- Navigate to [this repository](https://github.com/CodelineAtyab/oraclequantapi) provided by Codeline.
- Click on the "Fork" button at the top-right corner of the page to create a copy of the repository under your own GitHub account.

### Step 3: Clone the Forked Repository
- Open your terminal or command prompt.
- Clone the forked repository to your local machine using the following command:
```bash
git clone https://github.com/your-username/repo-name.git
```

### Step 4: Create a new branch
- Navigate to the cloned repository directory
```bash
cd repo-name
```
- Create a new branch for your code submissions (Replace your-name with your name in your-name-submission-branch):
```bash
git checkout -b your-name-submission-branch
```


### Step 5: Add Your Code
- Implement the API

### Step 6: Commit your changes
- Run the following commands in order to commit your changes:
```bash
git add *
git commit -m "Meaningful commit message here"
```

### Step 7: Push Your Branch to GitHub
- Run the following commands to upload the changes to the forked github repository (Replace your-name with your name in your-name-submission-branch):
```bash
git push origin your-name-submission-branch
```

### Step 8: Create a Pull Request
- Go to your forked repository on GitHub.
- You should see a prompt to create a pull request. Click on "Compare & pull request".
- Provide a title and description for your pull request, then click "Create pull request".

### Step 9: Notify Codeline
- Notify on slack that you have created a PR for your solution.

## Note: If you face any issues in the process above, Please do the following:
- Watch [this youtube tutorial](https://www.youtube.com/watch?v=a_FLqX3vGR4)
- Contact Ikhlas or Atyab.
## Project Overview

Oracle Quant API is a Spring Boot 3.5.14 / Java 17 REST API that decodes submitted sequence strings using a self-delimiting length-encoded parser and persists the results in an Oracle database.

**Tech Stack**
- Java 17
- Spring Boot 3.5.14
- Spring Web (embedded Tomcat)
- Spring Data JPA / Hibernate ORM (OracleDialect)
- Oracle JDBC (ojdbc11)
- Maven

---

## How to Run

**Prerequisites:** Java 17 JDK and an Oracle database configured in `application.yaml` (see Database Setup below).

### Run from source

```bash
# Windows
mvnw.cmd spring-boot:run

# macOS / Linux
./mvnw spring-boot:run
```

### Run the JAR (v1.0)

A pre-built executable JAR is available.

```bash
# Windows
java -jar oraclequantapi-1.0.jar

# macOS / Linux
java -jar oraclequantapi-1.0.jar
```

To override the datasource without modifying the bundled config, place an `application.yaml` in the same directory as the JAR — Spring Boot will pick it up automatically:

```yaml
spring:
datasource:
url: jdbc:oracle:thin:@//your-host:1521/your-service
username: YOUR_USERNAME
password: YOUR_PASSWORD
```

The server starts on `http://localhost:8080`.

---

## Architecture

Clean 3-layer architecture with strict Single Responsibility Principle (SRP):

```
HTTP Request
|
v
[ Controller ] -- HTTP mappings only, zero business logic
|
v
[ Service ] -- Input validation and decoder algorithm
|
v
[Sequence_DATABASE] -- Exception-safe Oracle persistence wrapper
|
v
[ Repository ] -- Spring Data JPA interface
|
v
[ Oracle DB ] -- SEQUENCE_ENQUIRIES table
```

**Package structure:**
```
com.oraclequantapi.oraclequantapi
+-- OraclequantapiApplication.java (entry point)
+-- controller/
| +-- Controller.java (REST layer - @RestController)
+-- services/
| +-- Service.java (business logic - @Service)
+-- module/
| +-- Sequence.java (JPA entity mapped to SEQUENCE_ENQUIRIES)
+-- repository/
+-- Repository.java (Spring Data JPA interface)
+-- Sequence_DATABASE.java (exception-safe Oracle persistence wrapper)
```

- The Controller delegates all logic to the Service via `@Autowired` injection.
- The Service validates input, runs the length-encoded parser, and delegates all persistence to `Sequence_DATABASE`.
- `Sequence.java` is the JPA `@Entity` mapped to the `SEQUENCE_ENQUIRIES` Oracle table. It owns all column mappings and JSON serialization rules.
- `id` and `currentTime` are always server-generated — never client-supplied.
- `input` is write-only — accepted in the request body but never returned in any response.
- Data persists across restarts via Oracle; the table is auto-created on first startup (`ddl-auto: update`).

---

## Database Diagram

```
+-----------------------------+
| SEQUENCE_ENQUIRIES | Oracle Table
+-----------------------------+
| PK ID VARCHAR2 | UUID, server-generated
| INPUT VARCHAR2 | Raw input (write-only in API)
| CURRENT_TIME VARCHAR2 | Timestamp of save or last update
+-----------------------------+
|
| managed by
v
+-----------------------------+
| Repository.java | Spring Data JPA interface
| JpaRepository< | Auto-provides: save, findAll,
| Sequence, String> | existsById, deleteById
+-----------------------------+
|
| wrapped by
v
+-----------------------------+
| Sequence_DATABASE.java | Exception-safe persistence layer
| persist() | -> repository.save()
| retrieveAll() | -> repository.findAll()
| update() | -> existsById() + save()
| remove() | -> existsById() + deleteById()
+-----------------------------+
|
| called by
v
+-----------------------------+
| Service.java | Business logic layer
| addSequence() | -> persist()
| getAllSequences() | -> retrieveAll()
| updateSequence() | -> update()
| deleteSequence() | -> remove()
+-----------------------------+
```

---

## Database Setup

1. **Configure credentials** in `src/main/resources/application.yaml`:
```yaml
spring:
datasource:
url: jdbc:oracle:thin:@//your-host:1521/your-service
username: YOUR_USERNAME
password: YOUR_PASSWORD
```

2. **Start the application** — `ddl-auto: update` will auto-create the `SEQUENCE_ENQUIRIES` table on first startup. No manual SQL required.

---

## Decoder Algorithm

The `sequenceLogicAlgorithm` method processes the input string using a self-delimiting length-encoded parser:

- Character values: `a=1, b=2, ... z=26, _=0`
- **Header phase:** consecutive `z` characters each add 26 to the block length; the first non-`z` character adds its own value. This determines how many characters to consume next.
- **Data phase:** consume exactly that many characters and sum their values; the sum is appended to the output array.
- Parsing repeats left-to-right until the full string is consumed.

**Examples:**

| Input | Decode steps | Output |
|---|---|---|
| `abbcc` | `a`=len 1 → `b`=2; `b`=len 2 → `c`+`c`=6 | `[2, 6]` |
| `cdaaabaa` | `c`=len 3 → `d`+`a`+`a`=6; `a`=len 1 → `b`=2; `a`=len 1 → `a`=1 | `[6, 2, 1]` |
| `zabc...` | `z`+`a`=len 27 → consume 27 chars | `[sum]` |

---

## API Reference

### POST `/sequenceDecoder`

Submit a sequence string for decoding. The `input` field must contain **only lowercase letters a-z and underscores** and **must not start with `_`** — any violation returns 400. The server decodes the input, auto-generates `id` and `currentTime`, and returns the result.

**Request:**
```http
POST http://localhost:8080/sequenceDecoder
Content-Type: application/json

{
"input": "abbcc"
}
```

**Response — 201 Created:**
```json
{
"id": "a3f9c1d2-84ab-4e11-b3c7-2f4400000001",
"currentTime": "2026-05-24 14:30:00",
"output": [2, 6]
}
```

**Another valid example:**
```http
{ "input": "cdaaabaa" }
```
```json
{
"id": "b7e2d3a1-91cd-4f22-c4d8-3g5500000002",
"currentTime": "2026-05-24 14:31:05",
"output": [6, 2, 1]
}
```

**Invalid input — Response 400 Bad Request:**
```json
{ "input": "Hello123!" }
```
```json
{ "input": "_abc" }
```
```
Input must only contain a-z and underscore, and must not start with underscore
```

---

### PUT `/sequenceDecoder`

Update an existing enquiry by `id`. Applies the same input validation rules as POST. Re-runs the decoder on the new input and refreshes `currentTime`.

**Request:**
```http
PUT http://localhost:8080/sequenceDecoder
Content-Type: application/json

{
"id": "a3f9c1d2-84ab-4e11-b3c7-2f4400000001",
"input": "cdaaabaa"
}
```

**Response — 201:**
```json
{
"id": "a3f9c1d2-84ab-4e11-b3c7-2f4400000001",
"currentTime": "2026-05-24 15:00:00",
"output": [6, 2, 1]
}
```

**Failure — 400 Bad Request:**
- `id` not found, or `input` fails validation:
```
Enquiry not found or input invalid
```

---

### DELETE `/sequenceDecoder`

Remove an existing enquiry by `id`.

**Request:**
```http
DELETE http://localhost:8080/sequenceDecoder
Content-Type: application/json

{
"id": "a3f9c1d2-84ab-4e11-b3c7-2f4400000001"
}
```

**Response — 201:**
```
Enquiry deleted successfully
```

**Failure — 400 Bad Request:**
```
Enquiry not found or already deleted
```

---

### GET `/sequenceDecoder`

Retrieve all stored sequence enquiries with their decoded outputs.

**Request:**
```http
GET http://localhost:8080/sequenceDecoder
```

**Response — 200 OK:**
```json
[
{
"id": "a3f9c1d2-84ab-4e11-b3c7-2f4400000001",
"currentTime": "2026-05-24 14:30:00",
"output": [2, 6]
},
{
"id": "b7e2d3a1-91cd-4f22-c4d8-3g5500000002",
"currentTime": "2026-05-24 14:31:05",
"output": [6, 2, 1]
}
]
```
Binary file added oraclequantapi-1.0.jar
Binary file not shown.
13 changes: 12 additions & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
</parent>
<groupId>com.oraclequantapi</groupId>
<artifactId>oraclequantapi</artifactId>
<version>0.0.1-SNAPSHOT</version>
<version>1.0</version>
<name/>
<description/>
<url/>
Expand All @@ -35,6 +35,17 @@
<artifactId>spring-boot-starter-web</artifactId>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>

<dependency>
<groupId>com.oracle.database.jdbc</groupId>
<artifactId>ojdbc11</artifactId>
<scope>runtime</scope>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
Expand Down
Loading