Capstone · Rust Programming
Capstone: a GST invoice tool with a CLI and a web API
The brief
Build gst_invoice, a portfolio-ready Rust tool for small businesses. It reads an invoice saved as JSON, checks the GSTINs and GST rates, works out the taxable value, CGST and SGST (same state) or IGST (another state) to the paisa, and prints a summary as text or JSON. The same library powers a small axum web API. It is covered by unit, integration and doc tests, clean under clippy and rustfmt, and shipped as a release build with a README.
Why it matters
GST invoicing is software that millions of Indian businesses need, from a Pune hardware shop to a Bengaluru distributor, and the rules (state codes, CGST/SGST versus IGST, exact rounding) leave no room for sloppy code. A well-tested Rust crate with a CLI and an HTTP API is exactly the kind of project that shows an employer you can design, test and ship real software, and you can talk through every line of it in an interview.
Skills you practise
- Cargo dependencies with cargo add and features
- serde Deserialize and Serialize, serde_json
- clap derive arguments
- thiserror error enums and ExitCode
- enums and match for business rules
- integer money and Indian digit grouping
- unit, integration and doc tests
- cargo clippy -D warnings and cargo fmt
- axum 0.8 handlers with Json and status codes
- release builds and a README
You need
- Rust stable installed with rustup, with clippy and rustfmt (rustup component add clippy rustfmt)
- An internet connection for cargo to download crates from crates.io
- curl (built into Windows 10 and 11 as curl.exe; in Windows PowerShell type curl.exe, because curl there means Invoke-WebRequest)
- Optional: a GitHub account to publish the finished project
What you will have at the end
The gst_invoice repository: a library with GST rules and thiserror errors, a clap CLI with text and --json output, an axum server, six unit tests, three integration tests, three doc tests, clean clippy and rustfmt runs, a release build and a README with a sample run.
How it is marked (rubric, 100 points)
| Correct GST resultsCGST/SGST and IGST, rounding, Indian grouping and totals are right to the paisa for both sample invoices. | 30 |
|---|---|
| Error handling and designOne thiserror enum, no unwrap on user input, exit code 1 for the CLI and 422 for the API, logic in lib.rs shared by both binaries. | 20 |
| Tests and toolingUnit, integration and doc tests that check edges and mistakes; cargo fmt --check and clippy -D warnings clean. | 25 |
| Web APIGET /health and POST /invoices/summary work with curl and return the same numbers as the CLI. | 10 |
| Portfolio finishA release build and a README a stranger can follow, with the project on GitHub. | 15 |
0/12 steps done
Step 1 of 12
Create the crate and add its dependencies
cargo tree shows clap 4, serde 1, serde_json 1 and thiserror 2 as direct dependencies.
Run cargo new gst_invoice and add the four crates with cargo add (see the comments in the starter Cargo.toml). serde needs its derive feature for #[derive(Deserialize, Serialize)], and clap needs derive for #[derive(Parser)]. cargo add writes the versions into Cargo.toml for you; Cargo.lock then pins the exact versions so every build is the same. Save invoice.json from the starter files into the project folder (next to Cargo.toml), then list the direct dependencies. Do not create src/bin/server.rs yet: it needs crates you add in step 10, and cargo builds every binary when it runs integration tests.
$ cargo tree --depth 1Also check yourself
Your notes: Cargo.toml, invoice.json, src/lib.rs, src/main.rs, tests/invoice.rs, src/bin/server.rs, README.md
Write down each command you ran. It goes into your project summary.