Skip to content

Commit e3cc8bf

Browse files
[PHP-70] Support for setting the user's address and date of birth (#46)
* [PHP-70] Support for setting the user's address and date of birth * [PHP-70] Strict types * [PHP-70] Simplify the address setter * [PHP-70] PHPStan errors * [PHP-70] Add PHP 8.2 and 8.3 to the code quality check matrix * Revert "[PHP-70] Add PHP 8.2 and 8.3 to the code quality check matrix" This reverts commit 55032c1. * [PHP-70] Make address fields optional and fix tests method * [PHP-70] Fix tests * [PHP-70] User address's State should be optional * [PHP-70] Update readme for user address and dob support * [PHP-70] Update changelog with the new version changes
1 parent aadd792 commit e3cc8bf

13 files changed

+615
-13
lines changed

CHANGELOG.md

+7
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,13 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres
66
to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
## [1.6.0] - 2024-02-09
9+
10+
### Added
11+
12+
- Support for setting the user's address using `$client->user()->address()`
13+
- Support for setting the user's date of birth using `$client->user()->dateOfBirth()`
14+
815
## [1.5.0] - 2024-01-12
916

1017
### Added

README.md

+15-1
Original file line numberDiff line numberDiff line change
@@ -207,7 +207,21 @@ $beneficiary = $client->beneficiary()->externalAccount()
207207
$user = $client->user()
208208
->name('Jane Doe')
209209
->phone('+44123456789')
210-
->email('[email protected]');
210+
->email('[email protected]')
211+
->dateOfBirth('2024-01-01');
212+
```
213+
214+
You are also able to set the user's address:
215+
216+
```php
217+
$address = $client->user()
218+
->address()
219+
->addressLine1('The Gilbert')
220+
->addressLine2('City of')
221+
->city('London')
222+
->state('London')
223+
->zip('EC2A 1PX')
224+
->countryCode('GB');
211225
```
212226

213227
<a name="creating-a-payment-method"></a>

config/bindings.php

+3-2
Original file line numberDiff line numberDiff line change
@@ -3,13 +3,14 @@
33
declare(strict_types=1);
44

55
use TrueLayer\Entities;
6-
use TrueLayer\Entities\User;
76
use TrueLayer\Interfaces;
87

98
return [
10-
Interfaces\UserInterface::class => User::class,
119
Interfaces\HppInterface::class => 'makeHpp',
1210

11+
Interfaces\AddressInterface::class => Entities\Address::class,
12+
Interfaces\UserInterface::class => Entities\User::class,
13+
1314
Interfaces\Beneficiary\BeneficiaryBuilderInterface::class => Entities\Beneficiary\BeneficiaryBuilder::class,
1415
Interfaces\Beneficiary\MerchantBeneficiaryInterface::class => Entities\Beneficiary\MerchantBeneficiary::class,
1516
Interfaces\Beneficiary\ExternalAccountBeneficiaryInterface::class => Entities\Beneficiary\ExternalAccountBeneficiary::class,

src/Entities/Address.php

+184
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,184 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace TrueLayer\Entities;
6+
7+
use TrueLayer\Interfaces\AddressInterface;
8+
9+
class Address extends Entity implements AddressInterface
10+
{
11+
/**
12+
* @var string
13+
*/
14+
protected string $addressLine1;
15+
16+
/**
17+
* @var string
18+
*/
19+
protected string $addressLine2;
20+
21+
/**
22+
* @var string
23+
*/
24+
protected string $city;
25+
26+
/**
27+
* @var string
28+
*/
29+
protected string $state;
30+
31+
/**
32+
* @var string
33+
*/
34+
protected string $zip;
35+
36+
/**
37+
* @var string
38+
*/
39+
protected string $countryCode;
40+
41+
/**
42+
* @var string[]
43+
*/
44+
protected array $arrayFields = [
45+
'address_line1',
46+
'address_line2',
47+
'city',
48+
'state',
49+
'zip',
50+
'country_code',
51+
];
52+
53+
/**
54+
* @var string[]
55+
*/
56+
protected array $rules = [
57+
'address_line1' => 'string|required',
58+
'address_line2' => 'string|nullable',
59+
'city' => 'string|required',
60+
'state' => 'string|nullable',
61+
'zip' => 'string|required',
62+
'country_code' => 'string|required',
63+
];
64+
65+
/**
66+
* @return string|null
67+
*/
68+
public function getAddressLine1(): ?string
69+
{
70+
return $this->addressLine1 ?? null;
71+
}
72+
73+
/**
74+
* @param string $addressLine1
75+
*
76+
* @return AddressInterface
77+
*/
78+
public function addressLine1(string $addressLine1): AddressInterface
79+
{
80+
$this->addressLine1 = $addressLine1;
81+
82+
return $this;
83+
}
84+
85+
/**
86+
* @return string|null
87+
*/
88+
public function getAddressLine2(): ?string
89+
{
90+
return $this->addressLine2 ?? null;
91+
}
92+
93+
/**
94+
* @param string $addressLine2
95+
*
96+
* @return AddressInterface
97+
*/
98+
public function addressLine2(string $addressLine2): AddressInterface
99+
{
100+
$this->addressLine2 = $addressLine2;
101+
102+
return $this;
103+
}
104+
105+
/**
106+
* @return string|null
107+
*/
108+
public function getCity(): ?string
109+
{
110+
return $this->city ?? null;
111+
}
112+
113+
/**
114+
* @param string $city
115+
*
116+
* @return AddressInterface
117+
*/
118+
public function city(string $city): AddressInterface
119+
{
120+
$this->city = $city;
121+
122+
return $this;
123+
}
124+
125+
/**
126+
* @return string|null
127+
*/
128+
public function getState(): ?string
129+
{
130+
return $this->state ?? null;
131+
}
132+
133+
/**
134+
* @param string $state
135+
*
136+
* @return AddressInterface
137+
*/
138+
public function state(string $state): AddressInterface
139+
{
140+
$this->state = $state;
141+
142+
return $this;
143+
}
144+
145+
/**
146+
* @return string|null
147+
*/
148+
public function getZip(): ?string
149+
{
150+
return $this->zip ?? null;
151+
}
152+
153+
/**
154+
* @param string $zip
155+
*
156+
* @return AddressInterface
157+
*/
158+
public function zip(string $zip): AddressInterface
159+
{
160+
$this->zip = $zip;
161+
162+
return $this;
163+
}
164+
165+
/**
166+
* @return string|null
167+
*/
168+
public function getCountryCode(): ?string
169+
{
170+
return $this->countryCode ?? null;
171+
}
172+
173+
/**
174+
* @param string $countryCode
175+
*
176+
* @return AddressInterface
177+
*/
178+
public function countryCode(string $countryCode): AddressInterface
179+
{
180+
$this->countryCode = $countryCode;
181+
182+
return $this;
183+
}
184+
}

src/Entities/Entity.php

+1-1
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ abstract class Entity implements ArrayableInterface, HasAttributesInterface
2323
/**
2424
* @var EntityFactoryInterface
2525
*/
26-
private EntityFactoryInterface $entityFactory;
26+
protected EntityFactoryInterface $entityFactory;
2727

2828
/**
2929
* @param ValidatorFactory $validatorFactory

src/Entities/User.php

+76-5
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,11 @@
44

55
namespace TrueLayer\Entities;
66

7+
use TrueLayer\Exceptions\InvalidArgumentException;
8+
use TrueLayer\Exceptions\ValidationException;
9+
use TrueLayer\Interfaces\AddressInterface;
710
use TrueLayer\Interfaces\UserInterface;
11+
use TrueLayer\Validation\ValidType;
812

913
final class User extends Entity implements UserInterface
1014
{
@@ -28,6 +32,16 @@ final class User extends Entity implements UserInterface
2832
*/
2933
protected string $phone;
3034

35+
/**
36+
* @var AddressInterface
37+
*/
38+
protected AddressInterface $address;
39+
40+
/**
41+
* @var string
42+
*/
43+
protected string $dateOfBirth;
44+
3145
/**
3246
* @var string[]
3347
*/
@@ -36,18 +50,32 @@ final class User extends Entity implements UserInterface
3650
'name',
3751
'email',
3852
'phone',
53+
'address',
54+
'date_of_birth',
3955
];
4056

4157
/**
4258
* @var string[]
4359
*/
44-
protected array $rules = [
45-
'id' => 'string|nullable',
46-
'name' => 'string|nullable|required_without:id',
47-
'email' => 'string|nullable|email|required_without_all:phone,id',
48-
'phone' => 'string|nullable|required_without_all:email,id',
60+
protected array $casts = [
61+
'address' => AddressInterface::class,
4962
];
5063

64+
/**
65+
* @return mixed[]
66+
*/
67+
protected function rules(): array
68+
{
69+
return [
70+
'id' => 'string|nullable',
71+
'name' => 'string|nullable|required_without:id',
72+
'email' => 'string|nullable|email|required_without_all:phone,id',
73+
'phone' => 'string|nullable|required_without_all:email,id',
74+
'address' => ['nullable', ValidType::of(AddressInterface::class)],
75+
'date_of_birth' => 'string|nullable|date',
76+
];
77+
}
78+
5179
/**
5280
* @return string|null
5381
*/
@@ -127,4 +155,47 @@ public function phone(string $phone): UserInterface
127155

128156
return $this;
129157
}
158+
159+
/**
160+
* @return AddressInterface|null
161+
*/
162+
public function getAddress(): ?AddressInterface
163+
{
164+
return $this->address ?? null;
165+
}
166+
167+
/**
168+
* @param AddressInterface|null $address
169+
*
170+
* @throws ValidationException
171+
* @throws InvalidArgumentException
172+
*
173+
* @return AddressInterface
174+
*/
175+
public function address(?AddressInterface $address = null): AddressInterface
176+
{
177+
$this->address = $address ?: $this->entityFactory->make(AddressInterface::class);
178+
179+
return $this->address;
180+
}
181+
182+
/**
183+
* @return string|null
184+
*/
185+
public function getDateOfBirth(): ?string
186+
{
187+
return $this->dateOfBirth ?? null;
188+
}
189+
190+
/**
191+
* @param string $dateOfBirth
192+
*
193+
* @return UserInterface
194+
*/
195+
public function dateOfBirth(string $dateOfBirth): UserInterface
196+
{
197+
$this->dateOfBirth = $dateOfBirth;
198+
199+
return $this;
200+
}
130201
}

0 commit comments

Comments
 (0)