Compare commits
5
Commits
37462e4646
...
4cb3971940
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4cb3971940 | ||
|
|
dcd0b5f064 | ||
|
|
28afb11ac4 | ||
|
|
3f1cf11cd7 | ||
|
|
80b8926a0e |
@@ -6,7 +6,9 @@ Powered by:
|
|||||||
- PHP Symfony.
|
- PHP Symfony.
|
||||||
- Easyadmin.
|
- Easyadmin.
|
||||||
|
|
||||||
## Commands:
|
## Get started:
|
||||||
|
|
||||||
|
### Dev commands
|
||||||
|
|
||||||
Build containers:
|
Build containers:
|
||||||
```bash
|
```bash
|
||||||
@@ -33,7 +35,7 @@ XDEBUG_LOG=/dev/stdout
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### Prod:
|
### Production commands:
|
||||||
|
|
||||||
When deploying to a production environment a production build should be used.
|
When deploying to a production environment a production build should be used.
|
||||||
Then, deployment can be done as containers or using docker-compose.
|
Then, deployment can be done as containers or using docker-compose.
|
||||||
@@ -47,7 +49,7 @@ docker build -t somniarooms:prod --target frankenphp_prod .
|
|||||||
|
|
||||||
**Deploy prod image**
|
**Deploy prod image**
|
||||||
|
|
||||||
You may use a env file to configure the SomniaRoom container:
|
You may use a env file to configure the SomniaRoom container (`.env.prod.local`):
|
||||||
|
|
||||||
```shell
|
```shell
|
||||||
SERVER_NAME=localhost
|
SERVER_NAME=localhost
|
||||||
@@ -83,6 +85,12 @@ If you want your app and DB to comunicate using it's hostname (like on this exam
|
|||||||
docker network create somniarooms-network
|
docker network create somniarooms-network
|
||||||
```
|
```
|
||||||
|
|
||||||
|
Check [deploy docs](docs/deploy.md) for complete examples on how to deploy SomniaRooms (backend+frontend) using Docker and Docker-compose.
|
||||||
|
|
||||||
|
<warning>
|
||||||
|
Examples shown on deploy docs may be out-of-date. Make sure all readme recommendations are applied before use on production.
|
||||||
|
</warning>
|
||||||
|
|
||||||
|
|
||||||
## Running the app!
|
## Running the app!
|
||||||
|
|
||||||
|
|||||||
@@ -16,6 +16,7 @@
|
|||||||
"easycorp/easyadmin-bundle": "^4.10",
|
"easycorp/easyadmin-bundle": "^4.10",
|
||||||
"nelmio/api-doc-bundle": "^4.30",
|
"nelmio/api-doc-bundle": "^4.30",
|
||||||
"nelmio/cors-bundle": "^2.4",
|
"nelmio/cors-bundle": "^2.4",
|
||||||
|
"php-ds/php-ds": "^1.5",
|
||||||
"phpdocumentor/reflection-docblock": "^5.4",
|
"phpdocumentor/reflection-docblock": "^5.4",
|
||||||
"phpstan/phpdoc-parser": "^1.28",
|
"phpstan/phpdoc-parser": "^1.28",
|
||||||
"runtime/frankenphp-symfony": "^0.2.0",
|
"runtime/frankenphp-symfony": "^0.2.0",
|
||||||
|
|||||||
Generated
+56
-1
@@ -4,7 +4,7 @@
|
|||||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||||
"This file is @generated automatically"
|
"This file is @generated automatically"
|
||||||
],
|
],
|
||||||
"content-hash": "974cb22b15d6dc64bd6dac49da5d671d",
|
"content-hash": "03b299c4c2e514090c879c8f71219e56",
|
||||||
"packages": [
|
"packages": [
|
||||||
{
|
{
|
||||||
"name": "composer/semver",
|
"name": "composer/semver",
|
||||||
@@ -1686,6 +1686,61 @@
|
|||||||
},
|
},
|
||||||
"time": "2023-11-30T16:41:19+00:00"
|
"time": "2023-11-30T16:41:19+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "php-ds/php-ds",
|
||||||
|
"version": "v1.5.0",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/php-ds/polyfill.git",
|
||||||
|
"reference": "7b2c5f1843466d50769a0682ce6fa9ddaaa99cb4"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/php-ds/polyfill/zipball/7b2c5f1843466d50769a0682ce6fa9ddaaa99cb4",
|
||||||
|
"reference": "7b2c5f1843466d50769a0682ce6fa9ddaaa99cb4",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"ext-json": "*",
|
||||||
|
"php": ">=7.0"
|
||||||
|
},
|
||||||
|
"provide": {
|
||||||
|
"ext-ds": "1.5.0"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"php-ds/tests": "^1.5"
|
||||||
|
},
|
||||||
|
"suggest": {
|
||||||
|
"ext-ds": "to improve performance and reduce memory usage"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"psr-4": {
|
||||||
|
"Ds\\": "src"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Rudi Theunissen",
|
||||||
|
"email": "[email protected]"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"keywords": [
|
||||||
|
"data structures",
|
||||||
|
"ds",
|
||||||
|
"php",
|
||||||
|
"polyfill"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/php-ds/polyfill/issues",
|
||||||
|
"source": "https://github.com/php-ds/polyfill/tree/v1.5.0"
|
||||||
|
},
|
||||||
|
"time": "2023-12-19T16:52:21+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "phpdocumentor/reflection-common",
|
"name": "phpdocumentor/reflection-common",
|
||||||
"version": "2.2.0",
|
"version": "2.2.0",
|
||||||
|
|||||||
@@ -24,5 +24,9 @@ services:
|
|||||||
arguments:
|
arguments:
|
||||||
$targetDirectory: 'images/'
|
$targetDirectory: 'images/'
|
||||||
|
|
||||||
|
App\Service\ExampleDataService:
|
||||||
|
arguments:
|
||||||
|
$sampleDirectory: '../samples/'
|
||||||
|
|
||||||
# add more service definitions when explicit configuration is needed
|
# add more service definitions when explicit configuration is needed
|
||||||
# please note that last definitions always *replace* previous ones
|
# please note that last definitions always *replace* previous ones
|
||||||
|
|||||||
+182
-36
@@ -1,54 +1,200 @@
|
|||||||
|
<!-- omit in toc -->
|
||||||
# SomniaRooms - App Configuration Variables.
|
# SomniaRooms - App Configuration Variables.
|
||||||
|
|
||||||
|
- [Config Sections](#config-sections)
|
||||||
|
- [Config implementation status](#config-implementation-status)
|
||||||
|
- [Company Information](#company-information)
|
||||||
|
- [Front-end Config](#front-end-config)
|
||||||
|
- [Var `NightAmountForContactDialog`](#var-nightamountforcontactdialog)
|
||||||
|
- [Var `GuestNumberForContactDialog`](#var-guestnumberforcontactdialog)
|
||||||
|
- [Var `ContactDialogShowBehaviour`](#var-contactdialogshowbehaviour)
|
||||||
|
- [Var `ShowNonAvailableRooms`](#var-shownonavailablerooms)
|
||||||
|
- [Var `SomniaAttributionNotice`](#var-somniaattributionnotice)
|
||||||
|
- [Var `PhotoAspectRatio`](#var-photoaspectratio)
|
||||||
|
- [Price Management](#price-management)
|
||||||
|
- [Var `TotalPriceMethod`.](#var-totalpricemethod)
|
||||||
|
- [Var `FareSelectionMethod`](#var-fareselectionmethod)
|
||||||
|
- [API Config.](#api-config)
|
||||||
|
- [Var `MaxAllowedNightAmount`](#var-maxallowednightamount)
|
||||||
|
- [Var `MaxAllowedGuestNumber`](#var-maxallowedguestnumber)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
This document contains a list of all config variables of SomniaRooms. Variables are stored in DB (table _`config_variable`_) and can be configured from admin panel.
|
This document contains a list of all config variables of SomniaRooms. Variables are stored in DB (table _`config_variable`_) and can be configured from admin panel.
|
||||||
|
|
||||||
Variables are divided in sections. Some sections are ony accesible from SomniaRoom, but others can be retrieved by anyone using config endpoint (_`/config`_).
|
Variables are divided in sections. Some sections are ony accesible from SomniaRoom, but others can be retrieved by anyone using config endpoint (_`/config`_).
|
||||||
|
|
||||||
## List of sections:
|
## Config Sections
|
||||||
|
|
||||||
WIP
|
| Section | SectionName | Description | Availability |
|
||||||
|
| :------------------------------------------ | :-------------- | :--------------------------------------------- | :----------: |
|
||||||
|
| [Company Information](#company-information) | COMPANY | Configure company information | Public |
|
||||||
|
| [Front-end config](#front-end-config) | FRONTEND_CONFIG | Configure front-end behaviour | Public |
|
||||||
|
| [Price API Management](#price-management) | API_PRICES | Configure how prices are calculated for a stay | Private |
|
||||||
|
| [API Config](#api-config) | API_CONFIG | Configure API | Private |
|
||||||
|
|
||||||
TODO -> Add default table with basic information to all sections.
|
|
||||||
|
|
||||||
### **Company**
|
### Config implementation status
|
||||||
Variables in this section contains information about the Hotel.
|
|
||||||
|
|
||||||
- SectionName -> company
|
Not all variables are fully implemented, some are experimental or have options that are.
|
||||||
- Availability -> public
|
Current status for a variable and it's options:
|
||||||
- Nº variables -> X
|
- New!: :sparkles:
|
||||||
|
- Fully available: :heavy_check_mark:
|
||||||
|
- Partially available: :construction:
|
||||||
|
- Experimental: :bulb:
|
||||||
|
- Not yet: :x:
|
||||||
|
|
||||||
**Variable list:**
|
|
||||||
|
|
||||||
- Name - Name of hotel.
|
## Company Information
|
||||||
|
Variables in this section contains information about the Company. Those are used to identify the business and to customize frontend.
|
||||||
|
|
||||||
|
| Variable | Type | Description | Constraints | Default Value | Status |
|
||||||
|
| :------------- | :----- | :-------------------- | :----------------------------------------------------------- | :------------ | :------------: |
|
||||||
|
| CompanyName | string | Company name | - | SomniaRooms | :construction: |
|
||||||
|
| CompanyWebsite | string | Company website URL | Valid URL to company website. | somnia.dev | :construction: |
|
||||||
|
| CompanyLogo | string | Company Logo URL | Valid URL to company logo. Somnia Backend system can be used | "" | :construction: |
|
||||||
|
| CompanyAddress | string | Company Address | - | "" | :construction: |
|
||||||
|
| CompanyEmail | string | Company email address | - | "" | :construction: |
|
||||||
|
| CompanyPhone | string | Company phone number | - | "" | :construction: |
|
||||||
|
|
||||||
|
|
||||||
|
## Front-end Config
|
||||||
|
This variable set the behaviour of front-end app.
|
||||||
|
|
||||||
|
| Variable | Type | Description | Constraints | Default Value | Status |
|
||||||
|
| :-------------------------- | :------ | :------------------------------------------------- | :---------------------------------------------- | :------------ | :------------: |
|
||||||
|
| NightAmountForContactDialog | int | Set the amount of nights to show a contact dialog. | See [details](#var-nightamountforcontactdialog) | 10 | :construction: |
|
||||||
|
| GuestNumberForContactDialog | int | Set the guest number to show a contact dialog. | See [details](#var-guestnumberforcontactdialog) | 6 | :construction: |
|
||||||
|
| ContactDialogShowBehaviour | options | Set how the contact dialog is shown | See [details](#var-contactdialogshowbehaviour) | show | :construction: |
|
||||||
|
| ShowNonAvailableRooms | bool | Show rooms without availability on search | See [details](#var-shownonavailablerooms) | true | :construction: |
|
||||||
|
| SomniaAttributionNotice | options | How SomniaRooms notice is shown. | See [details](#var-somniaattributionnotice) | full | :construction: |
|
||||||
|
| PhotoAspectRatio | string | Set the aspect ratio for photos | See [details](#var-photoaspectratio) | 4:3 | :construction: |
|
||||||
|
|
||||||
|
### Var `NightAmountForContactDialog`
|
||||||
|
Set the amount of nights to show a contact dialog. This dialog contains company contact information and may be used to get a custom price for long stays.
|
||||||
|
|
||||||
|
The contact dialog will be shown when night amount is equal or greater than configured amount.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :------------ | :---- | :-------------------------------------------------------- | :----: |
|
||||||
|
| Disabled | -1 | Disable this funcionality. Contact dialog won't be shown. | :x: |
|
||||||
|
| Always | 0 | Contact dialog is always shown. | :x: |
|
||||||
|
| Custom Amount | - | Set the minimun number of nights to show the dialog. | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
### Var `GuestNumberForContactDialog`
|
||||||
|
Set the guest number to show a contact dialog. This dialog contains company contact information and may be used to get a custom price for groups.
|
||||||
|
|
||||||
|
The contact dialog will be shown when guest number is equal or greater than configured amount.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :------------ | :---- | :-------------------------------------------------------- | :----: |
|
||||||
|
| Disabled | -1 | Disable this funcionality. Contact dialog won't be shown. | :x: |
|
||||||
|
| Always | 0 | Contact dialog is always shown. | :x: |
|
||||||
|
| Custom Amount | - | Set the minimun guest number to show the dialog. | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
### Var `ContactDialogShowBehaviour`
|
||||||
|
How the contact dialog is shown to the user (when conditions are meet).
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :----- | :---- | :------------------------------- | :----: |
|
||||||
|
| Show | SHOW | Show dialog on screen | :x: |
|
||||||
|
| Alert | ALERT | Show an alert to open the dialog | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
### Var `ShowNonAvailableRooms`
|
||||||
|
Show rooms without availability on search.
|
||||||
|
Non-available rooms will be shown at the end of the list.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :----- | :---- | :-------------------------------------------------------- | :----: |
|
||||||
|
| Show | true | All rooms will appear on search. Even non-available ones. | :x: |
|
||||||
|
| Hide | false | Only show available rooms. | :x: |
|
||||||
|
|
||||||
|
### Var `SomniaAttributionNotice`
|
||||||
|
Configure how SomniaRooms attribution note is display.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :----- | :---- | :------------------------------------ | :----: |
|
||||||
|
| Full | FULL | Show the full message. Thanks :heart: | :x: |
|
||||||
|
| Small | SMALL | Show a small notice :+1: | :x: |
|
||||||
|
| Hide | HIDE | SomniaRooms notice won't be shown. | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
### Var `PhotoAspectRatio`
|
||||||
|
Aspect ratio for front-end photos.
|
||||||
|
|
||||||
|
This setting is currently used for room photos. You may set any valid aspect-ratio you want.
|
||||||
|
It's recommended that all photos have the same aspect-ratio to avoid scaling.
|
||||||
|
|
||||||
|
|
||||||
|
## Price Management
|
||||||
|
How SomniaRooms API services calculates prices for bookings.
|
||||||
|
|
||||||
|
| Variable | Type | Description | Constraints | Default Value | Status |
|
||||||
|
| :------------------ | :----- | :---------------------------------------------------- | :-------------------------------------- | :------------ | :----: |
|
||||||
|
| TotalPriceMethod | option | How total price is calculated for a stay | See [details](#var-totalpricemethod) | SUM | :x: |
|
||||||
|
| FareSelectionMethod | option | What fare to select when multiple fares are available | See [details](#var-fareselectionmethod) | HIGHER | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
### Var `TotalPriceMethod`.
|
||||||
|
Establish the method used to calculate the total price for a stay.
|
||||||
|
|
||||||
|
The total price for a stay will be calculated from the price of the days that make the stay. A operation must be selected to get total price from daily prices.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :------------ | :------ | :----------------------------------------------------------------- | :----: |
|
||||||
|
| Lower Price | LOWER | The lower price will be apply for each day. | :x: |
|
||||||
|
| High Price | HIGHER | The highest price will be apply for each day. | :x: |
|
||||||
|
| Total Sum | SUM | Total price will be the sum of the price for each day. | :x: |
|
||||||
|
| Average Price | AVERAGE | The average for all days will be calculated and apply to each day. | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
### Var `FareSelectionMethod`
|
||||||
|
How to select the fare for a room when there are multiple fares applicable.
|
||||||
|
|
||||||
|
A faretable may contain multiple fares for a room and guest number given some conditions. If multiple conditions match for a date and therefore there are more than 1 applicable fare, one must be used. This method sets what to do in those cases.
|
||||||
|
Note: RoomPrices have more priority than fares. So if a RoomPrice is available, it will always be the prefered option.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :------------ | :------ | :---------------------------------------------------------------- | :----: |
|
||||||
|
| Lower Price | LOWER | Lower price available will be used. | :x: |
|
||||||
|
| High Price | HIGHER | Higher available price will be used. | :x: |
|
||||||
|
| Average price | AVERAGE | Selected price will be the aritmetic average of available prices. | :x: |
|
||||||
|
|
||||||
|
|
||||||
|
## API Config.
|
||||||
|
Configuration for some API endpoints.
|
||||||
|
|
||||||
|
| Variable | Type | Description | Constraints | Default Value | Status |
|
||||||
|
| :-------------------- | :--- | :----------------------------------- | :---------------------------------------- | :------------ | :------------: |
|
||||||
|
| MaxAllowedNightAmount | int | Max night amount that can be booked. | See [details](#var-maxallowednightamount) | 20 | :construction: |
|
||||||
|
| MaxAllowedGuestNumber | int | Max guest number that can be booked. | See [details](#var-maxallowedguestnumber) | 20 | :construction: |
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
### **Price Management**
|
### Var `MaxAllowedNightAmount`
|
||||||
Configure how backend services calculates prices for bookings.
|
Max number of nights that can be booked using the app. For longer stays the company should be contacted.
|
||||||
|
|
||||||
- SectionName -> price_mng
|
**Options:**
|
||||||
- Availability -> internal
|
| Option | Value | Usage | Status |
|
||||||
- Nº variables -> X
|
| :------------ | :---- | :---------------------------------------------------------- | :----: |
|
||||||
|
| Disabled | 0 | Disable this funcionality. No limit on booking will be set. | :x: |
|
||||||
**Variable list:**
|
| Custom Amount | - | Set the max number of nights allowed to book. | :x: |
|
||||||
|
|
||||||
WIP
|
|
||||||
|
|
||||||
#### FinalPriceCalculation.
|
|
||||||
Establece cómo se deben tratar los precios de cada día para generar el precio final de la estancia.
|
|
||||||
|
|
||||||
Algunos algoritmos para estos serán:
|
|
||||||
- Precio más alto.
|
|
||||||
- Precio más bajo.
|
|
||||||
- Suma de precios. --> Por defecto.
|
|
||||||
- Media de precios.
|
|
||||||
|
|
||||||
#### MultipleRoomFareValid
|
|
||||||
Estrategia de selección de tarifa en caso de que haya varias válidas (mientras no exista un sistema de prioridad de tarifas...)
|
|
||||||
|
|
||||||
Posibles algoritmos:
|
|
||||||
- Precio más alto.
|
|
||||||
- Precio más bajo.
|
|
||||||
- Media.
|
|
||||||
|
|
||||||
|
### Var `MaxAllowedGuestNumber`
|
||||||
|
Max guest number that can be booked using the app. For bigger groups the company should be contacted.
|
||||||
|
|
||||||
|
**Options:**
|
||||||
|
| Option | Value | Usage | Status |
|
||||||
|
| :------------ | :---- | :---------------------------------------------------------- | :----: |
|
||||||
|
| Disabled | 0 | Disable this funcionality. No limit on booking will be set. | :x: |
|
||||||
|
| Custom Amount | - | Set the max guest number allowed to book. | :x: |
|
||||||
@@ -1,5 +1,13 @@
|
|||||||
|
<!-- omit in toc -->
|
||||||
# SomniaRooms - How to deploy.
|
# SomniaRooms - How to deploy.
|
||||||
|
|
||||||
|
- [Docker compose examples.](#docker-compose-examples)
|
||||||
|
- [Deploy back-end and front-end on different servers (different ip address).](#deploy-back-end-and-front-end-on-different-servers-different-ip-address)
|
||||||
|
- [Deploy on the same server.](#deploy-on-the-same-server)
|
||||||
|
- [What's next?](#whats-next)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
SomniaRooms is designed to be easy to deploy and use.
|
SomniaRooms is designed to be easy to deploy and use.
|
||||||
|
|
||||||
Production images for Docker Containers are available from Gitea Registry.
|
Production images for Docker Containers are available from Gitea Registry.
|
||||||
|
|||||||
@@ -0,0 +1,10 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Double Bed",
|
||||||
|
"iconUrl": "icon-bed-double"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Single Bed",
|
||||||
|
"iconUrl": "icon-bed-single"
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,41 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Double room (double bed)",
|
||||||
|
"description": "Room with double bed and shared bathroom",
|
||||||
|
"maxGuestNum": 2,
|
||||||
|
"orderHomePage": null,
|
||||||
|
"roomCategoryPhotos": [
|
||||||
|
{
|
||||||
|
"path": "https://images.unsplash.com/photo-1559841644-08984562005a",
|
||||||
|
"altText": "Room",
|
||||||
|
"photoOrder": 1
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Double w/ bath (double bed)",
|
||||||
|
"description": "Room with double bed and private bathroom",
|
||||||
|
"maxGuestNum": 2,
|
||||||
|
"orderHomePage": null,
|
||||||
|
"roomCategoryPhotos": [
|
||||||
|
{
|
||||||
|
"path": "https://images.unsplash.com/photo-1559841644-08984562005a",
|
||||||
|
"altText": "Room",
|
||||||
|
"photoOrder": 1
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Double w/ bath (single bed)",
|
||||||
|
"description": "Room with 2 single beds and private bathroom",
|
||||||
|
"maxGuestNum": 2,
|
||||||
|
"orderHomePage": null,
|
||||||
|
"roomCategoryPhotos": [
|
||||||
|
{
|
||||||
|
"path": "https://images.unsplash.com/photo-1559841644-08984562005a",
|
||||||
|
"altText": "Room",
|
||||||
|
"photoOrder": 1
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,12 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"amount": 1,
|
||||||
|
"roomCategory": 0,
|
||||||
|
"bedType": 0
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"amount": 1,
|
||||||
|
"roomCategory": 2,
|
||||||
|
"bedType": 1
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,61 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Consts;
|
||||||
|
|
||||||
|
use App\Entity\ConfigVariable;
|
||||||
|
use App\Enum\ConfigVariableSectionEnum;
|
||||||
|
|
||||||
|
//Variable List Constants
|
||||||
|
// --> This constants contains all defined Config Variables. For each one a array is stored as [varKey => [varSection, varDefaultValue]].
|
||||||
|
class ConfigVariableConsts
|
||||||
|
{
|
||||||
|
public const CONFIG_COMPANY_NAME = ["CompanyName" => [ConfigVariableSectionEnum::Company, "SomniaRooms"]];
|
||||||
|
public const CONFIG_COMPANY_WEBSITE = ["CompanyWebsite" => [ConfigVariableSectionEnum::Company, "somnia.dev"]];
|
||||||
|
public const CONFIG_COMPANY_LOGO = ["CompanyLogo" => [ConfigVariableSectionEnum::Company, ""]];
|
||||||
|
public const CONFIG_COMPANY_ADDRESS = ["CompanyAddress" => [ConfigVariableSectionEnum::Company, ""]];
|
||||||
|
public const CONFIG_COMPANY_EMAIL = ["CompanyEmail" => [ConfigVariableSectionEnum::Company, ""]];
|
||||||
|
public const CONFIG_COMPANY_PHONE = ["CompanyPhone" => [ConfigVariableSectionEnum::Company, ""]];
|
||||||
|
|
||||||
|
public const CONFIG_FRONTEND_NIGHTSFORCONTACT = ["NightAmountForContactDialog" => [ConfigVariableSectionEnum::Frontend, "10"]];
|
||||||
|
public const CONFIG_FRONTEND_GUESTSFORCONTACT = ["GuestNumberForContactDialog" => [ConfigVariableSectionEnum::Frontend, "6"]];
|
||||||
|
public const CONFIG_FRONTEND_CONTACTDIALOGBEHAVIOUR = ["ContactDialogShowBehaviour" => [ConfigVariableSectionEnum::Frontend, "show"]];
|
||||||
|
public const CONFIG_FRONTEND_SHOWNONAVAILABLEROOMS = ["ShowNonAvailableRooms" => [ConfigVariableSectionEnum::Frontend, true]];
|
||||||
|
public const CONFIG_FRONTEND_SOMNIAATTRIBUTION = ["SomniaAttributionNotice" => [ConfigVariableSectionEnum::Frontend, "full"]];
|
||||||
|
public const CONFIG_FRONTEND_PHOTOASPECTRATIO = ["PhotoAspectRatio" => [ConfigVariableSectionEnum::Frontend, "4:3"]];
|
||||||
|
|
||||||
|
public const CONFIG_PRICES_PRICEMETHOD = ["TotalPriceMethod" => [ConfigVariableSectionEnum::API_PRICES, "SUM"]];
|
||||||
|
public const CONFIG_PRICES_FAREMETHOD = ["FareSelectionMethod" => [ConfigVariableSectionEnum::API_PRICES, "HIGHER"]];
|
||||||
|
|
||||||
|
public const CONFIG_API_NAXNIGHTS = ["MaxAllowedNightAmount" => [ConfigVariableSectionEnum::API_CONFIG, "20"]];
|
||||||
|
public const CONFIG_API_NAXGUESTS = ["MaxAllowedGuestNumber" => [ConfigVariableSectionEnum::API_CONFIG, "20"]];
|
||||||
|
|
||||||
|
public const CONFIG_INTERNAL_SETUP = ["SETUP_STATUS" => [ConfigVariableSectionEnum::Internal, "1"]];
|
||||||
|
|
||||||
|
public static function getKeyFromConstant(array $constant): string
|
||||||
|
{
|
||||||
|
return array_key_first($constant);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static function GetAllDefinedConfigVariablesList(): array
|
||||||
|
{
|
||||||
|
return array_merge(
|
||||||
|
ConfigVariableConsts::CONFIG_COMPANY_NAME,
|
||||||
|
ConfigVariableConsts::CONFIG_COMPANY_WEBSITE,
|
||||||
|
ConfigVariableConsts::CONFIG_COMPANY_LOGO,
|
||||||
|
ConfigVariableConsts::CONFIG_COMPANY_ADDRESS,
|
||||||
|
ConfigVariableConsts::CONFIG_COMPANY_EMAIL,
|
||||||
|
ConfigVariableConsts::CONFIG_COMPANY_PHONE,
|
||||||
|
ConfigVariableConsts::CONFIG_FRONTEND_NIGHTSFORCONTACT,
|
||||||
|
ConfigVariableConsts::CONFIG_FRONTEND_GUESTSFORCONTACT,
|
||||||
|
ConfigVariableConsts::CONFIG_FRONTEND_CONTACTDIALOGBEHAVIOUR,
|
||||||
|
ConfigVariableConsts::CONFIG_FRONTEND_SHOWNONAVAILABLEROOMS,
|
||||||
|
ConfigVariableConsts::CONFIG_FRONTEND_SOMNIAATTRIBUTION,
|
||||||
|
ConfigVariableConsts::CONFIG_FRONTEND_PHOTOASPECTRATIO,
|
||||||
|
ConfigVariableConsts::CONFIG_PRICES_PRICEMETHOD,
|
||||||
|
ConfigVariableConsts::CONFIG_PRICES_FAREMETHOD,
|
||||||
|
ConfigVariableConsts::CONFIG_API_NAXNIGHTS,
|
||||||
|
ConfigVariableConsts::CONFIG_API_NAXGUESTS,
|
||||||
|
ConfigVariableConsts::CONFIG_INTERNAL_SETUP,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -3,7 +3,8 @@
|
|||||||
namespace App\Controller\Admin;
|
namespace App\Controller\Admin;
|
||||||
|
|
||||||
use App\Entity\ConfigVariable;
|
use App\Entity\ConfigVariable;
|
||||||
use App\Enum\ConfigSectionType;
|
use App\Enum\ConfigVariableSectionEnum;
|
||||||
|
use EasyCorp\Bundle\EasyAdminBundle\Config\Actions;
|
||||||
use EasyCorp\Bundle\EasyAdminBundle\Config\Crud;
|
use EasyCorp\Bundle\EasyAdminBundle\Config\Crud;
|
||||||
use EasyCorp\Bundle\EasyAdminBundle\Controller\AbstractCrudController;
|
use EasyCorp\Bundle\EasyAdminBundle\Controller\AbstractCrudController;
|
||||||
use EasyCorp\Bundle\EasyAdminBundle\Field\ChoiceField;
|
use EasyCorp\Bundle\EasyAdminBundle\Field\ChoiceField;
|
||||||
@@ -21,10 +22,15 @@ class ConfigVariableCrudController extends AbstractCrudController
|
|||||||
return $crud;
|
return $crud;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function configureActions(Actions $actions): Actions
|
||||||
|
{
|
||||||
|
return $actions->disable("new", "delete");;
|
||||||
|
}
|
||||||
|
|
||||||
public function configureFields(string $pageName): iterable
|
public function configureFields(string $pageName): iterable
|
||||||
{
|
{
|
||||||
yield ChoiceField::new ('section')->setChoices(ConfigSectionType::cases());
|
yield ChoiceField::new('section')->setChoices(ConfigVariableSectionEnum::cases());
|
||||||
yield TextField::new ('key');
|
yield TextField::new('key');
|
||||||
yield TextField::new ('value');
|
yield TextField::new('value');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
namespace App\Controller;
|
namespace App\Controller;
|
||||||
|
|
||||||
|
use App\Consts\ConfigVariableConsts;
|
||||||
use App\DTO\AppSetupConfig;
|
use App\DTO\AppSetupConfig;
|
||||||
use App\DTO\ExampleDataConfig;
|
use App\DTO\ExampleDataConfig;
|
||||||
use App\Entity\ConfigVariable;
|
use App\Entity\ConfigVariable;
|
||||||
@@ -9,9 +10,9 @@ use App\Form\AppSetupFormType;
|
|||||||
use App\Form\ExampleDataFormType;
|
use App\Form\ExampleDataFormType;
|
||||||
use App\Repository\RoomCategoryRepository;
|
use App\Repository\RoomCategoryRepository;
|
||||||
use App\Service\AppSetupService;
|
use App\Service\AppSetupService;
|
||||||
|
use App\Service\ConfigVariableService;
|
||||||
use App\Service\ExampleDataService;
|
use App\Service\ExampleDataService;
|
||||||
use Doctrine\ORM\EntityManagerInterface;
|
use Doctrine\ORM\EntityManagerInterface;
|
||||||
use Monolog\Logger;
|
|
||||||
use Psr\Log\LoggerInterface;
|
use Psr\Log\LoggerInterface;
|
||||||
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
||||||
use Symfony\Component\HttpFoundation\Request;
|
use Symfony\Component\HttpFoundation\Request;
|
||||||
@@ -25,13 +26,13 @@ class AppSetupController extends AbstractController
|
|||||||
LoggerInterface $logger,
|
LoggerInterface $logger,
|
||||||
AppSetupService $setupService,
|
AppSetupService $setupService,
|
||||||
Request $request,
|
Request $request,
|
||||||
EntityManagerInterface $entityManager
|
ConfigVariableService $configVars
|
||||||
): Response {
|
): Response {
|
||||||
|
|
||||||
$configRepo = $entityManager->getRepository(ConfigVariable::class);
|
$setupVar_key = ConfigVariableConsts::getKeyFromConstant(ConfigVariableConsts::CONFIG_INTERNAL_SETUP);
|
||||||
$setupStatus = $configRepo->findBy(["key" => "SETUP_STATUS"]);
|
$setupStatus = $configVars->getVariable($setupVar_key);
|
||||||
|
|
||||||
if ($setupStatus != null && $setupStatus[0] != null && $setupStatus[0]->getValue() == 1) {
|
if ($setupStatus != null && $setupStatus->getValue()) {
|
||||||
$logger->warning("SomniaRooms was already setup");
|
$logger->warning("SomniaRooms was already setup");
|
||||||
|
|
||||||
return $this->GoToResultPage(
|
return $this->GoToResultPage(
|
||||||
|
|||||||
@@ -3,22 +3,22 @@
|
|||||||
namespace App\Entity;
|
namespace App\Entity;
|
||||||
|
|
||||||
use App\Repository\ConfigVariableRepository;
|
use App\Repository\ConfigVariableRepository;
|
||||||
use App\Enum\ConfigSectionType;
|
use App\Enum\ConfigVariableSectionEnum;
|
||||||
use Doctrine\ORM\Mapping as ORM;
|
use Doctrine\ORM\Mapping as ORM;
|
||||||
|
|
||||||
#[ORM\Entity(repositoryClass: ConfigVariableRepository::class)]
|
#[ORM\Entity(repositoryClass: ConfigVariableRepository::class)]
|
||||||
class ConfigVariable
|
class ConfigVariable
|
||||||
{
|
{
|
||||||
#[ORM\Id]
|
#[ORM\Id]
|
||||||
#[ORM\GeneratedValue("NONE")]
|
#[ORM\GeneratedValue(strategy: "NONE")]
|
||||||
#[ORM\Column(length: 32, unique: true, nullable: false)]
|
#[ORM\Column(length: 32, unique: true, nullable: false)]
|
||||||
private string $key = "";
|
private string $key = "";
|
||||||
|
|
||||||
#[ORM\Column(length: 255, nullable: false)]
|
#[ORM\Column(length: 255, nullable: false)]
|
||||||
private ?string $value = null;
|
private ?string $value = null;
|
||||||
|
|
||||||
#[ORM\Column(type: 'string', enumType: ConfigSectionType::class, nullable: false)]
|
#[ORM\Column(type: 'string', enumType: ConfigVariableSectionEnum::class, nullable: false)]
|
||||||
private ConfigSectionType $section = ConfigSectionType::General;
|
private ConfigVariableSectionEnum $section = ConfigVariableSectionEnum::Internal;
|
||||||
|
|
||||||
|
|
||||||
public function getKey(): string
|
public function getKey(): string
|
||||||
@@ -45,12 +45,12 @@ class ConfigVariable
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getSection(): ConfigSectionType
|
public function getSection(): ConfigVariableSectionEnum
|
||||||
{
|
{
|
||||||
return $this->section;
|
return $this->section;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function setSection(ConfigSectionType $section): static
|
public function setSection(ConfigVariableSectionEnum $section): static
|
||||||
{
|
{
|
||||||
$this->section = $section;
|
$this->section = $section;
|
||||||
|
|
||||||
|
|||||||
@@ -1,12 +0,0 @@
|
|||||||
<?php
|
|
||||||
|
|
||||||
namespace App\Enum;
|
|
||||||
|
|
||||||
enum ConfigSectionType: string {
|
|
||||||
case General = 'GENERAL';
|
|
||||||
case Internal = 'INTERNAL';
|
|
||||||
case Company = 'COMPANY';
|
|
||||||
case Backend = 'BACK';
|
|
||||||
case Frontend = 'FRONT';
|
|
||||||
case Test = 'TEST';
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,12 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Enum;
|
||||||
|
|
||||||
|
enum ConfigVariableSectionEnum: string
|
||||||
|
{
|
||||||
|
case Company = 'COMPANY';
|
||||||
|
case Frontend = 'FRONTEND_CONFIG';
|
||||||
|
case API_PRICES = 'API_PRICES';
|
||||||
|
case API_CONFIG = 'API_CONFIG';
|
||||||
|
case Internal = 'INTERNAL';
|
||||||
|
}
|
||||||
@@ -5,6 +5,7 @@ namespace App\Repository;
|
|||||||
use App\Entity\ConfigVariable;
|
use App\Entity\ConfigVariable;
|
||||||
use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository;
|
use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository;
|
||||||
use Doctrine\Persistence\ManagerRegistry;
|
use Doctrine\Persistence\ManagerRegistry;
|
||||||
|
use Ds\Set;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @extends ServiceEntityRepository<ConfigVariable>
|
* @extends ServiceEntityRepository<ConfigVariable>
|
||||||
@@ -51,14 +52,24 @@ class ConfigVariableRepository extends ServiceEntityRepository
|
|||||||
* @param string Variable Key
|
* @param string Variable Key
|
||||||
* @return ConfigVariable|null Config Variable.
|
* @return ConfigVariable|null Config Variable.
|
||||||
*/
|
*/
|
||||||
public function findVariableByKey($varKey)
|
public function findVariableByKey($varKey): ConfigVariable|null
|
||||||
{
|
{
|
||||||
return $this->createQueryBuilder('c')
|
$rs = $this->createQueryBuilder('c')
|
||||||
->select('c.key, c.value, c.section')
|
->select('c.key, c.value, c.section')
|
||||||
->andWhere('c.key = :val')
|
->andWhere('c.key = :val')
|
||||||
->setParameter('val', $varKey)
|
->setParameter('val', $varKey)
|
||||||
|
->setMaxResults(1)
|
||||||
->getQuery()
|
->getQuery()
|
||||||
->getOneOrNullResult();
|
->getResult();
|
||||||
|
// FIXME!!!
|
||||||
|
if (!$rs) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
$var = new ConfigVariable();
|
||||||
|
$var->setKey($rs[0]["key"]);
|
||||||
|
$var->setValue($rs[0]["value"]);
|
||||||
|
$var->setSection($rs[0]["section"]);
|
||||||
|
return $var;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -73,4 +84,18 @@ class ConfigVariableRepository extends ServiceEntityRepository
|
|||||||
->getQuery()
|
->getQuery()
|
||||||
->getResult();
|
->getResult();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get all DB config variables names on a Set.
|
||||||
|
* @return Set Returns a Set with all variable names.
|
||||||
|
*/
|
||||||
|
public function getVariableSet(): Set
|
||||||
|
{
|
||||||
|
$varList = $this->findAll();
|
||||||
|
$keyList = array_map(function ($var) {
|
||||||
|
return $var->getKey();
|
||||||
|
}, $varList);
|
||||||
|
|
||||||
|
return new Set($keyList);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,10 +2,11 @@
|
|||||||
|
|
||||||
namespace App\Service;
|
namespace App\Service;
|
||||||
|
|
||||||
|
use App\Consts\ConfigVariableConsts;
|
||||||
use App\DTO\AppSetupConfig;
|
use App\DTO\AppSetupConfig;
|
||||||
use App\Entity\ConfigVariable;
|
use App\Entity\ConfigVariable;
|
||||||
use App\Entity\User;
|
use App\Entity\User;
|
||||||
use App\Enum\ConfigSectionType;
|
use App\Enum\ConfigVariableSectionEnum;
|
||||||
use App\Enum\UserRoleEnum;
|
use App\Enum\UserRoleEnum;
|
||||||
use App\Repository\ConfigVariableRepository;
|
use App\Repository\ConfigVariableRepository;
|
||||||
|
|
||||||
@@ -23,7 +24,7 @@ class AppSetupService
|
|||||||
public function __construct(
|
public function __construct(
|
||||||
private LoggerInterface $logger,
|
private LoggerInterface $logger,
|
||||||
private EntityManagerInterface $entityManager,
|
private EntityManagerInterface $entityManager,
|
||||||
private ConfigVariableRepository $repoVariables,
|
private ConfigVariableService $configVars,
|
||||||
private UserPasswordHasherInterface $passwordHasher,
|
private UserPasswordHasherInterface $passwordHasher,
|
||||||
private Security $security
|
private Security $security
|
||||||
) {}
|
) {}
|
||||||
@@ -37,15 +38,18 @@ class AppSetupService
|
|||||||
//Create system variables.
|
//Create system variables.
|
||||||
$this->logger->info("SomniaRooms Setup - Creating system variables...");
|
$this->logger->info("SomniaRooms Setup - Creating system variables...");
|
||||||
|
|
||||||
$var_setup = $this->repoVariables->find("SETUP_STATUS");
|
//Not neccesary anymore. CONFIG_INTERNAL_SETUP will be initialized with all vars.
|
||||||
if (!$var_setup) {
|
// $var_setup_key = ConfigVariableConsts::getKeyFromConstant(ConfigVariableConsts::CONFIG_INTERNAL_SETUP);
|
||||||
$var_setup = new ConfigVariable();
|
// $var_setup = $this->configVars->getVariable($var_setup_key);
|
||||||
$var_setup->setKey("SETUP_STATUS");
|
// if (!$var_setup) {
|
||||||
}
|
// $var_setup = new ConfigVariable();
|
||||||
$var_setup->setValue("1");
|
// $var_setup->setKey($var_setup_key);
|
||||||
$var_setup->setSection(ConfigSectionType::Internal);
|
// $this->entityManager->persist($var_setup);
|
||||||
$this->entityManager->persist($var_setup);
|
// }
|
||||||
|
// $var_setup->setValue("1");
|
||||||
|
// $var_setup->setSection(ConfigVariableSectionEnum::Internal);
|
||||||
|
|
||||||
|
$this->configVars->InitVariablesOnSetup();
|
||||||
|
|
||||||
//Create user Admin.
|
//Create user Admin.
|
||||||
$this->logger->info("SomniaRooms Setup - Adding super-admin user...");
|
$this->logger->info("SomniaRooms Setup - Adding super-admin user...");
|
||||||
@@ -53,8 +57,6 @@ class AppSetupService
|
|||||||
$user->setRoles([UserRoleEnum::ROLE_USER->value, UserRoleEnum::ROLE_ADMIN->value, UserRoleEnum::ROLE_SUPERADMIN->value]);
|
$user->setRoles([UserRoleEnum::ROLE_USER->value, UserRoleEnum::ROLE_ADMIN->value, UserRoleEnum::ROLE_SUPERADMIN->value]);
|
||||||
$plaintextPassword = $configData->getAdminPass();
|
$plaintextPassword = $configData->getAdminPass();
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// hash the password (based on the security.yaml config for the $user class)
|
// hash the password (based on the security.yaml config for the $user class)
|
||||||
$hashedPassword = $this->passwordHasher->hashPassword(
|
$hashedPassword = $this->passwordHasher->hashPassword(
|
||||||
$user,
|
$user,
|
||||||
|
|||||||
@@ -2,10 +2,14 @@
|
|||||||
|
|
||||||
namespace App\Service;
|
namespace App\Service;
|
||||||
|
|
||||||
|
use App\Consts\ConfigVariableConsts;
|
||||||
use App\Entity\ConfigVariable;
|
use App\Entity\ConfigVariable;
|
||||||
|
use App\Enum\ConfigVariableSectionEnum;
|
||||||
use App\Repository\ConfigVariableRepository;
|
use App\Repository\ConfigVariableRepository;
|
||||||
|
|
||||||
use Doctrine\Common\Collections\ArrayCollection;
|
use Doctrine\Common\Collections\ArrayCollection;
|
||||||
|
use Doctrine\ORM\EntityManagerInterface;
|
||||||
|
use Psr\Log\LoggerInterface;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Service to manage config variables.
|
* Service to manage config variables.
|
||||||
@@ -14,33 +18,52 @@ class ConfigVariableService
|
|||||||
{
|
{
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
private ConfigVariableRepository $repoVariables
|
private EntityManagerInterface $entityManager,
|
||||||
) {}
|
private ConfigVariableRepository $repoVariables,
|
||||||
|
private LoggerInterface $logger,
|
||||||
|
) {}
|
||||||
|
|
||||||
public function getVariable(string $key) {
|
public function getVariable(string $key): ConfigVariable|null
|
||||||
$var = $this->repoVariables->findVariableByKey($key);
|
{
|
||||||
|
return $this->repoVariables->findVariableByKey($key);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create and init all variables.
|
* Create and init all variables.
|
||||||
* To be used during Setup process.
|
* To be used during Setup process.
|
||||||
*/
|
*/
|
||||||
public function InitVariablesOnSetup(): void {
|
public function InitVariablesOnSetup(): void
|
||||||
|
{
|
||||||
|
//Get a list of variables to check if those already exists.
|
||||||
|
//$this->entityManager->beginTransaction();
|
||||||
|
$varListDb = $this->repoVariables->getVariableSet();
|
||||||
|
$varListPHP = ConfigVariableConsts::GetAllDefinedConfigVariablesList();
|
||||||
|
|
||||||
$entityManager = $this->repoVariables->getEntityManager();
|
foreach ($varListPHP as $varKey => $varValue) {
|
||||||
$entityManager->beginTransaction();
|
if ($varListDb->contains($varKey)) {
|
||||||
|
$this->logger->info("Var $varKey already created. Skipped!", [$varKey, $varValue]);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->AddConfigVariable($varKey, $varValue[1], $varValue[0]);
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
} catch (\Throwable $th) {
|
||||||
}
|
$this->entityManager->rollback();
|
||||||
catch (\Throwable $th) {
|
|
||||||
$entityManager->rollback();
|
|
||||||
throw $th;
|
throw $th;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private function AddConfigVariable(string $key, string $value, string $section): void {
|
public function AddConfigVariable(string $key, string $value, ConfigVariableSectionEnum $section): void
|
||||||
|
{
|
||||||
}
|
$var = new ConfigVariable();
|
||||||
|
$var->setKey($key);
|
||||||
|
$var->setValue($value);
|
||||||
|
$var->setSection($section);
|
||||||
|
|
||||||
}
|
$this->entityManager->persist($var);
|
||||||
|
|
||||||
|
$this->logger->info("Variable added to DB", ["key" => $key, "value" => $value, "section" => $section]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -4,36 +4,67 @@ namespace App\Service;
|
|||||||
|
|
||||||
use App\DTO\AppSetupConfig;
|
use App\DTO\AppSetupConfig;
|
||||||
use App\DTO\ExampleDataConfig;
|
use App\DTO\ExampleDataConfig;
|
||||||
|
use App\Entity\BedType;
|
||||||
use App\Entity\ConfigVariable;
|
use App\Entity\ConfigVariable;
|
||||||
use App\Entity\FareTable;
|
use App\Entity\FareTable;
|
||||||
use App\Entity\RoomCategory;
|
use App\Entity\RoomCategory;
|
||||||
|
use App\Entity\RoomCategoryBedType;
|
||||||
use App\Entity\RoomFare;
|
use App\Entity\RoomFare;
|
||||||
use App\Entity\User;
|
use App\Entity\User;
|
||||||
use App\Enum\ConfigSectionType;
|
|
||||||
use App\Enum\UserRoleEnum;
|
use App\Enum\UserRoleEnum;
|
||||||
use App\Repository\ConfigVariableRepository;
|
use App\Repository\ConfigVariableRepository;
|
||||||
use App\Repository\FareTableRepository;
|
use App\Repository\FareTableRepository;
|
||||||
use App\Repository\RoomAvailabilityRepository;
|
use App\Repository\RoomAvailabilityRepository;
|
||||||
use App\Repository\RoomCategoryRepository;
|
use App\Repository\RoomCategoryRepository;
|
||||||
use App\Repository\RoomFareRepository;
|
use App\Repository\RoomFareRepository;
|
||||||
|
use App\Serializer\Normalizer\EntityByIdDenormalizer;
|
||||||
use DateTime;
|
use DateTime;
|
||||||
use Doctrine\ORM\EntityManagerInterface;
|
use Doctrine\ORM\EntityManagerInterface;
|
||||||
use Psr\Log\LoggerInterface;
|
use Psr\Log\LoggerInterface;
|
||||||
|
use stdClass;
|
||||||
|
use Symfony\Component\Config\FileLocator;
|
||||||
|
use Symfony\Component\PropertyInfo\Extractor\PhpDocExtractor;
|
||||||
|
use Symfony\Component\Serializer\Encoder\JsonEncoder;
|
||||||
|
use Symfony\Component\Serializer\Normalizer\ArrayDenormalizer;
|
||||||
|
use Symfony\Component\Serializer\Normalizer\GetSetMethodNormalizer;
|
||||||
|
use Symfony\Component\Serializer\Normalizer\ObjectNormalizer;
|
||||||
|
use Symfony\Component\Serializer\Serializer;
|
||||||
|
use Symfony\Component\Serializer\SerializerInterface;
|
||||||
|
use Symfony\Component\Serializer\Mapping\Factory\ClassMetadataFactory;
|
||||||
|
use Symfony\Component\Serializer\Mapping\Loader\AnnotationLoader;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Service for setup proccess.
|
* Service for setup proccess.
|
||||||
*/
|
*/
|
||||||
class ExampleDataService
|
class ExampleDataService
|
||||||
{
|
{
|
||||||
|
private Serializer $sampleSerializer;
|
||||||
|
private FileLocator $fileLocator;
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
|
private string $sampleDirectory,
|
||||||
private LoggerInterface $logger,
|
private LoggerInterface $logger,
|
||||||
private EntityManagerInterface $entityManager,
|
private EntityManagerInterface $entityManager,
|
||||||
private RoomCategoryRepository $roomCategoryRepository,
|
private RoomCategoryRepository $roomCategoryRepository,
|
||||||
private RoomAvailabilityRepository $roomAvailabilityRepository,
|
private RoomAvailabilityRepository $roomAvailabilityRepository,
|
||||||
private FareTableRepository $fareTableRepository,
|
private FareTableRepository $fareTableRepository,
|
||||||
private RoomFareRepository $roomFareRepository,
|
private RoomFareRepository $roomFareRepository
|
||||||
) {}
|
) {
|
||||||
|
|
||||||
|
$this->sampleSerializer = new Serializer(
|
||||||
|
array(
|
||||||
|
new ObjectNormalizer(
|
||||||
|
null,
|
||||||
|
null,
|
||||||
|
null,
|
||||||
|
new PhpDocExtractor()
|
||||||
|
),
|
||||||
|
new ArrayDenormalizer(),
|
||||||
|
),
|
||||||
|
array('json' => new JsonEncoder())
|
||||||
|
);
|
||||||
|
$this->fileLocator = new FileLocator($this->sampleDirectory);
|
||||||
|
}
|
||||||
|
|
||||||
public function AddExampleData(ExampleDataConfig $config): string
|
public function AddExampleData(ExampleDataConfig $config): string
|
||||||
{
|
{
|
||||||
@@ -65,12 +96,53 @@ class ExampleDataService
|
|||||||
return "OK";
|
return "OK";
|
||||||
}
|
}
|
||||||
|
|
||||||
private function GenerateRoomCategories(): bool
|
public function GenerateRoomCategories(): bool
|
||||||
{
|
{
|
||||||
//TODOME.
|
//Add Example BedTypes.
|
||||||
|
$bedTypeList = $this->DeserializeSampleFile("SampleBedTypes.json", BedType::class . '[]');
|
||||||
|
$this->PersistEntityArray($bedTypeList);
|
||||||
|
|
||||||
|
//Add Example RoomCategories
|
||||||
|
$roomCategoryList = $this->DeserializeSampleFile("SampleRoomCategories.json", RoomCategory::class . '[]');
|
||||||
|
$this->PersistEntityArray($roomCategoryList);
|
||||||
|
|
||||||
|
//Add Example RoomCategoryBedTypes
|
||||||
|
$sampleRcBtData = $this->GetFileData("SampleRoomCategoryBedTypes.json");
|
||||||
|
$sampleRcBtContent = json_decode($sampleRcBtData);
|
||||||
|
foreach ($sampleRcBtContent as $contentElement) {
|
||||||
|
$bedType = null;
|
||||||
|
if (count($bedTypeList) > $contentElement->bedType) {
|
||||||
|
$bedType = $bedTypeList[$contentElement->bedType];
|
||||||
|
}
|
||||||
|
|
||||||
|
$roomCategory = null;
|
||||||
|
if (count($roomCategoryList) > $contentElement->roomCategory) {
|
||||||
|
$roomCategory = $roomCategoryList[$contentElement->roomCategory];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!$roomCategory || !$bedType) {
|
||||||
|
$this->logger->error(
|
||||||
|
"Invalid RoomCategoryBedType: RoomCategory or BedType not found!",
|
||||||
|
["json" => $contentElement, "bedtype" => $bedType, "roomcategory" => $roomCategory]
|
||||||
|
);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
$item = new RoomCategoryBedType();
|
||||||
|
$item->setAmount($contentElement->amount);
|
||||||
|
$item->setBedType($bedType);
|
||||||
|
$item->setRoomCategory($roomCategory);
|
||||||
|
|
||||||
|
$this->entityManager->persist($item);
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->entityManager->flush();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#region Generate Ramdom Data
|
||||||
|
|
||||||
private function GenerateAvailability(ExampleDataConfig $config): bool
|
private function GenerateAvailability(ExampleDataConfig $config): bool
|
||||||
{
|
{
|
||||||
$roomCategoryList = $this->roomCategoryRepository->findAll();
|
$roomCategoryList = $this->roomCategoryRepository->findAll();
|
||||||
@@ -126,4 +198,51 @@ class ExampleDataService
|
|||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region Load Sample Data
|
||||||
|
|
||||||
|
//TODO
|
||||||
|
|
||||||
|
#endregion
|
||||||
|
|
||||||
|
#region Utils
|
||||||
|
|
||||||
|
private function DeserializeSampleFile(string $fileName, string $class)
|
||||||
|
{
|
||||||
|
$data = $this->GetFileData($fileName);
|
||||||
|
if (!$data) return;
|
||||||
|
|
||||||
|
$itemList = $this->sampleSerializer->deserialize($data, $class, "json");
|
||||||
|
|
||||||
|
return $itemList;
|
||||||
|
}
|
||||||
|
|
||||||
|
private function GetFileData(string $fileName): string|null
|
||||||
|
{
|
||||||
|
$file = $this->fileLocator->locate($fileName, null);
|
||||||
|
$data = file_get_contents($file);
|
||||||
|
if (!$data) {
|
||||||
|
$this->logger->error(
|
||||||
|
"ExampleDataService - DeserializeSampleFile - Unable to get file contents.",
|
||||||
|
["file" => $fileName, "fileData" => $data]
|
||||||
|
);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return $data;
|
||||||
|
}
|
||||||
|
|
||||||
|
private function PersistEntityArray(array $itemList): void
|
||||||
|
{
|
||||||
|
foreach ($itemList as $item) {
|
||||||
|
try {
|
||||||
|
$this->entityManager->persist($item);
|
||||||
|
} catch (\Throwable $th) {
|
||||||
|
$this->logger->error("Item can't be persisted", ["item" => $item, "exception" => $th]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user