Skip to content

Commit

Permalink
Merge branch '4.x' into 6708-contacts-sort-not-selected-right-value-f…
Browse files Browse the repository at this point in the history
…irst-time
  • Loading branch information
asbiin authored Nov 1, 2023
2 parents 4d50a33 + 0f636e4 commit b30f950
Show file tree
Hide file tree
Showing 16 changed files with 212 additions and 48 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -250,7 +250,7 @@ jobs:

# Test
- name: Upgrade Chrome Driver
run: php artisan dusk:chrome-driver $(google-chrome -version | awk '{ print $3 }' | cut -d . -f 1)
run: php artisan dusk:chrome-driver --detect
- name: Start Chrome Driver
run: |
chmod -R 0755 vendor/laravel/dusk/bin/
Expand Down
134 changes: 134 additions & 0 deletions app/Console/Commands/ImportAccounts.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
<?php

namespace App\Console\Commands;

use App\Models\Account\Account;
use Illuminate\Console\Command;

class ImportAccounts extends Command
{
/**
* The name and signature of the console command.
*
* @var string
*/
protected $signature = 'account:import_ldap
{--ldap_uri= : LDAP URI.}
{--ldap_user= : LDAP Bind DN.}
{--ldap_pass= : LDAP Bind Password.}
{--ldap_base= : LDAP base DN for searching.}
{--ldap_filter= : Filter to search for user accounts.}
{--ldap_attr_mail= : LDAP attribute to map to email (default: mail).}
{--ldap_attr_firstname= : LDAP attribute to map to firstname (default: gn).}
{--ldap_attr_lastname= : LDAP attribute to map to lastname (default: sn).}';

/**
* The console command description.
*
* @var string
*/
protected $description = 'Import user accounts from LDAP';

/**
* Missing argument errors. Exposed for testing.
*/
const ERROR_MISSING_LDAP_FILTER = '! You must specify an LDAP Filter';
const ERROR_MISSING_LDAP_BASE = '! You must specify an LDAP Base';
const ERROR_MISSING_LDAP_USER = '! You must specify an LDAP User';
const ERROR_MISSING_LDAP_PASS = '! You must specify an LDAP Password';

/**
* Execute the console command.
*
* @return mixed
*/
public function handle()
{
$ldap_uri = $this->option('ldap_uri') ?? '127.0.0.1';
$ldap_attr_mail = $this->option('ldap_attr_mail') ?? 'mail';
$ldap_attr_firstname = $this->option('ldap_attr_firstname') ?? 'givenName';
$ldap_attr_lastname = $this->option('ldap_attr_lastname') ?? 'sn';

$ldap_user = $this->option('ldap_user');
if (empty($ldap_user)) {
$this->error($this::ERROR_MISSING_LDAP_USER);
}

$ldap_pass = $this->option('ldap_pass');
if (empty($ldap_pass)) {
$this->error($this::ERROR_MISSING_LDAP_PASS);
}

$ldap_base = $this->option('ldap_base');
if (empty($ldap_base)) {
$this->error($this::ERROR_MISSING_LDAP_BASE);
}

$ldap_filter = $this->option('ldap_filter');
if (empty($ldap_filter)) {
$this->error($this::ERROR_MISSING_LDAP_FILTER);
}

if (empty($ldap_user) || empty($ldap_pass) || empty($ldap_base) || empty($ldap_filter)) {
return;
}

$ldap_conn = ldap_connect($ldap_uri);
if (! $ldap_conn) {
$this->error('Could not connect to LDAP URI');

return;
}
if (! ldap_set_option($ldap_conn, LDAP_OPT_PROTOCOL_VERSION, 3)) {
$this->error('Could not set LDAP protocol v3');

return false;
}

try {
$bind = ldap_bind($ldap_conn, $ldap_user, $ldap_pass);
if (! $bind) {
$this->error('Could not bind with given LDAP credentials');

return;
}
} catch (\Exception $e) {
$this->error($e->getMessage());

return;
}

$ldap_res = [];
try {
$ldap_res = ldap_search($ldap_conn, $ldap_base, $ldap_filter, [$ldap_attr_mail, $ldap_attr_firstname, $ldap_attr_lastname]);
} catch (\Exception $e) {
$this->error($e->getMessage());

return;
}

$ldap_data = ldap_get_entries($ldap_conn, $ldap_res);

for ($i = 0; $i < $ldap_data['count']; $i++) {
if (! (isset($ldap_data[$i][$ldap_attr_mail]) && $ldap_data[$i][$ldap_attr_mail]['count'] > 0)) {
continue;
}
$user_mail = $ldap_data[$i][$ldap_attr_mail][0];
$user_firstname = 'John';
$user_lastname = 'Doe';
$user_password = bin2hex(random_bytes(64));
if (isset($ldap_data[$i][$ldap_attr_firstname]) && $ldap_data[$i][$ldap_attr_firstname]['count'] > 0) {
$user_firstname = $ldap_data[$i][$ldap_attr_firstname][0];
}
if (isset($ldap_data[$i][$ldap_attr_lastname]) && $ldap_data[$i][$ldap_attr_lastname]['count'] > 0) {
$user_lastname = $ldap_data[$i][$ldap_attr_lastname][0];
}
$this->info('Importing user "'.$user_mail.'"');
try {
Account::createDefault($user_firstname, $user_lastname, $user_mail, $user_password);
} catch (\Exception $import_error) {
$this->warn('Could not import user "'.$user_mail.'": '.$import_error->getMessage());
}
}
}
}
2 changes: 1 addition & 1 deletion app/Helpers/CountriesHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,6 @@ public static function getDefaultTimezone($country): string
break;
}

return $timezone;
return $timezone ?? config('app.timezone');
}
}
5 changes: 4 additions & 1 deletion app/Http/Controllers/ContactsController.php
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,8 @@ private function contacts(Request $request, bool $active)
}

$tagsCount = Tag::contactsCount();
$contactsWithoutTagsCount = (clone $contacts)->doesntHave('tags')->count();

$tags = null;
$url = null;
$count = 1;
Expand Down Expand Up @@ -135,7 +137,8 @@ private function contacts(Request $request, bool $active)
->withTagsCount($tagsCount)
->withUrl($url)
->withTagCount($count)
->withTagLess($request->input('no_tag') ?? false);
->withTagLess($request->input('no_tag') ?? false)
->with('contactsWithoutTagsCount', $contactsWithoutTagsCount);
}

/**
Expand Down
4 changes: 3 additions & 1 deletion app/Http/Controllers/SettingsController.php
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,9 @@ public function index()
if (auth()->user()->me_contact_id) {
$meContact = Contact::where('account_id', auth()->user()->account_id)
->find(auth()->user()->me_contact_id);
$existingContacts->prepend($meContact);
if ($meContact) {
$existingContacts->prepend($meContact);
}
}

$accountHasLimitations = AccountHelper::hasLimitations(auth()->user()->account);
Expand Down
2 changes: 1 addition & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@
"barryvdh/laravel-debugbar": "^3",
"fakerphp/faker": "^1.10",
"khanamiryan/qrcode-detector-decoder": "^2.0",
"laravel/dusk": "^7.0",
"laravel/dusk": "^7.11",
"laravel/legacy-factories": "^1.0",
"laravel/tinker": "^2.6",
"matthiasnoback/live-code-coverage": "^1",
Expand Down
21 changes: 12 additions & 9 deletions composer.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion config/mail.php
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@
'encryption' => env('MAIL_ENCRYPTION', 'tls'),
'username' => env('MAIL_USERNAME'),
'password' => env('MAIL_PASSWORD'),
'verify_peer' => env('MAIL_VERIFY_PEER', true),
],

'ses' => [
Expand All @@ -57,7 +58,7 @@

'sendmail' => [
'transport' => 'sendmail',
'path' => '/usr/sbin/sendmail -bs',
'path' => env('MAIL_SENDMAIL_PATH', '/usr/sbin/sendmail -bs -i'),
],

'log' => [
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,11 @@ class RemoveViewedAtFromContacts extends Migration
*/
public function up()
{
Schema::table('contacts', function (Blueprint $table) {
$table->dropColumn(
'viewed_at'
);
});
if (Schema::hasColumn('contacts', 'viewed_at')) {
Schema::table('contacts', function (Blueprint $table) {
$table->dropColumn('viewed_at');
});
}
}

/**
Expand All @@ -27,8 +27,10 @@ public function up()
*/
public function down()
{
Schema::table('contacts', function (Blueprint $table) {
$table->dateTime('viewed_at')->nullable();
});
if (! Schema::hasColumn('contacts', 'viewed_at')) {
Schema::table('contacts', function (Blueprint $table) {
$table->dateTime('viewed_at')->nullable();
});
}
}
}
42 changes: 27 additions & 15 deletions docs/installation/providers/ubuntu.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

<img alt="Ubuntu" src="https://upload.wikimedia.org/wikipedia/commons/thumb/a/ab/Logo-ubuntu_cof-orange-hex.svg/120px-Logo-ubuntu_cof-orange-hex.svg.png" width="120" height="120" />

Monica can run on [Ubuntu 18.04 (Bionic Beaver)](http://releases.ubuntu.com/18.04/).
Monica can run on [Ubuntu 22.04 (Jammy Jellyfish)](http://releases.ubuntu.com/22.04/).

- [Prerequisites](#prerequisites)
- [Types of databases](#types-of-databases)
Expand Down Expand Up @@ -35,6 +35,13 @@ sudo apt update
sudo apt install -y git
```

**Unzip:** Unzip is required but was not installed by default. Install it with:

```sh
sudo apt update
sudo apt install -y unzip
```

**Apache:** Apache should come pre-installed with your server. If it's not, install it with:

```sh
Expand All @@ -55,9 +62,7 @@ Then install php 8.1 with these extensions:

```sh
sudo apt update
sudo apt install -y php8.1 php8.1-bcmath php8.1-cli php8.1-curl php8.1-common \
php8.1-fpm php8.1-gd php8.1-gmp php8.1-intl php-json php8.1-mbstring \
php8.1-mysql php8.1-opcache php8.1-redis php8.1-xml php8.1-zip
sudo apt install -y php8.1-{bcmath,cli,curl,common,fpm,gd,gmp,intl,mbstring,mysql,opcache,redis,xml,zip}
```

**Composer:** After you're done installing PHP, you'll need the [Composer](https://getcomposer.org/download/) dependency manager.
Expand All @@ -74,7 +79,7 @@ rm -f composer-setup.php
**Node.js:** Install node.js with package manager.

```sh
curl -fsSL https://deb.nodesource.com/setup_16.x | sudo -E bash -
curl -fsSL https://deb.nodesource.com/setup_18.x | sudo -E bash -
sudo apt install -y nodejs
```

Expand Down Expand Up @@ -115,7 +120,7 @@ cd /var/www/monica
# Get latest tags from GitHub
git fetch
# Clone the desired version
git checkout tags/v2.18.0
git checkout tags/v4.0.0
```

### 2. Setup the database
Expand Down Expand Up @@ -157,16 +162,23 @@ exit

1. `cp .env.example .env` to create your own version of all the environment variables needed for the project to work.
2. Update `.env` to your specific needs
- set `DB_USERNAME` and `DB_PASSWORD` with the settings used behind.
- Update database information.
```diff
- DB_USERNAME=homestead
- DB_PASSWORD=secret
+ DB_USERNAME=monica
# Use the password you created.
+ DB_PASSWORD=strongpassword
```
- configure a [mailserver](/docs/installation/mail.md) for registration & reminders to work correctly.
- set the `APP_ENV` variable to `production`, `local` is only used for the development version. Beware: setting `APP_ENV` to `production` will force HTTPS. Skip this if you're running Monica locally.
3. Run `composer install --no-interaction --no-dev` to install all packages.
4. Run `yarn install` to install frontend packages, then `yarn run production` to build the assets (js, css).
5. Run `php artisan key:generate` to generate an application key. This will set `APP_KEY` with the right value automatically.
6. Run `php artisan setup:production -v` to run the migrations, seed the database and symlink folders.
4. Run `composer install --no-interaction --no-dev` to install all packages.
5. Run `yarn install` to install frontend packages, then `yarn run production` to build the assets (js, css).
6. Run `php artisan key:generate` to generate an application key. This will set `APP_KEY` with the right value automatically.
7. Run `php artisan setup:production -v` to run the migrations, seed the database and symlink folders.
- You can use `email` and `password` parameter to setup a first account directly: `php artisan setup:production [email protected] --password=yourpassword -v`
7. _Optional_: Setup the queues with Redis, Beanstalk or Amazon SQS: see optional instruction of [generic installation](generic.md#setup-queues)
8. _Optional_: Setup the access tokens to use the API follow optional instruction of [generic installation](generic.md#setup-access-tokens)
8. _Optional_: Setup the queues with Redis, Beanstalk or Amazon SQS: see optional instruction of [generic installation](generic.md#setup-queues)
9. _Optional_: Setup the access tokens to use the API follow optional instruction of [generic installation](generic.md#setup-access-tokens)

### 4. Configure cron job

Expand Down Expand Up @@ -207,11 +219,11 @@ sudo a2enmod rewrite
sudo nano /etc/apache2/sites-available/monica.conf
```

Then, in the `nano` text editor window you just opened, copy the following - swapping the `**YOUR IP ADDRESS/DOMAIN**` with your server's IP address/associated domain:
Then, in the `nano` text editor window you just opened, copy the following - swapping the `monica.example.com` with your server's IP address/associated domain:

```html
<VirtualHost *:80>
ServerName **YOUR IP ADDRESS/DOMAIN**
ServerName monica.example.com

ServerAdmin webmaster@localhost
DocumentRoot /var/www/monica/public
Expand Down
Loading

0 comments on commit b30f950

Please sign in to comment.