I'm a self-taught developer from Sri Lanka. No bootcamp, no CS degree β just months of building, breaking things, and figuring it out.
Over the last 5 months I built KICKNOIR β a complete, production-ready full-stack e-commerce boilerplate. Not a tutorial project. Not a mockup. A real app, live in production, battle-tested, with real Stripe payments going through it.
π΄ Live demo: kicknoir.vercel.app
(Test card: 4242 4242 4242 4242 Β· any future date Β· any CVC)
TL;DR: If you just want to skip the 5 months β it's available as a developer boilerplate for $59 β grab it on Gumroad. Keep reading for the full technical breakdown.
The Stack
Backend: Java 22 + Spring Boot 4 + Spring Security + JWT
Frontend: Angular 19 (Standalone Components) + TailwindCSS 4
Database: PostgreSQL 17 on Neon
Payments: Stripe Hosted Checkout + Webhooks
DevOps: Docker Compose + GitHub Actions CI/CD
Deploy: Render (backend) + Vercel (frontend)
What's actually included
This isn't just source code dropped in a ZIP. Every layer is documented and wired up end-to-end:
- JWT Authentication + RBAC β register, login, token refresh, two roles (ADMIN / CUSTOMER), enforced on both Spring Security and Angular route guards
-
Stripe Hosted Checkout β real payments, not mocked. Webhook-driven order confirmation, inventory reduction, and cart clearing on
payment_intent.succeeded - Full Admin Panel β dashboard with live stats, product CRUD via modal, order status pipeline (PENDING β CONFIRMED β SHIPPED β DELIVERED), customer list
- Product Catalog β search by name, filter by brand and price range, pagination, dedicated product detail pages
- Shopping Cart β powered by Angular Signals, reactive, real-time badge updates, no extra state library needed
- Inventory Management β stock tracking per product, automatic reduction on successful payment, low-stock and out-of-stock status
-
Docker Compose β one command spins up PostgreSQL + Spring Boot + Angular together.
seed.sqlloads 10 sample products and a default admin account automatically -
CI/CD pipelines β GitHub Actions workflows for both repos, auto-deploy to Render and Vercel on push to
main
A problem I had to solve properly: Stripe + async payment state
One of the hardest parts was making the order lifecycle bulletproof.
The naive approach β confirming an order the moment the user hits "pay" β breaks when a user closes their browser mid-checkout, or when a network request fails after Stripe processes the payment but before your backend receives the response.
The correct approach is webhooks. Here's the core of how I handled it in Spring Boot:
@PostMapping("/stripe")
public ResponseEntity<String> handleWebhook(
@RequestBody String payload,
@RequestHeader("Stripe-Signature") String sigHeader
) {
Event event = Webhook.constructEvent(payload, sigHeader, webhookSecret);
if ("payment_intent.succeeded".equals(event.getType())) {
PaymentIntent intent = (PaymentIntent) event.getDataObjectDeserializer()
.getObject().orElseThrow();
// Idempotency check β ignore duplicate events
if (paymentRepository.existsByStripePaymentIntentId(intent.getId())) {
return ResponseEntity.ok("Already processed");
}
orderService.confirmOrder(intent.getId());
inventoryService.reduceStock(intent.getId());
cartService.clearCartForOrder(intent.getId());
}
return ResponseEntity.ok("Received");
}
Key decisions here:
- Idempotency check β Stripe can send the same webhook event more than once. Without the duplicate check, you'd reduce inventory twice.
- Event-driven confirmation β the order only confirms when Stripe tells you the payment succeeded, not when the user clicks a button.
-
Webhook signature validation β
Webhook.constructEvent()verifies the request is genuinely from Stripe, not a spoofed POST.
The frontend state problem: Angular Signals for the cart
The cart was another area where I made a deliberate architectural decision. Most tutorials reach for NgRx or a BehaviorSubject for reactive cart state. I used Angular Signals instead β built into Angular 19, zero extra dependencies.
// cart.service.ts
export class CartService {
private cartItems = signal<CartItem[]>([]);
readonly itemCount = computed(() =>
this.cartItems().reduce((sum, item) => sum + item.quantity, 0)
);
addToCart(item: CartItem) {
this.cartItems.update(items => {
const existing = items.find(i => i.productId === item.productId);
if (existing) {
return items.map(i =>
i.productId === item.productId
? { ...i, quantity: i.quantity + 1 }
: i
);
}
return [...items, item];
});
}
}
The navbar badge reads itemCount directly β it updates instantly, no subscription management, no memory leaks to worry about.
Docker: full stack in one command
One of the things I'm most happy with is the Docker setup. A lot of projects ship a docker-compose.yml that's half-working or requires you to manually set up the database. This one works out of the box:
git clone https://github.com/BuddheemaRyan/KICKNOIR_Backend
git clone https://github.com/BuddheemaRyan/KICKNOIR-frontend
cd KICKNOIR_Backend
# Add your env vars to docker-compose.yml (see DOCKER.md)
docker-compose up --build
That's it. PostgreSQL starts, seed data loads automatically, Spring Boot connects, Angular builds and serves via Nginx. Visit http://localhost:4200.
The Dockerfiles use multi-stage builds β Alpine-based JRE for the backend, Nginx for the Angular frontend β so image sizes stay minimal.
Who is this for?
Does any of these sound like you?
- You want to launch an online store without spending months building auth, payments, admin, and DevOps from scratch
- You're a freelancer who wants a solid, battle-tested client project starter
- You're learning Spring Boot + Angular and want to study a real production codebase, not another tutorial
- You want to rebrand and resell β the brand name lives in environment config, not hardcoded everywhere
If that's you, this is built exactly for you β $59 on Gumroad
What you get for $59
- Full source code β frontend and backend repos
- All Docker, CI/CD, and deployment configs
-
application-example.ymlβ clean environment variable reference -
DOCKER.mdβ step-by-step local setup guide - Full API endpoint documentation
- Database schema (auto-managed by Hibernate β no manual migrations)
- Direct email support β if you hit a wall getting it running, I'll help you through it personally
The codebase is modular. Adding a new product category, a new payment currency, or a new admin module doesn't require fighting the architecture β it's built to be extended.
Get it
Five months of architecture decisions, debugging, and production fixes β packaged so you can skip straight to building your actual product.
Test the full checkout flow first at kicknoir.vercel.app before you buy. Questions? Drop them in the comments β happy to answer anything technical.












