# Mobicoop V3 - Ad Ad service for Mobicoop V3. ## Requirements You need [Docker](https://docs.docker.com/engine/) and its [compose](https://docs.docker.com/compose/) plugin. You also need NodeJS installed locally : we **strongly** advise to install [Node Version Manager](https://github.com/nvm-sh/nvm) and use the latest LTS version of Node (check that your local version matches with the one used in the Dockerfile). The API will run inside a docker container, **but** the install itself is made outside the container, because during development we need tools that need to be available locally (eg. ESLint or Prettier with fix-on-save). A RabbitMQ instance is also required to send / receive messages when data has been inserted/updated/deleted. ## Installation - copy `.env.dist` to `.env` : ```bash cp .env.dist .env ``` Modify it if needed. - install the dependencies : ```bash npm install ``` - start the containers : ```bash docker compose up -d ``` The app runs automatically on port **5006**. ## Database migration Before using the app, you need to launch the database migration (it will be launched inside the container) : ```bash npm run migrate ``` ## Usage The app exposes the following [gRPC](https://grpc.io/) services : - **FindById** : find an ad by its id ```json { "id": "80126a61-d128-4f96-afdb-92e33c75a3e1" } ``` - **FindAllByIds** : find all ads for the given ids ```json { "ids": [ "80126a61-d128-4f96-afdb-92e33c75a3e1", "80126a61-d128-4f96-afdb-92e33c75a3e2", "80126a61-d128-4f96-afdb-92e33c75a3e3" ] } ``` - **FindAllByUserId** : find all ads for the given user id ```json { "id": "80c9bb02-0931-4a1d-bea6-22d358992245" } ``` - **Create** : create an ad Punctual driver ad : ```json { "userId": "80c9bb02-0931-4a1d-bea6-22d358992245", "driver": true, "passenger": false, "seatsProposed": 3, "frequency": "PUNCTUAL", "fromDate": "2023-01-15", "toDate": "2023-01-15", "schedule": [ { "day": 0, "time": "09:00", "margin": 900 } ], "waypoints": [ { "position": 0, "lon": 48.689445, "lat": 6.17651, "houseNumber": "5", "street": "Avenue Foch", "locality": "Nancy", "postalCode": "54000", "country": "France" }, { "position": 1, "lon": 48.8566, "lat": 2.3522, "locality": "Paris", "postalCode": "75000", "country": "France" } ], "comment": "I'm flexible with the departure time" } ``` Punctual driver and passenger ad : ```json { "userId": "80c9bb02-0931-4a1d-bea6-22d358992245", "driver": true, "passenger": true, "seatsProposed": 3, "seatsRequested": 1, "frequency": "PUNCTUAL", "fromDate": "2023-01-15", "toDate": "2023-01-15", "schedule": [ { "day": 0, "time": "09:00", "margin": 900 } ], "waypoints": [ { "position": 0, "lon": 48.689445, "lat": 6.17651, "houseNumber": "5", "street": "Avenue Foch", "locality": "Nancy", "postalCode": "54000", "country": "France" }, { "position": 1, "lon": 48.8566, "lat": 2.3522, "locality": "Paris", "postalCode": "75000", "country": "France" } ], "comment": "I'm flexible with the departure time" } ``` Recurrent passenger ad : ```json { "userId": "80c9bb02-0931-4a1d-bea6-22d358992245", "passenger": true, "seatsRequested": 1, "frequency": "RECURRRENT", "fromDate": "2023-01-15", "toDate": "2023-12-31", "schedule": [ { "day": 1, "time": "07:00", "margin": 600 }, { "day": 2, "time": "07:05", "margin": 600 }, { "day": 5, "time": "07:10", "margin": 600 } ], "waypoints": [ { "position": 0, "lon": 48.689445, "lat": 6.17651, "houseNumber": "5", "street": "Avenue Foch", "locality": "Nancy", "postalCode": "54000", "country": "France" }, { "position": 1, "lon": 48.8566, "lat": 2.3522, "locality": "Paris", "postalCode": "75000", "country": "France" } ], "comment": "I'm flexible with the departure time" } ``` The list of possible options when creating an ad : - userId: the user id (as a uuid) - driver (boolean): if the ad is a driver ad. Note that at least a role must be set to true (driver and/or passenger). - passenger (boolean): if the ad is a passenger ad. Note that at least a role must be set to true (driver and/or passenger). - frequency: `PUNCTUAL` or `RECURRENT` - fromDate: start date for recurrent ad, carpool date for punctual ad - toDate: end date for recurrent ad, same as fromDate for punctual ad - schedule: an array of schedule items, a schedule item containing : - the week day as a number, from 0 (sunday) to 6 (saturday) - the departure time (as HH:MM) - the margin around the departure time in seconds - seatsProposed: number of seats proposed as driver (required if `driver` is true) - seatsRequested: number of seats requested as passenger (required if `passenger` is true) - strict (boolean): if set to true, allow matching only with similar frequency ads - waypoints: an array of addresses that represent the waypoints of the journey (only first and last waypoints are used for passenger ads). Note that positions are **required** and **must** be consecutives - comment: optional freetext comment / description about the ad - **Update** : Replace the content of an ad Accepts the same data as the `Create` function + an ad id, and replace the given ad with the given data. - **Delete** : Delete permanently an ad ```json { "id": "80126a61-d128-4f96-afdb-92e33c75a3e1" } ``` ## Messages ### Handled The service listens to these RabbitMQ messages: - **matcher-ad.created** (to update the status of pending ads) - **matcher-ad.creation-failed** (to update the status of pending ads) - **user.deleted** (to delete the associated ads) ### Emitted As mentionned earlier, RabbitMQ messages are sent after these events : - **ad.created** (message: the created ad information) - **ad.updated** (message: the updated ad information) - **ad.deleted** (message: the id of the deleted ad) ## Tests / ESLint / Prettier Tests are run outside the container for ease of use (switching between different environments inside containers using prisma is complicated and error prone). The integration tests use a dedicated database (see _db-test_ section of _docker-compose.yml_). ```bash # run all tests (unit + integration) npm run test # unit tests only npm run test:unit # integration tests only npm run test:integration # coverage npm run test:cov # ESLint npm run lint # Prettier npm run pretty ``` ## License Mobicoop V3 - Ad Service is [AGPL licensed](LICENSE).