31 private static $filesToUnlink = array();
32 private static $countId = 0;
42 public static function getHtml($ids = array(), $title =
"")
44 if (static::class !== __CLASS__)
46 $title = static::getTitle();
47 $ids = [static::$moduleId => [ static::class ]];
48 return call_user_func(array(__CLASS__,
"getHtml"), $ids, $title);
57 $ids = array($ids =>
null);
62 if (is_string($classesId))
63 $classesId = array($classesId);
64 if (is_array($classesId))
66 foreach($classesId as $classId)
68 if (($option = Option::get(
"main.stepper.".
$moduleId, $classId,
"")) !==
"")
70 $option = unserialize($option, [
'allowed_classes' =>
false]);
71 if (is_array($option))
76 "title" => $option[
"title"],
77 "steps" => $option[
"steps"],
78 "count" => $option[
"count"]
80 $count += $option[
"count"];
81 $steps += ($option[
"count"] > $option[
"steps"] ? $option[
"steps"] : $option[
"count"]);
86 else if (is_null($classesId))
88 $options = Option::getForModule(
"main.stepper.".
$moduleId);
89 foreach($options as $classId => $option)
91 $option = unserialize($option, [
'allowed_classes' =>
false]);
92 if (is_array($option))
97 "title" => $option[
"title"],
98 "steps" => $option[
"steps"],
99 "count" => $option[
"count"]
101 $count += $option[
"count"];
102 $steps += ($option[
"count"] > $option[
"steps"] ? $option[
"steps"] : $option[
"count"]);
111 $id = ++self::$countId;
112 \CJSCore::Init(array(
'update_stepper'));
114 $progress = $count > 0 ? intval($steps * 100 / $count) : 0;
116<div
class=
"main-stepper main-stepper-show" id=
"{$id}-container" data-bx-steps-count=
"{$count}">
117 <div
class=
"main-stepper-info" id=
"{$id}-title">{$title}</div>
118 <div
class=
"main-stepper-inner">
119 <div
class=
"main-stepper-bar">
120 <div
class=
"main-stepper-bar-line" id=
"{$id}-bar" style=
"width:{$progress}%;"></div>
122 <div
class=
"main-stepper-steps"><span
id=
"{$id}-steps">{$steps}</span> / <span
id=
"{$id}-count">{$count}</span></div>
123 <div
class=
"main-stepper-error-text" id=
"{$id}-error"></div>
127 $return = \CUtil::PhpToJSObject($return);
129<div
class=
"main-stepper-block">{$result}
130<script>
BX.ready(
function(){
if (
BX &&
BX[
"UpdateStepperRegister"]) {
BX.UpdateStepperRegister({$id}, {$return}); }});</script>
148 $className = get_class($updater);
150 $option = Option::get(
"main.stepper.".$updater->getModuleId(), $className,
"");
152 $option = unserialize($option, [
'allowed_classes' =>
false]);
153 $option = is_array($option) ? $option : array();
154 $updater->setOuterParams(func_get_args());
155 if ($updater->execute($option) === self::CONTINUE_EXECUTION)
157 $option[
"steps"] = (array_key_exists(
"steps", $option) ? (int)$option[
"steps"] : 0);
158 $option[
"count"] = (array_key_exists(
"count", $option) ? (int)$option[
"count"] : 0);
159 $option[
"title"] = $updater::getTitle();
161 Option::set(
"main.stepper.".$updater->getModuleId(), $className, serialize($option));
162 return $className .
'::execAgent('.$updater::makeArguments($updater->getOuterParams()).
');';
166 $res = new \ReflectionClass($updater);
167 self::$filesToUnlink[] = $res->getFileName();
169 Option::delete(
'main.stepper.'.$updater->getModuleId(), [
'name' => $className]);
170 Option::delete(
'main.stepper.'.$updater->getModuleId(), [
'name' =>
'\\'.$className]);
177 if (!empty(self::$filesToUnlink))
179 while ($file = array_pop(self::$filesToUnlink))
181 $file = \CBXVirtualIo::GetInstance()->GetFile($file);
183 $langDir = $fileName =
"";
184 $filePath = $file->GetPathWithName();
185 while(($slashPos = mb_strrpos($filePath,
"/")) !==
false)
187 $filePath = mb_substr($filePath, 0, $slashPos);
188 $langPath = $filePath.
"/lang";
189 if(is_dir($langPath))
191 $langDir = $langPath;
192 $fileName = mb_substr($file->GetPathWithName(), $slashPos);
196 if ($langDir <>
"" && ($langDir = \CBXVirtualIo::GetInstance()->GetDirectory($langDir)) &&
197 $langDir->IsExists())
199 $languages = $langDir->GetChildren();
200 foreach ($languages as $language)
202 if ($language->IsDirectory() &&
203 ($f = \CBXVirtualIo::GetInstance()->GetFile($language->GetPathWithName().$fileName)) &&
240 if (is_array($arguments))
242 foreach ($arguments as $key=> $val)
246 $arguments[$key] =
"'".EscapePHPString($val,
"'").
"'";
250 $arguments[$key] = intval($val);
253 return implode(
", ", $arguments);
271 return static::$moduleId;
279 public static function bind($delay = 300, $withArguments = [])
282 $c = get_called_class();
283 self::bindClass($c, $c::getModuleId(), $delay, $withArguments);
294 public static function bindClass($className,
$moduleId, $delay = 300, $withArguments = [])
296 if (class_exists(
"\CAgent"))
299 $withArguments = is_array($withArguments) ? $withArguments : [];
301 $delay = (int)$delay;
305 $addAgent = (
'' !== call_user_func_array([$className,
"execAgent"], $withArguments));
310 if (Option::get(
"main.stepper.".
$moduleId, $className,
"") ===
"")
311 Option::set(
"main.stepper.".
$moduleId, $className, serialize([]));
312 \CTimeZone::Disable();
314 $className.
'::execAgent('.(empty($withArguments) ?
'' : call_user_func_array([$className,
"makeArguments"], [$withArguments])).
');',
320 date(Main\
Type\Date::convertFormatToPhp(\CSite::GetDateFormat(
"FULL")), time() + $delay),
325 \CTimeZone::Enable();
330 $connection = \Bitrix\Main\Application::getConnection();
331 $helper = $connection->getSqlHelper();
334 if (!empty($withArguments))
336 $arguments = class_exists($className)
337 ? call_user_func_array([$className,
"makeArguments"], [$withArguments])
341 $name = $helper->forSql($className.
'::execAgent('.$arguments.
');', 2000);
342 $className = $helper->forSql($className);
344 $agent = $connection->query(
"SELECT ID FROM b_agent WHERE MODULE_ID='".
$moduleId.
"' AND NAME = '".$name.
"' AND USER_ID IS NULL")->fetch();
347 $connection->query(
"INSERT INTO b_agent (MODULE_ID, SORT, NAME, ACTIVE, AGENT_INTERVAL, IS_PERIOD, NEXT_EXEC) VALUES ('".
$moduleId.
"', 100, '".$name.
"', 'Y', 1, 'Y', ".($delay > 0 ? $helper->addSecondsToDateTime($delay) : $helper->getCurrentDateTimeFunction()).
")");
348 $merge = $helper->prepareMerge(
'b_option', [
'MODULE_ID',
'NAME'], [
349 'MODULE_ID' =>
'main.stepper.' .
$moduleId,
350 'NAME' => $className,
357 $connection->Query($merge[0]);
372 foreach ($data as $stepper)
374 if (($option = Option::get(
"main.stepper.".$stepper[
"moduleId"], $stepper[
"class"],
"")) !==
"" &&
375 ($res = unserialize($option, [
'allowed_classes' =>
false])) && is_array($res))
378 "moduleId" => $stepper[
"moduleId"],
379 "class" => $stepper[
"class"],
380 "steps" => $res[
"steps"],
381 "count" => $res[
"count"]
387 self::sendJson($result);
394 private static function sendJson($result)
397 $APPLICATION->RestartBuffer();
399 header(
'Content-Type:application/json; charset=UTF-8');
401 echo Json::encode($result);
402 \CMain::finalActions();
409 $exceptionHandler = $application->getExceptionHandler();
410 $exceptionHandler->writeToLog($exception);
static getMessage($code, $replace=null, $language=null)
static isModuleInstalled($moduleName)
writeToLog(\Exception $exception)
setOuterParams(array $outerParams)
static makeArguments($arguments=[])
static getHtml($ids=array(), $title="")