@@ -37,267 +37,267 @@ |
||
37 | 37 | */ |
38 | 38 | abstract class TypeBase implements TypeInterface |
39 | 39 | { |
40 | - /** |
|
41 | - * The graphql namespace/prefix. |
|
42 | - */ |
|
43 | - protected string $namespace = 'Espresso'; |
|
44 | - |
|
45 | - protected ?EEM_Base $model = null; |
|
46 | - |
|
47 | - protected string $name = ''; |
|
48 | - |
|
49 | - protected string $description = ''; |
|
50 | - |
|
51 | - /** |
|
52 | - * @var GraphQLFieldInterface[] $fields |
|
53 | - */ |
|
54 | - protected array $fields = []; |
|
55 | - |
|
56 | - /** |
|
57 | - * @var GraphQLInterfaceInterface[] $interfaces |
|
58 | - */ |
|
59 | - protected array $interfaces = []; |
|
60 | - |
|
61 | - protected FieldResolver $field_resolver; |
|
62 | - |
|
63 | - protected bool $is_custom_post_type = false; |
|
64 | - |
|
65 | - |
|
66 | - /** |
|
67 | - * TypeBase constructor. |
|
68 | - * |
|
69 | - * @param EEM_Base|null $model |
|
70 | - */ |
|
71 | - public function __construct(EEM_Base $model = null) |
|
72 | - { |
|
73 | - $this->model = $model; |
|
74 | - $this->setFields($this->getFields()); |
|
75 | - $this->field_resolver = new FieldResolver( |
|
76 | - $this->model, |
|
77 | - $this->getFieldsForResolver() |
|
78 | - ); |
|
79 | - } |
|
80 | - |
|
81 | - |
|
82 | - /** |
|
83 | - * @return GraphQLFieldInterface[] |
|
84 | - * @since 5.0.0.p |
|
85 | - */ |
|
86 | - abstract protected function getFields(): array; |
|
87 | - |
|
88 | - |
|
89 | - /** |
|
90 | - * @return string |
|
91 | - */ |
|
92 | - public function name(): string |
|
93 | - { |
|
94 | - return $this->name; |
|
95 | - } |
|
96 | - |
|
97 | - |
|
98 | - /** |
|
99 | - * @param string $name |
|
100 | - */ |
|
101 | - protected function setName(string $name) |
|
102 | - { |
|
103 | - $this->name = $name; |
|
104 | - } |
|
105 | - |
|
106 | - |
|
107 | - /** |
|
108 | - * @return string |
|
109 | - */ |
|
110 | - public function description(): string |
|
111 | - { |
|
112 | - return $this->description; |
|
113 | - } |
|
114 | - |
|
115 | - |
|
116 | - /** |
|
117 | - * @param string $description |
|
118 | - */ |
|
119 | - protected function setDescription(string $description) |
|
120 | - { |
|
121 | - $this->description = $description; |
|
122 | - } |
|
123 | - |
|
124 | - |
|
125 | - /** |
|
126 | - * @return GraphQLFieldInterface[] |
|
127 | - * @since 5.0.0.p |
|
128 | - */ |
|
129 | - public function fields(): array |
|
130 | - { |
|
131 | - return $this->fields; |
|
132 | - } |
|
133 | - |
|
134 | - |
|
135 | - /** |
|
136 | - * @param GraphQLFieldInterface[] $fields |
|
137 | - */ |
|
138 | - protected function setFields(array $fields) |
|
139 | - { |
|
140 | - foreach ($fields as $field) { |
|
141 | - if ($field instanceof GraphQLField) { |
|
142 | - $this->fields[] = $field; |
|
143 | - } |
|
144 | - } |
|
145 | - } |
|
146 | - |
|
147 | - |
|
148 | - /** |
|
149 | - * Creates a key map for internal resolver. |
|
150 | - * |
|
151 | - * @return array |
|
152 | - * @since 5.0.0.p |
|
153 | - */ |
|
154 | - public function getFieldsForResolver(): array |
|
155 | - { |
|
156 | - $fields = []; |
|
157 | - foreach ($this->fields() as $field) { |
|
158 | - if ($field->useForOutput()) { |
|
159 | - $fields[ $field->name() ] = $field; |
|
160 | - } |
|
161 | - } |
|
162 | - return $fields; |
|
163 | - } |
|
164 | - |
|
165 | - |
|
166 | - public function interfaces(): array |
|
167 | - { |
|
168 | - return $this->interfaces; |
|
169 | - } |
|
170 | - |
|
171 | - |
|
172 | - /** |
|
173 | - * @return bool |
|
174 | - */ |
|
175 | - public function isCustomPostType(): bool |
|
176 | - { |
|
177 | - return $this->is_custom_post_type; |
|
178 | - } |
|
179 | - |
|
180 | - |
|
181 | - /** |
|
182 | - * @param bool $is_custom_post_type |
|
183 | - */ |
|
184 | - protected function setIsCustomPostType(bool $is_custom_post_type) |
|
185 | - { |
|
186 | - $this->is_custom_post_type = filter_var($is_custom_post_type, FILTER_VALIDATE_BOOLEAN); |
|
187 | - } |
|
188 | - |
|
189 | - |
|
190 | - /** |
|
191 | - * @param int|float $value |
|
192 | - * @return int |
|
193 | - * @since 5.0.0.p |
|
194 | - */ |
|
195 | - public function parseInfiniteValue($value): int |
|
196 | - { |
|
197 | - $value = trim((string) $value); |
|
198 | - return $value === '' |
|
199 | - || $value === '∞' |
|
200 | - || $value === 'INF' |
|
201 | - || $value === INF |
|
202 | - || $value === EE_INF |
|
203 | - || is_infinite((float) $value) |
|
204 | - ? -1 |
|
205 | - : $value; |
|
206 | - } |
|
207 | - |
|
208 | - |
|
209 | - /** |
|
210 | - * @param mixed $source |
|
211 | - * @return EE_Base_Class|null |
|
212 | - * @throws EE_Error |
|
213 | - * @throws ReflectionException |
|
214 | - */ |
|
215 | - private function getModel($source): ?EE_Base_Class |
|
216 | - { |
|
217 | - // If it comes from a custom connection |
|
218 | - // where the $source is already instantiated. |
|
219 | - if ($source instanceof EE_Base_Class) { |
|
220 | - return $source; |
|
221 | - } |
|
222 | - return $source instanceof Post |
|
223 | - ? $this->model->get_one_by_ID($source->ID) |
|
224 | - : null; |
|
225 | - } |
|
226 | - |
|
227 | - |
|
228 | - /** |
|
229 | - * @param mixed $source The source that's passed down the GraphQL queries |
|
230 | - * @param array $args The inputArgs on the field |
|
231 | - * @param AppContext $context The AppContext passed down the GraphQL tree |
|
232 | - * @param ResolveInfo $info The ResolveInfo passed down the GraphQL tree |
|
233 | - * @return EE_Base_Class|Deferred|string|null |
|
234 | - * @throws EE_Error |
|
235 | - * @throws InvalidDataTypeException |
|
236 | - * @throws InvalidInterfaceException |
|
237 | - * @throws UnexpectedEntityException |
|
238 | - * @throws UserError |
|
239 | - * @throws InvalidArgumentException |
|
240 | - * @throws ReflectionException |
|
241 | - * @since 5.0.0.p |
|
242 | - */ |
|
243 | - public function resolveField($source, array $args, AppContext $context, ResolveInfo $info) |
|
244 | - { |
|
245 | - $source = $source instanceof RootQuery |
|
246 | - ? $source |
|
247 | - : $this->getModel($source); |
|
248 | - |
|
249 | - return $this->field_resolver->resolve($source, $args, $context, $info); |
|
250 | - } |
|
251 | - |
|
252 | - |
|
253 | - /** |
|
254 | - * @param mixed $payload The payload returned after mutation |
|
255 | - * @param array $args The inputArgs on the field |
|
256 | - * @param AppContext $context The AppContext passed down the GraphQL tree |
|
257 | - * @return EE_Base_Class|EE_Soft_Delete_Base_Class|null |
|
258 | - * @throws EE_Error |
|
259 | - * @throws ReflectionException |
|
260 | - */ |
|
261 | - public function resolveFromPayload($payload, array $args, AppContext $context) |
|
262 | - { |
|
263 | - if (empty($payload['id'])) { |
|
264 | - return null; |
|
265 | - } |
|
266 | - return $this->model->get_one_by_ID($payload['id']); |
|
267 | - } |
|
268 | - |
|
269 | - |
|
270 | - /** |
|
271 | - * Prepares a datetime value in ISO8601/RFC3339 format. |
|
272 | - * It is assumed that the value of $datetime is in the format |
|
273 | - * returned by EE_Base_Class::get_format(). |
|
274 | - * |
|
275 | - * @param string $datetime The datetime value. |
|
276 | - * @param EE_Base_Class $source The source object. |
|
277 | - * @return string ISO8601/RFC3339 formatted datetime. |
|
278 | - * @throws Exception |
|
279 | - */ |
|
280 | - public function formatDatetime(string $datetime, EE_Base_Class $source): string |
|
281 | - { |
|
282 | - $format = $source->get_format(); |
|
283 | - // create date object based on local timezone |
|
284 | - $datetime = DateTime::createFromFormat($format, $datetime, new DateTimeZone($source->get_timezone())); |
|
285 | - // change the timezone to UTC |
|
286 | - $datetime->setTimezone(new DateTimeZone('UTC')); |
|
287 | - |
|
288 | - return $datetime->format(DateTimeInterface::RFC3339); |
|
289 | - } |
|
290 | - |
|
291 | - |
|
292 | - /** |
|
293 | - * Converts an object to JSON. The object must have a "toJson" method. |
|
294 | - * |
|
295 | - * @param JsonableInterface $object The object/value. |
|
296 | - * @param EE_Base_Class $source The source object. |
|
297 | - * @return string JSON representation of the object. |
|
298 | - */ |
|
299 | - public function toJson(JsonableInterface $object, EE_Base_Class $source): string |
|
300 | - { |
|
301 | - return $object->toJson(); |
|
302 | - } |
|
40 | + /** |
|
41 | + * The graphql namespace/prefix. |
|
42 | + */ |
|
43 | + protected string $namespace = 'Espresso'; |
|
44 | + |
|
45 | + protected ?EEM_Base $model = null; |
|
46 | + |
|
47 | + protected string $name = ''; |
|
48 | + |
|
49 | + protected string $description = ''; |
|
50 | + |
|
51 | + /** |
|
52 | + * @var GraphQLFieldInterface[] $fields |
|
53 | + */ |
|
54 | + protected array $fields = []; |
|
55 | + |
|
56 | + /** |
|
57 | + * @var GraphQLInterfaceInterface[] $interfaces |
|
58 | + */ |
|
59 | + protected array $interfaces = []; |
|
60 | + |
|
61 | + protected FieldResolver $field_resolver; |
|
62 | + |
|
63 | + protected bool $is_custom_post_type = false; |
|
64 | + |
|
65 | + |
|
66 | + /** |
|
67 | + * TypeBase constructor. |
|
68 | + * |
|
69 | + * @param EEM_Base|null $model |
|
70 | + */ |
|
71 | + public function __construct(EEM_Base $model = null) |
|
72 | + { |
|
73 | + $this->model = $model; |
|
74 | + $this->setFields($this->getFields()); |
|
75 | + $this->field_resolver = new FieldResolver( |
|
76 | + $this->model, |
|
77 | + $this->getFieldsForResolver() |
|
78 | + ); |
|
79 | + } |
|
80 | + |
|
81 | + |
|
82 | + /** |
|
83 | + * @return GraphQLFieldInterface[] |
|
84 | + * @since 5.0.0.p |
|
85 | + */ |
|
86 | + abstract protected function getFields(): array; |
|
87 | + |
|
88 | + |
|
89 | + /** |
|
90 | + * @return string |
|
91 | + */ |
|
92 | + public function name(): string |
|
93 | + { |
|
94 | + return $this->name; |
|
95 | + } |
|
96 | + |
|
97 | + |
|
98 | + /** |
|
99 | + * @param string $name |
|
100 | + */ |
|
101 | + protected function setName(string $name) |
|
102 | + { |
|
103 | + $this->name = $name; |
|
104 | + } |
|
105 | + |
|
106 | + |
|
107 | + /** |
|
108 | + * @return string |
|
109 | + */ |
|
110 | + public function description(): string |
|
111 | + { |
|
112 | + return $this->description; |
|
113 | + } |
|
114 | + |
|
115 | + |
|
116 | + /** |
|
117 | + * @param string $description |
|
118 | + */ |
|
119 | + protected function setDescription(string $description) |
|
120 | + { |
|
121 | + $this->description = $description; |
|
122 | + } |
|
123 | + |
|
124 | + |
|
125 | + /** |
|
126 | + * @return GraphQLFieldInterface[] |
|
127 | + * @since 5.0.0.p |
|
128 | + */ |
|
129 | + public function fields(): array |
|
130 | + { |
|
131 | + return $this->fields; |
|
132 | + } |
|
133 | + |
|
134 | + |
|
135 | + /** |
|
136 | + * @param GraphQLFieldInterface[] $fields |
|
137 | + */ |
|
138 | + protected function setFields(array $fields) |
|
139 | + { |
|
140 | + foreach ($fields as $field) { |
|
141 | + if ($field instanceof GraphQLField) { |
|
142 | + $this->fields[] = $field; |
|
143 | + } |
|
144 | + } |
|
145 | + } |
|
146 | + |
|
147 | + |
|
148 | + /** |
|
149 | + * Creates a key map for internal resolver. |
|
150 | + * |
|
151 | + * @return array |
|
152 | + * @since 5.0.0.p |
|
153 | + */ |
|
154 | + public function getFieldsForResolver(): array |
|
155 | + { |
|
156 | + $fields = []; |
|
157 | + foreach ($this->fields() as $field) { |
|
158 | + if ($field->useForOutput()) { |
|
159 | + $fields[ $field->name() ] = $field; |
|
160 | + } |
|
161 | + } |
|
162 | + return $fields; |
|
163 | + } |
|
164 | + |
|
165 | + |
|
166 | + public function interfaces(): array |
|
167 | + { |
|
168 | + return $this->interfaces; |
|
169 | + } |
|
170 | + |
|
171 | + |
|
172 | + /** |
|
173 | + * @return bool |
|
174 | + */ |
|
175 | + public function isCustomPostType(): bool |
|
176 | + { |
|
177 | + return $this->is_custom_post_type; |
|
178 | + } |
|
179 | + |
|
180 | + |
|
181 | + /** |
|
182 | + * @param bool $is_custom_post_type |
|
183 | + */ |
|
184 | + protected function setIsCustomPostType(bool $is_custom_post_type) |
|
185 | + { |
|
186 | + $this->is_custom_post_type = filter_var($is_custom_post_type, FILTER_VALIDATE_BOOLEAN); |
|
187 | + } |
|
188 | + |
|
189 | + |
|
190 | + /** |
|
191 | + * @param int|float $value |
|
192 | + * @return int |
|
193 | + * @since 5.0.0.p |
|
194 | + */ |
|
195 | + public function parseInfiniteValue($value): int |
|
196 | + { |
|
197 | + $value = trim((string) $value); |
|
198 | + return $value === '' |
|
199 | + || $value === '∞' |
|
200 | + || $value === 'INF' |
|
201 | + || $value === INF |
|
202 | + || $value === EE_INF |
|
203 | + || is_infinite((float) $value) |
|
204 | + ? -1 |
|
205 | + : $value; |
|
206 | + } |
|
207 | + |
|
208 | + |
|
209 | + /** |
|
210 | + * @param mixed $source |
|
211 | + * @return EE_Base_Class|null |
|
212 | + * @throws EE_Error |
|
213 | + * @throws ReflectionException |
|
214 | + */ |
|
215 | + private function getModel($source): ?EE_Base_Class |
|
216 | + { |
|
217 | + // If it comes from a custom connection |
|
218 | + // where the $source is already instantiated. |
|
219 | + if ($source instanceof EE_Base_Class) { |
|
220 | + return $source; |
|
221 | + } |
|
222 | + return $source instanceof Post |
|
223 | + ? $this->model->get_one_by_ID($source->ID) |
|
224 | + : null; |
|
225 | + } |
|
226 | + |
|
227 | + |
|
228 | + /** |
|
229 | + * @param mixed $source The source that's passed down the GraphQL queries |
|
230 | + * @param array $args The inputArgs on the field |
|
231 | + * @param AppContext $context The AppContext passed down the GraphQL tree |
|
232 | + * @param ResolveInfo $info The ResolveInfo passed down the GraphQL tree |
|
233 | + * @return EE_Base_Class|Deferred|string|null |
|
234 | + * @throws EE_Error |
|
235 | + * @throws InvalidDataTypeException |
|
236 | + * @throws InvalidInterfaceException |
|
237 | + * @throws UnexpectedEntityException |
|
238 | + * @throws UserError |
|
239 | + * @throws InvalidArgumentException |
|
240 | + * @throws ReflectionException |
|
241 | + * @since 5.0.0.p |
|
242 | + */ |
|
243 | + public function resolveField($source, array $args, AppContext $context, ResolveInfo $info) |
|
244 | + { |
|
245 | + $source = $source instanceof RootQuery |
|
246 | + ? $source |
|
247 | + : $this->getModel($source); |
|
248 | + |
|
249 | + return $this->field_resolver->resolve($source, $args, $context, $info); |
|
250 | + } |
|
251 | + |
|
252 | + |
|
253 | + /** |
|
254 | + * @param mixed $payload The payload returned after mutation |
|
255 | + * @param array $args The inputArgs on the field |
|
256 | + * @param AppContext $context The AppContext passed down the GraphQL tree |
|
257 | + * @return EE_Base_Class|EE_Soft_Delete_Base_Class|null |
|
258 | + * @throws EE_Error |
|
259 | + * @throws ReflectionException |
|
260 | + */ |
|
261 | + public function resolveFromPayload($payload, array $args, AppContext $context) |
|
262 | + { |
|
263 | + if (empty($payload['id'])) { |
|
264 | + return null; |
|
265 | + } |
|
266 | + return $this->model->get_one_by_ID($payload['id']); |
|
267 | + } |
|
268 | + |
|
269 | + |
|
270 | + /** |
|
271 | + * Prepares a datetime value in ISO8601/RFC3339 format. |
|
272 | + * It is assumed that the value of $datetime is in the format |
|
273 | + * returned by EE_Base_Class::get_format(). |
|
274 | + * |
|
275 | + * @param string $datetime The datetime value. |
|
276 | + * @param EE_Base_Class $source The source object. |
|
277 | + * @return string ISO8601/RFC3339 formatted datetime. |
|
278 | + * @throws Exception |
|
279 | + */ |
|
280 | + public function formatDatetime(string $datetime, EE_Base_Class $source): string |
|
281 | + { |
|
282 | + $format = $source->get_format(); |
|
283 | + // create date object based on local timezone |
|
284 | + $datetime = DateTime::createFromFormat($format, $datetime, new DateTimeZone($source->get_timezone())); |
|
285 | + // change the timezone to UTC |
|
286 | + $datetime->setTimezone(new DateTimeZone('UTC')); |
|
287 | + |
|
288 | + return $datetime->format(DateTimeInterface::RFC3339); |
|
289 | + } |
|
290 | + |
|
291 | + |
|
292 | + /** |
|
293 | + * Converts an object to JSON. The object must have a "toJson" method. |
|
294 | + * |
|
295 | + * @param JsonableInterface $object The object/value. |
|
296 | + * @param EE_Base_Class $source The source object. |
|
297 | + * @return string JSON representation of the object. |
|
298 | + */ |
|
299 | + public function toJson(JsonableInterface $object, EE_Base_Class $source): string |
|
300 | + { |
|
301 | + return $object->toJson(); |
|
302 | + } |
|
303 | 303 | } |
@@ -40,9 +40,9 @@ discard block |
||
40 | 40 | /** |
41 | 41 | * The graphql namespace/prefix. |
42 | 42 | */ |
43 | - protected string $namespace = 'Espresso'; |
|
43 | + protected string $namespace = 'Espresso'; |
|
44 | 44 | |
45 | - protected ?EEM_Base $model = null; |
|
45 | + protected ?EEM_Base $model = null; |
|
46 | 46 | |
47 | 47 | protected string $name = ''; |
48 | 48 | |
@@ -51,12 +51,12 @@ discard block |
||
51 | 51 | /** |
52 | 52 | * @var GraphQLFieldInterface[] $fields |
53 | 53 | */ |
54 | - protected array $fields = []; |
|
54 | + protected array $fields = []; |
|
55 | 55 | |
56 | 56 | /** |
57 | 57 | * @var GraphQLInterfaceInterface[] $interfaces |
58 | 58 | */ |
59 | - protected array $interfaces = []; |
|
59 | + protected array $interfaces = []; |
|
60 | 60 | |
61 | 61 | protected FieldResolver $field_resolver; |
62 | 62 | |
@@ -156,7 +156,7 @@ discard block |
||
156 | 156 | $fields = []; |
157 | 157 | foreach ($this->fields() as $field) { |
158 | 158 | if ($field->useForOutput()) { |
159 | - $fields[ $field->name() ] = $field; |
|
159 | + $fields[$field->name()] = $field; |
|
160 | 160 | } |
161 | 161 | } |
162 | 162 | return $fields; |
@@ -29,88 +29,88 @@ |
||
29 | 29 | */ |
30 | 30 | class BootstrapRequestResponseObjects |
31 | 31 | { |
32 | - protected LegacyRequestInterface $legacy_request; |
|
32 | + protected LegacyRequestInterface $legacy_request; |
|
33 | 33 | |
34 | - protected LoaderInterface $loader; |
|
34 | + protected LoaderInterface $loader; |
|
35 | 35 | |
36 | - protected RequestInterface $request; |
|
36 | + protected RequestInterface $request; |
|
37 | 37 | |
38 | - protected ResponseInterface $response; |
|
38 | + protected ResponseInterface $response; |
|
39 | 39 | |
40 | 40 | |
41 | - /** |
|
42 | - * BootstrapRequestResponseObjects constructor. |
|
43 | - * |
|
44 | - * @param LoaderInterface $loader |
|
45 | - */ |
|
46 | - public function __construct(LoaderInterface $loader) |
|
47 | - { |
|
48 | - $this->loader = $loader; |
|
49 | - } |
|
41 | + /** |
|
42 | + * BootstrapRequestResponseObjects constructor. |
|
43 | + * |
|
44 | + * @param LoaderInterface $loader |
|
45 | + */ |
|
46 | + public function __construct(LoaderInterface $loader) |
|
47 | + { |
|
48 | + $this->loader = $loader; |
|
49 | + } |
|
50 | 50 | |
51 | 51 | |
52 | - /** |
|
53 | - * @return void |
|
54 | - */ |
|
55 | - public function buildRequestResponse() |
|
56 | - { |
|
57 | - $email_validator = new Basic(); |
|
58 | - $request_sanitizer = new RequestSanitizer($email_validator); |
|
59 | - $server_sanitizer = new ServerSanitizer(); |
|
60 | - $request_params = new RequestParams($request_sanitizer, $_GET, $_POST); |
|
61 | - $server_params = new ServerParams($server_sanitizer, $_SERVER); |
|
62 | - // load our Request and Response objects |
|
63 | - $this->request = apply_filters( |
|
64 | - 'FHEE___EventEspresso_core_services_bootstrap_BootstrapRequestResponseObjects__buildRequestResponse__request', |
|
65 | - new Request($request_params, $server_params), |
|
66 | - $request_params, |
|
67 | - $server_params, |
|
68 | - $request_sanitizer, |
|
69 | - $server_sanitizer |
|
70 | - ); |
|
71 | - $this->response = apply_filters( |
|
72 | - 'FHEE___EventEspresso_core_services_bootstrap_BootstrapRequestResponseObjects__buildRequestResponse__response', |
|
73 | - new Response() |
|
74 | - ); |
|
75 | - $this->loader->share(Basic::class, $email_validator); |
|
76 | - $this->loader->share(RequestSanitizer::class, $request_sanitizer); |
|
77 | - $this->loader->share(ServerSanitizer::class, $server_sanitizer); |
|
78 | - $this->loader->share(RequestParams::class, $request_params); |
|
79 | - $this->loader->share(ServerParams::class, $server_params); |
|
80 | - } |
|
52 | + /** |
|
53 | + * @return void |
|
54 | + */ |
|
55 | + public function buildRequestResponse() |
|
56 | + { |
|
57 | + $email_validator = new Basic(); |
|
58 | + $request_sanitizer = new RequestSanitizer($email_validator); |
|
59 | + $server_sanitizer = new ServerSanitizer(); |
|
60 | + $request_params = new RequestParams($request_sanitizer, $_GET, $_POST); |
|
61 | + $server_params = new ServerParams($server_sanitizer, $_SERVER); |
|
62 | + // load our Request and Response objects |
|
63 | + $this->request = apply_filters( |
|
64 | + 'FHEE___EventEspresso_core_services_bootstrap_BootstrapRequestResponseObjects__buildRequestResponse__request', |
|
65 | + new Request($request_params, $server_params), |
|
66 | + $request_params, |
|
67 | + $server_params, |
|
68 | + $request_sanitizer, |
|
69 | + $server_sanitizer |
|
70 | + ); |
|
71 | + $this->response = apply_filters( |
|
72 | + 'FHEE___EventEspresso_core_services_bootstrap_BootstrapRequestResponseObjects__buildRequestResponse__response', |
|
73 | + new Response() |
|
74 | + ); |
|
75 | + $this->loader->share(Basic::class, $email_validator); |
|
76 | + $this->loader->share(RequestSanitizer::class, $request_sanitizer); |
|
77 | + $this->loader->share(ServerSanitizer::class, $server_sanitizer); |
|
78 | + $this->loader->share(RequestParams::class, $request_params); |
|
79 | + $this->loader->share(ServerParams::class, $server_params); |
|
80 | + } |
|
81 | 81 | |
82 | 82 | |
83 | - /** |
|
84 | - * @return void |
|
85 | - * @throws InvalidArgumentException |
|
86 | - */ |
|
87 | - public function shareRequestResponse() |
|
88 | - { |
|
89 | - $this->loader->share(Request::class, $this->request); |
|
90 | - $this->loader->share(Response::class, $this->response); |
|
91 | - EE_Dependency_Map::instance()->setRequest($this->request); |
|
92 | - EE_Dependency_Map::instance()->setResponse($this->response); |
|
93 | - } |
|
83 | + /** |
|
84 | + * @return void |
|
85 | + * @throws InvalidArgumentException |
|
86 | + */ |
|
87 | + public function shareRequestResponse() |
|
88 | + { |
|
89 | + $this->loader->share(Request::class, $this->request); |
|
90 | + $this->loader->share(Response::class, $this->response); |
|
91 | + EE_Dependency_Map::instance()->setRequest($this->request); |
|
92 | + EE_Dependency_Map::instance()->setResponse($this->response); |
|
93 | + } |
|
94 | 94 | |
95 | 95 | |
96 | - /** |
|
97 | - * @return void |
|
98 | - * @throws InvalidArgumentException |
|
99 | - * @throws EE_Error |
|
100 | - */ |
|
101 | - public function setupLegacyRequest() |
|
102 | - { |
|
103 | - espresso_load_required( |
|
104 | - 'EE_Request', |
|
105 | - EE_CORE . 'request_stack/EE_Request.core.php' |
|
106 | - ); |
|
107 | - $this->legacy_request = new EE_Request($_GET, $_POST, $_COOKIE, $_SERVER); |
|
108 | - $this->legacy_request->setRequest($this->request); |
|
109 | - $this->legacy_request->admin = $this->request->isAdmin(); |
|
110 | - $this->legacy_request->ajax = $this->request->isAjax(); |
|
111 | - $this->legacy_request->front_ajax = $this->request->isFrontAjax(); |
|
112 | - EE_Dependency_Map::instance()->setLegacyRequest($this->legacy_request); |
|
113 | - $this->loader->share('EE_Request', $this->legacy_request); |
|
114 | - $this->loader->share('EventEspresso\core\services\request\LegacyRequestInterface', $this->legacy_request); |
|
115 | - } |
|
96 | + /** |
|
97 | + * @return void |
|
98 | + * @throws InvalidArgumentException |
|
99 | + * @throws EE_Error |
|
100 | + */ |
|
101 | + public function setupLegacyRequest() |
|
102 | + { |
|
103 | + espresso_load_required( |
|
104 | + 'EE_Request', |
|
105 | + EE_CORE . 'request_stack/EE_Request.core.php' |
|
106 | + ); |
|
107 | + $this->legacy_request = new EE_Request($_GET, $_POST, $_COOKIE, $_SERVER); |
|
108 | + $this->legacy_request->setRequest($this->request); |
|
109 | + $this->legacy_request->admin = $this->request->isAdmin(); |
|
110 | + $this->legacy_request->ajax = $this->request->isAjax(); |
|
111 | + $this->legacy_request->front_ajax = $this->request->isFrontAjax(); |
|
112 | + EE_Dependency_Map::instance()->setLegacyRequest($this->legacy_request); |
|
113 | + $this->loader->share('EE_Request', $this->legacy_request); |
|
114 | + $this->loader->share('EventEspresso\core\services\request\LegacyRequestInterface', $this->legacy_request); |
|
115 | + } |
|
116 | 116 | } |
@@ -24,105 +24,105 @@ |
||
24 | 24 | */ |
25 | 25 | class BootstrapDependencyInjectionContainer |
26 | 26 | { |
27 | - private ClassInterfaceCache $class_cache; |
|
28 | - |
|
29 | - private Mirror $mirror; |
|
30 | - |
|
31 | - private ObjectIdentifier $object_identifier; |
|
32 | - |
|
33 | - protected EE_Dependency_Map $dependency_map; |
|
34 | - |
|
35 | - protected EE_Registry $registry; |
|
36 | - |
|
37 | - protected LoaderInterface $loader; |
|
38 | - |
|
39 | - |
|
40 | - // /** |
|
41 | - // * Can't use this just yet until we exorcise some more of our singleton usage from core |
|
42 | - // */ |
|
43 | - // public function buildDependencyInjectionContainer() |
|
44 | - // { |
|
45 | - // // build DI container |
|
46 | - // $OpenCoffeeShop = new EventEspresso\core\services\container\OpenCoffeeShop(); |
|
47 | - // $OpenCoffeeShop->addRecipes(); |
|
48 | - // $CoffeeShop = $OpenCoffeeShop->CoffeeShop(); |
|
49 | - // } |
|
50 | - |
|
51 | - |
|
52 | - /** |
|
53 | - * Setups EE_Registry and EE_Dependency_Map |
|
54 | - * |
|
55 | - * @throws EE_Error |
|
56 | - */ |
|
57 | - public function buildLegacyDependencyInjectionContainer() |
|
58 | - { |
|
59 | - $this->class_cache = new ClassInterfaceCache(); |
|
60 | - $this->object_identifier = new ObjectIdentifier($this->class_cache); |
|
61 | - $this->mirror = new Mirror(); |
|
62 | - // EE_Dependency_Map: info about how to load classes required by other classes |
|
63 | - espresso_load_required( |
|
64 | - 'EE_Dependency_Map', |
|
65 | - EE_CORE . 'EE_Dependency_Map.core.php' |
|
66 | - ); |
|
67 | - $this->dependency_map = EE_Dependency_Map::instance($this->class_cache); |
|
68 | - // EE_Registry: central repository for classes (legacy) |
|
69 | - espresso_load_required( |
|
70 | - 'EE_Registry', |
|
71 | - EE_CORE . 'EE_Registry.core.php' |
|
72 | - ); |
|
73 | - $this->registry = EE_Registry::instance( |
|
74 | - $this->dependency_map, |
|
75 | - $this->mirror, |
|
76 | - $this->class_cache, |
|
77 | - $this->object_identifier |
|
78 | - ); |
|
79 | - } |
|
80 | - |
|
81 | - |
|
82 | - /** |
|
83 | - * Performs initial setup for the generic Loader |
|
84 | - * |
|
85 | - * @throws InvalidDataTypeException |
|
86 | - * @throws InvalidInterfaceException |
|
87 | - * @throws InvalidArgumentException |
|
88 | - */ |
|
89 | - public function buildLoader() |
|
90 | - { |
|
91 | - $this->loader = LoaderFactory::getLoader( |
|
92 | - $this->registry, |
|
93 | - $this->class_cache, |
|
94 | - $this->object_identifier |
|
95 | - ); |
|
96 | - $this->loader->share('EventEspresso\core\services\loaders\ClassInterfaceCache', $this->class_cache); |
|
97 | - $this->loader->share('EventEspresso\core\services\loaders\ObjectIdentifier', $this->object_identifier); |
|
98 | - $this->loader->share('EventEspresso\core\services\container\Mirror', $this->mirror); |
|
99 | - $this->dependency_map->setLoader($this->loader); |
|
100 | - } |
|
101 | - |
|
102 | - |
|
103 | - /** |
|
104 | - * @return EE_Dependency_Map |
|
105 | - */ |
|
106 | - public function getDependencyMap(): EE_Dependency_Map |
|
107 | - { |
|
108 | - return $this->dependency_map; |
|
109 | - } |
|
110 | - |
|
111 | - |
|
112 | - /** |
|
113 | - * @return EE_Registry |
|
114 | - */ |
|
115 | - public function getRegistry(): EE_Registry |
|
116 | - { |
|
117 | - return $this->registry; |
|
118 | - } |
|
119 | - |
|
120 | - |
|
121 | - /** |
|
122 | - * @return LoaderInterface |
|
123 | - */ |
|
124 | - public function getLoader(): LoaderInterface |
|
125 | - { |
|
126 | - return $this->loader; |
|
127 | - } |
|
27 | + private ClassInterfaceCache $class_cache; |
|
28 | + |
|
29 | + private Mirror $mirror; |
|
30 | + |
|
31 | + private ObjectIdentifier $object_identifier; |
|
32 | + |
|
33 | + protected EE_Dependency_Map $dependency_map; |
|
34 | + |
|
35 | + protected EE_Registry $registry; |
|
36 | + |
|
37 | + protected LoaderInterface $loader; |
|
38 | + |
|
39 | + |
|
40 | + // /** |
|
41 | + // * Can't use this just yet until we exorcise some more of our singleton usage from core |
|
42 | + // */ |
|
43 | + // public function buildDependencyInjectionContainer() |
|
44 | + // { |
|
45 | + // // build DI container |
|
46 | + // $OpenCoffeeShop = new EventEspresso\core\services\container\OpenCoffeeShop(); |
|
47 | + // $OpenCoffeeShop->addRecipes(); |
|
48 | + // $CoffeeShop = $OpenCoffeeShop->CoffeeShop(); |
|
49 | + // } |
|
50 | + |
|
51 | + |
|
52 | + /** |
|
53 | + * Setups EE_Registry and EE_Dependency_Map |
|
54 | + * |
|
55 | + * @throws EE_Error |
|
56 | + */ |
|
57 | + public function buildLegacyDependencyInjectionContainer() |
|
58 | + { |
|
59 | + $this->class_cache = new ClassInterfaceCache(); |
|
60 | + $this->object_identifier = new ObjectIdentifier($this->class_cache); |
|
61 | + $this->mirror = new Mirror(); |
|
62 | + // EE_Dependency_Map: info about how to load classes required by other classes |
|
63 | + espresso_load_required( |
|
64 | + 'EE_Dependency_Map', |
|
65 | + EE_CORE . 'EE_Dependency_Map.core.php' |
|
66 | + ); |
|
67 | + $this->dependency_map = EE_Dependency_Map::instance($this->class_cache); |
|
68 | + // EE_Registry: central repository for classes (legacy) |
|
69 | + espresso_load_required( |
|
70 | + 'EE_Registry', |
|
71 | + EE_CORE . 'EE_Registry.core.php' |
|
72 | + ); |
|
73 | + $this->registry = EE_Registry::instance( |
|
74 | + $this->dependency_map, |
|
75 | + $this->mirror, |
|
76 | + $this->class_cache, |
|
77 | + $this->object_identifier |
|
78 | + ); |
|
79 | + } |
|
80 | + |
|
81 | + |
|
82 | + /** |
|
83 | + * Performs initial setup for the generic Loader |
|
84 | + * |
|
85 | + * @throws InvalidDataTypeException |
|
86 | + * @throws InvalidInterfaceException |
|
87 | + * @throws InvalidArgumentException |
|
88 | + */ |
|
89 | + public function buildLoader() |
|
90 | + { |
|
91 | + $this->loader = LoaderFactory::getLoader( |
|
92 | + $this->registry, |
|
93 | + $this->class_cache, |
|
94 | + $this->object_identifier |
|
95 | + ); |
|
96 | + $this->loader->share('EventEspresso\core\services\loaders\ClassInterfaceCache', $this->class_cache); |
|
97 | + $this->loader->share('EventEspresso\core\services\loaders\ObjectIdentifier', $this->object_identifier); |
|
98 | + $this->loader->share('EventEspresso\core\services\container\Mirror', $this->mirror); |
|
99 | + $this->dependency_map->setLoader($this->loader); |
|
100 | + } |
|
101 | + |
|
102 | + |
|
103 | + /** |
|
104 | + * @return EE_Dependency_Map |
|
105 | + */ |
|
106 | + public function getDependencyMap(): EE_Dependency_Map |
|
107 | + { |
|
108 | + return $this->dependency_map; |
|
109 | + } |
|
110 | + |
|
111 | + |
|
112 | + /** |
|
113 | + * @return EE_Registry |
|
114 | + */ |
|
115 | + public function getRegistry(): EE_Registry |
|
116 | + { |
|
117 | + return $this->registry; |
|
118 | + } |
|
119 | + |
|
120 | + |
|
121 | + /** |
|
122 | + * @return LoaderInterface |
|
123 | + */ |
|
124 | + public function getLoader(): LoaderInterface |
|
125 | + { |
|
126 | + return $this->loader; |
|
127 | + } |
|
128 | 128 | } |
@@ -53,212 +53,212 @@ |
||
53 | 53 | */ |
54 | 54 | class BootstrapCore |
55 | 55 | { |
56 | - private LoaderInterface $loader; |
|
56 | + private LoaderInterface $loader; |
|
57 | 57 | |
58 | - protected RequestInterface $request; |
|
58 | + protected RequestInterface $request; |
|
59 | 59 | |
60 | - protected ResponseInterface $response; |
|
60 | + protected ResponseInterface $response; |
|
61 | 61 | |
62 | - protected RequestStackBuilder $request_stack_builder; |
|
62 | + protected RequestStackBuilder $request_stack_builder; |
|
63 | 63 | |
64 | - protected RequestStack $request_stack; |
|
64 | + protected RequestStack $request_stack; |
|
65 | 65 | |
66 | 66 | |
67 | - /** |
|
68 | - * BootstrapCore constructor. |
|
69 | - */ |
|
70 | - public function __construct() |
|
71 | - { |
|
72 | - do_action('AHEE__EventEspresso_core_services_bootstrap_BootstrapCore___construct'); |
|
73 | - // construct request stack and run middleware apps as soon as all WP plugins are loaded |
|
74 | - add_action('plugins_loaded', [$this, 'initialize'], 0); |
|
75 | - } |
|
67 | + /** |
|
68 | + * BootstrapCore constructor. |
|
69 | + */ |
|
70 | + public function __construct() |
|
71 | + { |
|
72 | + do_action('AHEE__EventEspresso_core_services_bootstrap_BootstrapCore___construct'); |
|
73 | + // construct request stack and run middleware apps as soon as all WP plugins are loaded |
|
74 | + add_action('plugins_loaded', [$this, 'initialize'], 0); |
|
75 | + } |
|
76 | 76 | |
77 | 77 | |
78 | - /** |
|
79 | - * @throws DomainException |
|
80 | - * @throws EE_Error |
|
81 | - * @throws Exception |
|
82 | - * @throws InvalidArgumentException |
|
83 | - * @throws InvalidClassException |
|
84 | - * @throws InvalidDataTypeException |
|
85 | - * @throws InvalidFilePathException |
|
86 | - * @throws InvalidInterfaceException |
|
87 | - * @throws InvalidRequestStackMiddlewareException |
|
88 | - * @throws OutOfBoundsException |
|
89 | - * @throws ReflectionException |
|
90 | - * @throws Throwable |
|
91 | - */ |
|
92 | - public function initialize() |
|
93 | - { |
|
94 | - $this->bootstrapDependencyInjectionContainer(); |
|
95 | - $this->bootstrapDomain(); |
|
96 | - $bootstrap_request = $this->bootstrapRequestResponseObjects(); |
|
97 | - add_action( |
|
98 | - 'EE_Load_Espresso_Core__handle_request__initialize_core_loading', |
|
99 | - [$bootstrap_request, 'setupLegacyRequest'] |
|
100 | - ); |
|
101 | - $this->runRequestStack(); |
|
102 | - } |
|
78 | + /** |
|
79 | + * @throws DomainException |
|
80 | + * @throws EE_Error |
|
81 | + * @throws Exception |
|
82 | + * @throws InvalidArgumentException |
|
83 | + * @throws InvalidClassException |
|
84 | + * @throws InvalidDataTypeException |
|
85 | + * @throws InvalidFilePathException |
|
86 | + * @throws InvalidInterfaceException |
|
87 | + * @throws InvalidRequestStackMiddlewareException |
|
88 | + * @throws OutOfBoundsException |
|
89 | + * @throws ReflectionException |
|
90 | + * @throws Throwable |
|
91 | + */ |
|
92 | + public function initialize() |
|
93 | + { |
|
94 | + $this->bootstrapDependencyInjectionContainer(); |
|
95 | + $this->bootstrapDomain(); |
|
96 | + $bootstrap_request = $this->bootstrapRequestResponseObjects(); |
|
97 | + add_action( |
|
98 | + 'EE_Load_Espresso_Core__handle_request__initialize_core_loading', |
|
99 | + [$bootstrap_request, 'setupLegacyRequest'] |
|
100 | + ); |
|
101 | + $this->runRequestStack(); |
|
102 | + } |
|
103 | 103 | |
104 | 104 | |
105 | - /** |
|
106 | - * @throws ReflectionException |
|
107 | - * @throws EE_Error |
|
108 | - * @throws InvalidArgumentException |
|
109 | - * @throws InvalidDataTypeException |
|
110 | - * @throws InvalidInterfaceException |
|
111 | - * @throws OutOfBoundsException |
|
112 | - */ |
|
113 | - private function bootstrapDependencyInjectionContainer() |
|
114 | - { |
|
115 | - $bootstrap_di = new BootstrapDependencyInjectionContainer(); |
|
116 | - $bootstrap_di->buildLegacyDependencyInjectionContainer(); |
|
117 | - $bootstrap_di->buildLoader(); |
|
118 | - $registry = $bootstrap_di->getRegistry(); |
|
119 | - $dependency_map = $bootstrap_di->getDependencyMap(); |
|
120 | - $dependency_map->initialize(); |
|
121 | - $registry->initialize(); |
|
122 | - $this->loader = $bootstrap_di->getLoader(); |
|
123 | - } |
|
105 | + /** |
|
106 | + * @throws ReflectionException |
|
107 | + * @throws EE_Error |
|
108 | + * @throws InvalidArgumentException |
|
109 | + * @throws InvalidDataTypeException |
|
110 | + * @throws InvalidInterfaceException |
|
111 | + * @throws OutOfBoundsException |
|
112 | + */ |
|
113 | + private function bootstrapDependencyInjectionContainer() |
|
114 | + { |
|
115 | + $bootstrap_di = new BootstrapDependencyInjectionContainer(); |
|
116 | + $bootstrap_di->buildLegacyDependencyInjectionContainer(); |
|
117 | + $bootstrap_di->buildLoader(); |
|
118 | + $registry = $bootstrap_di->getRegistry(); |
|
119 | + $dependency_map = $bootstrap_di->getDependencyMap(); |
|
120 | + $dependency_map->initialize(); |
|
121 | + $registry->initialize(); |
|
122 | + $this->loader = $bootstrap_di->getLoader(); |
|
123 | + } |
|
124 | 124 | |
125 | 125 | |
126 | - /** |
|
127 | - * configures the Domain object for core |
|
128 | - * |
|
129 | - * @return void |
|
130 | - * @throws DomainException |
|
131 | - * @throws InvalidArgumentException |
|
132 | - * @throws InvalidDataTypeException |
|
133 | - * @throws InvalidClassException |
|
134 | - * @throws InvalidFilePathException |
|
135 | - * @throws InvalidInterfaceException |
|
136 | - */ |
|
137 | - private function bootstrapDomain() |
|
138 | - { |
|
139 | - DomainFactory::getEventEspressoCoreDomain(); |
|
140 | - } |
|
126 | + /** |
|
127 | + * configures the Domain object for core |
|
128 | + * |
|
129 | + * @return void |
|
130 | + * @throws DomainException |
|
131 | + * @throws InvalidArgumentException |
|
132 | + * @throws InvalidDataTypeException |
|
133 | + * @throws InvalidClassException |
|
134 | + * @throws InvalidFilePathException |
|
135 | + * @throws InvalidInterfaceException |
|
136 | + */ |
|
137 | + private function bootstrapDomain() |
|
138 | + { |
|
139 | + DomainFactory::getEventEspressoCoreDomain(); |
|
140 | + } |
|
141 | 141 | |
142 | 142 | |
143 | - /** |
|
144 | - * sets up the request and response objects |
|
145 | - * |
|
146 | - * @return BootstrapRequestResponseObjects |
|
147 | - * @throws InvalidArgumentException |
|
148 | - */ |
|
149 | - private function bootstrapRequestResponseObjects(): BootstrapRequestResponseObjects |
|
150 | - { |
|
151 | - /** @var BootstrapRequestResponseObjects $bootstrap_request */ |
|
152 | - $bootstrap_request = $this->loader->getShared( |
|
153 | - 'EventEspresso\core\services\bootstrap\BootstrapRequestResponseObjects', |
|
154 | - [$this->loader] |
|
155 | - ); |
|
156 | - $bootstrap_request->buildRequestResponse(); |
|
157 | - $bootstrap_request->shareRequestResponse(); |
|
158 | - $this->request = $this->loader->getShared('EventEspresso\core\services\request\Request'); |
|
159 | - $this->response = $this->loader->getShared('EventEspresso\core\services\request\Response'); |
|
160 | - return $bootstrap_request; |
|
161 | - } |
|
143 | + /** |
|
144 | + * sets up the request and response objects |
|
145 | + * |
|
146 | + * @return BootstrapRequestResponseObjects |
|
147 | + * @throws InvalidArgumentException |
|
148 | + */ |
|
149 | + private function bootstrapRequestResponseObjects(): BootstrapRequestResponseObjects |
|
150 | + { |
|
151 | + /** @var BootstrapRequestResponseObjects $bootstrap_request */ |
|
152 | + $bootstrap_request = $this->loader->getShared( |
|
153 | + 'EventEspresso\core\services\bootstrap\BootstrapRequestResponseObjects', |
|
154 | + [$this->loader] |
|
155 | + ); |
|
156 | + $bootstrap_request->buildRequestResponse(); |
|
157 | + $bootstrap_request->shareRequestResponse(); |
|
158 | + $this->request = $this->loader->getShared('EventEspresso\core\services\request\Request'); |
|
159 | + $this->response = $this->loader->getShared('EventEspresso\core\services\request\Response'); |
|
160 | + return $bootstrap_request; |
|
161 | + } |
|
162 | 162 | |
163 | 163 | |
164 | - /** |
|
165 | - * run_request_stack |
|
166 | - * construct request stack and run middleware apps |
|
167 | - * |
|
168 | - * @throws EE_Error |
|
169 | - * @throws Exception |
|
170 | - * @throws Throwable |
|
171 | - */ |
|
172 | - public function runRequestStack() |
|
173 | - { |
|
174 | - $this->loadAutoloader(); |
|
175 | - $this->setAutoloadersForRequiredFiles(); |
|
176 | - $this->request_stack_builder = $this->buildRequestStack(); |
|
177 | - $this->request_stack = $this->request_stack_builder->resolve( |
|
178 | - new RequestStackCoreApp() |
|
179 | - ); |
|
180 | - $this->request_stack->handleRequest($this->request, $this->response); |
|
181 | - $this->request_stack->handleResponse(); |
|
182 | - } |
|
164 | + /** |
|
165 | + * run_request_stack |
|
166 | + * construct request stack and run middleware apps |
|
167 | + * |
|
168 | + * @throws EE_Error |
|
169 | + * @throws Exception |
|
170 | + * @throws Throwable |
|
171 | + */ |
|
172 | + public function runRequestStack() |
|
173 | + { |
|
174 | + $this->loadAutoloader(); |
|
175 | + $this->setAutoloadersForRequiredFiles(); |
|
176 | + $this->request_stack_builder = $this->buildRequestStack(); |
|
177 | + $this->request_stack = $this->request_stack_builder->resolve( |
|
178 | + new RequestStackCoreApp() |
|
179 | + ); |
|
180 | + $this->request_stack->handleRequest($this->request, $this->response); |
|
181 | + $this->request_stack->handleResponse(); |
|
182 | + } |
|
183 | 183 | |
184 | 184 | |
185 | - /** |
|
186 | - * load_autoloader |
|
187 | - * |
|
188 | - * @throws EE_Error |
|
189 | - */ |
|
190 | - protected function loadAutoloader() |
|
191 | - { |
|
192 | - // load interfaces |
|
193 | - espresso_load_required( |
|
194 | - 'EEH_Autoloader', |
|
195 | - EE_CORE . 'helpers/EEH_Autoloader.helper.php' |
|
196 | - ); |
|
197 | - EEH_Autoloader::instance(); |
|
198 | - } |
|
185 | + /** |
|
186 | + * load_autoloader |
|
187 | + * |
|
188 | + * @throws EE_Error |
|
189 | + */ |
|
190 | + protected function loadAutoloader() |
|
191 | + { |
|
192 | + // load interfaces |
|
193 | + espresso_load_required( |
|
194 | + 'EEH_Autoloader', |
|
195 | + EE_CORE . 'helpers/EEH_Autoloader.helper.php' |
|
196 | + ); |
|
197 | + EEH_Autoloader::instance(); |
|
198 | + } |
|
199 | 199 | |
200 | 200 | |
201 | - /** |
|
202 | - * load_required_files |
|
203 | - * |
|
204 | - * @throws EE_Error |
|
205 | - */ |
|
206 | - protected function setAutoloadersForRequiredFiles() |
|
207 | - { |
|
208 | - // load interfaces |
|
209 | - EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_CORE . 'interfaces', true); |
|
210 | - // load helpers |
|
211 | - EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_HELPERS); |
|
212 | - // register legacy request stack classes just in case |
|
213 | - EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_CORE . 'request_stack/'); |
|
214 | - // register legacy middleware classes just in case |
|
215 | - EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_CORE . 'middleware/'); |
|
216 | - } |
|
201 | + /** |
|
202 | + * load_required_files |
|
203 | + * |
|
204 | + * @throws EE_Error |
|
205 | + */ |
|
206 | + protected function setAutoloadersForRequiredFiles() |
|
207 | + { |
|
208 | + // load interfaces |
|
209 | + EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_CORE . 'interfaces', true); |
|
210 | + // load helpers |
|
211 | + EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_HELPERS); |
|
212 | + // register legacy request stack classes just in case |
|
213 | + EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_CORE . 'request_stack/'); |
|
214 | + // register legacy middleware classes just in case |
|
215 | + EEH_Autoloader::register_autoloaders_for_each_file_in_folder(EE_CORE . 'middleware/'); |
|
216 | + } |
|
217 | 217 | |
218 | 218 | |
219 | - /** |
|
220 | - * build_request_stack |
|
221 | - * |
|
222 | - * @return RequestStackBuilder |
|
223 | - */ |
|
224 | - public function buildRequestStack(): RequestStackBuilder |
|
225 | - { |
|
226 | - $request_stack_builder = new RequestStackBuilder($this->loader); |
|
227 | - /** |
|
228 | - * ! IMPORTANT ! The middleware stack operates FILO : FIRST IN LAST OUT |
|
229 | - * so items at the beginning of the final middleware stack will run last. |
|
230 | - * First parameter is the middleware classname, second is an array of arguments |
|
231 | - */ |
|
232 | - $stack_apps = apply_filters( |
|
233 | - 'FHEE__EventEspresso_core_services_bootstrap_BootstrapCore__buildRequestStack__stack_apps', |
|
234 | - [ |
|
235 | - // first in last out |
|
236 | - BotDetector::class => [], |
|
237 | - DetectFileEditorRequest::class => [], |
|
238 | - PreProductionVersionWarning::class => [], |
|
239 | - RecommendedVersions::class => [], |
|
240 | - // last in first out |
|
241 | - DetectLogin::class => [], |
|
242 | - ] |
|
243 | - ); |
|
244 | - // legacy filter for backwards compatibility |
|
245 | - $stack_apps = apply_filters( |
|
246 | - 'FHEE__EE_Bootstrap__build_request_stack__stack_apps', |
|
247 | - $stack_apps |
|
248 | - ); |
|
249 | - // load middleware onto stack : FILO (First In Last Out) |
|
250 | - // items at the beginning of the $stack_apps array will run last |
|
251 | - foreach ((array) $stack_apps as $stack_app => $stack_app_args) { |
|
252 | - $request_stack_builder->push([$stack_app, $stack_app_args]); |
|
253 | - } |
|
254 | - // finally, we'll add this on its own because we need it to always be part of the stack |
|
255 | - // and we also need it to always run first because the rest of the system relies on it |
|
256 | - $request_stack_builder->push( |
|
257 | - [SetRequestTypeContextChecker::class, []] |
|
258 | - ); |
|
259 | - return apply_filters( |
|
260 | - 'FHEE__EE_Bootstrap__build_request_stack__request_stack_builder', |
|
261 | - $request_stack_builder |
|
262 | - ); |
|
263 | - } |
|
219 | + /** |
|
220 | + * build_request_stack |
|
221 | + * |
|
222 | + * @return RequestStackBuilder |
|
223 | + */ |
|
224 | + public function buildRequestStack(): RequestStackBuilder |
|
225 | + { |
|
226 | + $request_stack_builder = new RequestStackBuilder($this->loader); |
|
227 | + /** |
|
228 | + * ! IMPORTANT ! The middleware stack operates FILO : FIRST IN LAST OUT |
|
229 | + * so items at the beginning of the final middleware stack will run last. |
|
230 | + * First parameter is the middleware classname, second is an array of arguments |
|
231 | + */ |
|
232 | + $stack_apps = apply_filters( |
|
233 | + 'FHEE__EventEspresso_core_services_bootstrap_BootstrapCore__buildRequestStack__stack_apps', |
|
234 | + [ |
|
235 | + // first in last out |
|
236 | + BotDetector::class => [], |
|
237 | + DetectFileEditorRequest::class => [], |
|
238 | + PreProductionVersionWarning::class => [], |
|
239 | + RecommendedVersions::class => [], |
|
240 | + // last in first out |
|
241 | + DetectLogin::class => [], |
|
242 | + ] |
|
243 | + ); |
|
244 | + // legacy filter for backwards compatibility |
|
245 | + $stack_apps = apply_filters( |
|
246 | + 'FHEE__EE_Bootstrap__build_request_stack__stack_apps', |
|
247 | + $stack_apps |
|
248 | + ); |
|
249 | + // load middleware onto stack : FILO (First In Last Out) |
|
250 | + // items at the beginning of the $stack_apps array will run last |
|
251 | + foreach ((array) $stack_apps as $stack_app => $stack_app_args) { |
|
252 | + $request_stack_builder->push([$stack_app, $stack_app_args]); |
|
253 | + } |
|
254 | + // finally, we'll add this on its own because we need it to always be part of the stack |
|
255 | + // and we also need it to always run first because the rest of the system relies on it |
|
256 | + $request_stack_builder->push( |
|
257 | + [SetRequestTypeContextChecker::class, []] |
|
258 | + ); |
|
259 | + return apply_filters( |
|
260 | + 'FHEE__EE_Bootstrap__build_request_stack__request_stack_builder', |
|
261 | + $request_stack_builder |
|
262 | + ); |
|
263 | + } |
|
264 | 264 | } |
@@ -22,174 +22,174 @@ |
||
22 | 22 | */ |
23 | 23 | class RegistrationPayments |
24 | 24 | { |
25 | - /** |
|
26 | - * update registrations REG_paid field after successful payment and link registrations with payment |
|
27 | - * |
|
28 | - * @param EE_Transaction $transaction |
|
29 | - * @param EE_Payment $payment |
|
30 | - * @param EE_Registration[] $registrations |
|
31 | - * @throws EE_Error |
|
32 | - * @throws ReflectionException |
|
33 | - */ |
|
34 | - public function processRegistrationPayments( |
|
35 | - EE_Transaction $transaction, |
|
36 | - EE_Payment $payment, |
|
37 | - array $registrations = [] |
|
38 | - ) { |
|
39 | - // only process if payment was successful |
|
40 | - if ($payment->status() !== EEM_Payment::status_id_approved) { |
|
41 | - return; |
|
42 | - } |
|
43 | - $registrations = $this->loadRegistrationsIfMissing($transaction, $registrations); |
|
44 | - // still nothing ??!?? |
|
45 | - if (empty($registrations)) { |
|
46 | - return; |
|
47 | - } |
|
48 | - // todo: break out the following logic into a separate strategy class |
|
49 | - // todo: named something like "Sequential_Reg_Payment_Strategy" |
|
50 | - // todo: which would apply payments using the capitalist "first come first paid" approach |
|
51 | - // todo: then have another strategy class like "Distributed_Reg_Payment_Strategy" |
|
52 | - // todo: which would be the socialist "everybody gets a piece of pie" approach, |
|
53 | - // todo: which would be better for deposits, where you want a bit of the payment applied to each registration |
|
54 | - $available_payment_amount = $this->sequentialRegPaymentStrategy($payment, $registrations); |
|
55 | - $this->remainderNotice($payment, $available_payment_amount, $registrations); |
|
56 | - } |
|
25 | + /** |
|
26 | + * update registrations REG_paid field after successful payment and link registrations with payment |
|
27 | + * |
|
28 | + * @param EE_Transaction $transaction |
|
29 | + * @param EE_Payment $payment |
|
30 | + * @param EE_Registration[] $registrations |
|
31 | + * @throws EE_Error |
|
32 | + * @throws ReflectionException |
|
33 | + */ |
|
34 | + public function processRegistrationPayments( |
|
35 | + EE_Transaction $transaction, |
|
36 | + EE_Payment $payment, |
|
37 | + array $registrations = [] |
|
38 | + ) { |
|
39 | + // only process if payment was successful |
|
40 | + if ($payment->status() !== EEM_Payment::status_id_approved) { |
|
41 | + return; |
|
42 | + } |
|
43 | + $registrations = $this->loadRegistrationsIfMissing($transaction, $registrations); |
|
44 | + // still nothing ??!?? |
|
45 | + if (empty($registrations)) { |
|
46 | + return; |
|
47 | + } |
|
48 | + // todo: break out the following logic into a separate strategy class |
|
49 | + // todo: named something like "Sequential_Reg_Payment_Strategy" |
|
50 | + // todo: which would apply payments using the capitalist "first come first paid" approach |
|
51 | + // todo: then have another strategy class like "Distributed_Reg_Payment_Strategy" |
|
52 | + // todo: which would be the socialist "everybody gets a piece of pie" approach, |
|
53 | + // todo: which would be better for deposits, where you want a bit of the payment applied to each registration |
|
54 | + $available_payment_amount = $this->sequentialRegPaymentStrategy($payment, $registrations); |
|
55 | + $this->remainderNotice($payment, $available_payment_amount, $registrations); |
|
56 | + } |
|
57 | 57 | |
58 | 58 | |
59 | - /** |
|
60 | - * @param EE_Transaction $transaction |
|
61 | - * @param array $registrations |
|
62 | - * @return array |
|
63 | - * @throws EE_Error |
|
64 | - * @throws ReflectionException |
|
65 | - */ |
|
66 | - private function loadRegistrationsIfMissing(EE_Transaction $transaction, array $registrations = []): array |
|
67 | - { |
|
68 | - if (empty($registrations)) { |
|
69 | - // find registrations with monies owing that can receive a payment |
|
70 | - $registrations = $transaction->registrations( |
|
71 | - [ |
|
72 | - [ |
|
73 | - // only these reg statuses can receive payments |
|
74 | - 'STS_ID' => ['IN', EEM_Registration::reg_statuses_that_allow_payment()], |
|
75 | - 'REG_final_price' => ['!=', 0], |
|
76 | - 'REG_final_price*' => ['!=', 'REG_paid', true], |
|
77 | - ], |
|
78 | - ] |
|
79 | - ); |
|
80 | - } |
|
81 | - return $registrations; |
|
82 | - } |
|
59 | + /** |
|
60 | + * @param EE_Transaction $transaction |
|
61 | + * @param array $registrations |
|
62 | + * @return array |
|
63 | + * @throws EE_Error |
|
64 | + * @throws ReflectionException |
|
65 | + */ |
|
66 | + private function loadRegistrationsIfMissing(EE_Transaction $transaction, array $registrations = []): array |
|
67 | + { |
|
68 | + if (empty($registrations)) { |
|
69 | + // find registrations with monies owing that can receive a payment |
|
70 | + $registrations = $transaction->registrations( |
|
71 | + [ |
|
72 | + [ |
|
73 | + // only these reg statuses can receive payments |
|
74 | + 'STS_ID' => ['IN', EEM_Registration::reg_statuses_that_allow_payment()], |
|
75 | + 'REG_final_price' => ['!=', 0], |
|
76 | + 'REG_final_price*' => ['!=', 'REG_paid', true], |
|
77 | + ], |
|
78 | + ] |
|
79 | + ); |
|
80 | + } |
|
81 | + return $registrations; |
|
82 | + } |
|
83 | 83 | |
84 | 84 | |
85 | - /** |
|
86 | - * @param EE_Payment $payment |
|
87 | - * @param array $registrations |
|
88 | - * @return float |
|
89 | - * @throws EE_Error |
|
90 | - * @throws ReflectionException |
|
91 | - */ |
|
92 | - private function sequentialRegPaymentStrategy(EE_Payment $payment, array $registrations): float |
|
93 | - { |
|
94 | - $refund = $payment->is_a_refund(); |
|
95 | - // how much is available to apply to registrations? |
|
96 | - $available_payment_amount = (float) abs($payment->amount()); |
|
97 | - foreach ($registrations as $registration) { |
|
98 | - if ($registration instanceof EE_Registration) { |
|
99 | - // nothing left? |
|
100 | - if ($available_payment_amount <= 0) { |
|
101 | - break; |
|
102 | - } |
|
103 | - if ($refund) { |
|
104 | - $available_payment_amount = $this->processRegistrationRefund( |
|
105 | - $registration, |
|
106 | - $payment, |
|
107 | - $available_payment_amount |
|
108 | - ); |
|
109 | - } else { |
|
110 | - $available_payment_amount = $this->processRegistrationPayment( |
|
111 | - $registration, |
|
112 | - $payment, |
|
113 | - $available_payment_amount |
|
114 | - ); |
|
115 | - } |
|
116 | - } |
|
117 | - } |
|
118 | - return $available_payment_amount; |
|
119 | - } |
|
85 | + /** |
|
86 | + * @param EE_Payment $payment |
|
87 | + * @param array $registrations |
|
88 | + * @return float |
|
89 | + * @throws EE_Error |
|
90 | + * @throws ReflectionException |
|
91 | + */ |
|
92 | + private function sequentialRegPaymentStrategy(EE_Payment $payment, array $registrations): float |
|
93 | + { |
|
94 | + $refund = $payment->is_a_refund(); |
|
95 | + // how much is available to apply to registrations? |
|
96 | + $available_payment_amount = (float) abs($payment->amount()); |
|
97 | + foreach ($registrations as $registration) { |
|
98 | + if ($registration instanceof EE_Registration) { |
|
99 | + // nothing left? |
|
100 | + if ($available_payment_amount <= 0) { |
|
101 | + break; |
|
102 | + } |
|
103 | + if ($refund) { |
|
104 | + $available_payment_amount = $this->processRegistrationRefund( |
|
105 | + $registration, |
|
106 | + $payment, |
|
107 | + $available_payment_amount |
|
108 | + ); |
|
109 | + } else { |
|
110 | + $available_payment_amount = $this->processRegistrationPayment( |
|
111 | + $registration, |
|
112 | + $payment, |
|
113 | + $available_payment_amount |
|
114 | + ); |
|
115 | + } |
|
116 | + } |
|
117 | + } |
|
118 | + return $available_payment_amount; |
|
119 | + } |
|
120 | 120 | |
121 | 121 | |
122 | - /** |
|
123 | - * @throws EE_Error |
|
124 | - */ |
|
125 | - private function remainderNotice(EE_Payment $payment, float $available_payment_amount, array $registrations) |
|
126 | - { |
|
127 | - if ( |
|
128 | - $available_payment_amount > 0 |
|
129 | - && apply_filters( |
|
130 | - 'FHEE__EE_Payment_Processor__process_registration_payments__display_notifications', |
|
131 | - false |
|
132 | - ) |
|
133 | - ) { |
|
134 | - EE_Error::add_attention( |
|
135 | - sprintf( |
|
136 | - esc_html__( |
|
137 | - 'A remainder of %1$s exists after applying this payment to Registration(s) %2$s.%3$sPlease verify that the original payment amount of %4$s is correct. If so, you should edit this payment and select at least one additional registration in the "Registrations to Apply Payment to" section, so that the remainder of this payment can be applied to the additional registration(s).', |
|
138 | - 'event_espresso' |
|
139 | - ), |
|
140 | - EEH_Template::format_currency($available_payment_amount), |
|
141 | - implode(', ', array_keys($registrations)), |
|
142 | - '<br/>', |
|
143 | - EEH_Template::format_currency($payment->amount()) |
|
144 | - ), |
|
145 | - __FILE__, |
|
146 | - __FUNCTION__, |
|
147 | - __LINE__ |
|
148 | - ); |
|
149 | - } |
|
150 | - } |
|
122 | + /** |
|
123 | + * @throws EE_Error |
|
124 | + */ |
|
125 | + private function remainderNotice(EE_Payment $payment, float $available_payment_amount, array $registrations) |
|
126 | + { |
|
127 | + if ( |
|
128 | + $available_payment_amount > 0 |
|
129 | + && apply_filters( |
|
130 | + 'FHEE__EE_Payment_Processor__process_registration_payments__display_notifications', |
|
131 | + false |
|
132 | + ) |
|
133 | + ) { |
|
134 | + EE_Error::add_attention( |
|
135 | + sprintf( |
|
136 | + esc_html__( |
|
137 | + 'A remainder of %1$s exists after applying this payment to Registration(s) %2$s.%3$sPlease verify that the original payment amount of %4$s is correct. If so, you should edit this payment and select at least one additional registration in the "Registrations to Apply Payment to" section, so that the remainder of this payment can be applied to the additional registration(s).', |
|
138 | + 'event_espresso' |
|
139 | + ), |
|
140 | + EEH_Template::format_currency($available_payment_amount), |
|
141 | + implode(', ', array_keys($registrations)), |
|
142 | + '<br/>', |
|
143 | + EEH_Template::format_currency($payment->amount()) |
|
144 | + ), |
|
145 | + __FILE__, |
|
146 | + __FUNCTION__, |
|
147 | + __LINE__ |
|
148 | + ); |
|
149 | + } |
|
150 | + } |
|
151 | 151 | |
152 | 152 | |
153 | - /** |
|
154 | - * update registration REG_paid field after successful payment and link registration with payment |
|
155 | - * |
|
156 | - * @param EE_Registration $registration |
|
157 | - * @param EE_Payment $payment |
|
158 | - * @param float $available_payment_amount |
|
159 | - * @return float |
|
160 | - * @throws EE_Error |
|
161 | - * @throws ReflectionException |
|
162 | - * @throws ReflectionException |
|
163 | - */ |
|
164 | - public function processRegistrationPayment( |
|
165 | - EE_Registration $registration, |
|
166 | - EE_Payment $payment, |
|
167 | - float $available_payment_amount = 0.00 |
|
168 | - ): float { |
|
169 | - // update $available_payment_amount |
|
170 | - $available_payment_amount -= $registration->applyPayment($payment, $available_payment_amount); |
|
171 | - return $available_payment_amount; |
|
172 | - } |
|
153 | + /** |
|
154 | + * update registration REG_paid field after successful payment and link registration with payment |
|
155 | + * |
|
156 | + * @param EE_Registration $registration |
|
157 | + * @param EE_Payment $payment |
|
158 | + * @param float $available_payment_amount |
|
159 | + * @return float |
|
160 | + * @throws EE_Error |
|
161 | + * @throws ReflectionException |
|
162 | + * @throws ReflectionException |
|
163 | + */ |
|
164 | + public function processRegistrationPayment( |
|
165 | + EE_Registration $registration, |
|
166 | + EE_Payment $payment, |
|
167 | + float $available_payment_amount = 0.00 |
|
168 | + ): float { |
|
169 | + // update $available_payment_amount |
|
170 | + $available_payment_amount -= $registration->applyPayment($payment, $available_payment_amount); |
|
171 | + return $available_payment_amount; |
|
172 | + } |
|
173 | 173 | |
174 | 174 | |
175 | - /** |
|
176 | - * update registration REG_paid field after refund and link registration with payment |
|
177 | - * |
|
178 | - * @param EE_Registration $registration |
|
179 | - * @param EE_Payment $payment |
|
180 | - * @param float $available_refund_amount - IMPORTANT !!! SEND AVAILABLE REFUND AMOUNT AS A POSITIVE NUMBER |
|
181 | - * @return float |
|
182 | - * @throws EE_Error |
|
183 | - * @throws ReflectionException |
|
184 | - * @throws ReflectionException |
|
185 | - */ |
|
186 | - public function processRegistrationRefund( |
|
187 | - EE_Registration $registration, |
|
188 | - EE_Payment $payment, |
|
189 | - float $available_refund_amount = 0.00 |
|
190 | - ): float { |
|
191 | - // update $available_payment_amount |
|
192 | - $available_refund_amount -= $registration->applyPayment($payment, $available_refund_amount); |
|
193 | - return $available_refund_amount; |
|
194 | - } |
|
175 | + /** |
|
176 | + * update registration REG_paid field after refund and link registration with payment |
|
177 | + * |
|
178 | + * @param EE_Registration $registration |
|
179 | + * @param EE_Payment $payment |
|
180 | + * @param float $available_refund_amount - IMPORTANT !!! SEND AVAILABLE REFUND AMOUNT AS A POSITIVE NUMBER |
|
181 | + * @return float |
|
182 | + * @throws EE_Error |
|
183 | + * @throws ReflectionException |
|
184 | + * @throws ReflectionException |
|
185 | + */ |
|
186 | + public function processRegistrationRefund( |
|
187 | + EE_Registration $registration, |
|
188 | + EE_Payment $payment, |
|
189 | + float $available_refund_amount = 0.00 |
|
190 | + ): float { |
|
191 | + // update $available_payment_amount |
|
192 | + $available_refund_amount -= $registration->applyPayment($payment, $available_refund_amount); |
|
193 | + return $available_refund_amount; |
|
194 | + } |
|
195 | 195 | } |
@@ -29,316 +29,316 @@ |
||
29 | 29 | */ |
30 | 30 | class PaymentProcessor |
31 | 31 | { |
32 | - private EEM_Payment_Method $payment_method_model; |
|
32 | + private EEM_Payment_Method $payment_method_model; |
|
33 | 33 | |
34 | - private EEM_Transaction $transaction_model; |
|
34 | + private EEM_Transaction $transaction_model; |
|
35 | 35 | |
36 | - private EE_Organization_Config $organization; |
|
36 | + private EE_Organization_Config $organization; |
|
37 | 37 | |
38 | - private FeatureFlags $feature; |
|
38 | + private FeatureFlags $feature; |
|
39 | 39 | |
40 | - private PaymentProcessorFees $payment_processor_fees; |
|
40 | + private PaymentProcessorFees $payment_processor_fees; |
|
41 | 41 | |
42 | - private PostPaymentProcessor $post_payment_processor; |
|
42 | + private PostPaymentProcessor $post_payment_processor; |
|
43 | 43 | |
44 | - private RegistrationPayments $registration_payments; |
|
44 | + private RegistrationPayments $registration_payments; |
|
45 | 45 | |
46 | 46 | |
47 | - /** |
|
48 | - * @param EEM_Payment_Method $payment_method_model |
|
49 | - * @param EEM_Transaction $transaction_model |
|
50 | - * @param EE_Organization_Config $organization |
|
51 | - * @param FeatureFlags $feature |
|
52 | - * @param PaymentProcessorFees $payment_processor_fees |
|
53 | - * @param PostPaymentProcessor $post_payment_processor |
|
54 | - * @param RegistrationPayments $registration_payments |
|
55 | - */ |
|
56 | - public function __construct( |
|
57 | - EEM_Payment_Method $payment_method_model, |
|
58 | - EEM_Transaction $transaction_model, |
|
59 | - EE_Organization_Config $organization, |
|
60 | - FeatureFlags $feature, |
|
61 | - PaymentProcessorFees $payment_processor_fees, |
|
62 | - PostPaymentProcessor $post_payment_processor, |
|
63 | - RegistrationPayments $registration_payments |
|
64 | - ) { |
|
65 | - $this->payment_method_model = $payment_method_model; |
|
66 | - $this->transaction_model = $transaction_model; |
|
67 | - $this->organization = $organization; |
|
68 | - $this->feature = $feature; |
|
69 | - $this->payment_processor_fees = $payment_processor_fees; |
|
70 | - $this->post_payment_processor = $post_payment_processor; |
|
71 | - $this->registration_payments = $registration_payments; |
|
72 | - } |
|
47 | + /** |
|
48 | + * @param EEM_Payment_Method $payment_method_model |
|
49 | + * @param EEM_Transaction $transaction_model |
|
50 | + * @param EE_Organization_Config $organization |
|
51 | + * @param FeatureFlags $feature |
|
52 | + * @param PaymentProcessorFees $payment_processor_fees |
|
53 | + * @param PostPaymentProcessor $post_payment_processor |
|
54 | + * @param RegistrationPayments $registration_payments |
|
55 | + */ |
|
56 | + public function __construct( |
|
57 | + EEM_Payment_Method $payment_method_model, |
|
58 | + EEM_Transaction $transaction_model, |
|
59 | + EE_Organization_Config $organization, |
|
60 | + FeatureFlags $feature, |
|
61 | + PaymentProcessorFees $payment_processor_fees, |
|
62 | + PostPaymentProcessor $post_payment_processor, |
|
63 | + RegistrationPayments $registration_payments |
|
64 | + ) { |
|
65 | + $this->payment_method_model = $payment_method_model; |
|
66 | + $this->transaction_model = $transaction_model; |
|
67 | + $this->organization = $organization; |
|
68 | + $this->feature = $feature; |
|
69 | + $this->payment_processor_fees = $payment_processor_fees; |
|
70 | + $this->post_payment_processor = $post_payment_processor; |
|
71 | + $this->registration_payments = $registration_payments; |
|
72 | + } |
|
73 | 73 | |
74 | 74 | |
75 | - /** |
|
76 | - * Using the selected gateway, processes the payment for that transaction, and updates the transaction |
|
77 | - * appropriately. Saves the payment that is generated |
|
78 | - * |
|
79 | - * @param EE_Payment_Method $payment_method |
|
80 | - * @param EE_Transaction $transaction |
|
81 | - * @param EE_Billing_Info_Form|null $billing_form (or probably null, if it's an offline or offsite payment |
|
82 | - * method). |
|
83 | - * Receive_form_submission() should have |
|
84 | - * already been called on the billing form |
|
85 | - * (ie, its inputs should have their normalized values set). |
|
86 | - * @param float $amount if only part of the transaction is to be paid for, how much. |
|
87 | - * Leave null if payment is for the full amount owing |
|
88 | - * @param bool $by_admin TRUE if payment is being attempted from the admin |
|
89 | - * @param bool $update_txn whether to call EE_Transaction_Processor |
|
90 | - * ::update_transaction_and_registrations_after_checkout_or_payment() |
|
91 | - * @param string $return_url string used mostly by offsite gateways to specify |
|
92 | - * where to go AFTER the offsite gateway |
|
93 | - * @param string $cancel_url URL to return to if off-site payments are cancelled |
|
94 | - * @param string $method like 'CART', indicates who the client who called this was |
|
95 | - * @return EE_Payment|null |
|
96 | - * @throws EE_Error |
|
97 | - * @throws Exception |
|
98 | - * @throws ReflectionException |
|
99 | - */ |
|
100 | - public function processPayment( |
|
101 | - EE_Payment_Method $payment_method, |
|
102 | - EE_Transaction $transaction, |
|
103 | - ?EE_Billing_Info_Form $billing_form = null, |
|
104 | - float $amount = 0.00, |
|
105 | - bool $by_admin = false, |
|
106 | - bool $update_txn = true, |
|
107 | - string $return_url = '', |
|
108 | - string $cancel_url = '', |
|
109 | - string $method = 'CART' |
|
110 | - ): ?EE_Payment { |
|
111 | - $this->validatePaymentAmount($transaction, $amount); |
|
112 | - // verify payment method |
|
113 | - $payment_method = $this->payment_method_model->ensure_is_obj( |
|
114 | - $payment_method, |
|
115 | - true |
|
116 | - ); |
|
117 | - // verify transaction |
|
118 | - $this->transaction_model->ensure_is_obj($transaction); |
|
119 | - $transaction->set_payment_method_ID($payment_method->ID()); |
|
120 | - // make sure we don't overcharge |
|
121 | - $amount = min($amount, $transaction->remaining()); |
|
122 | - // TODO: add some extra logic to PaymentProcessorFees to designate where/when partner fees are applied based on the PM being used. |
|
123 | - // if ( |
|
124 | - // $this->feature->allowed(FeatureFlag::USE_PAYMENT_PROCESSOR_FEES) |
|
125 | - // && apply_filters( |
|
126 | - // 'FHEE__EE_Payment_Processor__apply_gateway_partner_fees', |
|
127 | - // true, |
|
128 | - // $transaction, |
|
129 | - // $payment_method, |
|
130 | - // $amount |
|
131 | - // ) |
|
132 | - // ) { |
|
133 | - // $amount = $this->payment_processor_fees->applyGatewayPartnerFees( |
|
134 | - // $transaction, |
|
135 | - // $payment_method->name(), |
|
136 | - // $amount |
|
137 | - // ); |
|
138 | - // } |
|
139 | - // verify payment method type |
|
140 | - if ($payment_method->type_obj() instanceof EE_PMT_Base) { |
|
141 | - $payment = $payment_method->type_obj()->process_payment( |
|
142 | - $transaction, |
|
143 | - $amount, |
|
144 | - $billing_form, |
|
145 | - $return_url, |
|
146 | - add_query_arg(['ee_cancel_payment' => true], $cancel_url), |
|
147 | - $method, |
|
148 | - $by_admin |
|
149 | - ); |
|
150 | - // check if payment method uses an off-site gateway |
|
151 | - if ($payment_method->type_obj()->payment_occurs() !== EE_PMT_Base::offsite) { |
|
152 | - // don't process payments for off-site gateways yet because no payment has occurred yet |
|
153 | - $this->updateTransactionBasedOnPayment($transaction, $payment, $update_txn); |
|
154 | - } |
|
155 | - return $payment; |
|
156 | - } |
|
157 | - EE_Error::add_error( |
|
158 | - sprintf( |
|
159 | - esc_html__( |
|
160 | - 'A valid payment method could not be determined due to a technical issue.%1$sPlease try again or contact %2$s for assistance.', |
|
161 | - 'event_espresso' |
|
162 | - ), |
|
163 | - '<br/>', |
|
164 | - $this->organization->get_pretty('email') |
|
165 | - ), |
|
166 | - __FILE__, |
|
167 | - __FUNCTION__, |
|
168 | - __LINE__ |
|
169 | - ); |
|
170 | - return null; |
|
171 | - } |
|
75 | + /** |
|
76 | + * Using the selected gateway, processes the payment for that transaction, and updates the transaction |
|
77 | + * appropriately. Saves the payment that is generated |
|
78 | + * |
|
79 | + * @param EE_Payment_Method $payment_method |
|
80 | + * @param EE_Transaction $transaction |
|
81 | + * @param EE_Billing_Info_Form|null $billing_form (or probably null, if it's an offline or offsite payment |
|
82 | + * method). |
|
83 | + * Receive_form_submission() should have |
|
84 | + * already been called on the billing form |
|
85 | + * (ie, its inputs should have their normalized values set). |
|
86 | + * @param float $amount if only part of the transaction is to be paid for, how much. |
|
87 | + * Leave null if payment is for the full amount owing |
|
88 | + * @param bool $by_admin TRUE if payment is being attempted from the admin |
|
89 | + * @param bool $update_txn whether to call EE_Transaction_Processor |
|
90 | + * ::update_transaction_and_registrations_after_checkout_or_payment() |
|
91 | + * @param string $return_url string used mostly by offsite gateways to specify |
|
92 | + * where to go AFTER the offsite gateway |
|
93 | + * @param string $cancel_url URL to return to if off-site payments are cancelled |
|
94 | + * @param string $method like 'CART', indicates who the client who called this was |
|
95 | + * @return EE_Payment|null |
|
96 | + * @throws EE_Error |
|
97 | + * @throws Exception |
|
98 | + * @throws ReflectionException |
|
99 | + */ |
|
100 | + public function processPayment( |
|
101 | + EE_Payment_Method $payment_method, |
|
102 | + EE_Transaction $transaction, |
|
103 | + ?EE_Billing_Info_Form $billing_form = null, |
|
104 | + float $amount = 0.00, |
|
105 | + bool $by_admin = false, |
|
106 | + bool $update_txn = true, |
|
107 | + string $return_url = '', |
|
108 | + string $cancel_url = '', |
|
109 | + string $method = 'CART' |
|
110 | + ): ?EE_Payment { |
|
111 | + $this->validatePaymentAmount($transaction, $amount); |
|
112 | + // verify payment method |
|
113 | + $payment_method = $this->payment_method_model->ensure_is_obj( |
|
114 | + $payment_method, |
|
115 | + true |
|
116 | + ); |
|
117 | + // verify transaction |
|
118 | + $this->transaction_model->ensure_is_obj($transaction); |
|
119 | + $transaction->set_payment_method_ID($payment_method->ID()); |
|
120 | + // make sure we don't overcharge |
|
121 | + $amount = min($amount, $transaction->remaining()); |
|
122 | + // TODO: add some extra logic to PaymentProcessorFees to designate where/when partner fees are applied based on the PM being used. |
|
123 | + // if ( |
|
124 | + // $this->feature->allowed(FeatureFlag::USE_PAYMENT_PROCESSOR_FEES) |
|
125 | + // && apply_filters( |
|
126 | + // 'FHEE__EE_Payment_Processor__apply_gateway_partner_fees', |
|
127 | + // true, |
|
128 | + // $transaction, |
|
129 | + // $payment_method, |
|
130 | + // $amount |
|
131 | + // ) |
|
132 | + // ) { |
|
133 | + // $amount = $this->payment_processor_fees->applyGatewayPartnerFees( |
|
134 | + // $transaction, |
|
135 | + // $payment_method->name(), |
|
136 | + // $amount |
|
137 | + // ); |
|
138 | + // } |
|
139 | + // verify payment method type |
|
140 | + if ($payment_method->type_obj() instanceof EE_PMT_Base) { |
|
141 | + $payment = $payment_method->type_obj()->process_payment( |
|
142 | + $transaction, |
|
143 | + $amount, |
|
144 | + $billing_form, |
|
145 | + $return_url, |
|
146 | + add_query_arg(['ee_cancel_payment' => true], $cancel_url), |
|
147 | + $method, |
|
148 | + $by_admin |
|
149 | + ); |
|
150 | + // check if payment method uses an off-site gateway |
|
151 | + if ($payment_method->type_obj()->payment_occurs() !== EE_PMT_Base::offsite) { |
|
152 | + // don't process payments for off-site gateways yet because no payment has occurred yet |
|
153 | + $this->updateTransactionBasedOnPayment($transaction, $payment, $update_txn); |
|
154 | + } |
|
155 | + return $payment; |
|
156 | + } |
|
157 | + EE_Error::add_error( |
|
158 | + sprintf( |
|
159 | + esc_html__( |
|
160 | + 'A valid payment method could not be determined due to a technical issue.%1$sPlease try again or contact %2$s for assistance.', |
|
161 | + 'event_espresso' |
|
162 | + ), |
|
163 | + '<br/>', |
|
164 | + $this->organization->get_pretty('email') |
|
165 | + ), |
|
166 | + __FILE__, |
|
167 | + __FUNCTION__, |
|
168 | + __LINE__ |
|
169 | + ); |
|
170 | + return null; |
|
171 | + } |
|
172 | 172 | |
173 | 173 | |
174 | - /** |
|
175 | - * Processes a direct refund request, saves the payment, and updates the transaction appropriately. |
|
176 | - * |
|
177 | - * @param EE_Payment_Method|null $payment_method |
|
178 | - * @param EE_Payment $payment_to_refund |
|
179 | - * @param array $refund_info |
|
180 | - * @return EE_Payment |
|
181 | - * @throws EE_Error |
|
182 | - * @throws ReflectionException |
|
183 | - */ |
|
184 | - public function processRefund( |
|
185 | - ?EE_Payment_Method $payment_method, |
|
186 | - EE_Payment $payment_to_refund, |
|
187 | - array $refund_info = [] |
|
188 | - ): EE_Payment { |
|
189 | - if ($payment_method instanceof EE_Payment_Method && $payment_method->type_obj()->supports_sending_refunds()) { |
|
190 | - $payment_method->type_obj()->process_refund($payment_to_refund, $refund_info); |
|
191 | - $this->updateTransactionBasedOnPayment( |
|
192 | - $payment_to_refund->transaction(), |
|
193 | - $payment_to_refund |
|
194 | - ); |
|
195 | - } |
|
196 | - return $payment_to_refund; |
|
197 | - } |
|
174 | + /** |
|
175 | + * Processes a direct refund request, saves the payment, and updates the transaction appropriately. |
|
176 | + * |
|
177 | + * @param EE_Payment_Method|null $payment_method |
|
178 | + * @param EE_Payment $payment_to_refund |
|
179 | + * @param array $refund_info |
|
180 | + * @return EE_Payment |
|
181 | + * @throws EE_Error |
|
182 | + * @throws ReflectionException |
|
183 | + */ |
|
184 | + public function processRefund( |
|
185 | + ?EE_Payment_Method $payment_method, |
|
186 | + EE_Payment $payment_to_refund, |
|
187 | + array $refund_info = [] |
|
188 | + ): EE_Payment { |
|
189 | + if ($payment_method instanceof EE_Payment_Method && $payment_method->type_obj()->supports_sending_refunds()) { |
|
190 | + $payment_method->type_obj()->process_refund($payment_to_refund, $refund_info); |
|
191 | + $this->updateTransactionBasedOnPayment( |
|
192 | + $payment_to_refund->transaction(), |
|
193 | + $payment_to_refund |
|
194 | + ); |
|
195 | + } |
|
196 | + return $payment_to_refund; |
|
197 | + } |
|
198 | 198 | |
199 | 199 | |
200 | - /** |
|
201 | - * This should be called each time there may have been an update to a |
|
202 | - * payment on a transaction (ie, we asked for a payment to process a |
|
203 | - * payment for a transaction, or we told a payment method about an IPN, or |
|
204 | - * we told a payment method to |
|
205 | - * "finalize_payment_for" (a transaction), or we told a payment method to |
|
206 | - * process a refund. This should handle firing the correct hooks to |
|
207 | - * indicate |
|
208 | - * what exactly happened and updating the transaction appropriately). This |
|
209 | - * could be integrated directly into EE_Transaction upon save, but we want |
|
210 | - * this logic to be separate from 'normal' plain-jane saving and updating |
|
211 | - * of transactions and payments, and to be tied to payment processing. |
|
212 | - * Note: this method DOES NOT save the payment passed into it. It is the responsibility |
|
213 | - * of previous code to decide whether to save (because the payment passed into |
|
214 | - * this method might be a temporary, never-to-be-saved payment from an offline gateway, |
|
215 | - * in which case we only want that payment object for some temporary usage during this request, |
|
216 | - * but we don't want it to be saved). |
|
217 | - * |
|
218 | - * @param EE_Transaction $transaction |
|
219 | - * @param EE_Payment|null $payment |
|
220 | - * @param bool $update_txn whether to call EE_Transaction_Processor:: |
|
221 | - * update_transaction_and_registrations_after_checkout_or_payment() |
|
222 | - * (you can save 1 DB query if you know you're going |
|
223 | - * to save it later instead) |
|
224 | - * @param bool $IPN |
|
225 | - * if processing IPNs or other similar payment |
|
226 | - * related activities that occur in alternate |
|
227 | - * requests than the main one that is processing the |
|
228 | - * TXN, then set this to true to check whether the |
|
229 | - * TXN is locked before updating |
|
230 | - * @throws EE_Error |
|
231 | - * @throws ReflectionException |
|
232 | - */ |
|
233 | - public function updateTransactionBasedOnPayment( |
|
234 | - EE_Transaction $transaction, |
|
235 | - ?EE_Payment $payment, |
|
236 | - bool $update_txn = true, |
|
237 | - bool $IPN = false |
|
238 | - ) { |
|
239 | - $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__not_successful'; |
|
240 | - /** @type EE_Transaction $transaction */ |
|
241 | - $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
242 | - // can we freely update the TXN at this moment? |
|
243 | - if ($IPN && $transaction->is_locked()) { |
|
244 | - // don't update the transaction at this exact moment |
|
245 | - // because the TXN is active in another request |
|
246 | - EE_Cron_Tasks::schedule_update_transaction_with_payment( |
|
247 | - time(), |
|
248 | - $transaction->ID(), |
|
249 | - $payment->ID() |
|
250 | - ); |
|
251 | - } else { |
|
252 | - // verify payment and that it has been saved |
|
253 | - if ($payment instanceof EE_Payment) { |
|
254 | - $do_action = $this->processRegistrationPayments($transaction, $payment, $do_action); |
|
255 | - $this->updateTransactionAndPayment($transaction, $payment, $update_txn, $IPN); |
|
256 | - } |
|
257 | - // granular hook for others to use. |
|
258 | - do_action($do_action, $transaction, $payment); |
|
259 | - do_action('AHEE_log', __CLASS__, __FUNCTION__, $do_action, '$do_action'); |
|
260 | - // global hook for others to use. |
|
261 | - do_action('AHEE__EE_Payment_Processor__update_txn_based_on_payment', $transaction, $payment); |
|
262 | - } |
|
263 | - } |
|
200 | + /** |
|
201 | + * This should be called each time there may have been an update to a |
|
202 | + * payment on a transaction (ie, we asked for a payment to process a |
|
203 | + * payment for a transaction, or we told a payment method about an IPN, or |
|
204 | + * we told a payment method to |
|
205 | + * "finalize_payment_for" (a transaction), or we told a payment method to |
|
206 | + * process a refund. This should handle firing the correct hooks to |
|
207 | + * indicate |
|
208 | + * what exactly happened and updating the transaction appropriately). This |
|
209 | + * could be integrated directly into EE_Transaction upon save, but we want |
|
210 | + * this logic to be separate from 'normal' plain-jane saving and updating |
|
211 | + * of transactions and payments, and to be tied to payment processing. |
|
212 | + * Note: this method DOES NOT save the payment passed into it. It is the responsibility |
|
213 | + * of previous code to decide whether to save (because the payment passed into |
|
214 | + * this method might be a temporary, never-to-be-saved payment from an offline gateway, |
|
215 | + * in which case we only want that payment object for some temporary usage during this request, |
|
216 | + * but we don't want it to be saved). |
|
217 | + * |
|
218 | + * @param EE_Transaction $transaction |
|
219 | + * @param EE_Payment|null $payment |
|
220 | + * @param bool $update_txn whether to call EE_Transaction_Processor:: |
|
221 | + * update_transaction_and_registrations_after_checkout_or_payment() |
|
222 | + * (you can save 1 DB query if you know you're going |
|
223 | + * to save it later instead) |
|
224 | + * @param bool $IPN |
|
225 | + * if processing IPNs or other similar payment |
|
226 | + * related activities that occur in alternate |
|
227 | + * requests than the main one that is processing the |
|
228 | + * TXN, then set this to true to check whether the |
|
229 | + * TXN is locked before updating |
|
230 | + * @throws EE_Error |
|
231 | + * @throws ReflectionException |
|
232 | + */ |
|
233 | + public function updateTransactionBasedOnPayment( |
|
234 | + EE_Transaction $transaction, |
|
235 | + ?EE_Payment $payment, |
|
236 | + bool $update_txn = true, |
|
237 | + bool $IPN = false |
|
238 | + ) { |
|
239 | + $do_action = 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__not_successful'; |
|
240 | + /** @type EE_Transaction $transaction */ |
|
241 | + $transaction = EEM_Transaction::instance()->ensure_is_obj($transaction); |
|
242 | + // can we freely update the TXN at this moment? |
|
243 | + if ($IPN && $transaction->is_locked()) { |
|
244 | + // don't update the transaction at this exact moment |
|
245 | + // because the TXN is active in another request |
|
246 | + EE_Cron_Tasks::schedule_update_transaction_with_payment( |
|
247 | + time(), |
|
248 | + $transaction->ID(), |
|
249 | + $payment->ID() |
|
250 | + ); |
|
251 | + } else { |
|
252 | + // verify payment and that it has been saved |
|
253 | + if ($payment instanceof EE_Payment) { |
|
254 | + $do_action = $this->processRegistrationPayments($transaction, $payment, $do_action); |
|
255 | + $this->updateTransactionAndPayment($transaction, $payment, $update_txn, $IPN); |
|
256 | + } |
|
257 | + // granular hook for others to use. |
|
258 | + do_action($do_action, $transaction, $payment); |
|
259 | + do_action('AHEE_log', __CLASS__, __FUNCTION__, $do_action, '$do_action'); |
|
260 | + // global hook for others to use. |
|
261 | + do_action('AHEE__EE_Payment_Processor__update_txn_based_on_payment', $transaction, $payment); |
|
262 | + } |
|
263 | + } |
|
264 | 264 | |
265 | 265 | |
266 | - /** |
|
267 | - * @param EE_Transaction $transaction |
|
268 | - * @param EE_Payment $payment |
|
269 | - * @param string $do_action |
|
270 | - * @return string |
|
271 | - * @throws EE_Error |
|
272 | - * @throws ReflectionException |
|
273 | - */ |
|
274 | - private function processRegistrationPayments( |
|
275 | - EE_Transaction $transaction, |
|
276 | - EE_Payment $payment, |
|
277 | - string $do_action |
|
278 | - ): string { |
|
279 | - if ($payment->ID()) { |
|
280 | - if ( |
|
281 | - $payment->payment_method() instanceof EE_Payment_Method |
|
282 | - && $payment->payment_method()->type_obj() instanceof EE_PMT_Base |
|
283 | - ) { |
|
284 | - $payment->payment_method()->type_obj()->update_txn_based_on_payment($payment); |
|
285 | - // update TXN registrations with payment info |
|
286 | - $this->registration_payments->processRegistrationPayments($transaction, $payment); |
|
287 | - } |
|
288 | - return $payment->just_approved() |
|
289 | - ? 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__successful' |
|
290 | - : $do_action; |
|
291 | - } |
|
292 | - // send out notifications |
|
293 | - add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true'); |
|
294 | - return 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__no_payment_made'; |
|
295 | - } |
|
266 | + /** |
|
267 | + * @param EE_Transaction $transaction |
|
268 | + * @param EE_Payment $payment |
|
269 | + * @param string $do_action |
|
270 | + * @return string |
|
271 | + * @throws EE_Error |
|
272 | + * @throws ReflectionException |
|
273 | + */ |
|
274 | + private function processRegistrationPayments( |
|
275 | + EE_Transaction $transaction, |
|
276 | + EE_Payment $payment, |
|
277 | + string $do_action |
|
278 | + ): string { |
|
279 | + if ($payment->ID()) { |
|
280 | + if ( |
|
281 | + $payment->payment_method() instanceof EE_Payment_Method |
|
282 | + && $payment->payment_method()->type_obj() instanceof EE_PMT_Base |
|
283 | + ) { |
|
284 | + $payment->payment_method()->type_obj()->update_txn_based_on_payment($payment); |
|
285 | + // update TXN registrations with payment info |
|
286 | + $this->registration_payments->processRegistrationPayments($transaction, $payment); |
|
287 | + } |
|
288 | + return $payment->just_approved() |
|
289 | + ? 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__successful' |
|
290 | + : $do_action; |
|
291 | + } |
|
292 | + // send out notifications |
|
293 | + add_filter('FHEE__EED_Messages___maybe_registration__deliver_notifications', '__return_true'); |
|
294 | + return 'AHEE__EE_Payment_Processor__update_txn_based_on_payment__no_payment_made'; |
|
295 | + } |
|
296 | 296 | |
297 | 297 | |
298 | - /** |
|
299 | - * @param EE_Transaction $transaction |
|
300 | - * @param EE_Payment $payment |
|
301 | - * @param bool $update_txn |
|
302 | - * @param bool $IPN |
|
303 | - * @return void |
|
304 | - * @throws EE_Error |
|
305 | - * @throws ReflectionException |
|
306 | - */ |
|
307 | - private function updateTransactionAndPayment( |
|
308 | - EE_Transaction $transaction, |
|
309 | - EE_Payment $payment, |
|
310 | - bool $update_txn, |
|
311 | - bool $IPN |
|
312 | - ) { |
|
313 | - if ($payment->status() !== EEM_Payment::status_id_failed) { |
|
314 | - /** @type EE_Transaction_Payments $transaction_payments */ |
|
315 | - $transaction_payments = EE_Registry::instance()->load_class('Transaction_Payments'); |
|
316 | - // set new value for total paid |
|
317 | - $transaction_payments->calculate_total_payments_and_update_status($transaction); |
|
318 | - if ($update_txn) { |
|
319 | - $this->post_payment_processor->updateTransactionAndPayment($transaction, $payment, $IPN); |
|
320 | - } |
|
321 | - } |
|
322 | - } |
|
298 | + /** |
|
299 | + * @param EE_Transaction $transaction |
|
300 | + * @param EE_Payment $payment |
|
301 | + * @param bool $update_txn |
|
302 | + * @param bool $IPN |
|
303 | + * @return void |
|
304 | + * @throws EE_Error |
|
305 | + * @throws ReflectionException |
|
306 | + */ |
|
307 | + private function updateTransactionAndPayment( |
|
308 | + EE_Transaction $transaction, |
|
309 | + EE_Payment $payment, |
|
310 | + bool $update_txn, |
|
311 | + bool $IPN |
|
312 | + ) { |
|
313 | + if ($payment->status() !== EEM_Payment::status_id_failed) { |
|
314 | + /** @type EE_Transaction_Payments $transaction_payments */ |
|
315 | + $transaction_payments = EE_Registry::instance()->load_class('Transaction_Payments'); |
|
316 | + // set new value for total paid |
|
317 | + $transaction_payments->calculate_total_payments_and_update_status($transaction); |
|
318 | + if ($update_txn) { |
|
319 | + $this->post_payment_processor->updateTransactionAndPayment($transaction, $payment, $IPN); |
|
320 | + } |
|
321 | + } |
|
322 | + } |
|
323 | 323 | |
324 | 324 | |
325 | - /** |
|
326 | - * @throws EE_Error |
|
327 | - * @throws ReflectionException |
|
328 | - */ |
|
329 | - private function validatePaymentAmount(EE_Transaction $transaction, float $amount) |
|
330 | - { |
|
331 | - if ($amount < 0) { |
|
332 | - throw new EE_Error( |
|
333 | - sprintf( |
|
334 | - esc_html__( |
|
335 | - 'Attempting to make a payment for a negative amount of %1$d for transaction %2$d. That should be a refund', |
|
336 | - 'event_espresso' |
|
337 | - ), |
|
338 | - $amount, |
|
339 | - $transaction->ID() |
|
340 | - ) |
|
341 | - ); |
|
342 | - } |
|
343 | - } |
|
325 | + /** |
|
326 | + * @throws EE_Error |
|
327 | + * @throws ReflectionException |
|
328 | + */ |
|
329 | + private function validatePaymentAmount(EE_Transaction $transaction, float $amount) |
|
330 | + { |
|
331 | + if ($amount < 0) { |
|
332 | + throw new EE_Error( |
|
333 | + sprintf( |
|
334 | + esc_html__( |
|
335 | + 'Attempting to make a payment for a negative amount of %1$d for transaction %2$d. That should be a refund', |
|
336 | + 'event_espresso' |
|
337 | + ), |
|
338 | + $amount, |
|
339 | + $transaction->ID() |
|
340 | + ) |
|
341 | + ); |
|
342 | + } |
|
343 | + } |
|
344 | 344 | } |
@@ -32,378 +32,378 @@ |
||
32 | 32 | */ |
33 | 33 | class IpnHandler |
34 | 34 | { |
35 | - private EEM_Payment_Method $payment_method_model; |
|
36 | - |
|
37 | - private EEM_Transaction $transaction_model; |
|
38 | - |
|
39 | - private EE_Core_Config $core_config; |
|
40 | - |
|
41 | - private EE_Organization_Config $organization; |
|
42 | - |
|
43 | - private PaymentProcessor $payment_processor; |
|
44 | - |
|
45 | - |
|
46 | - /** |
|
47 | - * @param EEM_Payment_Method $payment_method_model |
|
48 | - * @param EEM_Transaction $transaction_model |
|
49 | - * @param EE_Core_Config $core_config |
|
50 | - * @param EE_Organization_Config $organization |
|
51 | - * @param PaymentProcessor $payment_processor |
|
52 | - */ |
|
53 | - public function __construct( |
|
54 | - EEM_Payment_Method $payment_method_model, |
|
55 | - EEM_Transaction $transaction_model, |
|
56 | - EE_Core_Config $core_config, |
|
57 | - EE_Organization_Config $organization, |
|
58 | - PaymentProcessor $payment_processor |
|
59 | - ) { |
|
60 | - $this->payment_method_model = $payment_method_model; |
|
61 | - $this->transaction_model = $transaction_model; |
|
62 | - $this->core_config = $core_config; |
|
63 | - $this->organization = $organization; |
|
64 | - $this->payment_processor = $payment_processor; |
|
65 | - } |
|
66 | - |
|
67 | - |
|
68 | - /** |
|
69 | - * @param EE_Transaction $transaction |
|
70 | - * @param EE_Payment_Method $payment_method |
|
71 | - * @return string |
|
72 | - * @throws EE_Error |
|
73 | - * @throws ReflectionException |
|
74 | - */ |
|
75 | - public function getIpnUrlForPaymentMethod(EE_Transaction $transaction, EE_Payment_Method $payment_method): string |
|
76 | - { |
|
77 | - $primary_reg = $transaction->primary_registration(); |
|
78 | - if (! $primary_reg instanceof EE_Registration) { |
|
79 | - throw new EE_Error( |
|
80 | - sprintf( |
|
81 | - esc_html__( |
|
82 | - 'Cannot get IPN URL for transaction with ID %d because it has no primary registration', |
|
83 | - 'event_espresso' |
|
84 | - ), |
|
85 | - $transaction->ID() |
|
86 | - ) |
|
87 | - ); |
|
88 | - } |
|
89 | - $payment_method = $this->payment_method_model->ensure_is_obj( |
|
90 | - $payment_method, |
|
91 | - true |
|
92 | - ); |
|
93 | - return add_query_arg( |
|
94 | - [ |
|
95 | - 'e_reg_url_link' => $primary_reg->reg_url_link(), |
|
96 | - 'ee_payment_method' => $payment_method->slug(), |
|
97 | - ], |
|
98 | - $this->core_config->txn_page_url() |
|
99 | - ); |
|
100 | - } |
|
101 | - |
|
102 | - |
|
103 | - /** |
|
104 | - * Process the IPN. Firstly, we'll hope we put the standard args into the IPN URL so |
|
105 | - * we can easily find what registration the IPN is for and what payment method. |
|
106 | - * However, if not, we'll give all payment methods a chance to claim it and process it. |
|
107 | - * If a payment is found for the IPN info, it is saved. |
|
108 | - * |
|
109 | - * @param array $request_data form post data |
|
110 | - * @param EE_Transaction|int|null $transaction optional (or a transaction's id) |
|
111 | - * @param EE_Payment_Method|int|string|null $payment_method optional (or a slug or id of PM) |
|
112 | - * @param bool $update_txn whether to call |
|
113 | - * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
114 | - * @param bool $separate_IPN_request whether the IPN uses a separate request (true, |
|
115 | - * like PayPal) or is processed manually (false, |
|
116 | - * like Authorize.net) |
|
117 | - * @return EE_Payment |
|
118 | - * @throws EE_Error |
|
119 | - * @throws ReflectionException |
|
120 | - */ |
|
121 | - public function processIPN( |
|
122 | - array $request_data, |
|
123 | - $transaction = null, |
|
124 | - $payment_method = null, |
|
125 | - bool $update_txn = true, |
|
126 | - bool $separate_IPN_request = true |
|
127 | - ): EE_Payment { |
|
128 | - $request_data = $this->removeUnusableCharactersFromArray($request_data); |
|
129 | - EE_Processor_Base::set_IPN($separate_IPN_request); |
|
130 | - ['log' => $log, 'object' => $log_object] = $this->logIPN($request_data, $transaction, $payment_method); |
|
131 | - |
|
132 | - try { |
|
133 | - if ($transaction && $payment_method) { |
|
134 | - $payment = $this->processStandardIPN($request_data, $log, $log_object, $transaction, $payment_method); |
|
135 | - } else { |
|
136 | - ['payment' => $payment, 'payment_method' => $payment_method] = $this->processWaywardIPN( |
|
137 | - $request_data, |
|
138 | - $log_object |
|
139 | - ); |
|
140 | - } |
|
141 | - return $this->postIpnProcessing( |
|
142 | - $payment, |
|
143 | - $request_data, |
|
144 | - $update_txn, |
|
145 | - $separate_IPN_request, |
|
146 | - $transaction, |
|
147 | - $payment_method |
|
148 | - ); |
|
149 | - } catch (EE_Error $exception) { |
|
150 | - $this->invalidIpnException($exception, $transaction, $request_data); |
|
151 | - } |
|
152 | - } |
|
153 | - |
|
154 | - |
|
155 | - /** |
|
156 | - * @param array $request_data |
|
157 | - * @param EE_Change_Log $log |
|
158 | - * @param EE_Base_Class|null $log_object |
|
159 | - * @param EE_Transaction|int|null $transaction optional (model object or a transaction's id) |
|
160 | - * @param EE_Payment_Method|int|string|null $payment_method optional (model object or a slug or id of PM) |
|
161 | - * @return EE_Payment|null |
|
162 | - * @throws EE_Error |
|
163 | - * @throws ReflectionException |
|
164 | - */ |
|
165 | - private function processStandardIPN( |
|
166 | - array $request_data, |
|
167 | - EE_Change_Log $log, |
|
168 | - ?EE_Base_Class $log_object, |
|
169 | - $transaction = null, |
|
170 | - $payment_method = null |
|
171 | - ): ?EE_Payment { |
|
172 | - /** @type EE_Transaction $transaction */ |
|
173 | - $transaction = $this->transaction_model->ensure_is_obj($transaction); |
|
174 | - /** @type EE_Payment_Method $payment_method */ |
|
175 | - $payment_method = $this->payment_method_model->ensure_is_obj($payment_method); |
|
176 | - if (! $payment_method->type_obj() instanceof EE_PMT_Base) { |
|
177 | - // not a payment |
|
178 | - $this->invalidPaymentError(); |
|
179 | - return null; |
|
180 | - } |
|
181 | - try { |
|
182 | - $payment = $payment_method->type_obj()->handle_ipn($request_data, $transaction); |
|
183 | - $log->set_object($payment); |
|
184 | - return $payment; |
|
185 | - } catch (IpnException $exception) { |
|
186 | - $payment = $this->logIpnException($exception, $log_object); |
|
187 | - } |
|
188 | - return $payment; |
|
189 | - } |
|
190 | - |
|
191 | - |
|
192 | - /** |
|
193 | - * @param array $request_data |
|
194 | - * @param EE_Base_Class|null $log_object |
|
195 | - * @return array |
|
196 | - * @throws EE_Error |
|
197 | - * @throws ReflectionException |
|
198 | - */ |
|
199 | - private function processWaywardIPN( |
|
200 | - array $request_data, |
|
201 | - ?EE_Base_Class $log_object |
|
202 | - ): array { |
|
203 | - $payment = null; |
|
204 | - $payment_method = null; |
|
205 | - // that's actually pretty ok. The IPN just wasn't able |
|
206 | - // to identify which transaction or payment method this was for |
|
207 | - // give all active payment methods a chance to claim it |
|
208 | - $active_payment_methods = $this->payment_method_model->get_all_active(); |
|
209 | - foreach ($active_payment_methods as $payment_method) { |
|
210 | - try { |
|
211 | - $pm_type = $payment_method->type_obj(); |
|
212 | - $payment = $pm_type instanceof EE_PMT_Base ? $pm_type->handle_unclaimed_ipn($request_data) : $payment; |
|
213 | - $this->logIpnData(['IPN data' => $request_data], $payment); |
|
214 | - break; |
|
215 | - } catch (IpnException $exception) { |
|
216 | - $payment = $this->logIpnException($exception, $log_object); |
|
217 | - } catch (EE_Error $e) { |
|
218 | - // that's fine- it apparently couldn't handle the IPN |
|
219 | - } |
|
220 | - } |
|
221 | - return [$payment, $payment_method]; |
|
222 | - } |
|
223 | - |
|
224 | - |
|
225 | - /** |
|
226 | - * @param EE_Payment|null $payment |
|
227 | - * @param array $request_data |
|
228 | - * @param bool $update_txn |
|
229 | - * @param bool $separate_IPN_request |
|
230 | - * @param EE_Transaction|int|null $transaction optional (model object or a transaction's id) |
|
231 | - * @param EE_Payment_Method|int|string|null $payment_method optional (model object or a slug or id of PM) |
|
232 | - * @return EE_Payment|null |
|
233 | - * @throws EE_Error |
|
234 | - * @throws ReflectionException |
|
235 | - */ |
|
236 | - private function postIpnProcessing( |
|
237 | - ?EE_Payment $payment, |
|
238 | - array $request_data, |
|
239 | - bool $update_txn, |
|
240 | - bool $separate_IPN_request, |
|
241 | - $transaction = null, |
|
242 | - $payment_method = null |
|
243 | - ): ?EE_Payment { |
|
244 | - if ($payment instanceof EE_Payment) { |
|
245 | - $payment->save(); |
|
246 | - $this->payment_processor->updateTransactionBasedOnPayment( |
|
247 | - $transaction, |
|
248 | - $payment, |
|
249 | - $update_txn, |
|
250 | - $separate_IPN_request |
|
251 | - ); |
|
252 | - } else { |
|
253 | - // we couldn't find the payment for this IPN... let's try and log at least SOMETHING |
|
254 | - if ($payment_method) { |
|
255 | - $this->logIpnData(['IPN data' => $request_data], $payment_method); |
|
256 | - } elseif ($transaction) { |
|
257 | - $this->logIpnData(['IPN data' => $request_data], $transaction); |
|
258 | - } |
|
259 | - } |
|
260 | - return $payment; |
|
261 | - } |
|
262 | - |
|
263 | - |
|
264 | - /** |
|
265 | - * @param array $request_data |
|
266 | - * @param EE_Transaction|int|null $transaction optional (model object or a transaction's id) |
|
267 | - * @param EE_Payment_Method|int|string|null $payment_method optional (model object or a slug or id of PM) |
|
268 | - * @return array |
|
269 | - * @throws EE_Error |
|
270 | - * @throws ReflectionException |
|
271 | - */ |
|
272 | - private function logIPN( |
|
273 | - array $request_data, |
|
274 | - $transaction = null, |
|
275 | - $payment_method = null |
|
276 | - ): array { |
|
277 | - $log_object = null; |
|
278 | - if ($transaction instanceof EE_Transaction) { |
|
279 | - $log_object = $transaction; |
|
280 | - if ($payment_method instanceof EE_Payment_Method) { |
|
281 | - $log_object = EEM_Payment::instance()->get_one( |
|
282 | - [ |
|
283 | - ['TXN_ID' => $transaction->ID(), 'PMD_ID' => $payment_method->ID()], |
|
284 | - 'order_by' => ['PAY_timestamp' => 'desc'], |
|
285 | - ] |
|
286 | - ); |
|
287 | - } |
|
288 | - } |
|
289 | - $log = $this->logIpnData(['IPN data received' => $request_data], $log_object); |
|
290 | - return [ |
|
291 | - 'log' => $log, |
|
292 | - 'object' => $log_object, |
|
293 | - ]; |
|
294 | - } |
|
295 | - |
|
296 | - |
|
297 | - /** |
|
298 | - * @param array $data |
|
299 | - * @param EE_Base_Class|null $log_object |
|
300 | - * @return EE_Change_Log |
|
301 | - * @throws EE_Error |
|
302 | - * @throws ReflectionException |
|
303 | - */ |
|
304 | - private function logIpnData(array $data, ?EE_Base_Class $log_object): EE_Change_Log |
|
305 | - { |
|
306 | - return EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, $data, $log_object); |
|
307 | - } |
|
308 | - |
|
309 | - |
|
310 | - /** |
|
311 | - * @param IpnException $exception |
|
312 | - * @param EE_Base_Class|null $log_object |
|
313 | - * @return EE_Payment|null |
|
314 | - * @throws EE_Error |
|
315 | - * @throws ReflectionException |
|
316 | - */ |
|
317 | - private function logIpnException(IpnException $exception, ?EE_Base_Class $log_object): ?EE_Payment |
|
318 | - { |
|
319 | - $this->logIpnData( |
|
320 | - [ |
|
321 | - 'message' => 'IPN Exception: ' . $exception->getMessage(), |
|
322 | - 'current_url' => EEH_URL::current_url(), |
|
323 | - 'payment' => $exception->getPaymentProperties(), |
|
324 | - 'IPN_data' => $exception->getIpnData(), |
|
325 | - ], |
|
326 | - $log_object |
|
327 | - ); |
|
328 | - return $exception->getPayment(); |
|
329 | - } |
|
330 | - |
|
331 | - |
|
332 | - /** |
|
333 | - * @return void |
|
334 | - * @throws EE_Error |
|
335 | - */ |
|
336 | - private function invalidPaymentError() |
|
337 | - { |
|
338 | - EE_Error::add_error( |
|
339 | - sprintf( |
|
340 | - esc_html__( |
|
341 | - 'A valid payment method could not be determined due to a technical issue.%1$sPlease refresh your browser and try again or contact %2$s for assistance.', |
|
342 | - 'event_espresso' |
|
343 | - ), |
|
344 | - '<br/>', |
|
345 | - $this->organization->get_pretty('email') |
|
346 | - ), |
|
347 | - __FILE__, |
|
348 | - __FUNCTION__, |
|
349 | - __LINE__ |
|
350 | - ); |
|
351 | - } |
|
352 | - |
|
353 | - |
|
354 | - /** |
|
355 | - * @param Exception $exception |
|
356 | - * @param $transaction |
|
357 | - * @param $request_data |
|
358 | - * @return mixed |
|
359 | - * @throws Exception |
|
360 | - */ |
|
361 | - private function invalidIpnException(Exception $exception, $transaction, $request_data) |
|
362 | - { |
|
363 | - do_action( |
|
364 | - 'AHEE__log', |
|
365 | - __FILE__, |
|
366 | - __FUNCTION__, |
|
367 | - sprintf( |
|
368 | - esc_html__( |
|
369 | - 'Error occurred while receiving IPN. Transaction: %1$s, req data: %2$s. The error was "%3$s"', |
|
370 | - 'event_espresso' |
|
371 | - ), |
|
372 | - print_r($transaction, true), |
|
373 | - print_r($request_data, true), |
|
374 | - $exception->getMessage() |
|
375 | - ) |
|
376 | - ); |
|
377 | - throw $exception; |
|
378 | - } |
|
379 | - |
|
380 | - |
|
381 | - /** |
|
382 | - * Removes any non-printable illegal characters from the input, |
|
383 | - * which might cause a raucous when trying to insert into the database |
|
384 | - * |
|
385 | - * @param array $request_data |
|
386 | - * @return array |
|
387 | - */ |
|
388 | - private function removeUnusableCharactersFromArray(array $request_data): array |
|
389 | - { |
|
390 | - $return_data = []; |
|
391 | - foreach ($request_data as $key => $value) { |
|
392 | - $return_data[ $this->removeUnusableCharacters($key) ] = $this->removeUnusableCharacters($value); |
|
393 | - } |
|
394 | - return $return_data; |
|
395 | - } |
|
396 | - |
|
397 | - |
|
398 | - /** |
|
399 | - * Removes any non-printable illegal characters from the input, |
|
400 | - * which might cause a raucous when trying to insert into the database |
|
401 | - * |
|
402 | - * @param string $request_data |
|
403 | - * @return string |
|
404 | - */ |
|
405 | - private function removeUnusableCharacters(string $request_data): string |
|
406 | - { |
|
407 | - return preg_replace('/[^[:print:]]/', '', $request_data); |
|
408 | - } |
|
35 | + private EEM_Payment_Method $payment_method_model; |
|
36 | + |
|
37 | + private EEM_Transaction $transaction_model; |
|
38 | + |
|
39 | + private EE_Core_Config $core_config; |
|
40 | + |
|
41 | + private EE_Organization_Config $organization; |
|
42 | + |
|
43 | + private PaymentProcessor $payment_processor; |
|
44 | + |
|
45 | + |
|
46 | + /** |
|
47 | + * @param EEM_Payment_Method $payment_method_model |
|
48 | + * @param EEM_Transaction $transaction_model |
|
49 | + * @param EE_Core_Config $core_config |
|
50 | + * @param EE_Organization_Config $organization |
|
51 | + * @param PaymentProcessor $payment_processor |
|
52 | + */ |
|
53 | + public function __construct( |
|
54 | + EEM_Payment_Method $payment_method_model, |
|
55 | + EEM_Transaction $transaction_model, |
|
56 | + EE_Core_Config $core_config, |
|
57 | + EE_Organization_Config $organization, |
|
58 | + PaymentProcessor $payment_processor |
|
59 | + ) { |
|
60 | + $this->payment_method_model = $payment_method_model; |
|
61 | + $this->transaction_model = $transaction_model; |
|
62 | + $this->core_config = $core_config; |
|
63 | + $this->organization = $organization; |
|
64 | + $this->payment_processor = $payment_processor; |
|
65 | + } |
|
66 | + |
|
67 | + |
|
68 | + /** |
|
69 | + * @param EE_Transaction $transaction |
|
70 | + * @param EE_Payment_Method $payment_method |
|
71 | + * @return string |
|
72 | + * @throws EE_Error |
|
73 | + * @throws ReflectionException |
|
74 | + */ |
|
75 | + public function getIpnUrlForPaymentMethod(EE_Transaction $transaction, EE_Payment_Method $payment_method): string |
|
76 | + { |
|
77 | + $primary_reg = $transaction->primary_registration(); |
|
78 | + if (! $primary_reg instanceof EE_Registration) { |
|
79 | + throw new EE_Error( |
|
80 | + sprintf( |
|
81 | + esc_html__( |
|
82 | + 'Cannot get IPN URL for transaction with ID %d because it has no primary registration', |
|
83 | + 'event_espresso' |
|
84 | + ), |
|
85 | + $transaction->ID() |
|
86 | + ) |
|
87 | + ); |
|
88 | + } |
|
89 | + $payment_method = $this->payment_method_model->ensure_is_obj( |
|
90 | + $payment_method, |
|
91 | + true |
|
92 | + ); |
|
93 | + return add_query_arg( |
|
94 | + [ |
|
95 | + 'e_reg_url_link' => $primary_reg->reg_url_link(), |
|
96 | + 'ee_payment_method' => $payment_method->slug(), |
|
97 | + ], |
|
98 | + $this->core_config->txn_page_url() |
|
99 | + ); |
|
100 | + } |
|
101 | + |
|
102 | + |
|
103 | + /** |
|
104 | + * Process the IPN. Firstly, we'll hope we put the standard args into the IPN URL so |
|
105 | + * we can easily find what registration the IPN is for and what payment method. |
|
106 | + * However, if not, we'll give all payment methods a chance to claim it and process it. |
|
107 | + * If a payment is found for the IPN info, it is saved. |
|
108 | + * |
|
109 | + * @param array $request_data form post data |
|
110 | + * @param EE_Transaction|int|null $transaction optional (or a transaction's id) |
|
111 | + * @param EE_Payment_Method|int|string|null $payment_method optional (or a slug or id of PM) |
|
112 | + * @param bool $update_txn whether to call |
|
113 | + * EE_Transaction_Processor::update_transaction_and_registrations_after_checkout_or_payment() |
|
114 | + * @param bool $separate_IPN_request whether the IPN uses a separate request (true, |
|
115 | + * like PayPal) or is processed manually (false, |
|
116 | + * like Authorize.net) |
|
117 | + * @return EE_Payment |
|
118 | + * @throws EE_Error |
|
119 | + * @throws ReflectionException |
|
120 | + */ |
|
121 | + public function processIPN( |
|
122 | + array $request_data, |
|
123 | + $transaction = null, |
|
124 | + $payment_method = null, |
|
125 | + bool $update_txn = true, |
|
126 | + bool $separate_IPN_request = true |
|
127 | + ): EE_Payment { |
|
128 | + $request_data = $this->removeUnusableCharactersFromArray($request_data); |
|
129 | + EE_Processor_Base::set_IPN($separate_IPN_request); |
|
130 | + ['log' => $log, 'object' => $log_object] = $this->logIPN($request_data, $transaction, $payment_method); |
|
131 | + |
|
132 | + try { |
|
133 | + if ($transaction && $payment_method) { |
|
134 | + $payment = $this->processStandardIPN($request_data, $log, $log_object, $transaction, $payment_method); |
|
135 | + } else { |
|
136 | + ['payment' => $payment, 'payment_method' => $payment_method] = $this->processWaywardIPN( |
|
137 | + $request_data, |
|
138 | + $log_object |
|
139 | + ); |
|
140 | + } |
|
141 | + return $this->postIpnProcessing( |
|
142 | + $payment, |
|
143 | + $request_data, |
|
144 | + $update_txn, |
|
145 | + $separate_IPN_request, |
|
146 | + $transaction, |
|
147 | + $payment_method |
|
148 | + ); |
|
149 | + } catch (EE_Error $exception) { |
|
150 | + $this->invalidIpnException($exception, $transaction, $request_data); |
|
151 | + } |
|
152 | + } |
|
153 | + |
|
154 | + |
|
155 | + /** |
|
156 | + * @param array $request_data |
|
157 | + * @param EE_Change_Log $log |
|
158 | + * @param EE_Base_Class|null $log_object |
|
159 | + * @param EE_Transaction|int|null $transaction optional (model object or a transaction's id) |
|
160 | + * @param EE_Payment_Method|int|string|null $payment_method optional (model object or a slug or id of PM) |
|
161 | + * @return EE_Payment|null |
|
162 | + * @throws EE_Error |
|
163 | + * @throws ReflectionException |
|
164 | + */ |
|
165 | + private function processStandardIPN( |
|
166 | + array $request_data, |
|
167 | + EE_Change_Log $log, |
|
168 | + ?EE_Base_Class $log_object, |
|
169 | + $transaction = null, |
|
170 | + $payment_method = null |
|
171 | + ): ?EE_Payment { |
|
172 | + /** @type EE_Transaction $transaction */ |
|
173 | + $transaction = $this->transaction_model->ensure_is_obj($transaction); |
|
174 | + /** @type EE_Payment_Method $payment_method */ |
|
175 | + $payment_method = $this->payment_method_model->ensure_is_obj($payment_method); |
|
176 | + if (! $payment_method->type_obj() instanceof EE_PMT_Base) { |
|
177 | + // not a payment |
|
178 | + $this->invalidPaymentError(); |
|
179 | + return null; |
|
180 | + } |
|
181 | + try { |
|
182 | + $payment = $payment_method->type_obj()->handle_ipn($request_data, $transaction); |
|
183 | + $log->set_object($payment); |
|
184 | + return $payment; |
|
185 | + } catch (IpnException $exception) { |
|
186 | + $payment = $this->logIpnException($exception, $log_object); |
|
187 | + } |
|
188 | + return $payment; |
|
189 | + } |
|
190 | + |
|
191 | + |
|
192 | + /** |
|
193 | + * @param array $request_data |
|
194 | + * @param EE_Base_Class|null $log_object |
|
195 | + * @return array |
|
196 | + * @throws EE_Error |
|
197 | + * @throws ReflectionException |
|
198 | + */ |
|
199 | + private function processWaywardIPN( |
|
200 | + array $request_data, |
|
201 | + ?EE_Base_Class $log_object |
|
202 | + ): array { |
|
203 | + $payment = null; |
|
204 | + $payment_method = null; |
|
205 | + // that's actually pretty ok. The IPN just wasn't able |
|
206 | + // to identify which transaction or payment method this was for |
|
207 | + // give all active payment methods a chance to claim it |
|
208 | + $active_payment_methods = $this->payment_method_model->get_all_active(); |
|
209 | + foreach ($active_payment_methods as $payment_method) { |
|
210 | + try { |
|
211 | + $pm_type = $payment_method->type_obj(); |
|
212 | + $payment = $pm_type instanceof EE_PMT_Base ? $pm_type->handle_unclaimed_ipn($request_data) : $payment; |
|
213 | + $this->logIpnData(['IPN data' => $request_data], $payment); |
|
214 | + break; |
|
215 | + } catch (IpnException $exception) { |
|
216 | + $payment = $this->logIpnException($exception, $log_object); |
|
217 | + } catch (EE_Error $e) { |
|
218 | + // that's fine- it apparently couldn't handle the IPN |
|
219 | + } |
|
220 | + } |
|
221 | + return [$payment, $payment_method]; |
|
222 | + } |
|
223 | + |
|
224 | + |
|
225 | + /** |
|
226 | + * @param EE_Payment|null $payment |
|
227 | + * @param array $request_data |
|
228 | + * @param bool $update_txn |
|
229 | + * @param bool $separate_IPN_request |
|
230 | + * @param EE_Transaction|int|null $transaction optional (model object or a transaction's id) |
|
231 | + * @param EE_Payment_Method|int|string|null $payment_method optional (model object or a slug or id of PM) |
|
232 | + * @return EE_Payment|null |
|
233 | + * @throws EE_Error |
|
234 | + * @throws ReflectionException |
|
235 | + */ |
|
236 | + private function postIpnProcessing( |
|
237 | + ?EE_Payment $payment, |
|
238 | + array $request_data, |
|
239 | + bool $update_txn, |
|
240 | + bool $separate_IPN_request, |
|
241 | + $transaction = null, |
|
242 | + $payment_method = null |
|
243 | + ): ?EE_Payment { |
|
244 | + if ($payment instanceof EE_Payment) { |
|
245 | + $payment->save(); |
|
246 | + $this->payment_processor->updateTransactionBasedOnPayment( |
|
247 | + $transaction, |
|
248 | + $payment, |
|
249 | + $update_txn, |
|
250 | + $separate_IPN_request |
|
251 | + ); |
|
252 | + } else { |
|
253 | + // we couldn't find the payment for this IPN... let's try and log at least SOMETHING |
|
254 | + if ($payment_method) { |
|
255 | + $this->logIpnData(['IPN data' => $request_data], $payment_method); |
|
256 | + } elseif ($transaction) { |
|
257 | + $this->logIpnData(['IPN data' => $request_data], $transaction); |
|
258 | + } |
|
259 | + } |
|
260 | + return $payment; |
|
261 | + } |
|
262 | + |
|
263 | + |
|
264 | + /** |
|
265 | + * @param array $request_data |
|
266 | + * @param EE_Transaction|int|null $transaction optional (model object or a transaction's id) |
|
267 | + * @param EE_Payment_Method|int|string|null $payment_method optional (model object or a slug or id of PM) |
|
268 | + * @return array |
|
269 | + * @throws EE_Error |
|
270 | + * @throws ReflectionException |
|
271 | + */ |
|
272 | + private function logIPN( |
|
273 | + array $request_data, |
|
274 | + $transaction = null, |
|
275 | + $payment_method = null |
|
276 | + ): array { |
|
277 | + $log_object = null; |
|
278 | + if ($transaction instanceof EE_Transaction) { |
|
279 | + $log_object = $transaction; |
|
280 | + if ($payment_method instanceof EE_Payment_Method) { |
|
281 | + $log_object = EEM_Payment::instance()->get_one( |
|
282 | + [ |
|
283 | + ['TXN_ID' => $transaction->ID(), 'PMD_ID' => $payment_method->ID()], |
|
284 | + 'order_by' => ['PAY_timestamp' => 'desc'], |
|
285 | + ] |
|
286 | + ); |
|
287 | + } |
|
288 | + } |
|
289 | + $log = $this->logIpnData(['IPN data received' => $request_data], $log_object); |
|
290 | + return [ |
|
291 | + 'log' => $log, |
|
292 | + 'object' => $log_object, |
|
293 | + ]; |
|
294 | + } |
|
295 | + |
|
296 | + |
|
297 | + /** |
|
298 | + * @param array $data |
|
299 | + * @param EE_Base_Class|null $log_object |
|
300 | + * @return EE_Change_Log |
|
301 | + * @throws EE_Error |
|
302 | + * @throws ReflectionException |
|
303 | + */ |
|
304 | + private function logIpnData(array $data, ?EE_Base_Class $log_object): EE_Change_Log |
|
305 | + { |
|
306 | + return EEM_Change_Log::instance()->log(EEM_Change_Log::type_gateway, $data, $log_object); |
|
307 | + } |
|
308 | + |
|
309 | + |
|
310 | + /** |
|
311 | + * @param IpnException $exception |
|
312 | + * @param EE_Base_Class|null $log_object |
|
313 | + * @return EE_Payment|null |
|
314 | + * @throws EE_Error |
|
315 | + * @throws ReflectionException |
|
316 | + */ |
|
317 | + private function logIpnException(IpnException $exception, ?EE_Base_Class $log_object): ?EE_Payment |
|
318 | + { |
|
319 | + $this->logIpnData( |
|
320 | + [ |
|
321 | + 'message' => 'IPN Exception: ' . $exception->getMessage(), |
|
322 | + 'current_url' => EEH_URL::current_url(), |
|
323 | + 'payment' => $exception->getPaymentProperties(), |
|
324 | + 'IPN_data' => $exception->getIpnData(), |
|
325 | + ], |
|
326 | + $log_object |
|
327 | + ); |
|
328 | + return $exception->getPayment(); |
|
329 | + } |
|
330 | + |
|
331 | + |
|
332 | + /** |
|
333 | + * @return void |
|
334 | + * @throws EE_Error |
|
335 | + */ |
|
336 | + private function invalidPaymentError() |
|
337 | + { |
|
338 | + EE_Error::add_error( |
|
339 | + sprintf( |
|
340 | + esc_html__( |
|
341 | + 'A valid payment method could not be determined due to a technical issue.%1$sPlease refresh your browser and try again or contact %2$s for assistance.', |
|
342 | + 'event_espresso' |
|
343 | + ), |
|
344 | + '<br/>', |
|
345 | + $this->organization->get_pretty('email') |
|
346 | + ), |
|
347 | + __FILE__, |
|
348 | + __FUNCTION__, |
|
349 | + __LINE__ |
|
350 | + ); |
|
351 | + } |
|
352 | + |
|
353 | + |
|
354 | + /** |
|
355 | + * @param Exception $exception |
|
356 | + * @param $transaction |
|
357 | + * @param $request_data |
|
358 | + * @return mixed |
|
359 | + * @throws Exception |
|
360 | + */ |
|
361 | + private function invalidIpnException(Exception $exception, $transaction, $request_data) |
|
362 | + { |
|
363 | + do_action( |
|
364 | + 'AHEE__log', |
|
365 | + __FILE__, |
|
366 | + __FUNCTION__, |
|
367 | + sprintf( |
|
368 | + esc_html__( |
|
369 | + 'Error occurred while receiving IPN. Transaction: %1$s, req data: %2$s. The error was "%3$s"', |
|
370 | + 'event_espresso' |
|
371 | + ), |
|
372 | + print_r($transaction, true), |
|
373 | + print_r($request_data, true), |
|
374 | + $exception->getMessage() |
|
375 | + ) |
|
376 | + ); |
|
377 | + throw $exception; |
|
378 | + } |
|
379 | + |
|
380 | + |
|
381 | + /** |
|
382 | + * Removes any non-printable illegal characters from the input, |
|
383 | + * which might cause a raucous when trying to insert into the database |
|
384 | + * |
|
385 | + * @param array $request_data |
|
386 | + * @return array |
|
387 | + */ |
|
388 | + private function removeUnusableCharactersFromArray(array $request_data): array |
|
389 | + { |
|
390 | + $return_data = []; |
|
391 | + foreach ($request_data as $key => $value) { |
|
392 | + $return_data[ $this->removeUnusableCharacters($key) ] = $this->removeUnusableCharacters($value); |
|
393 | + } |
|
394 | + return $return_data; |
|
395 | + } |
|
396 | + |
|
397 | + |
|
398 | + /** |
|
399 | + * Removes any non-printable illegal characters from the input, |
|
400 | + * which might cause a raucous when trying to insert into the database |
|
401 | + * |
|
402 | + * @param string $request_data |
|
403 | + * @return string |
|
404 | + */ |
|
405 | + private function removeUnusableCharacters(string $request_data): string |
|
406 | + { |
|
407 | + return preg_replace('/[^[:print:]]/', '', $request_data); |
|
408 | + } |
|
409 | 409 | } |
@@ -28,162 +28,162 @@ |
||
28 | 28 | */ |
29 | 29 | class PaymentProcessorFees |
30 | 30 | { |
31 | - public const GATEWAY_PAYPAL = 'PayPal Commerce'; |
|
32 | - |
|
33 | - public const GATEWAY_SQUARE = 'Square'; |
|
34 | - |
|
35 | - public const GATEWAY_STRIPE = 'Stripe'; |
|
36 | - |
|
37 | - private GracePeriod $grace_period; |
|
38 | - |
|
39 | - private LicenseData $license_data; |
|
40 | - |
|
41 | - /** |
|
42 | - * @var float[][] $gateway_fees |
|
43 | - */ |
|
44 | - private array $gateway_fees = [ |
|
45 | - LicenseData::LICENSE_ACTIVE => [ |
|
46 | - PaymentProcessorFees::GATEWAY_PAYPAL => 0.00, |
|
47 | - PaymentProcessorFees::GATEWAY_SQUARE => 0.00, |
|
48 | - PaymentProcessorFees::GATEWAY_STRIPE => 0.00, |
|
49 | - ], |
|
50 | - LicenseData::LICENSE_EXPIRED => [ |
|
51 | - PaymentProcessorFees::GATEWAY_PAYPAL => 3.00, |
|
52 | - PaymentProcessorFees::GATEWAY_SQUARE => 2.50, |
|
53 | - PaymentProcessorFees::GATEWAY_STRIPE => 2.50, |
|
54 | - ], |
|
55 | - LicenseData::LICENSE_DECAF => [ |
|
56 | - PaymentProcessorFees::GATEWAY_PAYPAL => 3.00, |
|
57 | - PaymentProcessorFees::GATEWAY_SQUARE => 2.50, |
|
58 | - PaymentProcessorFees::GATEWAY_STRIPE => 2.50, |
|
59 | - ], |
|
60 | - ]; |
|
61 | - |
|
62 | - private array $partner_gateways = [ |
|
63 | - PaymentProcessorFees::GATEWAY_PAYPAL, |
|
64 | - PaymentProcessorFees::GATEWAY_SQUARE, |
|
65 | - PaymentProcessorFees::GATEWAY_STRIPE, |
|
66 | - ]; |
|
67 | - |
|
68 | - |
|
69 | - /** |
|
70 | - * @param GracePeriod $grace_period |
|
71 | - * @param LicenseData $license_data |
|
72 | - */ |
|
73 | - public function __construct(GracePeriod $grace_period, LicenseData $license_data) |
|
74 | - { |
|
75 | - $this->grace_period = $grace_period; |
|
76 | - $this->license_data = $license_data; |
|
77 | - } |
|
78 | - |
|
79 | - |
|
80 | - /** |
|
81 | - * @param EE_Transaction $transaction |
|
82 | - * @param string $payment_method_name |
|
83 | - * @param float $amount |
|
84 | - * @return float |
|
85 | - * @throws EE_Error|ReflectionException|RuntimeException |
|
86 | - * @throws Exception |
|
87 | - */ |
|
88 | - public function applyGatewayPartnerFees( |
|
89 | - EE_Transaction $transaction, |
|
90 | - string $payment_method_name, |
|
91 | - float $amount = 0.00 |
|
92 | - ): float { |
|
93 | - $processing_fee = $this->forPaymentMethod($payment_method_name); |
|
94 | - if ($processing_fee <= 0.00) { |
|
95 | - return $amount; |
|
96 | - } |
|
97 | - $grand_total = $transaction->total_line_item(false); |
|
98 | - if ( |
|
99 | - ! $grand_total instanceof EE_Line_Item |
|
100 | - || ! $grand_total->is_total() |
|
101 | - || $grand_total->TXN_ID() !== $transaction->ID() |
|
102 | - ) { |
|
103 | - // throw RuntimeException if total_line_item is not a total line item |
|
104 | - throw new RuntimeException( |
|
105 | - sprintf( |
|
106 | - esc_html__( |
|
107 | - 'Invalid or missing grand total line item for transaction %1$d.', |
|
108 | - 'event_espresso' |
|
109 | - ), |
|
110 | - $transaction->ID() |
|
111 | - ) |
|
112 | - ); |
|
113 | - } |
|
114 | - $line_item = EEH_Line_Item::add_percentage_based_item( |
|
115 | - EEH_Line_Item::get_pre_tax_subtotal($grand_total), |
|
116 | - esc_html__('Payment Processing Fee', 'event_espresso'), |
|
117 | - $processing_fee, |
|
118 | - '', |
|
119 | - false, |
|
120 | - sanitize_key( |
|
121 | - sprintf( |
|
122 | - '%1$s-fee-%2$d', |
|
123 | - $payment_method_name, |
|
124 | - $transaction->ID() |
|
125 | - ) |
|
126 | - ), |
|
127 | - true |
|
128 | - ); |
|
129 | - $line_item->save(); |
|
130 | - return $grand_total->recalculate_total_including_taxes(); |
|
131 | - } |
|
132 | - |
|
133 | - |
|
134 | - /** |
|
135 | - * Returns the fee for a specific payment method based on the license status. |
|
136 | - * |
|
137 | - * @param string $payment_method_name |
|
138 | - * @return float |
|
139 | - * @throws Exception|OutOfBoundsException|RuntimeException |
|
140 | - */ |
|
141 | - public function forPaymentMethod(string $payment_method_name): float |
|
142 | - { |
|
143 | - if (! $this->isPartnerGateway($payment_method_name)) { |
|
144 | - return 0.0; |
|
145 | - } |
|
146 | - $license_status = $this->license_data->licenseStatus(); |
|
147 | - $license_expires = $this->license_data->licenseExpiry(); |
|
148 | - // decaf, new activations, or expired licenses are allowed a grace period |
|
149 | - if ($this->grace_period->withinGracePeriod($license_status, $license_expires)) { |
|
150 | - return 0.0; |
|
151 | - } |
|
152 | - return $this->getGatewayFee($payment_method_name, $license_status); |
|
153 | - } |
|
154 | - |
|
155 | - |
|
156 | - /** |
|
157 | - * Checks if a gateway is a partner gateway. |
|
158 | - * |
|
159 | - * @param string $payment_method_name |
|
160 | - * @return bool |
|
161 | - */ |
|
162 | - private function isPartnerGateway(string $payment_method_name): bool |
|
163 | - { |
|
164 | - return in_array($payment_method_name, $this->partner_gateways, true); |
|
165 | - } |
|
166 | - |
|
167 | - |
|
168 | - /** |
|
169 | - * Returns the fee for a specific payment method based on the license status. |
|
170 | - * |
|
171 | - * @param string $payment_method_name |
|
172 | - * @param string $license_status |
|
173 | - * @return float |
|
174 | - * @throws OutOfBoundsException |
|
175 | - */ |
|
176 | - private function getGatewayFee(string $payment_method_name, string $license_status): float |
|
177 | - { |
|
178 | - if (isset($this->gateway_fees[ $license_status ][ $payment_method_name ])) { |
|
179 | - return $this->gateway_fees[ $license_status ][ $payment_method_name ]; |
|
180 | - } |
|
181 | - throw new OutOfBoundsException( |
|
182 | - sprintf( |
|
183 | - esc_html__('A partner fee for %1$s with %2$s license is not defined.', 'event_espresso'), |
|
184 | - $payment_method_name, |
|
185 | - $license_status |
|
186 | - ) |
|
187 | - ); |
|
188 | - } |
|
31 | + public const GATEWAY_PAYPAL = 'PayPal Commerce'; |
|
32 | + |
|
33 | + public const GATEWAY_SQUARE = 'Square'; |
|
34 | + |
|
35 | + public const GATEWAY_STRIPE = 'Stripe'; |
|
36 | + |
|
37 | + private GracePeriod $grace_period; |
|
38 | + |
|
39 | + private LicenseData $license_data; |
|
40 | + |
|
41 | + /** |
|
42 | + * @var float[][] $gateway_fees |
|
43 | + */ |
|
44 | + private array $gateway_fees = [ |
|
45 | + LicenseData::LICENSE_ACTIVE => [ |
|
46 | + PaymentProcessorFees::GATEWAY_PAYPAL => 0.00, |
|
47 | + PaymentProcessorFees::GATEWAY_SQUARE => 0.00, |
|
48 | + PaymentProcessorFees::GATEWAY_STRIPE => 0.00, |
|
49 | + ], |
|
50 | + LicenseData::LICENSE_EXPIRED => [ |
|
51 | + PaymentProcessorFees::GATEWAY_PAYPAL => 3.00, |
|
52 | + PaymentProcessorFees::GATEWAY_SQUARE => 2.50, |
|
53 | + PaymentProcessorFees::GATEWAY_STRIPE => 2.50, |
|
54 | + ], |
|
55 | + LicenseData::LICENSE_DECAF => [ |
|
56 | + PaymentProcessorFees::GATEWAY_PAYPAL => 3.00, |
|
57 | + PaymentProcessorFees::GATEWAY_SQUARE => 2.50, |
|
58 | + PaymentProcessorFees::GATEWAY_STRIPE => 2.50, |
|
59 | + ], |
|
60 | + ]; |
|
61 | + |
|
62 | + private array $partner_gateways = [ |
|
63 | + PaymentProcessorFees::GATEWAY_PAYPAL, |
|
64 | + PaymentProcessorFees::GATEWAY_SQUARE, |
|
65 | + PaymentProcessorFees::GATEWAY_STRIPE, |
|
66 | + ]; |
|
67 | + |
|
68 | + |
|
69 | + /** |
|
70 | + * @param GracePeriod $grace_period |
|
71 | + * @param LicenseData $license_data |
|
72 | + */ |
|
73 | + public function __construct(GracePeriod $grace_period, LicenseData $license_data) |
|
74 | + { |
|
75 | + $this->grace_period = $grace_period; |
|
76 | + $this->license_data = $license_data; |
|
77 | + } |
|
78 | + |
|
79 | + |
|
80 | + /** |
|
81 | + * @param EE_Transaction $transaction |
|
82 | + * @param string $payment_method_name |
|
83 | + * @param float $amount |
|
84 | + * @return float |
|
85 | + * @throws EE_Error|ReflectionException|RuntimeException |
|
86 | + * @throws Exception |
|
87 | + */ |
|
88 | + public function applyGatewayPartnerFees( |
|
89 | + EE_Transaction $transaction, |
|
90 | + string $payment_method_name, |
|
91 | + float $amount = 0.00 |
|
92 | + ): float { |
|
93 | + $processing_fee = $this->forPaymentMethod($payment_method_name); |
|
94 | + if ($processing_fee <= 0.00) { |
|
95 | + return $amount; |
|
96 | + } |
|
97 | + $grand_total = $transaction->total_line_item(false); |
|
98 | + if ( |
|
99 | + ! $grand_total instanceof EE_Line_Item |
|
100 | + || ! $grand_total->is_total() |
|
101 | + || $grand_total->TXN_ID() !== $transaction->ID() |
|
102 | + ) { |
|
103 | + // throw RuntimeException if total_line_item is not a total line item |
|
104 | + throw new RuntimeException( |
|
105 | + sprintf( |
|
106 | + esc_html__( |
|
107 | + 'Invalid or missing grand total line item for transaction %1$d.', |
|
108 | + 'event_espresso' |
|
109 | + ), |
|
110 | + $transaction->ID() |
|
111 | + ) |
|
112 | + ); |
|
113 | + } |
|
114 | + $line_item = EEH_Line_Item::add_percentage_based_item( |
|
115 | + EEH_Line_Item::get_pre_tax_subtotal($grand_total), |
|
116 | + esc_html__('Payment Processing Fee', 'event_espresso'), |
|
117 | + $processing_fee, |
|
118 | + '', |
|
119 | + false, |
|
120 | + sanitize_key( |
|
121 | + sprintf( |
|
122 | + '%1$s-fee-%2$d', |
|
123 | + $payment_method_name, |
|
124 | + $transaction->ID() |
|
125 | + ) |
|
126 | + ), |
|
127 | + true |
|
128 | + ); |
|
129 | + $line_item->save(); |
|
130 | + return $grand_total->recalculate_total_including_taxes(); |
|
131 | + } |
|
132 | + |
|
133 | + |
|
134 | + /** |
|
135 | + * Returns the fee for a specific payment method based on the license status. |
|
136 | + * |
|
137 | + * @param string $payment_method_name |
|
138 | + * @return float |
|
139 | + * @throws Exception|OutOfBoundsException|RuntimeException |
|
140 | + */ |
|
141 | + public function forPaymentMethod(string $payment_method_name): float |
|
142 | + { |
|
143 | + if (! $this->isPartnerGateway($payment_method_name)) { |
|
144 | + return 0.0; |
|
145 | + } |
|
146 | + $license_status = $this->license_data->licenseStatus(); |
|
147 | + $license_expires = $this->license_data->licenseExpiry(); |
|
148 | + // decaf, new activations, or expired licenses are allowed a grace period |
|
149 | + if ($this->grace_period->withinGracePeriod($license_status, $license_expires)) { |
|
150 | + return 0.0; |
|
151 | + } |
|
152 | + return $this->getGatewayFee($payment_method_name, $license_status); |
|
153 | + } |
|
154 | + |
|
155 | + |
|
156 | + /** |
|
157 | + * Checks if a gateway is a partner gateway. |
|
158 | + * |
|
159 | + * @param string $payment_method_name |
|
160 | + * @return bool |
|
161 | + */ |
|
162 | + private function isPartnerGateway(string $payment_method_name): bool |
|
163 | + { |
|
164 | + return in_array($payment_method_name, $this->partner_gateways, true); |
|
165 | + } |
|
166 | + |
|
167 | + |
|
168 | + /** |
|
169 | + * Returns the fee for a specific payment method based on the license status. |
|
170 | + * |
|
171 | + * @param string $payment_method_name |
|
172 | + * @param string $license_status |
|
173 | + * @return float |
|
174 | + * @throws OutOfBoundsException |
|
175 | + */ |
|
176 | + private function getGatewayFee(string $payment_method_name, string $license_status): float |
|
177 | + { |
|
178 | + if (isset($this->gateway_fees[ $license_status ][ $payment_method_name ])) { |
|
179 | + return $this->gateway_fees[ $license_status ][ $payment_method_name ]; |
|
180 | + } |
|
181 | + throw new OutOfBoundsException( |
|
182 | + sprintf( |
|
183 | + esc_html__('A partner fee for %1$s with %2$s license is not defined.', 'event_espresso'), |
|
184 | + $payment_method_name, |
|
185 | + $license_status |
|
186 | + ) |
|
187 | + ); |
|
188 | + } |
|
189 | 189 | } |
@@ -140,7 +140,7 @@ discard block |
||
140 | 140 | */ |
141 | 141 | public function forPaymentMethod(string $payment_method_name): float |
142 | 142 | { |
143 | - if (! $this->isPartnerGateway($payment_method_name)) { |
|
143 | + if ( ! $this->isPartnerGateway($payment_method_name)) { |
|
144 | 144 | return 0.0; |
145 | 145 | } |
146 | 146 | $license_status = $this->license_data->licenseStatus(); |
@@ -175,8 +175,8 @@ discard block |
||
175 | 175 | */ |
176 | 176 | private function getGatewayFee(string $payment_method_name, string $license_status): float |
177 | 177 | { |
178 | - if (isset($this->gateway_fees[ $license_status ][ $payment_method_name ])) { |
|
179 | - return $this->gateway_fees[ $license_status ][ $payment_method_name ]; |
|
178 | + if (isset($this->gateway_fees[$license_status][$payment_method_name])) { |
|
179 | + return $this->gateway_fees[$license_status][$payment_method_name]; |
|
180 | 180 | } |
181 | 181 | throw new OutOfBoundsException( |
182 | 182 | sprintf( |
@@ -8,65 +8,65 @@ |
||
8 | 8 | |
9 | 9 | class WpdbDataFormat |
10 | 10 | { |
11 | - /** |
|
12 | - * used for table/field names |
|
13 | - */ |
|
14 | - const IDENTIFIER = '%i'; |
|
11 | + /** |
|
12 | + * used for table/field names |
|
13 | + */ |
|
14 | + const IDENTIFIER = '%i'; |
|
15 | 15 | |
16 | - const INTEGER = '%d'; |
|
16 | + const INTEGER = '%d'; |
|
17 | 17 | |
18 | - const FLOAT = '%f'; |
|
18 | + const FLOAT = '%f'; |
|
19 | 19 | |
20 | - const STRING = '%s'; |
|
20 | + const STRING = '%s'; |
|
21 | 21 | |
22 | 22 | |
23 | - /** |
|
24 | - * Return `%d`, `%s` or `%f` to indicate the data type for the field that should be indicated in wpdb queries. |
|
25 | - * |
|
26 | - * @param string $type Included if a specific type is requested. |
|
27 | - * @return string |
|
28 | - * @uses get_schema_type() |
|
29 | - */ |
|
30 | - public static function getWpdbDataType(string $type = ''): string |
|
31 | - { |
|
32 | - switch ($type) { |
|
33 | - case SchemaType::BOOLEAN: |
|
34 | - case SchemaType::INTEGER: |
|
35 | - return WpdbDataFormat::INTEGER; // '%d' |
|
36 | - case SchemaType::DB_FIELD: |
|
37 | - return WpdbDataFormat::IDENTIFIER; // '%i' |
|
38 | - case SchemaType::NUMBER: |
|
39 | - return WpdbDataFormat::FLOAT; // '%f' |
|
40 | - case SchemaType::STRING: |
|
41 | - default: |
|
42 | - return WpdbDataFormat::STRING; // '%s' |
|
43 | - } |
|
44 | - } |
|
23 | + /** |
|
24 | + * Return `%d`, `%s` or `%f` to indicate the data type for the field that should be indicated in wpdb queries. |
|
25 | + * |
|
26 | + * @param string $type Included if a specific type is requested. |
|
27 | + * @return string |
|
28 | + * @uses get_schema_type() |
|
29 | + */ |
|
30 | + public static function getWpdbDataType(string $type = ''): string |
|
31 | + { |
|
32 | + switch ($type) { |
|
33 | + case SchemaType::BOOLEAN: |
|
34 | + case SchemaType::INTEGER: |
|
35 | + return WpdbDataFormat::INTEGER; // '%d' |
|
36 | + case SchemaType::DB_FIELD: |
|
37 | + return WpdbDataFormat::IDENTIFIER; // '%i' |
|
38 | + case SchemaType::NUMBER: |
|
39 | + return WpdbDataFormat::FLOAT; // '%f' |
|
40 | + case SchemaType::STRING: |
|
41 | + default: |
|
42 | + return WpdbDataFormat::STRING; // '%s' |
|
43 | + } |
|
44 | + } |
|
45 | 45 | |
46 | 46 | |
47 | - public static function getWpdbDataTypeForTypeArray(array $type): string |
|
48 | - { |
|
49 | - // first let's flip because then we can do a faster key check |
|
50 | - $type = array_flip($type); |
|
47 | + public static function getWpdbDataTypeForTypeArray(array $type): string |
|
48 | + { |
|
49 | + // first let's flip because then we can do a faster key check |
|
50 | + $type = array_flip($type); |
|
51 | 51 | |
52 | - // check for things that mean '%s' |
|
53 | - if (isset($type[ SchemaType::STRING ], $type[ SchemaType::OBJECT ], $type[ SchemaType::ARRAY ])) { |
|
54 | - return WpdbDataFormat::STRING; |
|
55 | - } |
|
52 | + // check for things that mean '%s' |
|
53 | + if (isset($type[ SchemaType::STRING ], $type[ SchemaType::OBJECT ], $type[ SchemaType::ARRAY ])) { |
|
54 | + return WpdbDataFormat::STRING; |
|
55 | + } |
|
56 | 56 | |
57 | - // if makes it past the above condition and there's float in the array |
|
58 | - // then the type is %f |
|
59 | - if (isset($type[ SchemaType::NUMBER ])) { |
|
60 | - return WpdbDataFormat::FLOAT; |
|
61 | - } |
|
57 | + // if makes it past the above condition and there's float in the array |
|
58 | + // then the type is %f |
|
59 | + if (isset($type[ SchemaType::NUMBER ])) { |
|
60 | + return WpdbDataFormat::FLOAT; |
|
61 | + } |
|
62 | 62 | |
63 | - // if it makes it past the above conditions and there is an integer in the array |
|
64 | - // then the type is %d |
|
65 | - if (isset($type[ SchemaType::INTEGER ])) { |
|
66 | - return WpdbDataFormat::INTEGER; |
|
67 | - } |
|
63 | + // if it makes it past the above conditions and there is an integer in the array |
|
64 | + // then the type is %d |
|
65 | + if (isset($type[ SchemaType::INTEGER ])) { |
|
66 | + return WpdbDataFormat::INTEGER; |
|
67 | + } |
|
68 | 68 | |
69 | - // anything else is a string |
|
70 | - return WpdbDataFormat::STRING; |
|
71 | - } |
|
69 | + // anything else is a string |
|
70 | + return WpdbDataFormat::STRING; |
|
71 | + } |
|
72 | 72 | } |
@@ -50,19 +50,19 @@ |
||
50 | 50 | $type = array_flip($type); |
51 | 51 | |
52 | 52 | // check for things that mean '%s' |
53 | - if (isset($type[ SchemaType::STRING ], $type[ SchemaType::OBJECT ], $type[ SchemaType::ARRAY ])) { |
|
53 | + if (isset($type[SchemaType::STRING], $type[SchemaType::OBJECT], $type[SchemaType::ARRAY])) { |
|
54 | 54 | return WpdbDataFormat::STRING; |
55 | 55 | } |
56 | 56 | |
57 | 57 | // if makes it past the above condition and there's float in the array |
58 | 58 | // then the type is %f |
59 | - if (isset($type[ SchemaType::NUMBER ])) { |
|
59 | + if (isset($type[SchemaType::NUMBER])) { |
|
60 | 60 | return WpdbDataFormat::FLOAT; |
61 | 61 | } |
62 | 62 | |
63 | 63 | // if it makes it past the above conditions and there is an integer in the array |
64 | 64 | // then the type is %d |
65 | - if (isset($type[ SchemaType::INTEGER ])) { |
|
65 | + if (isset($type[SchemaType::INTEGER])) { |
|
66 | 66 | return WpdbDataFormat::INTEGER; |
67 | 67 | } |
68 | 68 |