# Drupal with DDEV Setup for Local Machine

This repository provides a local development setup for **Drupal 10** using **DDEV** and **Docker**.
DDEV is a container-based local development environment built on Docker, specifically designed for web development, and it makes setting up Drupal super quick and easy.

## Prerequisites

Before you begin, ensure that you have the following installed on your machine:

- **Docker**: [Download Docker](https://www.docker.com/products/docker-desktop)
- **DDEV**: [Install DDEV](https://ddev.com/get-started/)
- **Git** (for version control)
- **PHP** and **Composer** (optional for managing dependencies)

## Getting Started

Follow these steps to set up Drupal 10 with ddev:

### 1. Clone the Repository

If you haven't already cloned the repository, run the following command to get the project:

```bash
git clone <repository-url>
cd <project-directory>
```

### 2. Initialize DDEV

```bash
ddev config --project-type=drupal10 --docroot=web --create-docroot
```

### 3. Start the DDEV environment

```bash
ddev start
```

### 4. Install Dependencies with Composer

```bash
ddev composer install
```

### 5. Import Database or Install Drupal

```bash
ddev import-db --src=path/to/your-database.sql.gz
```

### 6. Import Database or Install Drupal

```bash
ddev drush cr
```

Once DDEV is running, visit your site at:
https://<project-name>.ddev.site

## Environment configuration

Copy `.env.example` to `.env` and update the values for your environment. These variables configure Drupal and the supporting services.

| Variable                         | Description                                            |
| -------------------------------- | ------------------------------------------------------ |
| `APP_ENV`                        | Application environment (`local`, `dev`, `prod`, etc.) |
| `DRUPAL_HASH_SALT`               | Unique hash salt for Drupal.                           |
| `DB_HOST`                        | Database host.                                         |
| `DB_PORT`                        | Database port.                                         |
| `DB_NAME`                        | Database name.                                         |
| `DB_USER`                        | Database user.                                         |
| `DB_PASSWORD`                    | Database password.                                     |
| `REDIS_HOST`                     | Redis host.                                            |
| `REDIS_PORT`                     | Redis port.                                            |
| `REDIS_PASSWORD`                 | Redis password if required.                            |
| `SENDGRID_API_KEY`               | API key for SendGrid.                                  |
| `SENDGRID_SMTP_USER`             | SMTP username for SendGrid.                            |
| `SENDGRID_SMTP_PASS`             | SMTP password for SendGrid.                            |
| `FIREBASE_AUTH_TOKEN`            | Authentication token used when querying Firebase.      |
| `GOOGLE_APPLICATION_CREDENTIALS` | Path to the Google service account JSON file.          |
| `GOOGLE_PROJECT_ID`              | Google Cloud project used for BigQuery.                |
| `BIGQUERY_DATASET`               | BigQuery dataset ID.                                   |
| `BIGQUERY_TABLE`                 | BigQuery table ID.                                     |
| `PANTHEON_ENVIRONMENT`           | Current Pantheon environment identifier.               |

Load these variables in your local `settings.php` or through your hosting provider's configuration to ensure Drupal can access the required services.

## Running Tests

Drupal uses PHPUnit for testing. The project includes both unit and functional tests. Here's how to run and configure tests:

### Prerequisites

1. Ensure all dependencies are installed:

```bash
ddev composer install
```

2. Create and set permissions for the browser output directory:

```bash
ddev exec mkdir -p /tmp/browser_output
ddev exec chmod 777 /tmp/browser_output
```

### Test Configuration

The project uses `phpunit.xml` for test configuration. Key settings include:

```xml
<php>
  <env name="SIMPLETEST_BASE_URL" value="http://cstv.ddev.site"/>
  <env name="SIMPLETEST_DB" value="mysql://db:db@db/db"/>
  <env name="BROWSERTEST_OUTPUT_DIRECTORY" value="/tmp/browser_output"/>
</php>
```

### Running Tests

1. **Run all tests:**

```bash
ddev exec ./vendor/bin/phpunit -c /var/www/html/phpunit.xml
```

2. **Run specific test class:**

```bash
ddev exec ./vendor/bin/phpunit -c /var/www/html/phpunit.xml web/modules/custom/cstv_main/tests/src/Functional/SendLocationDataControllerTest.php
```

3. **Run specific test method:**

```bash
ddev exec ./vendor/bin/phpunit -c /var/www/html/phpunit.xml --filter testViewsGet web/modules/custom/cstv_main/tests/src/Functional/SendLocationDataControllerTest.php
```

### Test Types

1. **Unit Tests** (`tests/src/Unit/`)

   - Test individual functions and classes
   - Fast execution
   - No database or browser required
   - Located in `tests/src/Unit/`

2. **Functional Tests** (`tests/src/Functional/`)

   - Test complete features
   - Use a real browser
   - Require database
   - Located in `tests/src/Functional/`

3. **Kernel Tests** (`tests/src/Kernel/`)
   - Test services and integration
   - Use a minimal Drupal environment
   - Located in `tests/src/Kernel/`

### Writing Tests

1. **Test Class Structure:**

```php
namespace Drupal\Tests\your_module\Functional;

use Drupal\Tests\BrowserTestBase;

class YourTest extends BrowserTestBase {
  protected static $modules = ['your_module', 'required_module'];
  protected $defaultTheme = 'stark';

  public function testSomething() {
    // Test code here
  }
}
```

2. **Common Assertions:**

```php
$this->assertSession()->statusCodeEquals(200);
$this->assertSession()->pageTextContains('Expected text');
$this->assertEquals($expected, $actual);
```

## Cron Jobs

This Drupal installation uses the Ultimate Cron module to manage scheduled tasks. The table below lists each job, its purpose, schedule, and whether it is enabled.

| ID                                  | Description                                          | Schedule                | Enabled |
| ----------------------------------- | ---------------------------------------------------- | ----------------------- | ------- |
| comment_cron                        | Store the maximum possible comments per thread       | Every 3 hours (default) | true    |
| cstv_main_cron                      | Device version/last seen updates                     | Every 3 hours           | false   |
| dblog_cron                          | Remove expired log messages and flood control events | Every 3 hours (default) | true    |
| feeds_cron                          | Default cron handler                                 | Hourly                  | true    |
| feeds_log_cron                      | Default cron handler                                 | Hourly                  | true    |
| field_cron                          | Purges deleted Field API data                        | Every 3 hours (default) | true    |
| file_cron                           | Deletes temporary files                              | Every 3 hours (default) | true    |
| history_cron                        | Deletes history                                      | Every 3 hours (default) | true    |
| managers_playlist_slide_delete_cron | Managers Playlist Slide delete                       | Every 15 minutes        | true    |
| node_cron                           | Updates search rankings for nodes                    | Every 3 hours           | true    |
| services_count_cron                 | Services count                                       | Daily at midnight       | true    |
| slide_scheduling_cron               | Slide Scheduling                                     | Every 15 minutes        | true    |
| smartads_playlists_cron_cron        | Smart Ads Playlists                                  | Every 3 hours           | true    |
| system_cron                         | Cleanup (caches, batch, flood, temp-files, etc.)     | Every 3 hours (default) | true    |
| ultimate_cron_cron                  | Runs internal cleanup operations                     | Every 3 hours (default) | true    |
| update_cron                         | Check for updates                                    | Hourly                  | true    |

## Custom Drupal Modules

The repository includes several custom modules located in `web/modules/custom`. The following table lists each module and its purpose.

| Module                           | Description                                                                                                 |
| -------------------------------- | ----------------------------------------------------------------------------------------------------------- |
| better_exposed_filters           | Provides advanced options (e.g. links, checkboxes, or other widgets) to exposed Views elements.             |
| color                            | Pulls Media Asset type for all image and video medias.                                                      |
| cstv_advertisement               | Provides cstv advertisement customisation for global updates.                                               |
| cstv_main                        | Provides cstv main module for global changes.                                                               |
| cstv_migration                   | Contains custom logic for migration.                                                                        |
| custom_node_delete_modal         | Provides a modal confirmation for node deletion without redirecting.                                        |
| location_user_cron               | Provides details on whether a location has User or not.                                                     |
| managers_playlist_slide_delete   | Deletes slide from the Managers Playlist once the field_slide_unix_end_time has passed.                     |
| media_asset_type                 | Pulls Media Asset type for all image and video medias.                                                      |
| media_updates                    | Pulls Media type, ownership and orientation for all Non-admin uploaded medias.                              |
| product_cache                    | Provides capabilities to cache Products data for all required locations.                                    |
| selective_better_exposed_filters | Provide extra option for better exposed filters to show only used terms in filter.                          |
| services_count                   | Provides services count to Store location content type for individual Locations.                            |
| slide_scheduling                 | Deletes scheduled slides which are no longer required in the system.                                        |
| smart_ad_advertisers             | Provides Smart Ad Advertisement.                                                                            |
| smartads_playlists_cron          | Pulls the Smart Ads Playlists on cron run and sets it to its location on field `field_smart_ads_playlists`. |
| swiftmailer                      | Pulls Media Asset type for all image and video medias.                                                      |
| we_megamenu                      | This powerful Drupal module helps you create custom menu, video and Drupal Blocks.                          |

## Custom JSON Endpoints

The custom modules expose several routes that return JSON data. These endpoints live under `web/modules/custom` and can be used by external integrations.

| Path                              | Method   | Description                                                                                |
| --------------------------------- | -------- | ------------------------------------------------------------------------------------------ |
| `/services/json`                  | **POST** | Returns view data or session details depending on the `method` and `view_name` parameters. |
| `/location-ratio-set`             | **POST** | Updates location ratio fields based on `locid`, `pro`, `soc` and `ent` values.             |
| `/slide-ratio-set`                | **POST** | Sets the slide ratio for a slide using `nid` and `ratio` parameters.                       |
| `/send-reminder/{node}`           | **GET**  | Records a reminder for the specified node and returns a success flag.                      |
| `/update-folder-ownership`        | **POST** | Assigns or removes a location from a folder term.                                          |
| `/update-folder-ownership-bulk`   | **POST** | Performs bulk updates on folder ownership.                                                 |
| `/node/{node}/delete/ajax`        | **GET**  | Deletes a node via AJAX and responds with a status message.                                |
| `/services/advertise-data`        | **GET**  | Provides advertiser and campaign data.                                                     |
| `/product-offer/sku-data/{skuId}` | **GET**  | Returns detailed information about a SKU.                                                  |
| `/product-offer/forecast-data`    | **GET**  | Retrieves forecast counts from the external service.                                       |
| `/product-offer/forecast-details` | **GET**  | Fetches extended forecast details from the external service.                               |


## Services

The `./services` directory contains custom configs and overrides for php, apache, and any other services that run on the VM.

```bash
services
├── <service-name>
│   ├── file/path/1.conf
│   └── file/path/2.conf
```

Where `file/path/1.conf` corresponds **directly** to the path to which the file exists on the deployment server, in this case `/file/path/1.conf`. Any and all custom service configurations or overrides **must** be placed in this directory. 

To load the service configurations and overrides, run the `./scripts/services.sh` script.

## This code is only for testing purpose
Test file deployment for CI testing