{"id":21307818,"url":"https://github.com/jdegand/chat-group-backend","last_synced_at":"2026-05-13T07:41:07.912Z","repository":{"id":110668558,"uuid":"531668221","full_name":"jdegand/chat-group-backend","owner":"jdegand","description":"Devchallenges -  Legacy - Full-Stack Developer - Chat Group","archived":false,"fork":false,"pushed_at":"2024-10-05T20:27:41.000Z","size":67,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-01-22T09:13:38.552Z","etag":null,"topics":["devchallenges","devchallenges-legacy","express","mongoose","multer"],"latest_commit_sha":null,"homepage":"","language":"JavaScript","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":"2022-09-01T20:00:00.000Z","updated_at":"2024-10-05T20:27:45.000Z","dependencies_parsed_at":null,"dependency_job_id":"5619485a-9784-452a-8c91-a134fdd6344e","html_url":"https://github.com/jdegand/chat-group-backend","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Fchat-group-backend","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Fchat-group-backend/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Fchat-group-backend/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jdegand%2Fchat-group-backend/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jdegand","download_url":"https://codeload.github.com/jdegand/chat-group-backend/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":243785089,"owners_count":20347409,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","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":["devchallenges","devchallenges-legacy","express","mongoose","multer"],"created_at":"2024-11-21T16:34:29.481Z","updated_at":"2026-05-13T07:41:02.875Z","avatar_url":"https://github.com/jdegand.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003ch1 align=\"center\"\u003eChat Group Backend\u003c/h1\u003e\n\n\u003cdiv align=\"center\"\u003e\n   Solution for a challenge from  \u003ca href=\"https://web.archive.org/web/20231130042247/https://legacy.devchallenges.io/challenges/UgCqszKR7Q7oqb4kRfI0\" target=\"_blank\"\u003eDevchallenges.io\u003c/a\u003e.\n\u003c/div\u003e\n\n## Table of Contents\n\n- [Overview](#overview)\n  - [Built With](#built-with)\n- [Features](#features)\n- [Thoughts](#thoughts)\n- [Continued Development](#continued-development)\n- [How to use](#how-to-use)\n- [Useful Resources](#useful-resources)\n\n## Overview\n\n### Built With\n\n- express generator\n- bcrypt\n- cookie-parser\n- cors\n- express\n- jsonwebtoken\n- mongoose\n- multer\n\n## Features\n\nThis application/site was created as a submission to a [DevChallenges](https://devchallenges.io/challenges) challenge. The [challenge](https://web.archive.org/web/20231130042247/https://legacy.devchallenges.io/challenges/UgCqszKR7Q7oqb4kRfI0) was to build an application to complete the given user stories. **Note**: The previous design document may be incomplete, as you need to find an archived version of the challenge as all `legacy` challenges have had their documentation removed from DevChallenges.\n\n## Thoughts\n\n- I left many routes open - could add `JWTVerifys` to all routes vs. just the mutate routes (post, put, delete).\n- Messages and Channels are open. You can see the chat before signing in.\n- Need another server, `socket.io`, to have chat group be realtime across users - don't think so - because useEffect will update the view when channels and messages change\n- `Promise.all()` might be needed for multiple route calls in some functions - async - have to worry about order of results.\n- Design choice: seeding the database vs. using my hacky way of creating a welcome channel if it doesn't exist.\n- \"select: false\" in model vs removing field with `.select('-password')` vs removing field in `populate` call - what is best approach?\n- Password field may be sent back in some calls - intermediate step - password forwarded along with userInfo then removed later - should exlude first and then forward or overly concerned - password is hashed and protected by jwt\n- You can't pass two parameters to the same route because Express can't differentiate between them. You need to add an extra word in between i.e. `/:channel/:id` vs. `/:channel/id/:id`.\n- `Channel` controller has a very convoluted route because of that and it could be cleaned up.\n- Design choice: sorting with Mongoose vs. sorting `response.data` in the client. In React, use `memo` on the data.\n- Multer and controllers don't mix.\n- Getting file path is difficult - fakepath issues - can't get the file to save - the folder will be created - dir name in Multer middleware.\n- I had issues with the Multer callback syntax. `console.logs` need to be inside functions inside the callbacks.\n- Added `fs.unlink` logic to remove photos that are no longer tied to user profiles.\n- Profile pictures are sourced from [freepik](https://freepik.com).  Check for links below - the majority of pictures belong to the same series.\n- Added `public/uploads` to `.gitignore`.\n\n## Continued Development\n\n- Adding `helmet` will give better security for the server.\n- Testing\n- Multer (2.0) may require significant changes.\n- To upgrade application to Express 5, some other changes may be needed.  I removed `maxAge` from the cookie used and move may need to be done.\n\n## How To Use\n\nTo clone and run this application, you'll need [Git](https://git-scm.com) and [Node.js](https://nodejs.org/en/download/) (which comes with [npm](http://npmjs.com)) installed on your computer. From your command line:\n\n```bash\n# Clone this repository\n$ git clone https://github.com/jdegand/chat-group-backend.git\n\n# Install dependencies\n$ npm install\n\n# Add env variables (PORT, MONGO_URI, REFRESH_TOKEN_SECRET, ACCESS_TOKEN_SECRET) and connect to mongo\n\n# Run the app\n$ npm start\n```\n\n## Useful Resources\n\n- [Steps to replicate a design with only HTML and CSS](https://devchallenges-blogs.web.app/how-to-replicate-design/)\n- [Mafia vector created by pikisuperstar - www.freepik.com](https://www.freepik.com/vectors/mafia)\n- [Cute cat vector created by catalyststuff - www.freepik.com](https://www.freepik.com/vectors/cute-cat)\n- [3d avatar psd created by freepik - www.freepik.com](https://www.freepik.com/psd/3d-avatar)\n- [Github](https://github.com/piyush-eon/notezipper) - Notezipper\n- [Stack Overflow](https://stackoverflow.com/questions/60323551/how-to-exclude-password-field-in-the-response-in-mongodb) - exclude password field in response\n- [Stack Overflow](https://stackoverflow.com/questions/40370363/express-routes-with-same-path-but-different-parameters) - express routes with same path but different parameters\n- [Stack Overflow](https://stackoverflow.com/questions/12096262/how-to-protect-the-password-field-in-mongoose-mongodb-so-it-wont-return-in-a-qu) - populate and exclude fields\n- [Stack Overflow](https://stackoverflow.com/questions/44860181/mongoose-findbyidandupdate-not-adding-item-in-array) - findByIdAndUpdate and arrays\n- [Stack Overflow](https://stackoverflow.com/questions/36193289/moongoose-aggregate-match-does-not-match-ids) - mongoose matching ids\n- [Stack Overflow](https://stackoverflow.com/questions/11637353/comparing-mongoose-id-and-strings) - compare mongoose ids\n- [Stack Overflow](https://stackoverflow.com/questions/70899119/filter-an-array-to-return-matching-ids-of-a-nested-array-in-javascript) - filter nested array\n- [Stack Overflow](https://stackoverflow.com/questions/21069813/mongoose-multiple-query-populate-in-a-single-call) - mutiple query populates in single call\n- [Stack Overflow](https://stackoverflow.com/questions/67264632/mongoose-sorting-by-createdat) - mongoose sorting by createdAt\n- [Express Docs](http://expressjs.com/en/resources/middleware/multer.html) - multer middleware\n- [Stack Overflow](https://stackoverflow.com/questions/27213418/node-js-and-multer-handle-the-destination-of-the-uploaded-file-in-callback-fun) - destination of uploaded file multer\n- [Stack Overflow](https://stackoverflow.com/questions/58474765/how-to-call-multer-middleware-inside-a-controller-in-nodejs) - multer and controllers\n- [Stack Overflow](https://stackoverflow.com/questions/52206055/nodejs-multer-diskstorage-not-working-why-destination-targeting-temp-folder-an) - destination troubleshooting multer\n- [Stack Overflow](https://stackoverflow.com/questions/69347579/multer-didnt-work-for-me-not-storing-image-in-local-folder-or-database) - storing image in local folder\n- [Positronx](https://www.positronx.io/react-file-upload-tutorial-with-node-express-and-multer/) - file upload tutorial with express \u0026 multer\n- [Stack Overflow](https://stackoverflow.com/questions/33976006/multer-wont-recognize-files-with-put) - multer \u0026 put\n- [Stack Overflow](https://stackoverflow.com/questions/4851595/how-to-resolve-the-c-fakepath) - fakepath in image file name\n- [Stack Overflow](https://stackoverflow.com/questions/29317045/why-i-cant-directly-set-console-log-as-callback-function) - console.log and callback functions\n- [Stack Overflow](https://stackoverflow.com/questions/34697502/how-to-limit-the-file-size-when-uploading-with-multer) - limit file size \n- [CodingShisha](https://codingshiksha.com/javascript/node-js-multer-file-upload-type-validation-filters-and-limit-file-size-and-error-handling-using-express-full-tutorial-for-beginners-with-examples/) - multer validation\n- [Blog](https://sebhastian.com/node-check-if-file-exists/#:~:text=In%20NodeJS%2C%20You%20can%20check,%3D%20require(%22fs%22)%3B) - node check if file exists\n- [Geeks for Geeks](https://www.geeksforgeeks.org/node-js-fs-readdir-method/) - node fs readdir method\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjdegand%2Fchat-group-backend","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjdegand%2Fchat-group-backend","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjdegand%2Fchat-group-backend/lists"}