{"id":21307542,"url":"https://github.com/jdegand/origin-angular-frontend","last_synced_at":"2026-04-27T18:03:10.654Z","repository":{"id":168789069,"uuid":"644586526","full_name":"jdegand/origin-angular-frontend","owner":"jdegand","description":"Frontend for my origin-backend-take-home-assignment repo","archived":false,"fork":false,"pushed_at":"2023-06-11T17:09:18.000Z","size":196,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-06-25T23:36:20.791Z","etag":null,"topics":["angular","angular-material"],"latest_commit_sha":null,"homepage":"","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jdegand.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-05-23T20:44:22.000Z","updated_at":"2023-05-23T20:53:31.000Z","dependencies_parsed_at":null,"dependency_job_id":"0cafeb69-a14d-43ec-afea-473675461c7a","html_url":"https://github.com/jdegand/origin-angular-frontend","commit_stats":null,"previous_names":["jdegand/origin-angular-frontend"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/jdegand/origin-angular-frontend","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Forigin-angular-frontend","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Forigin-angular-frontend/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Forigin-angular-frontend/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Forigin-angular-frontend/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jdegand","download_url":"https://codeload.github.com/jdegand/origin-angular-frontend/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Forigin-angular-frontend/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":32348058,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-27T17:12:42.749Z","status":"ssl_error","status_checked_at":"2026-04-27T17:12:41.658Z","response_time":128,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["angular","angular-material"],"created_at":"2024-11-21T16:32:32.877Z","updated_at":"2026-04-27T18:03:10.639Z","avatar_url":"https://github.com/jdegand.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Origin Angular Frontend\n\nThis expands upon this [challenge](https://github.com/OriginFinancial/origin-backend-take-home-assignment) and [my own solution](https://github.com/jdegand/origin-backend-take-home-assignment).\n\n## Screenshots\n\n![](screenshots/origin-angular-frontend-1.png)\n\n***\n\n![](screenshots/origin-angular-frontend-1-error.png)\n\n***\n\n![](screenshots/origin-angular-frontend-2.png)\n\n***\n\n![](screenshots/origin-angular-frontend-3.png)\n\n***\n\n![](screenshots/origin-angular-frontend-4.png)\n\n***\n\n![](screenshots/origin-angular-frontend-5.png)\n\n***\n\n![](screenshots/origin-angular-frontend-results.png)\n\n***\n\n## Tasks\n\nOrigin offers its users an insurance package personalized to their specific needs without requiring the user to understand anything about insurance. This allows Origin to act as their *de facto* insurance advisor.\n\nOrigin determines the user’s insurance needs by asking personal \u0026 risk-related questions and gathering information about the user’s vehicle and house. Using this data, Origin determines their risk profile for **each** line of insurance and then suggests an insurance plan (`\"economic\"`, `\"regular\"`, `\"responsible\"`) corresponding to her risk profile.\n\nFor this assignment, you will create a simple version of that application by coding a simple API endpoint that receives a JSON payload with the user information and returns her risk profile (JSON again) – you don’t have to worry about the frontend of the application.\n\n## The input\nFirst, the would-be frontend of this application asks the user for her **personal information**. Then, it lets her add her **house** and **vehicle**. Finally, it asks her to answer 3 binary **risk questions**. The result produces a JSON payload, posted to the application’s API endpoint, like this example:\n\n```JSON\n{\n  \"age\": 35,\n  \"dependents\": 2,\n  \"house\": {\"ownership_status\": \"owned\"},\n  \"income\": 0,\n  \"marital_status\": \"married\",\n  \"risk_questions\": [0, 1, 0],\n  \"vehicle\": {\"year\": 2018}\n}\n```\n\n### User attributes\nAll user attributes are required:\n\n- Age (an integer equal or greater than 0).\n- The number of dependents (an integer equal or greater than 0).\n- Income (an integer equal or greater than 0).\n- Marital status (`\"single\"` or `\"married\"`).\n- Risk answers (an array with 3 booleans).\n\n### House\nUsers can have 0 or 1 house. When they do, it has just one attribute: `ownership_status`, which can be `\"owned\"` or `\"mortgaged\"`.\n\n### Vehicle\nUsers can have 0 or 1 vehicle. When they do, it has just one attribute: a positive integer corresponding to the `year` it was manufactured.\n\n## The risk algorithm\nThe application receives the JSON payload through the API endpoint and transforms it into a *risk profile* by calculating a *risk score* for each line of insurance (life, disability, home \u0026 auto) based on the information provided by the user.\n\nFirst, it calculates the *base score* by summing the answers from the risk questions, resulting in a number ranging from 0 to 3. Then, it applies the following rules to determine a *risk score* for each line of insurance.\n\n1. If the user doesn’t have income, vehicles or houses, she is ineligible for disability, auto, and home insurance, respectively.\n2. If the user is over 60 years old, she is ineligible for disability and life insurance.\n3. If the user is under 30 years old, deduct 2 risk points from all lines of insurance. If she is between 30 and 40 years old, deduct 1.\n4. If her income is above $200k, deduct 1 risk point from all lines of insurance. \n5. If the user's house is mortgaged, add 1 risk point to her home score and add 1 risk point to her disability score. \n6. If the user has dependents, add 1 risk point to both the disability and life scores. \n7. If the user is married, add 1 risk point to the life score and remove 1 risk point from disability. \n8. If the user's vehicle was produced in the last 5 years, add 1 risk point to auto score.\n\nThis algorithm results in a final score for each line of insurance, which should be processed using the following ranges:\n\n- **0 and below** maps to **“economic”**.\n- **1 and 2** maps to **“regular”**.\n- **3 and above** maps to **“responsible”**.\n\n\n## The output\nConsidering the data provided above, the application should return the following JSON payload:\n\n```JSON\n{\n    \"auto\": \"regular\",\n    \"disability\": \"ineligible\",\n    \"home\": \"economic\",\n    \"life\": \"regular\"\n}\n```\n\n## Criteria\nYou can choose any technology stack to implement this assignment. Using our stack is not a requirement in the selection process - we will consider exclusively that you build a solid system with an emphasis on code quality, simplicity, readability, maintainability, and reliability, particularly regarding architecture and testing to evaluate your work.\n\nBe aware that Origin will mainly take into consideration the following evaluation criteria:\n* How clean and organized your code is;\n* If you implemented the business rules correctly;\n* How good your automated tests are (qualitative over quantitative).\n\nOther important notes:\n* Develop a extensible score calculation engine\n* Add to the README file: (1) instructions to run the code; (2) what were the main technical decisions you made; (3) relevant comments about your project \n* You must use English in your code and also in your docs\n\nThis assignment should be doable in less than one day. We expect you to learn fast, **communicate with us**, and make decisions regarding its implementation \u0026 scope to achieve the expected results on time.\n\nIt is not necessary to build the screens a user would interact with, however, as the API is intended to power a user-facing application, we expect the implementation to be as close as possible to what would be necessary in real-life. Consider another developer would get your project/repository to evolve and implement new features from exactly where you stopped. \n\n## Built With\n\n- [Angular](https://angular.io/docs)\n- [Angular CLI](https://github.com/angular/angular-cli) version 15.2.5.\n- [Angular Material](https://material.angular.io/)\n\n## How to Use\n\nThe Express application runs by default on `http://localhost:4000` and has the following endpoints:\n\n - `http://localhost:4000/api/score` - post endpoint that expects the form object - complete the form and the object's shape is shown on the last step.\n\n### Running the Express Backend Application\n\nYou can clone my the whole [repo](https://github.com/jdegand/origin-backend-take-home-assignment) and checkout to the angular branch or just clone the angular branch.  \n\n```bash \n\ngit clone https://github.com/jdegand/origin-backend-take-home-assignment.git -b angular --single-branch\n\n# cd into the directory\nnpm install\n\nnpm start\n```\n\n### Running the Angular Application\n\nRun the express application first.  Use two terminals.  \n\n```bash\n\ngit clone https://github.com/jdegand/origin-angular-frontend.git\n\n# cd into the directory\nnpm install \n\nnpm start\n```\n\n## Thoughts\n\n- Reworked my express backend interfaces and risk calculation function to match the personalInfo object.\n- Some properties are now nested so minor tweaks were necessary i.e. personal.income vs income \n- Depending how you want to group categories, you will have to make the necessary adjustments on the backend.\n- CORS and its typescript types were added as well.   \n- I added router in a limited way.  I only used routes for the home page and results page.\n- Instead of showing the api's response in another route, I could have used an ngIf to make the form disappear and show the results in the same component.  \n- Passing the api response data to another route gives you a lot of implementation choices. I initially tried setting the data to a variable in the form component and using an Input decorator to get the variable in the response component.  I also thought about subscribing directly in the service and setting a variable in the service and using a function to get the variable's value in the response component. Ulitmately, I used a state object to pass the data to the route during navigation.  Best practices here is tough to determine and as all approaches seem to be equally viable.  But using Input may be less performant.  Subjects also could be considered.  \n- I used Angular Material to make the multi-step form.  \n- The grouping of the various categories could be different i.e. dependents could go with house or personal.  The risk questions could easily be changed.  I thought about adding various extras like name, address, etc but ultimately, the form has to match the backend so I left it as is.  Extra field could be added and not be factored in to the risk calculation.\n- Not a fan of most of the preset Angular Material themes - most of the color combinations are terrible.  \n- Desktop version is just the mobile version stretched.\n- Chrome shows error of \"Incorrect use of label for=\"FORM_ELEMENT\" -\u003e problem comes from implementation of mat-select\n- Error reappears on any step with a mat-select \n- Label appears to be linked to the select so error may be a false positive - syntax is not obviously incorrect\n- The select is inside a mat-form-field so the mat-label should be directly linked to the select and you can't use a matInput attribute on a mat-select.    \n- Putting a formControlName on a mat-select is problematic ?\n- mat-select does have more problems than other angular material components - changing back to a select tag would require styling adjustments\n\n## Continued Development\n\n- Styling tweaks for desktop\n- Confirm step rework versus just rendering a json object\n- Angular 16 update ?\n- Testing\n- Problem with form component html -\u003e warnings about incorrect use of form label \n\n## Useful Resources\n\n- [YouTube](https://www.youtube.com/watch?v=KwQ-N2p0VGc) - Multi Forms in angular with validation | Angular Reactive forms example | Material UI Stepper\n- [Stack Overflow](https://stackoverflow.com/questions/46705101/mat-form-field-must-contain-a-matformfieldcontrol) - mat form field must containa mat form field control\n- [YouTube](https://www.youtube.com/watch?v=nEuO2iBPceE) - Angular Material Radio button groups and lists - explained with live easy examples\n- [Angular Wiki](https://www.angularjswiki.com/httpclient/post/) - httpClient POST\n- [Stack Overflow](https://stackoverflow.com/questions/72867495/pass-api-response-from-one-component-to-another-component-in-angular) - pass api response from one component to another component\n- [Tek Tutorials Hub](https://www.tektutorialshub.com/angular/angular-pass-data-to-route/#passing-dynamic-data-to-a-route) - passing dynamic data to a route\n- [Stack Overflow](https://stackoverflow.com/questions/59670358/angular-8-not-getting-the-state-value-in-required-format-using-routerlink-and-s) - getting the state value\n- [Stack Overflow](https://stackoverflow.com/questions/36835123/how-do-i-pass-data-to-angular-routed-components) - pass data to angular routed components\n- [In Depth Dev](https://indepth.dev/tutorials/angular/indepth-guide-to-passing-data-via-routing) - indepth guide to passing data via routing\n- [Medium](https://medium.com/javascript-everyday/keep-data-in-the-state-object-during-navigation-in-angular-5657af156fb8) - keep data in the state object during navigation\n- [Stack Overflow](https://stackoverflow.com/questions/52663044/angular-only-allow-routing-if-routed-using-router-navigate-method) - only allow routing with router navigate\n- [Stack Overflow](https://stackoverflow.com/questions/263965/how-can-i-convert-a-string-to-boolean-in-javascript) - convert string to boolean\n- [Stack Overflow](https://stackoverflow.com/questions/56882657/mat-select-value-doesnt-work-with-formcontrolname) - mat select value doesn't work with formControlName","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjdegand%2Forigin-angular-frontend","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjdegand%2Forigin-angular-frontend","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjdegand%2Forigin-angular-frontend/lists"}