PluginProbe
Templately – Elementor & Gutenberg Template Library: 6500+ Free & Pro Ready Templates And Cloud! / 3.2.7
Templately – Elementor & Gutenberg Template Library: 6500+ Free & Pro Ready Templates And Cloud! v3.2.7
3.7.5 3.7.4 3.7.3 3.7.2 1-final 3.7.1 3.7.0 3.6.8 3.6.7 3.6.6 3.6.5 3.6.4 3.6.3 3.6.2 3.6.1 3.0.3 3.0.4 3.0.5 3.0.6 3.0.7 3.0.8 3.0.9 3.1.0 3.1.1 3.1.10 All 111 releases
← All changes | includes/Core/Importer/Runners/Loop.php +104 -192 3.7.53.2.7 View file →
@@ -1,13 +1,10 @@
1 1 <?php
2 2
3 3 namespace Templately\Core\Importer\Runners;
4 4
5 -use Exception;
6 -use Templately\Core\Importer\Exception\SkippableErrorException;
7 5 use Templately\Core\Importer\FullSiteImport;
8 6 use Templately\Core\Importer\LogHelper;
9 -use Templately\Core\Importer\Utils\SessionData;
10 7 use Templately\Core\Importer\Utils\Utils;
11 8 use Templately\Utils\Helper;
12 9
13 10 /**
@@ -15,11 +12,8 @@
15 12 * @method void sse_message(array $data)
16 13 */
17 14 trait Loop {
18 15
19 - public static $max_error_attempts = 2;
20 - public static $max_consecutive_skips = 5;
21 -
22 16 /**
23 17 * Undocumented function
24 18 *
25 19 * @param [type] $items
@@ -36,10 +30,12 @@
36 30 if (!is_array($items)) {
37 31 throw new \Exception('The items should be an array');
38 32 }
39 33
40 - $results = $this->_get_loop_result([], $unique_id);
34 + $results = $this->_get_result([], $unique_id);
35 + $progress = $this->_get_progress([], $unique_id);
41 36
37 +
42 38 if(!empty($this->backup_attributes)){
43 39 $this->_retrieve_attributes($this->backup_attributes, $unique_id);
44 40 }
45 41
@@ -44,60 +40,20 @@
44 40 }
45 41
46 42 foreach ($items as $key => $item) {
47 43 // If the template has been processed, skip it
48 - if ($this->_is_key_processed($key, $unique_id)) {
44 + if (in_array("key_$key", $progress, true)) {
49 45 continue;
50 46 }
51 47
52 - // Skip-on-error: Check if feature is enabled and item should be skipped
53 - if ($this->_is_skip_feature_enabled()) {
54 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
55 - $error_attempts = SessionData::get_error_attempts($this->session_id, $calling_class, $key);
48 + $result = $callback($key, $item, $results);
49 + $results = Helper::recursive_wp_parse_args($result, $results);
56 50
57 - // Skip if error attempts >= MAX_ERROR_ATTEMPTS
58 - if ($error_attempts >= self::$max_error_attempts) {
59 - $this->_mark_key_skipped($key, $unique_id, 'Max error attempts reached');
60 - $this->_increment_consecutive_skips();
61 - continue;
62 - }
63 - }
64 51
65 - // Wrap callback in try-catch for skip-on-error handling
66 - try {
67 - $result = $callback($key, $item, $results);
68 - if($result === 'continue'){
69 - // If the callback returns 'continue', skip to the next iteration
70 - continue;
71 - }
72 - $results = $result;
52 + // Add the template to the processed templates and update the session data
53 + $progress[] = "key_$key";
54 + $this->_update_progress( $progress, $result, $unique_id);
73 55
74 - // Success - reset consecutive skip counter
75 - if ($this->_is_skip_feature_enabled()) {
76 - $this->_reset_consecutive_skips();
77 - }
78 - } catch (SkippableErrorException $e) {
79 - // Catchable skip error - increment attempts and mark as skipped
80 - if ($this->_is_skip_feature_enabled()) {
81 - $this->_increment_error_attempts($key, $unique_id);
82 - $this->_mark_key_skipped($key, $unique_id, $e->getMessage());
83 - continue;
84 - } else {
85 - // Feature disabled - throw as normal exception
86 - throw new Exception($e->getMessage(), $e->getCode(), $e);
87 - }
88 - } catch (Exception $e) {
89 - // Other exceptions - increment error attempts then re-throw
90 - if ($this->_is_skip_feature_enabled()) {
91 - $this->_increment_error_attempts($key, $unique_id);
92 - }
93 - throw $e;
94 - }
95 -
96 - // Mark as processed and save result
97 - $this->_mark_key_processed($key, $unique_id);
98 - $this->_set_loop_result($results, $unique_id);
99 -
100 56 // If it's not the last item, send the SSE message and exit
101 57
102 58 $is_last_runner = key( array_slice( $items, -1, 1, true ) ) === $key;
103 59
@@ -109,9 +65,9 @@
109 65 'type' => 'continue',
110 66 'action' => 'continue',
111 67 'name' => method_exists($this, 'get_name') ? $this->get_name() : '',
112 68 'index' => $key,
113 - 'results' => SessionData::get_calling_identifier($unique_id, true, false, 3),
69 + 'results' => (function() use ($unique_id) {$this->CallingFunctionName($unique_id);})(),
114 70 ] );
115 71 exit;
116 72 }
117 73 }
@@ -117,98 +73,126 @@
117 73 }
118 74 return $results;
119 75 }
120 76
121 - /**
122 - * Check if a key has been processed (internal)
123 - *
124 - * @param mixed $key The item key
125 - * @param string|null $unique_id Optional unique identifier
126 - * @return bool True if processed
127 - */
128 - private function _is_key_processed($key, $unique_id = null): bool {
129 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
130 - return SessionData::is_key_processed($this->session_id, $calling_class, $key);
77 + private function CallingFunctionName($id = null, $function = true, $line = false, $level = 3) {
78 + $return = 'unknown';
79 + $trace = debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT, ($level + 1));
80 +
81 + // Check if the trace has at least three elements
82 + if (isset($trace[$level])) {
83 + $final_call = $trace[$level];
84 + $return = '';
85 +
86 + if (isset($final_call['object'])) {
87 + $return .= get_class($final_call['object']);
88 + } elseif (isset($final_call['class'])) {
89 + $return .= $final_call['class'];
90 + }
91 +
92 + if ($function && isset($final_call['function'])) {
93 + $return .= ($return ? '::' : '') . $final_call['function'];
94 + }
95 +
96 + if ($line && isset($final_call['line'])) {
97 + $return .= ($return ? '::' : '') . $final_call['line'];
98 + }
99 +
100 + if (!empty($id)) {
101 + $return .= ($return ? '::' : '') . $id;
102 + }
103 +
104 + if (!$return) {
105 + $return = 'unknown';
106 + }
107 + }
108 + // error_log($return . PHP_EOL, 3, ABSPATH . 'wp-content/debug.log');
109 +
110 + return $return;
131 111 }
132 112
133 - /**
134 - * Check if a key has been processed (public wrapper)
135 - */
136 - public function is_key_processed($key, $unique_id = null): bool {
137 - return $this->_is_key_processed($key, $unique_id);
113 + private function _get_progress($defaults = [], $unique_id = null, $function = true) {
114 + $data = $this->get_session_data();
115 + $calling_class = $this->CallingFunctionName($unique_id, $function);
116 + if(isset($data['loop']['progress'][$calling_class])){
117 + return $data['loop']['progress'][$calling_class];
118 + }
119 + else if(!empty($defaults)){
120 + $this->_update_progress($defaults, null, $unique_id, $function);
121 + }
122 + return $defaults;
138 123 }
139 124
140 - /**
141 - * Mark a key as processed (internal)
142 - *
143 - * @param mixed $key The item key
144 - * @param string|null $unique_id Optional unique identifier
145 - * @return bool Success status
146 - */
147 - private function _mark_key_processed($key, $unique_id = null): bool {
148 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
149 - return SessionData::mark_key_processed($this->session_id, $calling_class, $key);
125 +
126 + public function get_progress($defaults = [], $unique_id = null, $function = true) {
127 + return $this->_get_progress($defaults, $unique_id, $function);
150 128 }
151 129
152 - /**
153 - * Mark a key as processed (public wrapper)
154 - */
155 - public function mark_key_processed($key, $unique_id = null): bool {
156 - return $this->_mark_key_processed($key, $unique_id);
130 +
131 + private function _get_result($defaults = [], $unique_id = null, $function = true) {
132 + $data = $this->get_session_data();
133 + $calling_class = $this->CallingFunctionName($unique_id, $function);
134 + if(isset($data['loop']['result'][$calling_class])){
135 + return $data['loop']['result'][$calling_class];
136 + }
137 + return $defaults;
157 138 }
158 139
159 - /**
160 - * Set loop result (internal)
161 - *
162 - * @param array $result The result data
163 - * @param string|null $unique_id Optional unique identifier
164 - * @return bool Success status
165 - */
166 - private function _set_loop_result($result, $unique_id = null): bool {
167 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
168 - return SessionData::set_loop_result($this->session_id, $calling_class, $result);
140 + public function get_result($defaults = [], $unique_id = null, $function = true) {
141 + return $this->_get_result($defaults, $unique_id, $function);
169 142 }
170 143
171 - /**
172 - * Set loop result (public wrapper)
173 - */
174 - public function set_loop_result($result, $unique_id = null): bool {
175 - return $this->_set_loop_result($result, $unique_id);
176 - }
177 144
178 - private function _get_loop_result($defaults = [], $unique_id = null, $function = true) {
179 - $calling_class = SessionData::get_calling_identifier($unique_id, $function, false);
180 - return SessionData::get_loop_result($this->session_id, $calling_class, $defaults);
145 + private function _update_progress( $progress, $imported_data = null, $unique_id = null, $function = true ): bool {
146 + $calling_class = $this->CallingFunctionName($unique_id, $function);
147 + $old_data = $this->get_session_data();
148 +
149 + $new_data = [];
150 +
151 + if($progress !== null){
152 + $new_data['loop']['progress'] = [$calling_class => $progress];
153 + }
154 + if($imported_data !== null){
155 + $new_data['loop']['result'] = [$calling_class => $imported_data];
156 + }
157 +
158 + $new_data = Helper::recursive_wp_parse_args( $new_data, $old_data );
159 + return $this->update_session_data( $new_data );
181 160 }
182 161
183 - public function get_loop_result($defaults = [], $unique_id = null, $function = true) {
184 - return $this->_get_loop_result($defaults, $unique_id, $function);
162 + public function update_progress( $progress, $imported_data = null, $unique_id = null, $function = true ): bool {
163 + return $this->_update_progress( $progress, $imported_data, $unique_id, $function );
185 164 }
186 165
187 - // Modified get_session_data to use SessionData
166 + // Modified get_session_data to use the static version
188 167 protected function get_session_data(): array {
189 - return SessionData::get_data($this->session_id);
168 + return Utils::get_session_data($this->session_id);
190 169 }
191 170
192 - // Modified update_session_data to use SessionData (deprecated - use specific methods)
171 + // Modified update_session_data to use the static version
193 172 protected function update_session_data($data): bool {
194 - $existing = SessionData::get_data($this->session_id);
195 - return SessionData::save($this->session_id, array_merge($existing, $data));
173 + return Utils::update_session_data($this->session_id, $data);
196 174 }
197 175
198 176 private function _retrieve_attributes($attributes, $unique_id){
199 - $calling_class = SessionData::get_calling_identifier($unique_id, false, false, 4);
200 - $attr_values = SessionData::get($this->session_id, "loop.backup_attributes.{$calling_class}", []);
177 + $calling_class = $this->CallingFunctionName($unique_id, false);
201 178
202 - foreach ($attributes as $attribute) {
203 - if(isset($attr_values[$attribute])){
204 - $this->$attribute = $attr_values[$attribute];
179 + $data = $this->get_session_data();
180 + if(isset($data['loop']['backup_attributes'][$calling_class])){
181 + $attr_values = $data['loop']['backup_attributes'][$calling_class];
182 + foreach ($attributes as $attribute) {
183 + if(isset($attr_values[$attribute])){
184 + $this->$attribute = $attr_values[$attribute];
185 + }
205 186 }
206 187 }
207 188 }
208 189
209 190 private function _backup_attributes($attributes, $unique_id){
210 - $calling_class = SessionData::get_calling_identifier($unique_id, false, false, 4);
191 + $calling_class = $this->CallingFunctionName($unique_id, false);
192 + $old_data = $this->get_session_data();
193 +
194 + $new_data = [];
211 195 $attr_values = [];
212 196
213 197 foreach ($attributes as $attribute) {
214 198 if(isset($this->$attribute)){
@@ -215,85 +199,13 @@
215 199 $attr_values[$attribute] = $this->$attribute;
216 200 }
217 201 }
218 202
219 - return SessionData::set($this->session_id, "loop.backup_attributes.{$calling_class}", $attr_values);
220 - }
203 + $new_data['loop']['backup_attributes'] = [$calling_class => $attr_values];
221 204
222 - // ============================================================================
223 - // Skip-on-Error Helper Methods
224 - // ============================================================================
225 205
226 - /**
227 - * Check if skip-on-error feature is enabled
228 - *
229 - * @return bool True if enabled
230 - */
231 - protected function _is_skip_feature_enabled(): bool {
232 - return (bool) get_option('templately_enable_fsi_skip_on_error', false);
233 - }
234 -
235 - /**
236 - * Increment error attempts for a loop item
237 - *
238 - * @param mixed $key The item key
239 - * @param string|null $unique_id Optional unique identifier
240 - * @return int New error attempt count
241 - */
242 - private function _increment_error_attempts($key, $unique_id = null): int {
243 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
244 - return SessionData::increment_error_attempts($this->session_id, $calling_class, $key);
245 - }
246 -
247 - /**
248 - * Get error attempts for a loop item
249 - *
250 - * @param mixed $key The item key
251 - * @param string|null $unique_id Optional unique identifier
252 - * @return int Error attempt count
253 - */
254 - private function _get_error_attempts($key, $unique_id = null): int {
255 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
256 - return SessionData::get_error_attempts($this->session_id, $calling_class, $key);
257 - }
258 -
259 - /**
260 - * Mark a loop item as skipped
261 - *
262 - * @param mixed $key The item key
263 - * @param string|null $unique_id Optional unique identifier
264 - * @param string $reason The reason for skipping
265 - * @return bool Success status
266 - */
267 - private function _mark_key_skipped($key, $unique_id = null, $reason = ''): bool {
268 - $calling_class = SessionData::get_calling_identifier($unique_id, true, false);
269 - return SessionData::mark_key_skipped($this->session_id, $calling_class, $key, $reason);
270 - }
271 -
272 - /**
273 - * Increment consecutive skip counter
274 - *
275 - * @return int New consecutive skip count
276 - */
277 - private function _increment_consecutive_skips(): int {
278 - return SessionData::increment_consecutive_skips($this->session_id);
279 - }
280 -
281 - /**
282 - * Reset consecutive skip counter
283 - *
284 - * @return bool Success status
285 - */
286 - private function _reset_consecutive_skips(): bool {
287 - return SessionData::reset_consecutive_skips($this->session_id);
288 - }
289 -
290 - /**
291 - * Get consecutive skip count
292 - *
293 - * @return int Consecutive skip count
294 - */
295 - private function _get_consecutive_skips(): int {
296 - return SessionData::get_consecutive_skips($this->session_id);
206 + // @todo: not sure if we need this.
207 + $new_data = Helper::recursive_wp_parse_args( $new_data, $old_data );
208 + return $this->update_session_data( $new_data );
297 209 }
298 210
299 211 }